-
Notifications
You must be signed in to change notification settings - Fork 0
/
WeaponAnims.pas
212 lines (172 loc) · 5.59 KB
/
WeaponAnims.pas
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
unit WeaponAnims;
interface
function Init(dwFlags:cardinal):boolean;
implementation
uses BaseGameData, HudItems, xr_strings, sysutils, strutils, dynamic_caster, Inventory, Keys, gunsl_config;
procedure CalcMotionSpeed_Patch; stdcall;
asm
push $3F800000
movss xmm0, [esp]
add esp, 4
end;
procedure auth_get_hack(); stdcall;
asm
mov eax, $5B2D10FD
mov edx, $0
end;
function CHudItem__PlayHUDMotion_DecidePlayAnimOrNot(itm:pCHudItem; anim_name:pshared_str):boolean; stdcall;
var
wpn:pCWeaponMagazined;
begin
result:=true;
if (itm.m_current_motion.p_=nil) or (anim_name.p_=nil) then exit;
wpn:=dynamic_cast(itm, 0, RTTI_CHudItem, RTTI_CWeaponMagazined, false);
if wpn=nil then exit;
if (itm.m_dwMotionEndTm=0) and (leftstr(PChar(@itm.m_current_motion.p_.value), length('anm_idle'))='anm_idle') and (0=StrComp(PChar(@itm.m_current_motion.p_.value), PChar(@anim_name.p_.value))) then begin
//óæå èãðàåì ýòó èäëîâóþ àíèìó - íåò ñìûñëà ïåðåíàçíà÷àòü
result:=false;
end else if (leftstr(PChar(@anim_name.p_.value), length('anm_idle'))<>'anm_idle') then begin
result:=true;
end else if (leftstr(PChar(@itm.m_current_motion.p_.value), length('anm_shot'))='anm_shot') then begin
//âñëåä çà âûñòðåëîì õîòèì ïåðåõîä â èäë
if game_ini_r_bool_def(PChar(@itm.hud_sect.p_.value), PChar('locked_'+PChar(@itm.m_current_motion.p_.value)), false) then begin
SetAnimFinishing(itm, true);
SetPending(itm, true);
result:=false;
end else begin
result:=false;
end;
result:=true;
end else if (itm.m_dwMotionEndTm<>0) and not IsAnimFinished(itm) and (leftstr(PChar(@itm.m_current_motion.p_.value), length('anm_idle'))<>'anm_idle') and (leftstr(PChar(@anim_name.p_.value), length('anm_idle'))='anm_idle') then begin
//ó íàñ åùå íå çàêîí÷èëàñü ïðåäûäóùàÿ àíèìà, íî ìû óæå õîòèì â èäë... Æä¸ì îêîí÷àíèÿ
SetAnimFinishing(itm, true);
SetPending(itm, true);
result:=false;
end;
end;
procedure CHudItem__PlayHUDMotion_DecidePlayAnimOrNot_Patch(); stdcall;
asm
pop edx //ret addr
pushad
push eax
push ecx
call CHudItem__PlayHUDMotion_DecidePlayAnimOrNot
cmp al, 0
popad
jne @allok
xor eax, eax
ret 4
@allok:
pushad
//ïîêàæåì, ÷òî àíèìà ÍÅ çàâåðøåíà (èáî òîëüêî ñòàðòîâàëà)
push 0
push ecx
push 0
push ecx
call SetAnimFinished
call SetAnimFinishing
popad
push ebp //original code
mov ebp, esp
and esp, $FFFFFFF8
jmp edx
end;
procedure OnAnimationEnd(itm:pCHudItem); stdcall;
begin
if IsAnimFinishing(itm) then begin
SetAnimFinishing(itm, false);
SetAnimFinished(itm, true);
SetPending(itm, false);
virtual_CHudItem__PlayAnimIdle(itm);
end;
end;
procedure CWeaponMagazined__OnAnimationEnd_Patch(); stdcall;
asm
pushad
push ecx
call OnAnimationEnd
popad
mov eax, [esp+8]
cmp eax, 07
end;
procedure CWeaponShotgun__OnAnimationEnd_Patch(); stdcall;
asm
pushad
push esi
call OnAnimationEnd
popad
call edx
pop esi
ret 4
end;
function NeedIgnoreAction(inv:pCInventory; cmd:cardinal; flags:cardinal):boolean; stdcall;
var
curslot:pCInventorySlot;
itm:pCInventoryItem;
wpn:pCWeaponMagazined;
begin
result:=false;
if (cmd=kDROP) or (cmd=kWPN_ZOOM_INC) or (cmd=kWPN_ZOOM_DEC) or ((cmd>=kWPN_1) and (cmd<=kARTEFACT)) then exit;
curslot:=GetActiveSlot(inv);
if curslot=nil then exit;
itm:=curslot.m_pIItem;
if itm=nil then exit;
wpn:=dynamic_cast(itm, 0, RTTI_CInventoryItem, RTTI_CWeaponMagazined, false);
if wpn=nil then exit;
if (cmd=kWPN_ZOOM) and (wpn.base_CWeapon.m_zoom_params.m_bIsZoomModeNow<>0) then exit;
//íàæàòèå âûñòðåëà âî âðåìÿ ïåðåçàðÿäêè ìîæåò áûòü âàæíûì ñèãíàëîì (íàïð., äëÿ äðîáàøåé)
if EWeaponStates__eReload=wpn.base_CWeapon.base_CHUDItem.base_CHUDState.m_hud_item_state then exit;
if IsPending(@wpn.base_CWeapon.base_CHUDItem) or IsAnimFinishing(@wpn.base_CWeapon.base_CHUDItem) then result:=true;
end;
procedure CInventory__Action_Patch(); stdcall;
asm
pop eax //ret addr
mov ecx, [esp+$4]
pushad
push ebx
push ecx
push esi
call NeedIgnoreAction
cmp al, 0
popad
je @allok
xor eax, eax
ret 4
@allok:
mov ecx, [esi+$4C]
push ebp
mov ebp, [esp+8]
jmp eax
end;
function Init(dwFlags:cardinal):boolean;
var
addr:cardinal;
begin
result:=false;
if dwFlags and FLG_PATCH_GAME >0 then begin
//óáèðàåì óñêîðåíèå â 2 ðàçà àíèìàöèé äîñòàâàíèÿ è óáèðàíèÿ â ÌÏ
addr:=xrGame_addr+$2880C0;
if not WriteJump(addr, cardinal(@CalcMotionSpeed_Patch), 6, false) then exit;
//îáåñïå÷åíèå íîðìàëüíîé ðàáîòû àíèìàöèé â óñëîâèÿõ èçìåíèâøåéñÿ äëèíû
addr:=xrGame_addr+$286BA0;
if not WriteJump(addr, cardinal(@CHudItem__PlayHUDMotion_DecidePlayAnimOrNot_Patch), 6, true) then exit;
addr:=xrGame_addr+$2619E0;
if not WriteJump(addr, cardinal(@CWeaponMagazined__OnAnimationEnd_Patch), 7, true) then exit;
addr:=xrGame_addr+$26DBC7;
if not WriteJump(addr, cardinal(@CWeaponShotgun__OnAnimationEnd_Patch), 5, false) then exit;
addr:=xrGame_addr+$26DBF6;
if not WriteJump(addr, cardinal(@CWeaponShotgun__OnAnimationEnd_Patch), 5, false) then exit;
addr:=xrGame_addr+$26DC09;
if not WriteJump(addr, cardinal(@CWeaponShotgun__OnAnimationEnd_Patch), 5, false) then exit;
//çàïðåò íà äåéñòâèÿ ïðè àêòèâíîñòè áëîêà îðóæèÿ
addr:=xrGame_addr+$23D970;
if not WriteJump(addr, cardinal(@CInventory__Action_Patch), 8, true) then exit;
end;
if dwFlags and FLG_PATCH_CORE >0 then begin
//ñîîáùåíèå ñåðâåðó î ÷èñòûõ ðåñóðñàõ èãðû
addr:=xrCore_addr+$15010;
if not WriteJump(addr, cardinal(@auth_get_hack), 6, false) then exit;
end;
result:=true;
end;
end.