forked from gunslingermod/gunslinger_wpnpatch
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathLevel.pas
270 lines (219 loc) · 6.34 KB
/
Level.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
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
unit Level;
{$IFDEF FPC}{$MODE DELPHI}{$ENDIF}
interface
uses MatVectors, xr_Cartridge, Misc;
function GetLevel():pointer; stdcall;
function Level_to_CObjectSpace(l:pointer):pointer; stdcall;
procedure spawn_phantom(pos:pFVector3);
procedure AddBullet(position:pFVector3; direction:pFVector3; starting_speed:single; power:single; impulse:single; sender_id:word; sendersweapon_id:word; e_hit_type:cardinal; maximum_distance:single; cartridge:pCCartridge; air_resistance_factor:single; SendHit:boolean; AimBullet:boolean); stdcall;
procedure MakeWeaponKick(pos:pFVector3; dir:pFVector3; wpn:pointer); stdcall;
function CLevel__SpawnItem(this:pointer; section:PChar; pos:pFVector3; vertex_id:cardinal; parent_id:word; return_item:boolean):pCSE_Abstract; stdcall;
procedure CLevel__AfterSpawnSendAndFree(this:pointer; obj:pCSE_Abstract); stdcall;
function GetObjectById(id:word):pointer; stdcall;
implementation
uses BaseGameData, gunsl_config, HudItemUtils, HitUtils, math, sysutils, xr_strings;
function GetLevel():pointer; stdcall;
begin
asm
mov eax, xrEngine_addr
mov eax, [eax+$92d2c]
mov @result, eax
end;
end;
function Level_to_CObjectSpace(l:pointer):pointer; stdcall;
asm
mov eax, l
add eax, $40094
mov @result, eax
end;
procedure spawn_phantom(pos:pFVector3);
asm
pushad
mov eax, pos
push eax
mov eax, xrgame_addr
add eax, $23cdd0
call eax
add esp, 4
popad
end;
procedure AddBullet(position:pFVector3; direction:pFVector3; starting_speed:single; power:single; impulse:single; sender_id:word; sendersweapon_id:word; e_hit_type:cardinal; maximum_distance:single; cartridge:pCCartridge; air_resistance_factor:single; SendHit:boolean; AimBullet:boolean); stdcall;
asm
pushad
movzx eax, AimBullet
push eax
movzx ebx, SendHit
push ebx
push air_resistance_factor
push cartridge
push maximum_distance
push e_hit_type
movzx eax, sendersweapon_id
push eax
movzx ebx, sender_id
push ebx
push impulse
push power
push starting_speed
push direction
push position
call GetLevel
mov ecx, [eax+$487c4]
mov eax, xrgame_addr
add eax, $24ef70
call eax
popad
end;
function CLevel__SpawnItem(this:pointer; section:PChar; pos:pFVector3; vertex_id:cardinal; parent_id:word; return_item:boolean):pCSE_Abstract; stdcall;
asm
pushad
xor eax, eax
mov al, return_item
push eax
mov ax, parent_id
push eax
push vertex_id
push pos
push section
mov ecx, this
mov eax, xrgame_addr
add eax, $23BB40
call eax
mov @result, eax
popad
end;
procedure CLevel__AfterSpawnSendAndFree(this:pointer; obj:pCSE_Abstract); stdcall;
asm
//âçÿòî èç CLevel::SpawnItem - ôðàãìåíò îòïðàâêè ñîîáùåíèÿ ñåðâåðó è óíè÷òîæåíèÿ îáúåêòà
sub esp, $4020
lea ecx, [esp]
mov eax, xrgame_addr
add eax, $512818 //NET_Packet constructor
call [eax]
lea eax, [esp]
mov esi, obj
mov edx, [esi]
mov ecx, [edx]
push 01
push eax //packet
push esi //this
call ecx //obj->Spawn_Write
lea eax, [esp]
mov ecx, this
add ecx, $40110
mov edx, [ecx]
mov edx, [edx+$10]
push 0
push 8
push eax //packet
call edx //CLevel->Send
push esi
mov eax, xrgame_addr
add eax, $509DA6
call eax
lea ecx, [esi+$08]
mov edi, eax
mov eax, [ecx]
mov edx, [eax+$14]
add esp, 4
push 0
call edx
mov ecx, xrgame_addr
mov ecx, [ecx+$5127B4]
push edi
mov eax, xrgame_addr
call [eax+$5127B8]
add esp, $4020
end;
procedure MakeWeaponKick(pos:pFVector3; dir:pFVector3; wpn:pointer); stdcall;
var
c:CCartridge;
sect:PChar;
material:PChar;
cnt, i, htype:integer;
hp, imp, hdist:single;
tmpdir:FVector3;
right, up:FVector3;
disp_hor, disp_ver:single;
begin
sect:=GetSection(wpn);
if game_ini_line_exist(sect, 'kick_material') then begin
material:=game_ini_read_string(sect, 'kick_material')
end else begin
material:='objects\knife';
end;
material:=FindStrValueInUpgradesDef(wpn, 'kick_material', material);
InitCartridge(@c);
c.SCartridgeParam__kAP:=ModifyFloatUpgradedValue(wpn, 'kick_ap', game_ini_r_single_def(sect, 'kick_ap', 0.001));
c.SCartridgeParam__fWallmarkSize:=ModifyFloatUpgradedValue(wpn, 'kick_wallmark_size', game_ini_r_single_def(sect, 'kick_wallmark_size', 0.05));
c.bullet_material_idx:=GetMaterialIdx(material);
cnt:=FindIntValueInUpgradesDef(wpn, 'kick_hit_count', game_ini_r_int_def(sect, 'kick_hit_count', 1));
hp:=ModifyFloatUpgradedValue(wpn, 'kick_hit_power', game_ini_r_single_def(sect, 'kick_hit_power', 0.0));
imp:=ModifyFloatUpgradedValue(wpn, 'kick_hit_impulse', game_ini_r_single_def(sect, 'kick_hit_impulse', 0.0));
htype:= FindIntValueInUpgradesDef(wpn, 'kick_hit_type', game_ini_r_int_def(sect, 'kick_hit_type', EHitType__eHitTypeWound));
hdist:=ModifyFloatUpgradedValue(wpn, 'kick_distance', game_ini_r_single_def(sect, 'kick_distance', 0.0));
disp_hor:=ModifyFloatUpgradedValue(wpn, 'kick_disp_hor', game_ini_r_single_def(sect, 'kick_disp_hor', 0.0));
disp_ver:=ModifyFloatUpgradedValue(wpn, 'kick_disp_ver', game_ini_r_single_def(sect, 'kick_disp_ver', 0.0));
//log(PChar(floattostr(hp)));
//log(PChar(inttostr(htype)));
//äëÿ îäíîãî âîëìàðêà
AddBullet(pos, dir, 10000,
0,
0,
0,
GetID(wpn),
htype,
hdist,
@c,
1.0,
true,
false);
//äëÿ õèòà
c.bullet_material_idx:=GetMaterialIdx('objects\clothes');
c.SCartridgeParam__fWallmarkSize:=0.0001;
for i:=0 to cnt-1 do begin
tmpdir:=dir^;
generate_orthonormal_basis_normalized(@tmpdir, @up, @right);
//ïîñ÷èòàåì ìàêñèìàëüíîå îòêëîíåíèå
v_mul(@up, disp_ver);
v_mul(@right, disp_hor);
//âûñòàâèì äèðåêöèþ â êðàéíåå ïîëîæåíèå
v_sub(@tmpdir, @up);
v_sub(@tmpdir, @right);
//ïîñìîòðèì, íàñêîëüêî ñìåñòèòü äèðåêöèþ äëÿ òåêóùåãî óäàðà
v_mul(@up, 2*i/cnt);
v_mul(@right, 2*i/cnt);
//âûñòàâèì òåêóùåå ñìåùåíèå
v_add(@tmpdir, @up);
v_add(@tmpdir, @right);
AddBullet(pos, @tmpdir, 10000,
hp,
imp,
0,
GetID(wpn),
htype,
hdist,
@c,
1.0,
true,
false);
end;
FreeCartridge(@c);
end;
function GetObjectById(id:word):pointer; stdcall;
asm
pushad
movzx eax, id
push eax
mov eax, xrgame_addr;
add eax, $23f5a0
call eax // get_object_by_id
pop ecx
cmp eax, 0
je @finish
mov eax, [eax+$4]
@finish:
mov @result, eax
popad
end;
end.