[Half-Life AMXX] / grab_plus.sma Repository:
ViewVC logotype

Annotation of /grab_plus.sma

Parent Directory Parent Directory | Revision Log Revision Log


Revision 15 - (view) (download)

1 : ian 1 /*
2 : ian 15 Grab+ v1.2.1
3 : ian 1 Copyright (C) 2007 Ian (Juan) Cammarata
4 :    
5 :     This program is free software; you can redistribute it and/or modify it under
6 :     the terms of the GNU General Public License as published by the Free Software
7 :     Foundation; either version 2 of the License, or (at your option) any later
8 :     version.
9 :    
10 :     This program is distributed in the hope that it will be useful, but WITHOUT ANY
11 :     WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
12 :     PARTICULAR PURPOSE. See the GNU General Public License for more details.
13 :    
14 :     You should have received a copy of the GNU General Public License along with
15 :     this program; go to http://www.opensource.org/licenses/gpl-license.php
16 :     --------------------------------------------------------------------------------
17 :    
18 :     http://ian.cammarata.us/projects/grab_plus
19 : ian 15 Nov 12 14:35
20 : ian 1
21 :    
22 :     Description:
23 :     This is a remake from scratch of SpaceDude's Jedi Force Grab plugin. It has many additional features and optimizations, is less spammy, multilingual and requires fewer binds.
24 :    
25 :    
26 :     Features:
27 :     Multilingual
28 :     Screenfade to indicate grab activity instead of chat spam.
29 :     Can grab players off a ladder.
30 :     Automatically choke by holding down +pull while at min distance.
31 :     Choke with use key.
32 :     Throw with drop.
33 :     Can't have mutliple admins grabbing the same player.
34 :     Auto drop on death.
35 :     Grab entities other than players, such as bombs, weapons, and hostages.
36 :    
37 :    
38 :     Commands:
39 :    
40 :     +grab : Grab something for as long as you hold down the key.
41 :     grab_toggle : Same as +grab but toggles.
42 :     amx_grab <name> : Grab client by name or id and teleport them to you. Use +grab or grab_toggle key to release.
43 :    
44 :     +pull/+push (or invnext/invprev): Pulls/pushes the grabbed towards/away from you as you hold the button.
45 :    
46 : ian 10 +use : Chokes the grabbed (it damages the grabbed with 5 (cvar: gp_choke_dmg) hp per 1.5 (cvar: gp_choke_time) seconds)
47 :     drop - Throws the grabbed with 1500 velocity. (cvar: gp_throw_force)
48 : ian 1
49 :    
50 :     Cvars (First value is default):
51 :     gp_enabled <1|0> Enables all plugin functionality.
52 : ian 10 gp_players_only <0|1> Disables admins grabbing entities other than players.
53 : ian 1
54 :     gp_min_dist <90|...> Min distance between the grabber and grabbed.
55 : ian 10 gp_grab_force <8|...> Sets the amount of force used when grabbing players.
56 :     gp_throw_force <1500|...> Sets the power used when throwing players.
57 : ian 1 gp_speed <5|...> How fast the grabbed moves when using push and pull.
58 :    
59 : ian 10 gp_choke_time <1.5|...> Time frequency for choking.
60 :     gp_choke_dmg <5|...> Amount of damage done with each choke.
61 :     gp_auto_choke <1|0> Enable/disable choking automatically with +pull command.
62 : ian 1
63 : ian 10 gp_screen_fade <1|0> Enables/disables screenfade when grabbing.
64 : ian 9 gp_glow <1|0> Enables/disables glowing for grabbed objects.
65 : ian 1
66 : ian 9 gp_glow_r <50|0-255> Sets red amount for glow and screenfade.
67 :     gp_glow_g <0|0-255> Sets green amount for glow and screenfade.
68 :     gp_glow_b <0|0-255> Sets blue amount for glow and screenfade.
69 :     gp_glow_a <0|0-255> Sets alpha for glow and screenfade.
70 : ian 1
71 : ian 9
72 : ian 1 Notes:
73 :     Make sure you place the grab_plus.txt file in addons\amxmodx\data\lang
74 :    
75 :    
76 :     Credits:
77 : ian 5 Thanks to vittu for contributing code (changed all engine/fun module stuff to fakemeta).
78 :    
79 : ian 1 Thanks to all the coders who worked on the original Jedi Force Grab plugin for all their ideas:
80 :     SpaceDude
81 :     KCE
82 :     KRoTaL
83 :     BOB_SLAYER
84 :     kosmo111
85 :    
86 :    
87 :     Supported Languages:
88 :     1337 (100%) - Thanks to l337newb
89 :     Brazilian Portuguese (100%) - Thanks to Arion
90 :     Danish (100%) - Thanks to nellerbabz
91 :     Dutch (100%) - Thanks to BlackMilk
92 :     English (100%)
93 :     Finnish (100%) - Thanks to Pro Patria Finland
94 :     French (100%) - Thanks to connorr
95 :     German (100%) - Thanks to SchlumPF*
96 :     Russian (100%) - Thanks to `666
97 :     Spanish (100%) - Hope these don't suck.
98 :     Swedish (100%) - Thanks to Bend3r
99 :    
100 :    
101 :     Change Log:
102 :     Key (+ added | - removed | c changed | f fixed)
103 :    
104 : ian 15 v1.2.1 (Nov 12, 2007)
105 :     f: Elimited two run time warnings in the player prethink function.
106 :    
107 : ian 11 v1.2 (Nov 06, 2007)
108 : ian 10 +: Cvars gp_screen_fade and gp_glow to enable/disable these features.
109 : ian 5 +: Cvar gp_glow_a controls to control alpha of screenfade and glow.
110 : ian 10 +: Cvar gp_auto_choke to enable/disable choking automatically with +pull command.
111 : ian 11 c: Removed dependency of engine and fun modules. Thanks to vittu for doing most of the work.
112 : ian 10 c: Made cvar names more consistent by adding more underscores.
113 : ian 11 f: Fixed compile bug with amxx 1.8.0 (Compiles with 1.7.x as well).
114 : ian 5
115 : ian 1 v1.1 (Oct 16, 2007)
116 :     +: Grab a few types of entities other than players.
117 : ian 10 +: Cvar gp_players_only.
118 : ian 1
119 :     v1.0 (Oct 13, 2007)
120 :     !: Initial release
121 :    
122 :     */
123 :    
124 :     #include <amxmodx>
125 :     #include <amxmisc>
126 :     #include <fakemeta>
127 :    
128 : ian 15 #define VERSION "1.2.1"
129 : ian 1 #define ADMIN ADMIN_LEVEL_A
130 :    
131 :     #define TSK_CHKE 50
132 :    
133 : ian 5 #define SVC_DAMAGE 19
134 : ian 1 #define SF_FADEOUT 0
135 :    
136 :     new client_data[33][4]
137 :     #define GRABBED 0
138 :     #define GRABBER 1
139 :     #define GRAB_LEN 2
140 :     #define FLAGS 3
141 :    
142 :     #define CDF_IN_PUSH (1<<0)
143 :     #define CDF_IN_PULL (1<<1)
144 :     #define CDF_NO_CHOKE (1<<2)
145 :    
146 :     //Cvar Pointers
147 : ian 10 new p_enabled, p_players_only
148 :     new p_throw_force, p_min_dist, p_speed, p_grab_force
149 :     new p_choke_time, p_choke_dmg, p_auto_choke
150 : ian 5 new p_glow_r, p_glow_b, p_glow_g, p_glow_a
151 :     new p_fade, p_glow
152 : ian 1
153 :     //Pseudo Constants
154 :     new MAXPLAYERS
155 : ian 5 new SVC_SCREENFADE, SVC_SCREENSHAKE
156 : ian 1
157 :     public plugin_init( )
158 :     {
159 :     register_plugin( "Grab+", VERSION, "Ian Cammarata" )
160 :     register_cvar( "grab_plus_version", VERSION, FCVAR_SERVER )
161 :     set_cvar_string( "grab_plus_version", VERSION )
162 :    
163 :     p_enabled = register_cvar( "gp_enabled", "1" )
164 : ian 10 p_players_only = register_cvar( "gp_players_only", "0" )
165 : ian 1
166 : ian 10 p_min_dist = register_cvar ( "gp_min_dist", "90" )
167 :     p_throw_force = register_cvar( "gp_throw_force", "1500" )
168 :     p_grab_force = register_cvar( "gp_grab_force", "8" )
169 : ian 1 p_speed = register_cvar( "gp_speed", "5" )
170 :    
171 : ian 10 p_choke_time = register_cvar( "gp_choke_time", "1.5" )
172 :     p_choke_dmg = register_cvar( "gp_choke_dmg", "5" )
173 :     p_auto_choke = register_cvar( "gp_auto_choke", "1" )
174 : ian 1
175 :     p_glow_r = register_cvar( "gp_glow_r", "50" )
176 :     p_glow_g = register_cvar( "gp_glow_g", "0" )
177 :     p_glow_b = register_cvar( "gp_glow_b", "0" )
178 : ian 5 p_glow_a = register_cvar( "gp_glow_a", "200" )
179 : ian 1
180 : ian 10 p_fade = register_cvar( "gp_screen_fade", "1" )
181 : ian 5 p_glow = register_cvar( "gp_glow", "1" )
182 :    
183 : ian 1 register_clcmd( "amx_grab", "force_grab", ADMIN, "Grab client & teleport to you." )
184 :     register_clcmd( "grab_toggle", "grab_toggle", ADMIN, "press once to grab and again to release" )
185 :     register_clcmd( "+grab", "grab", ADMIN, "bind a key to +grab" )
186 :     register_clcmd( "-grab", "unset_grabbed" )
187 :    
188 :     register_clcmd( "+push", "push", ADMIN, "bind a key to +push" )
189 :     register_clcmd( "-push", "push" )
190 :     register_clcmd( "+pull", "pull", ADMIN, "bind a key to +pull" )
191 :     register_clcmd( "-pull", "pull" )
192 :     register_clcmd( "push", "push2" )
193 :     register_clcmd( "pull", "pull2" )
194 :    
195 :     register_clcmd( "drop" ,"throw" )
196 :    
197 :     register_event( "DeathMsg", "DeathMsg", "a" )
198 :    
199 : ian 8 register_forward( FM_PlayerPreThink, "fm_player_prethink" )
200 :    
201 : ian 1 register_dictionary( "grab_plus.txt" )
202 :    
203 :     MAXPLAYERS = get_maxplayers()
204 :    
205 :     SVC_SCREENFADE = get_user_msgid( "ScreenFade" )
206 :     SVC_SCREENSHAKE = get_user_msgid( "ScreenShake" )
207 :     }
208 :    
209 :     public plugin_precache( )
210 :     {
211 :     precache_sound( "player/PL_PAIN2.WAV" )
212 :     }
213 :    
214 : ian 8 public fm_player_prethink( id )
215 : ian 1 {
216 :     //Search for a target
217 :     if ( client_data[id][GRABBED] == -1 )
218 :     {
219 :     new Float:orig[3], Float:ret[3]
220 : ian 11 get_view_pos( id, orig )
221 :     ret = vel_by_aim( id, 9999 )
222 : ian 1
223 : ian 11 for( new i = 0; i < 3; i++ ) ret[i] = orig[i] + ret[i]
224 :     new target = traceline( orig, ret, id, ret )
225 : ian 1
226 :     if( 0 < target <= MAXPLAYERS )
227 :     {
228 : ian 15 if( is_grabbed( target, id ) ) return FMRES_IGNORED
229 : ian 1 set_grabbed( id, target )
230 :     }
231 : ian 10 else if( !get_pcvar_num( p_players_only ) )
232 : ian 1 {
233 :     new movetype
234 : ian 15 if( target && pev_valid( target ) )
235 : ian 1 {
236 :     movetype = pev( target, pev_movetype )
237 :     if( !( movetype == MOVETYPE_WALK || movetype == MOVETYPE_STEP || movetype == MOVETYPE_TOSS ) )
238 : ian 15 return FMRES_IGNORED
239 : ian 1 }
240 :     else
241 :     {
242 : ian 15 target = 0
243 : ian 5 new ent = engfunc( EngFunc_FindEntityInSphere, -1, ret, 12.0 )
244 : ian 1 while( !target && ent > 0 )
245 :     {
246 :     movetype = pev( ent, pev_movetype )
247 :     if( ( movetype == MOVETYPE_WALK || movetype == MOVETYPE_STEP || movetype == MOVETYPE_TOSS )
248 :     && ent != id )
249 :     target = ent
250 : ian 5 ent = engfunc( EngFunc_FindEntityInSphere, ent, ret, 12.0 )
251 : ian 1 }
252 :     }
253 :     if( target )
254 :     {
255 : ian 15 if( is_grabbed( target, id ) ) return FMRES_IGNORED
256 : ian 1 set_grabbed( id, target )
257 :     }
258 :     }
259 :     }
260 :     //If they've grabbed something
261 :     if( client_data[id][GRABBED] > 0 )
262 :     {
263 :     new target = client_data[id][GRABBED]
264 :     if( !pev_valid( target ) || ( pev( target, pev_health ) < 1 && pev( target, pev_max_health ) ) )
265 :     {
266 :     unset_grabbed( id )
267 : ian 15 return FMRES_IGNORED
268 : ian 1 }
269 :    
270 :     //Use key choke
271 :     if( pev( id, pev_button ) & IN_USE )
272 :     do_choke( id )
273 :    
274 :     //Push and pull
275 :     if ( client_data[id][FLAGS] & CDF_IN_PULL )
276 :     do_pull( id )
277 :     else if ( client_data[id][FLAGS] & CDF_IN_PUSH )
278 :     do_push( id )
279 :    
280 :     grab_think( id )
281 :     }
282 :     if( client_data[id][GRABBER] > 0 ) grab_think( client_data[id][GRABBER] )
283 :    
284 : ian 15 return FMRES_IGNORED
285 : ian 1 }
286 :    
287 :     public grab_think ( id )
288 :     {
289 :     new target = client_data[id][GRABBED]
290 :    
291 :     //Keep grabbed clients from sticking to ladders
292 :     if( pev( target, pev_movetype ) == MOVETYPE_FLY && !(pev( target, pev_button ) & IN_JUMP ) ) client_cmd( target, "+jump;wait;-jump" )
293 :    
294 :     //Move targeted client
295 : ian 12 new Float:tmpvec[3], Float:tmpvec2[3], Float:torig[3], Float:tvel[3]
296 : ian 1
297 : ian 11 get_view_pos( id, tmpvec )
298 : ian 10
299 : ian 11 tmpvec2 = vel_by_aim( id, client_data[id][GRAB_LEN] )
300 : ian 10
301 : ian 1 torig = get_target_origin_f( target )
302 :    
303 : ian 10 new force = get_pcvar_num( p_grab_force )
304 : ian 1
305 :     for( new i = 0; i < 3; i++ )
306 : ian 11 tvel[i] = ( ( tmpvec[i] + tmpvec2[i] ) - torig[i] ) * force
307 : ian 1
308 : ian 5 set_pev( target, pev_velocity, tvel )
309 : ian 1 }
310 :    
311 :     stock Float:get_target_origin_f( id )
312 :     {
313 :     new Float:orig[3]
314 : ian 5 pev( id, pev_origin, orig )
315 : ian 1
316 :     //If grabbed is not a player, move origin to center
317 :     if( id > MAXPLAYERS )
318 :     {
319 :     new Float:mins[3], Float:maxs[3]
320 : ian 5 pev( id, pev_mins, mins )
321 :     pev( id, pev_maxs, maxs )
322 : ian 1
323 :     if( !mins[2] ) orig[2] += maxs[2] / 2
324 :     }
325 :    
326 :     return orig
327 :     }
328 :    
329 :     public grab_toggle( id, level, cid )
330 :     {
331 :     if( !client_data[id][GRABBED] ) grab( id, level, cid )
332 :     else unset_grabbed( id )
333 :    
334 :     return PLUGIN_HANDLED
335 :     }
336 :    
337 :     public grab( id, level, cid )
338 :     {
339 :     if( !cmd_access( id, level, cid, 1 ) || !get_pcvar_num( p_enabled ) ) return PLUGIN_HANDLED
340 :    
341 :     if ( !client_data[id][GRABBED] ) client_data[id][GRABBED] = -1
342 :     screenfade_in( id )
343 :    
344 :     return PLUGIN_HANDLED
345 :     }
346 :    
347 :     public screenfade_in( id )
348 :     {
349 : ian 5 if( get_pcvar_num( p_fade ) )
350 :     {
351 :     message_begin( MSG_ONE, SVC_SCREENFADE, _, id )
352 :     write_short( 10000 ) //duration
353 :     write_short( 0 ) //hold
354 :     write_short( SF_FADE_IN + SF_FADE_ONLYONE ) //flags
355 :     write_byte( get_pcvar_num( p_glow_r ) ) //r
356 :     write_byte( get_pcvar_num( p_glow_g ) ) //g
357 :     write_byte( get_pcvar_num( p_glow_b ) ) //b
358 :     write_byte( get_pcvar_num( p_glow_a ) / 2 ) //a
359 :     message_end( )
360 :     }
361 : ian 1 }
362 :    
363 :     public throw( id )
364 :     {
365 :     new target = client_data[id][GRABBED]
366 :     if( target > 0 )
367 :     {
368 : ian 11 set_pev( target, pev_velocity, vel_by_aim( id, get_pcvar_num(p_throw_force) ) )
369 : ian 1 unset_grabbed( id )
370 :     return PLUGIN_HANDLED
371 :     }
372 : ian 11
373 : ian 1 return PLUGIN_CONTINUE
374 :     }
375 :    
376 :     public unset_grabbed( id )
377 :     {
378 :     new target = client_data[id][GRABBED]
379 :     if( target > 0 && pev_valid( target ) )
380 :     {
381 : ian 5 set_pev( target, pev_renderfx, kRenderFxNone )
382 :     set_pev( target, pev_rendercolor, {255.0, 255.0, 255.0} )
383 :     set_pev( target, pev_rendermode, kRenderNormal )
384 :     set_pev( target, pev_renderamt, 16.0 )
385 :    
386 : ian 1 if( 0 < target <= MAXPLAYERS )
387 :     client_data[target][GRABBER] = 0
388 :     }
389 :     client_data[id][GRABBED] = 0
390 :    
391 : ian 5 if( get_pcvar_num( p_fade ) )
392 :     {
393 :     message_begin( MSG_ONE, SVC_SCREENFADE, _, id )
394 :     write_short( 10000 ) //duration
395 :     write_short( 0 ) //hold
396 :     write_short( SF_FADEOUT ) //flags
397 :     write_byte( get_pcvar_num( p_glow_r ) ) //r
398 :     write_byte( get_pcvar_num( p_glow_g ) ) //g
399 :     write_byte( get_pcvar_num( p_glow_b ) ) //b
400 :     write_byte( get_pcvar_num( p_glow_a ) / 2 ) //a
401 :     message_end( )
402 :     }
403 : ian 1 }
404 :    
405 :     //Grabs onto someone
406 :     public set_grabbed( id, target )
407 :     {
408 : ian 5 if( get_pcvar_num( p_glow ) )
409 :     {
410 :     new Float:color[3]
411 :     color[0] = get_pcvar_float( p_glow_r )
412 :     color[1] = get_pcvar_float( p_glow_g )
413 :     color[2] = get_pcvar_float( p_glow_b )
414 : ian 6 set_pev( target, pev_renderfx, kRenderFxGlowShell )
415 :     set_pev( target, pev_rendercolor, color )
416 :     set_pev( target, pev_rendermode, kRenderTransColor )
417 :     set_pev( target, pev_renderamt, get_pcvar_float( p_glow_a ) )
418 : ian 5 }
419 : ian 1
420 :     if( 0 < target <= MAXPLAYERS )
421 :     client_data[target][GRABBER] = id
422 :     client_data[id][FLAGS] = 0
423 :     client_data[id][GRABBED] = target
424 : ian 5 new Float:torig[3], Float:orig[3]
425 :     pev( target, pev_origin, torig )
426 :     pev( id, pev_origin, orig )
427 :     client_data[id][GRAB_LEN] = floatround( get_distance_f( torig, orig ) )
428 : ian 10 if( client_data[id][GRAB_LEN] < get_pcvar_num( p_min_dist ) ) client_data[id][GRAB_LEN] = get_pcvar_num( p_min_dist )
429 : ian 1 }
430 :    
431 :     public push( id )
432 :     {
433 :     client_data[id][FLAGS] ^= CDF_IN_PUSH
434 :     return PLUGIN_HANDLED
435 :     }
436 :    
437 :     public pull( id )
438 :     {
439 :     client_data[id][FLAGS] ^= CDF_IN_PULL
440 :     return PLUGIN_HANDLED
441 :     }
442 :    
443 :     public push2( id )
444 :     {
445 :     if( client_data[id][GRABBED] > 0 )
446 :     {
447 :     do_push( id )
448 :     return PLUGIN_HANDLED
449 :     }
450 :     return PLUGIN_CONTINUE
451 :     }
452 :    
453 :     public pull2( id )
454 :     {
455 :     if( client_data[id][GRABBED] > 0 )
456 :     {
457 :     do_pull( id )
458 :     return PLUGIN_HANDLED
459 :     }
460 :     return PLUGIN_CONTINUE
461 :     }
462 :    
463 :     public do_push( id )
464 :     if( client_data[id][GRAB_LEN] < 9999 )
465 :     client_data[id][GRAB_LEN] += get_pcvar_num( p_speed )
466 :    
467 :     public do_pull( id )
468 :     {
469 : ian 10 new mindist = get_pcvar_num( p_min_dist )
470 : ian 1 new len = client_data[id][GRAB_LEN]
471 :    
472 :     if( len > mindist )
473 :     {
474 :     len -= get_pcvar_num( p_speed )
475 :     if( len < mindist ) len = mindist
476 :     client_data[id][GRAB_LEN] = len
477 :     }
478 : ian 10 else if( get_pcvar_num( p_auto_choke ) )
479 :     do_choke( id )
480 : ian 1 }
481 :    
482 :     public do_choke( id )
483 :     {
484 :     new target = client_data[id][GRABBED]
485 :     if( client_data[id][FLAGS] & CDF_NO_CHOKE || id == target || target > MAXPLAYERS) return
486 :    
487 : ian 10 new dmg = get_pcvar_num( p_choke_dmg )
488 : ian 1 new Float:vec[3]
489 :     get_target_origin_f( target )
490 :    
491 :     message_begin( MSG_ONE, SVC_SCREENSHAKE, _, target )
492 :     write_short( 999999 ) //amount
493 :     write_short( 9999 ) //duration
494 :     write_short( 999 ) //frequency
495 :     message_end( )
496 :    
497 :     message_begin( MSG_ONE, SVC_SCREENFADE, _, target )
498 :     write_short( 9999 ) //duration
499 :     write_short( 100 ) //hold
500 :     write_short( SF_FADE_MODULATE ) //flags
501 :     write_byte( get_pcvar_num( p_glow_r ) ) //r
502 :     write_byte( get_pcvar_num( p_glow_g ) ) //g
503 :     write_byte( get_pcvar_num( p_glow_b ) ) //b
504 :     write_byte( 200 ) //a
505 :     message_end( )
506 :    
507 :     message_begin( MSG_ONE, SVC_DAMAGE, _, target )
508 :     write_byte( 0 ) //damage armor
509 :     write_byte( dmg ) //damage health
510 :     write_long( DMG_CRUSH ) //damage type
511 :     write_coord( floatround( vec[0] ) ) //origin[x]
512 :     write_coord( floatround( vec[1] ) ) //origin[y]
513 :     write_coord( floatround( vec[2] ) ) //origin[z]
514 :     message_end( )
515 :    
516 :     message_begin( MSG_BROADCAST, SVC_TEMPENTITY )
517 :     write_byte( TE_BLOODSTREAM )
518 :     write_coord( floatround( vec[0] ) ) //pos.x
519 :     write_coord( floatround( vec[1] ) ) //pos.y
520 :     write_coord( floatround( vec[2] ) + 15 ) //pos.z
521 :     write_coord( random_num( 0, 255 ) ) //vec.x
522 :     write_coord( random_num( 0, 255 ) ) //vec.y
523 :     write_coord( random_num( 0, 255 ) ) //vec.z
524 :     write_byte( 70 ) //col index
525 :     write_byte( random_num( 50, 250 ) ) //speed
526 :     message_end( )
527 :    
528 :     new health = pev( target, pev_health ) - dmg
529 :     set_pev( target, pev_health, float( health ) )
530 :     if( health < 1 ) dllfunc( DLLFunc_ClientKill, target )
531 :    
532 :     emit_sound( target, CHAN_BODY, "player/PL_PAIN2.WAV", VOL_NORM, ATTN_NORM, 0, PITCH_NORM )
533 :    
534 :     client_data[id][FLAGS] ^= CDF_NO_CHOKE
535 : ian 10 set_task( get_pcvar_float( p_choke_time ), "clear_no_choke", TSK_CHKE + id )
536 : ian 1 }
537 :    
538 :     public clear_no_choke( tskid )
539 :     {
540 :     new id = tskid - TSK_CHKE
541 :     client_data[id][FLAGS] ^= CDF_NO_CHOKE
542 :     }
543 :    
544 :     //Grabs the client and teleports them to the admin
545 :     public force_grab(id, level, cid)
546 :     {
547 :     if( !cmd_access( id, level, cid, 1 ) || !get_pcvar_num( p_enabled ) ) return PLUGIN_HANDLED
548 :    
549 :     new arg[33]
550 :     read_argv( 1, arg, 32 )
551 :    
552 :     new targetid = cmd_target( id, arg, 1 )
553 :    
554 :     if( is_grabbed( targetid, id ) ) return PLUGIN_HANDLED
555 :     if( !is_user_alive( targetid ) )
556 :     {
557 :     client_print( id, print_console, "[AMXX] %L", id, "COULDNT" )
558 :     return PLUGIN_HANDLED
559 :     }
560 :    
561 :     //Safe to tp target to aim spot?
562 : ian 11 new Float:tmpvec[3], Float:orig[3], Float:torig[3], Float:trace_ret[3]
563 : ian 1 new bool:safe = false, i
564 :    
565 : ian 11 get_view_pos( id, orig )
566 :     tmpvec = vel_by_aim( id, get_pcvar_num( p_min_dist ) )
567 : ian 1
568 :     for( new j = 1; j < 11 && !safe; j++ )
569 :     {
570 : ian 11 for( i = 0; i < 3; i++ ) torig[i] = orig[i] + tmpvec[i] * j
571 :     traceline( tmpvec, torig, id, trace_ret )
572 : ian 5
573 : ian 1 if( get_distance_f( trace_ret, torig ) ) break
574 : ian 8
575 :     engfunc( EngFunc_TraceHull, torig, torig, 0, HULL_HUMAN, 0, 0 )
576 :     if ( !get_tr2( 0, TR_StartSolid ) && !get_tr2( 0, TR_AllSolid ) && get_tr2( 0, TR_InOpen ) )
577 :     safe = true
578 : ian 1 }
579 :    
580 :     //Still not safe? Then find another safe spot somewhere around the grabber
581 : ian 11 pev( id, pev_origin, orig )
582 : ian 1 new try[3]
583 :     orig[2] += 2
584 :     while( try[2] < 3 && !safe )
585 :     {
586 :     for( i = 0; i < 3; i++ )
587 :     switch( try[i] )
588 :     {
589 :     case 0 : torig[i] = orig[i] + ( i == 2 ? 80 : 40 )
590 :     case 1 : torig[i] = orig[i]
591 :     case 2 : torig[i] = orig[i] - ( i == 2 ? 80 : 40 )
592 :     }
593 :    
594 : ian 11 traceline( tmpvec, torig, id, trace_ret )
595 : ian 1
596 : ian 8 engfunc( EngFunc_TraceHull, torig, torig, 0, HULL_HUMAN, 0, 0 )
597 :     if ( !get_tr2( 0, TR_StartSolid ) && !get_tr2( 0, TR_AllSolid ) && get_tr2( 0, TR_InOpen )
598 :     && !get_distance_f( trace_ret, torig ) ) safe = true
599 : ian 5
600 : ian 1 try[0]++
601 :     if( try[0] == 3 )
602 :     {
603 :     try[0] = 0
604 :     try[1]++
605 :     if( try[1] == 3 )
606 :     {
607 :     try[1] = 0
608 :     try[2]++
609 :     }
610 :     }
611 :     }
612 :    
613 :     if( safe )
614 :     {
615 : ian 5 set_pev( targetid, pev_origin, torig )
616 : ian 1 set_grabbed( id, targetid )
617 :     screenfade_in( id )
618 :     }
619 :     else client_print( id, print_chat, "[AMXX] %L", id, "COULDNT" )
620 :    
621 :     return PLUGIN_HANDLED
622 :     }
623 :    
624 :     public is_grabbed( target, grabber )
625 :     {
626 :     for( new i = 1; i <= MAXPLAYERS; i++ )
627 :     if( client_data[i][GRABBED] == target )
628 :     {
629 :     client_print( grabber, print_chat, "[AMXX] %L", grabber, "ALREADY" )
630 :     unset_grabbed( grabber )
631 :     return true
632 :     }
633 :     return false
634 :     }
635 :    
636 :     public DeathMsg( )
637 :     kill_grab( read_data( 2 ) )
638 :    
639 :     public client_disconnect( id )
640 :     {
641 :     kill_grab( id )
642 :     return PLUGIN_CONTINUE
643 :     }
644 :    
645 :     public kill_grab( id )
646 :     {
647 :     //If given client has grabbed, or has a grabber, unset it
648 :     if( client_data[id][GRABBED] )
649 :     unset_grabbed( id )
650 :     else if( client_data[id][GRABBER] )
651 :     unset_grabbed( client_data[id][GRABBER] )
652 :     }
653 : ian 11
654 :     stock traceline( const Float:vStart[3], const Float:vEnd[3], const pIgnore, Float:vHitPos[3] )
655 :     {
656 :     engfunc( EngFunc_TraceLine, vStart, vEnd, 0, pIgnore, 0 )
657 :     get_tr2( 0, TR_vecEndPos, vHitPos )
658 :     return get_tr2( 0, TR_pHit )
659 :     }
660 :    
661 :     stock get_view_pos( const id, Float:vViewPos[3] )
662 :     {
663 :     new Float:ofs[3]
664 :     pev( id, pev_origin, vViewPos )
665 :     pev( id, pev_view_ofs, ofs )
666 :     for( new i = 0; i < 3; i++ ) vViewPos[i] += ofs[i]
667 :     }
668 :    
669 :     stock Float:vel_by_aim( id, speed = 1 )
670 :     {
671 :     new Float:v1[3], Float:vBlah[3]
672 :     pev( id, pev_v_angle, v1 )
673 :     engfunc( EngFunc_AngleVectors, v1, v1, vBlah, vBlah )
674 :     for( new i = 0; i < 3; i++ ) v1[i] *= speed
675 :     return v1
676 :     }

Contact
ViewVC Help
Powered by ViewVC 1.0.4