// TruVisuals Telemetry — 3 keyframeable HUD readouts in one DCTL.
//   Power %  -> amber gauge (bottom-right), needle sweeps + ...
//   Signal % -> cyan equalizer spectrum (bottom-left)
//   Data %   -> cyan waveform graph (top-left)
// Pixel math designed & verified in Python before shipping (identical result).

DEFINE_UI_PARAMS(power,  Power %,   DCTLUI_SLIDER_FLOAT, 62.0, 0.0, 100.0, 1.0)
DEFINE_UI_PARAMS(signal, Signal %,  DCTLUI_SLIDER_FLOAT, 70.0, 0.0, 100.0, 1.0)
DEFINE_UI_PARAMS(data,   Data %,    DCTLUI_SLIDER_FLOAT, 65.0, 0.0, 100.0, 1.0)
DEFINE_UI_PARAMS(gaugeX, Gauge X,   DCTLUI_SLIDER_FLOAT, 0.86, 0.0, 1.0, 0.005)
DEFINE_UI_PARAMS(gaugeY, Gauge Y,   DCTLUI_SLIDER_FLOAT, 0.72, 0.0, 1.0, 0.005)
DEFINE_UI_PARAMS(gaugeSz,Gauge Size,DCTLUI_SLIDER_FLOAT, 0.12, 0.03, 0.4, 0.005)
DEFINE_UI_PARAMS(eqX,    EQ X,       DCTLUI_SLIDER_FLOAT, 0.03, 0.0, 1.0, 0.005)
DEFINE_UI_PARAMS(eqY,    EQ Y,       DCTLUI_SLIDER_FLOAT, 0.90, 0.0, 1.0, 0.005)
DEFINE_UI_PARAMS(grX,    Graph X,    DCTLUI_SLIDER_FLOAT, 0.035,0.0, 1.0, 0.005)
DEFINE_UI_PARAMS(grY,    Graph Y,    DCTLUI_SLIDER_FLOAT, 0.07, 0.0, 1.0, 0.005)

__DEVICE__ float3 over3(float3 b, float3 c, float a)
{
    a = _saturatef(a);
    return make_float3(b.x*(1.0f-a)+c.x*a, b.y*(1.0f-a)+c.y*a, b.z*(1.0f-a)+c.z*a);
}
__DEVICE__ float band(float x, float c, float hw, float pxper)
{
    return _saturatef((hw - _fabs(x - c)) / (1.5f * pxper) + 0.5f);
}

__DEVICE__ float3 transform(int p_Width, int p_Height, int p_X, int p_Y, float p_R, float p_G, float p_B)
{
    float Hf = (float)p_Height;
    float WoverH = (float)p_Width / Hf;
    float pxper = 1.0f / Hf;
    float px = (float)p_X / Hf;
    float py = (float)p_Y / Hf;

    float3 AM = make_float3(1.0f, 0.69f, 0.16f);   // amber
    float3 CY = make_float3(0.47f, 0.94f, 1.0f);   // cyan
    float3 col = make_float3(p_R, p_G, p_B);

    // ===== GAUGE (amber, full circle) =====
    float gcx = gaugeX * WoverH, gcy = gaugeY, R = gaugeSz;
    float dx = px - gcx, dy = gcy - py;
    float r = _sqrtf(dx*dx + dy*dy);
    float ang = _fmod(_atan2f(dy, dx) * 57.29578f + 360.0f, 360.0f);
    col = over3(col, AM, band(r, R, 0.0015f, pxper) * 0.85f);           // outer ring
    col = over3(col, AM, band(r, R * 0.72f, 0.0012f, pxper) * 0.5f);    // inner ring
    float tickA = 0.0f;
    for (int k = 0; k < 40; k++)
    {
        float ta = (float)k * 9.0f;
        float da = _fabs(_fmod(ang - ta + 540.0f, 360.0f) - 180.0f);
        int major = (k % 5 == 0) ? 1 : 0;
        float inner = R - (major ? 0.02f : 0.011f);
        float tr = _saturatef((r - inner)/pxper + 0.5f) * _saturatef((R - 0.002f - r)/pxper + 0.5f);
        tickA = _fmaxf(tickA, ((da < (major ? 1.3f : 0.8f)) ? 1.0f : 0.0f) * tr);
    }
    col = over3(col, AM, tickA * 0.7f);
    float na = (225.0f - (power/100.0f) * 270.0f) * 0.01745329f;
    float ndx = _cosf(na), ndy = _sinf(na);
    float proj = dx*ndx + dy*ndy, perp = _fabs(dx*ndy - dy*ndx);
    col = over3(col, AM, _saturatef((0.0022f - perp)/pxper + 0.5f) * ((proj > 0.0f && proj < R*0.82f) ? 1.0f : 0.0f));
    col = over3(col, AM, _saturatef((0.007f - r)/pxper + 0.5f));        // hub

    // ===== EQUALIZER (cyan bars, bottom-left) =====
    float ex0 = eqX, ex1 = eqX + 0.37f, baseY = eqY, topMax = 0.30f;
    float pitch = (ex1 - ex0) / 16.0f, barw = pitch * 0.55f;
    if (px >= ex0 && px < ex1)
    {
        int bi = (int)((px - ex0) / pitch);
        if (bi < 0) bi = 0; if (bi > 15) bi = 15;
        float patt = 0.35f + 0.65f * (0.5f + 0.5f*_sinf((float)bi*1.7f)) * (0.5f + 0.5f*_sinf((float)bi*0.9f + 1.3f));
        float bh = patt * topMax * (signal/100.0f);
        float barC = ex0 + ((float)bi + 0.5f) * pitch;
        float inbar = (_fabs(px - barC) < barw*0.5f) ? 1.0f : 0.0f;
        col = over3(col, CY, inbar * ((py <= baseY && py >= baseY - bh) ? 1.0f : 0.0f) * 0.85f);
        col = over3(col, CY, inbar * _saturatef((0.0015f - _fabs(py - (baseY - bh)))/pxper + 0.5f)); // cap
        col = over3(col, CY, band(py, baseY + 0.01f, 0.001f, pxper) * 0.4f);                          // baseline
    }

    // ===== GRAPH (cyan waveform, top-left) =====
    float gx0 = grX, gx1 = grX + 0.49f, gy0 = grY, gy1 = grY + 0.15f;
    float mid = (gy0 + gy1) * 0.5f;
    float amp = (data/100.0f) * (gy1 - gy0) * 0.42f;
    float boxV = (band(px, gx0, 0.0012f, pxper) + band(px, gx1, 0.0012f, pxper)) * ((py >= gy0 && py <= gy1) ? 1.0f : 0.0f)
               + (band(py, gy0, 0.0012f, pxper) + band(py, gy1, 0.0012f, pxper)) * ((px >= gx0 && px <= gx1) ? 1.0f : 0.0f);
    col = over3(col, CY, _saturatef(boxV) * 0.45f);
    if (px >= gx0 && px <= gx1)
    {
        float wy = mid + amp * (_sinf((px - gx0) * 55.0f) * 0.6f + _sinf((px - gx0) * 23.0f + 1.0f) * 0.4f);
        col = over3(col, CY, band(py, wy, 0.0016f, pxper) * 0.9f);
    }

    return col;
}
