// Image Adjustment
// Comprehensive color and brightness controls
// Based on image-adjustment shader from libretro
// Ported from https://github.com/libretro/slang-shaders/blob/master/misc/image-adjustment.slang

//!BGFX EFFECT
//!VERSION 1
//!NAME Image Adjustment
//!CATEGORY Post Processing
//!DESCRIPTION Provides comprehensive color adjustment controls including gamma correction, saturation, luminance, contrast, brightness, black level, and individual RGB channel adjustment.

//!PARAMETER
//!LABEL Target Gamma
//!DESC The gamma value of the content being displayed
//!DEFAULT 2.2
//!MIN 0.01
//!MAX 5
//!STEP 0.01
float targetGamma;

//!PARAMETER
//!LABEL Monitor Gamma
//!DESC The gamma value of your display monitor
//!DEFAULT 2.2
//!MIN 0.01
//!MAX 5
//!STEP 0.01
float monitorGamma;

//!PARAMETER
//!LABEL Saturation
//!DESC Color saturation multiplier. Values below 1.0 desaturate, above 1.0 increase saturation.
//!DEFAULT 1
//!MIN 0
//!MAX 5
//!STEP 0.01
float saturation;

//!PARAMETER
//!LABEL Luminance
//!DESC Overall luminance/brightness multiplier in HSV color space
//!DEFAULT 1
//!MIN 0
//!MAX 2
//!STEP 0.01
float luminance;

//!PARAMETER
//!LABEL Contrast
//!DESC Image contrast adjustment. Values above 1.0 increase contrast.
//!DEFAULT 1
//!MIN 0
//!MAX 10
//!STEP 0.1
float contrast;

//!PARAMETER
//!LABEL Brightness Boost
//!DESC Additional brightness offset applied after contrast adjustment
//!DEFAULT 0
//!MIN -1
//!MAX 1
//!STEP 0.01
float brightBoost;

//!PARAMETER
//!LABEL Black Level
//!DESC Adjusts the black point of the image. Positive values crush blacks.
//!DEFAULT 0
//!MIN -1
//!MAX 1
//!STEP 0.01
float blackLevel;

//!PARAMETER
//!LABEL Red Channel
//!DESC Multiplier for the red color channel
//!DEFAULT 1
//!MIN 0
//!MAX 2
//!STEP 0.01
float redChannel;

//!PARAMETER
//!LABEL Green Channel
//!DESC Multiplier for the green color channel
//!DEFAULT 1
//!MIN 0
//!MAX 2
//!STEP 0.01
float greenChannel;

//!PARAMETER
//!LABEL Blue Channel
//!DESC Multiplier for the blue color channel
//!DEFAULT 1
//!MIN 0
//!MAX 2
//!STEP 0.01
float blueChannel;


//!TEXTURE
Texture2D INPUT;

//!TEXTURE
//!WIDTH INPUT_WIDTH
//!HEIGHT INPUT_HEIGHT
Texture2D OUTPUT;

//!SAMPLER
//!FILTER POINT
SamplerState sam;


//!PASS 1
//!STYLE PS
//!IN INPUT
//!OUT OUTPUT

// Convert RGB to HSV color space
float3 ConvertRGBtoHSV(float3 c) {
    float4 K = float4(0.0, -1.0 / 3.0, 2.0 / 3.0, -1.0);
    float4 p = c.y < c.z ? float4(c.bg, K.wz) : float4(c.gb, K.xy);
    float4 q = c.x < p.x ? float4(p.xyw, c.x) : float4(c.x, p.yzx);

    float d = q.x - min(q.w, q.y);
    float e = 1.0e-10;
    return float3(abs(q.z + (q.w - q.y) / (6.0 * d + e)), d / (q.x + e), q.x);
}

// Convert HSV to RGB color space
float3 ConvertHSVtoRGB(float3 c) {
    float4 K = float4(1.0, 2.0 / 3.0, 1.0 / 3.0, 3.0);
    float3 p = abs(frac(c.xxx + K.xyz) * 6.0 - K.www);
    return c.z * lerp(K.xxx, saturate(p - K.xxx), c.y);
}

float4 Pass1(float2 pos) {
    float3 color = INPUT.SampleLevel(sam, pos, 0).rgb;

    // Apply saturation and luminance adjustments in HSV space
    float3 hsv = ConvertRGBtoHSV(color);
    hsv.y *= saturation;
    hsv.z *= luminance;
    color = saturate(ConvertHSVtoRGB(hsv));

    // Apply contrast and brightness adjustments
    color = saturate((color - 0.5) * contrast + 0.5 + brightBoost);

    // Apply black level adjustment
    color -= blackLevel;
    color = saturate(color / (1 - blackLevel));

    // Apply gamma correction
    color = pow(color, targetGamma / monitorGamma);

    // Apply individual channel adjustments
    color *= float3(redChannel, greenChannel, blueChannel);

    return float4(color, 1);
}
