#ifndef BREEZE_LOGGER_H
#define BREEZE_LOGGER_H

#include "../defines.h"

#include <stdarg.h>

typedef enum BzLoggerLevel {
    BZ_LOG_TRACE,
    BZ_LOG_DEBUG,
    BZ_LOG_INFO,
    BZ_LOG_WARNING,
    BZ_LOG_ERROR,
    BZ_LOG_FATAL,
} BzLoggerLevel;

typedef struct BzLoggerEvent {
    void *userData;

    const char *time;
    BzLoggerLevel level;
    const char *file;
    int line;

    const char *fmt;
    va_list va;
} BzLoggerEvent;

typedef struct BzLoggerCallback {
    void (*callback)(BzLoggerEvent *ev);
    enum BzLoggerLevel level;
    void *userData;
} BzLoggerCallback;

bool bzLoggerInit();
void bzLoggerDeinit();

void bzLoggerEnableDefaultLog(bool enable);

void bzLoggerSetLevel(BzLoggerLevel level);
BzLoggerLevel bzLoggerGetLevel();

void bzLoggerLog(BzLoggerLevel level, const char *file, int line, const char *fmt, ...);
void bzLoggerLogV(BzLoggerLevel level, const char *file, int line, const char *fmt, va_list va);
void bzLoggerOnlyLog(BzLoggerLevel level, const char *fmt, ...);
void bzLoggerOnlyLogV(BzLoggerLevel level, const char *fmt, va_list va);


bool bzLoggerAddFP(void *fp, BzLoggerLevel level);
bool bzLoggerAddCB(const BzLoggerCallback *callback);

#define bzLogTrace(...) bzLoggerLog(BZ_LOG_TRACE, __FILE__, __LINE__, __VA_ARGS__)
#define bzLogDebug( ...) bzLoggerLog(BZ_LOG_DEBUG, __FILE__, __LINE__, __VA_ARGS__)
#define bzLogInfo(...) bzLoggerLog(BZ_LOG_INFO, __FILE__, __LINE__, __VA_ARGS__)
#define bzLogWarning(...) bzLoggerLog(BZ_LOG_WARNING, __FILE__, __LINE__, __VA_ARGS__)
#define bzLogError(...) bzLoggerLog(BZ_LOG_ERROR, __FILE__, __LINE__, __VA_ARGS__)
#define bzLogFatal(...) bzLoggerLog(BZ_LOG_FATAL, __FILE__, __LINE__, __VA_ARGS__)

#endif //BREEZE_LOGGER_H
