summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorsalmonik <salmonik@tuta.io>2026-11-04 18:37:04 +0100
committersalmonik <salmonik@tuta.io>2026-11-04 18:37:04 +0100
commit8e6efa22610be51391459238a2c5e16d1ff1a060 (patch)
treeba5c80fe079967fd93bcb270aeeb304e7e1da698
parentChams: model-safe styles and a dedicated viewmodel material (diff)
downloadhl2h-8e6efa22610be51391459238a2c5e16d1ff1a060.tar.gz
hl2h-8e6efa22610be51391459238a2c5e16d1ff1a060.zip
Chams: style flags on the resident debug material
The base game only has debug/debugtranslucentsinglecolor resident, so the other debug VMTs silently fell back to it and every style looked flat. Use that material for every style and apply material flags instead: FLAT, WIREFRAME, ADDITIVE, and FLAT|SELFILLUM for fullbright; white forces the colour. Flags are cleared after the draw.
-rw-r--r--CONTEXT.md21
-rw-r--r--src/studio.cpp53
2 files changed, 43 insertions, 31 deletions
diff --git a/CONTEXT.md b/CONTEXT.md
index ce79800..72559ac 100644
--- a/CONTEXT.md
+++ b/CONTEXT.md
@@ -296,20 +296,17 @@ vocabulary / decisions.
296 vars (IMaterialVar slot 11, SetVecValue 3-float slot 11), because some forced 296 vars (IMaterialVar slot 11, SetVecValue 3-float slot 11), because some forced
297 materials ignore ColorModulate. The shared material's flag and colour are 297 materials ignore ColorModulate. The shared material's flag and colour are
298 restored to (false, white) after the draw. 298 restored to (false, white) after the draw.
299- Material lookup walks the `IMaterialSystem` list (`world_find_material`), with 299- The base game does not have the other debug VMTs resident and `FindMaterial`
300 `FindMaterial` (slot 71) as the fallback. The **exact requested style** is 300 does not make them available reliably, so all styles use the resident
301 tried first (resident, then loaded on demand), and only if that fails does it 301 `debug/debugtranslucentsinglecolor` and differ by material flags:
302 fall back to `debug/debugtranslucentsinglecolor`/debugwhite/vgui white. 302 0 Flat (`FLAT`), 1 Wireframe (`WIREFRAME`), 2 Additive (`ADDITIVE`),
303 Styles: 0 Flat (`models/debug/debugwhite`), 1 Wireframe 303 3 Solid (none), 4 White (colour forced to white), 5 Fullbright
304 (`debug/debugwireframe`), 2 Additive (`debug/additivevertexcolorvertexalpha`), 304 (`FLAT|SELFILLUM`). Flags are reset after the draw.
305 3 Solid (`debug/debugtranslucentsinglecolor`), 4 White
306 (`debug/debugtranslucentvertexcolor`), 5 Fullbright
307 (`debug/debugmrmfullbright2`). The chosen material name is logged.
308- `Viewmodel (hands/weapon)` applies the override to entities whose class 305- `Viewmodel (hands/weapon)` applies the override to entities whose class
309 contains `viewmodel` or whose model path is `.../v_...`. Viewmodels always 306 contains `viewmodel` or whose model path is `.../v_...`. Viewmodels always
310 use the model-safe solid material (`debug/debugtranslucentsinglecolor`); 307 use the solid style (no style flags) with the selected colour; VGUI/white
311 VGUI/white materials do not draw skinned models and made the hands/weapon 308 materials do not draw skinned models and made the hands/weapon disappear.
312 disappear. Only the normal-depth pass is used. 309 Only the normal-depth pass is used.
313- Feature is off by default; `[chams] active/bind/walls/viewmodel/material/r/g/b`, 310- Feature is off by default; `[chams] active/bind/walls/viewmodel/material/r/g/b`,
314 with Through walls, Viewmodel, a Material dropdown and colour in the Visuals 311 with Through walls, Viewmodel, a Material dropdown and colour in the Visuals
315 card. 312 card.
diff --git a/src/studio.cpp b/src/studio.cpp
index f67936c..1ca8ad7 100644
--- a/src/studio.cpp
+++ b/src/studio.cpp
@@ -200,14 +200,11 @@ void *g_chams_mat = nullptr;
200int g_chams_mat_idx = -1; 200int g_chams_mat_idx = -1;
201 201
202const char *chams_material_name(int idx) { 202const char *chams_material_name(int idx) {
203 switch (idx) { 203 (void)idx;
204 case 1: return "debug/debugwireframe"; 204 // Only this debug material is reliably resident in the base game; the other
205 case 2: return "debug/additivevertexcolorvertexalpha"; 205 // debug VMTs are not loaded and FindMaterial does not make them available.
206 case 3: return "debug/debugtranslucentsinglecolor"; 206 // Visual styles are applied as material flags instead.
207 case 4: return "debug/debugtranslucentvertexcolor"; 207 return "debug/debugtranslucentsinglecolor";
208 case 5: return "debug/debugmrmfullbright2";
209 default: return "models/debug/debugwhite";
210 }
211} 208}
212 209
213void *chams_material() { 210void *chams_material() {
@@ -248,12 +245,29 @@ void chams_color(void *mat, float r, float g, float b) {
248 vfunc<ColorFn>(mat, 28)(mat, r, g, b); 245 vfunc<ColorFn>(mat, 28)(mat, r, g, b);
249} 246}
250 247
251void chams_apply(void *mat, bool ignorez) { 248void chams_apply(void *mat, bool ignorez, int style, bool force_white) {
249 using FlagFn = void (*)(void *, int, bool);
250 float r = force_white ? 1.0f : (float)g_chams_rgb[0] / 255.0f;
251 float g = force_white ? 1.0f : (float)g_chams_rgb[1] / 255.0f;
252 float b = force_white ? 1.0f : (float)g_chams_rgb[2] / 255.0f;
253 chams_color(mat, r, g, b);
254 // 0 Flat, 1 Wireframe, 2 Additive, 3 Solid, 4 White, 5 Fullbright.
255 vfunc<FlagFn>(mat, 29)(mat, 1 << 15 /* IGNOREZ */, ignorez);
256 vfunc<FlagFn>(mat, 29)(mat, 1 << 28 /* WIREFRAME */, style == 1);
257 vfunc<FlagFn>(mat, 29)(mat, 1 << 7 /* ADDITIVE */, style == 2);
258 vfunc<FlagFn>(mat, 29)(mat, 1 << 12 /* FLAT */,
259 style == 0 || style == 5);
260 vfunc<FlagFn>(mat, 29)(mat, 1 << 6 /* SELFILLUM */, style == 5);
261}
262
263void chams_reset(void *mat) {
252 using FlagFn = void (*)(void *, int, bool); 264 using FlagFn = void (*)(void *, int, bool);
253 chams_color(mat, (float)g_chams_rgb[0] / 255.0f, 265 vfunc<FlagFn>(mat, 29)(mat, 1 << 15, false);
254 (float)g_chams_rgb[1] / 255.0f, 266 vfunc<FlagFn>(mat, 29)(mat, 1 << 28, false);
255 (float)g_chams_rgb[2] / 255.0f); 267 vfunc<FlagFn>(mat, 29)(mat, 1 << 7, false);
256 vfunc<FlagFn>(mat, 29)(mat, 1 << 15 /* MATERIAL_VAR_IGNOREZ */, ignorez); 268 vfunc<FlagFn>(mat, 29)(mat, 1 << 12, false);
269 vfunc<FlagFn>(mat, 29)(mat, 1 << 6, false);
270 chams_color(mat, 1.0f, 1.0f, 1.0f);
257} 271}
258 272
259void hkdModelExecute(void *self, const void *state, const void *info, 273void hkdModelExecute(void *self, const void *state, const void *info,
@@ -269,19 +283,20 @@ void hkdModelExecute(void *self, const void *state, const void *info,
269 if (is_npc || is_vm) { 283 if (is_npc || is_vm) {
270 void *mat = is_vm ? viewmodel_material() : chams_material(); 284 void *mat = is_vm ? viewmodel_material() : chams_material();
271 if (mat) { 285 if (mat) {
286 int style = is_vm ? 3 : g_chams_mat_index;
287 if (style < 0) style = 0;
288 if (style > 5) style = 5;
289 bool white = !is_vm && style == 4;
272 if (g_chams_walls && !is_vm) { 290 if (g_chams_walls && !is_vm) {
273 chams_apply(mat, true); 291 chams_apply(mat, true, style, white);
274 g_force_override(self, mat, 0 /* OVERRIDE_NORMAL */); 292 g_force_override(self, mat, 0 /* OVERRIDE_NORMAL */);
275 g_orig_model_exec(self, state, info, bone); 293 g_orig_model_exec(self, state, info, bone);
276 } 294 }
277 chams_apply(mat, false); 295 chams_apply(mat, false, style, white);
278 g_force_override(self, mat, 0); 296 g_force_override(self, mat, 0);
279 g_orig_model_exec(self, state, info, bone); 297 g_orig_model_exec(self, state, info, bone);
280 g_force_override(self, nullptr, 0); 298 g_force_override(self, nullptr, 0);
281 // debugwhite is shared: restore colour and depth behaviour. 299 chams_reset(mat);
282 using FlagFn = void (*)(void *, int, bool);
283 vfunc<FlagFn>(mat, 29)(mat, 1 << 15, false);
284 chams_color(mat, 1.0f, 1.0f, 1.0f);
285 return; 300 return;
286 } 301 }
287 } 302 }