diff options
Diffstat (limited to 'src/hl2h.cpp')
| -rw-r--r-- | src/hl2h.cpp | 74 |
1 files changed, 69 insertions, 5 deletions
diff --git a/src/hl2h.cpp b/src/hl2h.cpp index 0261ff2..a4a1a88 100644 --- a/src/hl2h.cpp +++ b/src/hl2h.cpp | |||
| @@ -117,9 +117,20 @@ static void *entitylist_get(int idx) { | |||
| 117 | 117 | ||
| 118 | 118 | ||
| 119 | static void do_move(int seq) { | 119 | static void do_move(int seq) { |
| 120 | static bool g_echo_sent = false; | ||
| 120 | if (!g_input || !g_net.ok()) | 121 | if (!g_input || !g_net.ok()) |
| 121 | return; | 122 | return; |
| 122 | 123 | ||
| 124 | if (!g_echo_sent) { | ||
| 125 | g_echo_sent = true; | ||
| 126 | if (g_conmsg) { | ||
| 127 | g_conmsg("[hl2hake] succesfully loaded\n"); | ||
| 128 | logf("console echo sent (first CreateMove)"); | ||
| 129 | } else { | ||
| 130 | logf("g_conmsg is NULL — in-game console output unavailable"); | ||
| 131 | } | ||
| 132 | } | ||
| 133 | |||
| 123 | int localIdx = engine_get_local_player(); | 134 | int localIdx = engine_get_local_player(); |
| 124 | if (localIdx <= 0 || localIdx > 64) | 135 | if (localIdx <= 0 || localIdx > 64) |
| 125 | return; | 136 | return; |
| @@ -137,17 +148,16 @@ static void do_move(int seq) { | |||
| 137 | return; | 148 | return; |
| 138 | 149 | ||
| 139 | uintptr_t e = (uintptr_t)ent; | 150 | uintptr_t e = (uintptr_t)ent; |
| 140 | uint8_t movetype = *(uint8_t *)(e + g_net.movetype); | ||
| 141 | int flags = *(int *)(e + g_net.flags); | 151 | int flags = *(int *)(e + g_net.flags); |
| 142 | bool onground = (flags & FL_ONGROUND) != 0; | 152 | bool onground = (flags & FL_ONGROUND) != 0; |
| 143 | bool inwater = (flags & FL_INWATER) != 0; | 153 | bool inwater = (flags & FL_INWATER) != 0; |
| 144 | 154 | ||
| 145 | if (movetype == MOVETYPE_NOCLIP || movetype == MOVETYPE_LADDER) | 155 | bool climb_on = feature_active(FEAT_CLIMB); // bind held (or middle mouse when unbound) |
| 146 | return; | 156 | bool bhop_on = feature_active(FEAT_BHOP); |
| 147 | 157 | ||
| 148 | static bool lastground = false; | 158 | static bool lastground = false; |
| 149 | 159 | ||
| 150 | if (middle_mouse_down()) { | 160 | if (climb_on) { |
| 151 | if (cmd->command_number % 2) { | 161 | if (cmd->command_number % 2) { |
| 152 | cmd->buttons &= ~IN_JUMP; | 162 | cmd->buttons &= ~IN_JUMP; |
| 153 | cmd->buttons |= IN_USE; | 163 | cmd->buttons |= IN_USE; |
| @@ -156,7 +166,7 @@ static void do_move(int seq) { | |||
| 156 | cmd->buttons |= IN_JUMP; | 166 | cmd->buttons |= IN_JUMP; |
| 157 | } | 167 | } |
| 158 | note_modified(cmd, flags, (float *)(e + g_net.velocity)); | 168 | note_modified(cmd, flags, (float *)(e + g_net.velocity)); |
| 159 | } else if (cmd->buttons & IN_JUMP) { | 169 | } else if (bhop_on && (cmd->buttons & IN_JUMP)) { |
| 160 | if (inwater && (cmd->buttons & IN_DUCK)) { | 170 | if (inwater && (cmd->buttons & IN_DUCK)) { |
| 161 | lastground = onground; | 171 | lastground = onground; |
| 162 | return; | 172 | return; |
| @@ -193,9 +203,63 @@ static void do_move(int seq) { | |||
| 193 | using CreateMoveFn = bool (*)(void *, int, float, bool); | 203 | using CreateMoveFn = bool (*)(void *, int, float, bool); |
| 194 | static CreateMoveFn oCreateMove = nullptr; | 204 | static CreateMoveFn oCreateMove = nullptr; |
| 195 | 205 | ||
| 206 | using DrawPrintTextFn = void (*)(void *self, const wchar_t *text, int len, int drawType); | ||
| 207 | static DrawPrintTextFn oDrawPrintText = nullptr; | ||
| 208 | using PaintTraverseExFn = void (*)(void *, long, bool); | ||
| 209 | static PaintTraverseExFn oPaintTraverseEx = nullptr; | ||
| 210 | static bool g_in_draw = false; | ||
| 211 | |||
| 212 | // Hooked ISurface slot 22. The game calls this from a valid paint context; | ||
| 213 | // our overlay draws are submitted through outer_draw() (menu.cpp), which | ||
| 214 | // wraps them in PushMakeCurrent/PopMakeCurrent with the embedded panel. | ||
| 215 | static void hkdDrawPrintText(void *self, const wchar_t *text, int len, int drawType) { | ||
| 216 | if (g_in_draw) { | ||
| 217 | oDrawPrintText(self, text, len, drawType); | ||
| 218 | return; | ||
| 219 | } | ||
| 220 | g_in_draw = true; | ||
| 221 | oDrawPrintText(self, text, len, drawType); | ||
| 222 | // fallback trigger: fires when the game draws text (menus). Primary draw | ||
| 223 | // path is the PaintTraverseEx hook (slot 114), which fires every frame. | ||
| 224 | outer_draw(); | ||
| 225 | g_in_draw = false; | ||
| 226 | } | ||
| 227 | |||
| 228 | // PaintTraverseEx (slot 114, verified: IsVisible check + popups loop + "Too many | ||
| 229 | // popups" assert). Fires every frame for the root panel — unlike DrawPrintText | ||
| 230 | // (slot 22) which only fires when text is drawn, so it never fires in-world. | ||
| 231 | static void hkdPaintTraverseEx(void *self, long panel, bool paintPopups) { | ||
| 232 | using Fn = void (*)(void *, long, bool); | ||
| 233 | ((Fn)oPaintTraverseEx)(self, panel, paintPopups); | ||
| 234 | if (!g_in_draw) { | ||
| 235 | g_in_draw = true; | ||
| 236 | outer_draw(); | ||
| 237 | g_in_draw = false; | ||
| 238 | } | ||
| 239 | } | ||
| 240 | |||
| 196 | static bool hkdCreateMove(void *self, int seq, float frametime, bool active) { | 241 | static bool hkdCreateMove(void *self, int seq, float frametime, bool active) { |
| 197 | bool ret = oCreateMove(self, seq, frametime, active); | 242 | bool ret = oCreateMove(self, seq, frametime, active); |
| 198 | do_move(seq); | 243 | do_move(seq); |
| 244 | |||
| 245 | // Hook ISurface once: PaintTraverseEx (slot 114) fires every frame; keep | ||
| 246 | // DrawPrintText (slot 22) hooked as a fallback text-draw trigger. | ||
| 247 | static int isurface_hooked = 0; | ||
| 248 | if (!isurface_hooked && g_surface) { | ||
| 249 | void **svt = VTABLE(g_surface); | ||
| 250 | constexpr size_t VT_SIZE = 256; | ||
| 251 | void **newsvt = new void *[VT_SIZE]; | ||
| 252 | memcpy(newsvt, svt, VT_SIZE * sizeof(void *)); | ||
| 253 | oDrawPrintText = (DrawPrintTextFn)svt[22]; | ||
| 254 | newsvt[22] = (void *)&hkdDrawPrintText; | ||
| 255 | oPaintTraverseEx = (PaintTraverseExFn)svt[114]; | ||
| 256 | newsvt[114] = (void *)&hkdPaintTraverseEx; | ||
| 257 | VTABLE(g_surface) = newsvt; | ||
| 258 | isurface_hooked = 1; | ||
| 259 | logf("ISurface hooked: DrawPrintText slot 22 orig=%p, PaintTraverseEx slot 114 orig=%p", | ||
| 260 | (void *)oDrawPrintText, (void *)oPaintTraverseEx); | ||
| 261 | } | ||
| 262 | |||
| 199 | return ret; | 263 | return ret; |
| 200 | } | 264 | } |
| 201 | 265 | ||
