/* date = April 26th 2023 11:04 pm */

#ifndef VN_RENDER_H
#define VN_RENDER_H

#define MAX_BOUND_TEXTURES 16
#define MAX_QUAD_COUNT     128*1024

#define ColorFromHex(Value) V4((((Value) >> 24) & 0xFF) / 255.0, (((Value) >> 16) & 0xFF) / 255.0, (((Value) >> 8) & 0xFF) / 255.0, (((Value) >> 0) & 0xFF) / 255.0)

#define Brighten(Color, Amount) (Color*(Amount))
#define Darken(Color, Amount) (Color*(1.0/(Amount)))

read_only v4 Color_Black   = V4(0, 0, 0, 1);
read_only v4 Color_White   = V4(1, 1, 1, 1);
read_only v4 Color_Grey    = V4(0.5, 0.5, 0.5, 1);
read_only v4 Color_Red     = V4(1, 0, 0, 1);
read_only v4 Color_Green   = V4(0, 1, 0, 1);
read_only v4 Color_Blue    = V4(0, 0, 1, 1);
read_only v4 Color_Yellow  = V4(1, 1, 0, 1);
read_only v4 Color_Magenta = V4(1, 0, 1, 1);
read_only v4 Color_Cyan    = V4(0, 1, 1, 1);

#define SetAlpha(Color, Value) V4(Color.x, Color.y, Color.z, Value)

enum render_texture_format
{
    Render_TextureFormat_Invalid,
    Render_TextureFormat_R8,
    Render_TextureFormat_RGB8,
    Render_TextureFormat_RGBA8,
};

struct render_handle
{
    union
    {
        u64 U64[4];
        u32 U32[8];
    };
};

enum render_command_type
{
    Render_Command_render_command_clear,
    Render_Command_render_command_quads,
    Render_Command_render_command_instanced_quads,
    Render_Command_render_command_clip,
};

struct render_command_clear
{
    v3 Color;
};

struct render_texture_mapping
{
    s32 TexturesUsed;
    render_handle Textures[16];
};

struct render_command_quads
{
    render_texture_mapping Mapping;
    u64 QuadCount;
    u64 QuadBufferIndex;
};

struct render_command_instanced_quads
{
    render_texture_mapping Mapping;
    u64 QuadCount;
    u64 QuadBufferIndex;
};

struct render_command_clip
{
    range2_r32 ClipRect;
};

struct render_command_header
{
    render_command_type Type;
};

struct render_group
{
    struct vn_render_commands *Commands;
    
    render_command_header *CurrentCommand;
    
    range2_r32 ClipStack[64];
    s32 ClipStackUsed;
};

struct instanced_quad
{
    range2_r32 Dest;
    range2_r32 Source;
    u32 TextureIndex;
    u32 Color[4];
    r32 CornerRadius;
    r32 EdgeSoftness;
    r32 BorderThickness;
};

struct quad_vertex
{
    v2 P;
    v2 SourceP;
    u32 TextureIndex;
    u32 Color;
    v2 ToCenter; // sixten: ToCenter = Center - P
    v2 HalfSize;
    r32 CornerRadius;
    r32 EdgeSoftness;
    r32 BorderThickness;
};

#endif //VN_RENDER_H
