summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorsalmonik <salmonik@tuta.io>2026-11-04 19:17:12 +0100
committersalmonik <salmonik@tuta.io>2026-11-04 19:17:12 +0100
commitea4b9d1f6de4c0c781a48999e793a5bf976c2b38 (patch)
tree24d7af7c91d740076cf9c5ca932a0ed2a0d51cea
parentChams: use the model solid shader for flat, drop vgui/white (diff)
downloadhl2h-ea4b9d1f6de4c0c781a48999e793a5bf976c2b38.tar.gz
hl2h-ea4b9d1f6de4c0c781a48999e793a5bf976c2b38.zip
Chams: keep additive viewmodel visible on bright backgrounds
Viewmodels are collated as RENDER_GROUP_VIEW_MODEL_OPAQUE, so an additive forced material can vanish against a bright sky/wall (additive adds nothing to an already-bright surface). Draw a dim opaque solid base before the additive viewmodel pass so the first-person model always has a visible silhouette; the additive layer still provides the glow.
-rw-r--r--CONTEXT.md5
-rw-r--r--src/studio.cpp12
2 files changed, 17 insertions, 0 deletions
diff --git a/CONTEXT.md b/CONTEXT.md
index ad9ce2d..c75e36c 100644
--- a/CONTEXT.md
+++ b/CONTEXT.md
@@ -307,6 +307,11 @@ vocabulary / decisions.
307 VGUI additive material was invisible on NPCs. 307 VGUI additive material was invisible on NPCs.
308- Style materials are preloaded from `outer_draw` (throttled) and cached; the 308- Style materials are preloaded from `outer_draw` (throttled) and cached; the
309 render hook never calls FindMaterial itself. A missing style uses solid. 309 render hook never calls FindMaterial itself. A missing style uses solid.
310- Viewmodels are collated by the engine as `RENDER_GROUP_VIEW_MODEL_OPAQUE`,
311 so an additive forced material can wash out against a bright sky or wall
312 (and the engine may not treat the draw as translucent). Additive styles on
313 the viewmodel therefore draw a dim opaque solid base first, then the
314 additive pass; the first-person model never disappears.
310- Feature is off by default. Config sections: `[chams]` (active/bind), 315- Feature is off by default. Config sections: `[chams]` (active/bind),
311 `[chams_hostile|neutral|friendly]` (`vis`, `vis_mat`, `vis_r/g/b`, `inv`, 316 `[chams_hostile|neutral|friendly]` (`vis`, `vis_mat`, `vis_r/g/b`, `inv`,
312 `inv_mat`, `inv_r/g/b`) and `[chams_vm]` (`on`, `mat`, `r/g/b`). The GUI has 317 `inv_mat`, `inv_r/g/b`) and `[chams_vm]` (`on`, `mat`, `r/g/b`). The GUI has
diff --git a/src/studio.cpp b/src/studio.cpp
index 4941142..bee6db5 100644
--- a/src/studio.cpp
+++ b/src/studio.cpp
@@ -313,6 +313,18 @@ void hkdModelExecute(void *self, const void *state, const void *info,
313 brgb[i] = rgb[i] + (255 - rgb[i]) / 2; 313 brgb[i] = rgb[i] + (255 - rgb[i]) / 2;
314 use_rgb = brgb; 314 use_rgb = brgb;
315 } 315 }
316 // Additive blending vanishes against bright backgrounds (sky,
317 // white walls, strong fog), which made the viewmodel disappear in
318 // some places. Lay down a dim opaque base first so the first-person
319 // model always has a visible silhouette; the additive pass still
320 // adds the glow on top.
321 if (is_vm && (style == 2 || style == 5)) {
322 int drgb[3] = {rgb[0] / 2, rgb[1] / 2, rgb[2] / 2};
323 chams_apply(mat, ignorez, 3, false, drgb, false);
324 g_force_override(self, mat, 0 /* OVERRIDE_NORMAL */);
325 g_orig_model_exec(self, state, info, bone);
326 chams_reset(mat);
327 }
316 chams_apply(mat, ignorez, style, white, use_rgb, false); 328 chams_apply(mat, ignorez, style, white, use_rgb, false);
317 g_force_override(self, mat, 0 /* OVERRIDE_NORMAL */); 329 g_force_override(self, mat, 0 /* OVERRIDE_NORMAL */);
318 g_orig_model_exec(self, state, info, bone); 330 g_orig_model_exec(self, state, info, bone);