Searchlight beam: the btfx brighten material class + BT_SPOT_SELF rig
SPOT.BGF decoded: a 7-vert cone from the mount, ~50u forward and ~35deg DOWN
(a ground-pool lamp, not an air beam), verts tinted cyan-white, material
class 'brighten' smuggling its additive factor in DIFFUSE.r (0.25) with a
warm emissive on the night page. The loader had never met the class -- it
drew as an opaque dark-red blob. Now: brightenFactor parsed (name-gated to
brighten*), batch -> L4DRAWOP.brightenAlpha, drawn in the blend pass as an
additive veil (dest += vertexRGB x factor), unlit. [T3] tint compose
(vertex cyan vs night emissive warm) noted in the draw branch -- field
eyeball accepted the current look.
BT_SPOT_SELF=1 (bench-only): builds the cone on the own-cockpit tree so the
BT_CAM=face view can inspect it solo. KB: view toggle is BACKTICK ('V' is
the rear-view hold since #68 -- the toggle skips bound keys); stale V-toggle
claims swept.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Fable 5
parent
7d8f109241
commit
b75bb4a04c
@@ -443,8 +443,13 @@ d3d_OBJECT* d3d_OBJECT::LoadObjectBGF(LPDIRECT3DDEVICE9 device, char *fileName)
|
||||
// drawAsSky) and vanishes -- DECLOUDS carries vertex alpha but must
|
||||
// stay in the sky pass.
|
||||
const bool vtxAlphaOp = data.batches[i].vertexAlpha && !isSkyObj;
|
||||
object->mDrawOps[i].alphaTest = (object->mIsShadow != 0) || vtxAlphaOp;
|
||||
// BTFX brighten veil (spot cone): route to the blend pass like the
|
||||
// vertex-alpha cards; the draw-state branch in DrawMesh adds
|
||||
// dest += emissive x factor instead of SRCALPHA/INVSRCALPHA.
|
||||
const bool brightenOp = data.batches[i].brightenFactor > 0.0f && !isSkyObj;
|
||||
object->mDrawOps[i].alphaTest = (object->mIsShadow != 0) || vtxAlphaOp || brightenOp;
|
||||
object->mDrawOps[i].vertexAlphaBlend = vtxAlphaOp;
|
||||
object->mDrawOps[i].brightenAlpha = brightenOp ? data.batches[i].brightenFactor : 0.0f;
|
||||
object->mDrawOps[i].drawAsDecal = false;
|
||||
object->mDrawOps[i].drawAsSky = isSkyObj; // sky dome -> PASS_SKY (fullbright)
|
||||
// PUNCH (dpl_Punchize; BT_PUNCH=0 disables): cutout batch -- black texels
|
||||
@@ -1279,7 +1284,9 @@ void d3d_OBJECT::DrawMesh(int pass, const D3DXMATRIX *viewTransform, Time target
|
||||
// (SRCALPHA/INVSRCALPHA). Runs only in the blend pass (the op filter
|
||||
// above routed it there; ALPHABLEND is on and z-write off pass-wide).
|
||||
DWORD sVLight = 0, sVSrc = 0, sVDst = 0, sVCop = 0, sVCa1 = 0, sVCa2 = 0, sVAop = 0, sVAa2 = 0;
|
||||
const bool vtxAlphaCard = (drawOp->vertexAlphaBlend && pass == PASS_ALPHABLEND);
|
||||
const bool brightenCard = (drawOp->brightenAlpha > 0.0f && pass == PASS_ALPHABLEND);
|
||||
const bool vtxAlphaCard =
|
||||
((drawOp->vertexAlphaBlend && pass == PASS_ALPHABLEND) || brightenCard);
|
||||
if (vtxAlphaCard)
|
||||
{
|
||||
mDevice->GetRenderState(D3DRS_LIGHTING, &sVLight);
|
||||
@@ -1292,13 +1299,35 @@ void d3d_OBJECT::DrawMesh(int pass, const D3DXMATRIX *viewTransform, Time target
|
||||
mDevice->GetTextureStageState(0, D3DTSS_ALPHAARG2, &sVAa2);
|
||||
mDevice->SetRenderState(D3DRS_LIGHTING, FALSE);
|
||||
mDevice->SetRenderState(D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);
|
||||
mDevice->SetRenderState(D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA);
|
||||
mDevice->SetRenderState(D3DRS_DESTBLEND,
|
||||
brightenCard ? D3DBLEND_ONE : D3DBLEND_INVSRCALPHA);
|
||||
if (brightenCard)
|
||||
{
|
||||
// BTFX brighten veil: dest += vertexRGB x factor. SPOT.BGF's
|
||||
// verts author the beam tint (cyan-white 0.12/0.98/1.0, alpha
|
||||
// 1.0 -- no fade gradient); the factor rides TFACTOR alpha.
|
||||
// [T3 tint compose]: the night material ALSO authors emissive
|
||||
// (0.9,0.4,0.2 warm) -- whether the DIV board tinted the veil
|
||||
// by vertex, emissive, or their product is unconfirmed; vertex
|
||||
// (a white-blue searchlight) matches the authored geometry
|
||||
// gradient model. Flip here if era-look evidence says warm.
|
||||
mDevice->SetRenderState(D3DRS_TEXTUREFACTOR,
|
||||
D3DCOLOR_COLORVALUE(1.0f, 1.0f, 1.0f, drawOp->brightenAlpha));
|
||||
mDevice->SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
|
||||
mDevice->SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_DIFFUSE);
|
||||
mDevice->SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_TFACTOR);
|
||||
mDevice->SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG2);
|
||||
mDevice->SetTextureStageState(0, D3DTSS_ALPHAARG2, D3DTA_TFACTOR);
|
||||
}
|
||||
else
|
||||
{
|
||||
mDevice->SetTextureStageState(0, D3DTSS_COLOROP,
|
||||
drawOp->texture.texture != NULL ? D3DTOP_MODULATE : D3DTOP_SELECTARG2);
|
||||
mDevice->SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_TEXTURE);
|
||||
mDevice->SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE);
|
||||
mDevice->SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG2);
|
||||
mDevice->SetTextureStageState(0, D3DTSS_ALPHAARG2, D3DTA_DIFFUSE);
|
||||
}
|
||||
}
|
||||
|
||||
const bool copCut = (drawOp->copRole == 2 && iOp > 0
|
||||
|
||||
Reference in New Issue
Block a user