]> icculus.org git repositories - divverent/nexuiz.git/blob - TeamNexuiz/game/gamec/soldier.c
- Added new backpack/tfitem property -- item_backpack gives metal ammo when var...
[divverent/nexuiz.git] / TeamNexuiz / game / gamec / soldier.c
1 void W_RicochetRocket_Explode ();\r
2 \r
3 void W_RicochetRocket_Damage (entity inflictor, entity attacker, float damage, float deathtype, vector hitloc, vector force)\r
4 {\r
5         self.health = self.health - damage;\r
6         if (self.health <= 0)\r
7         {\r
8                 other = self;\r
9                 W_RicochetRocket_Explode();\r
10         }\r
11 }\r
12 \r
13 entity W_Launch_RicochetRocket (vector org, vector vel, float rocket_grav, float num, float totalbounces)\r
14 {\r
15         local entity gren;\r
16 \r
17         gren = spawn ();\r
18         gren.classname = "rocket";\r
19         gren.solid = SOLID_BBOX;\r
20         gren.movetype = MOVETYPE_BOUNCEMISSILE;\r
21         gren.gravity = rocket_grav;//0.01;\r
22         setmodel(gren, "models/rocket.md3");\r
23         if(self.classname == "player")\r
24         {\r
25                 gren.owner = self;\r
26                 setsize(gren, '-6 -6 -3', '6 6 3');\r
27         }\r
28         else\r
29         {\r
30                 gren.owner = self.owner;\r
31                 setsize(gren, '0 0 0', '0 0 0');\r
32         }\r
33         setorigin(gren, org);\r
34 \r
35         gren.cnt = num;                         // what # this one is\r
36         gren.count = totalbounces;      // how many missiles this missile splits into\r
37 \r
38         gren.nextthink = time + 10;\r
39         gren.think = W_RicochetRocket_Explode;\r
40         gren.touch = W_RicochetRocket_Explode;\r
41         gren.velocity = vel;\r
42         gren.angles = vectoangles (gren.velocity);\r
43 \r
44         gren.colormod = 2 * '1 1 0';\r
45 \r
46         return gren;\r
47 }\r
48 \r
49 // bounce off the wall, then become volatile\r
50 void W_RicochetRocket_NullTouch ()\r
51 {\r
52         self.delay = self.delay - 1;\r
53         if(self.delay <= 0)\r
54                 self.touch = SUB_Null;\r
55 \r
56         //self.touch = W_RicochetRocket_Explode;\r
57         //self.think = self.touch;\r
58         //self.nextthink = time + 10;\r
59         //self.angles = vectoangles(self.velocity);\r
60 }\r
61 \r
62 void W_RicochetRocket_Update ()\r
63 {\r
64         self.angles = vectoangles(self.velocity);\r
65         if(self.wait < time && self.delay <= 0)\r
66         {\r
67                 self.touch = W_RicochetRocket_Explode;\r
68                 self.think = W_RicochetRocket_Explode;\r
69                 self.nextthink = time + 10;\r
70         }\r
71         else\r
72         {\r
73                 self.think = W_RicochetRocket_Update;\r
74                 self.nextthink = time + 0.1;\r
75         }\r
76 }\r
77 \r
78 void W_RicochetRocket_Explode ()\r
79 {\r
80         vector  org2, vel, dir;\r
81         float num, spread, bouncecount;\r
82         string rocketid;\r
83         entity e;\r
84 \r
85         if(other != self && other.classname == self.classname)\r
86         {\r
87                 self.angles = vectoangles(self.velocity);\r
88                 return; // don't touch other ricochet rockets\r
89         }\r
90 \r
91         if(self.cnt <= 1)\r
92         {\r
93                 rocketid = "";\r
94         }\r
95         else\r
96                 rocketid = ftos(self.cnt);\r
97 \r
98         spread = cvar(strcat("g_balance_ricochet_spread",rocketid));\r
99 \r
100         org2 = findbetterlocation (self.origin);\r
101         te_explosion (org2);\r
102         effect (org2, "models/sprites/rocketexplosion.spr32", 0, 20, 40);\r
103         sound (self, CHAN_BODY, "weapons/rocket_impact.wav", 1, ATTN_NORM);\r
104 \r
105         self.event_damage = SUB_Null;\r
106         RadiusDamage (self, self.owner, cvar(strcat("g_balance_ricochet_damage",rocketid)), cvar(strcat("g_balance_ricochet_edgedamage",rocketid)), cvar(strcat("g_balance_ricochet_radius",rocketid)), world, cvar(strcat("g_balance_ricochet_force",rocketid)), WEP_SOLDIER_SPECIAL);\r
107 \r
108         bouncecount = cvar("g_balance_ricochet_bouncecount");\r
109 \r
110         if(self.cnt >= bouncecount)\r
111         {\r
112                 // don't spawn more rockets\r
113                 remove(self);\r
114                 return;\r
115         }\r
116 \r
117         self.solid = SOLID_NOT;\r
118 \r
119         self.cnt = self.cnt + 1;\r
120 \r
121         if(self.cnt <= 1)\r
122         {\r
123                 rocketid = "";\r
124         }\r
125         else\r
126                 rocketid = ftos(self.cnt);\r
127 \r
128         //bprint("Rocket", ftos(self.cnt-1));\r
129         //bprint(" splits ", ftos(self.count), "times\n");\r
130 \r
131         num = self.count;\r
132         dir = normalize(self.velocity);\r
133         while(num)\r
134         {\r
135                 vel_x = dir_x + crandom()*spread;\r
136                 vel_y = dir_y + crandom()*spread;\r
137                 vel_z = dir_z + crandom()*spread;\r
138                 vel = normalize(vel) * cvar(strcat("g_balance_ricochet_speed",rocketid));\r
139                 e = W_Launch_RicochetRocket(org2, vel, \r
140                         cvar(strcat("g_balance_ricochet_gravity",rocketid)), \r
141                         self.cnt, cvar(strcat("g_balance_ricochet_splitcount",rocketid)) );\r
142                 //if(other != self) // touched something else, not detonated by damage\r
143                 {\r
144                         // going to hit the same thing that detonated this rocket;\r
145                         // avoid that by bouncing off before setting an explosion touch\r
146                         e.touch = W_RicochetRocket_NullTouch;\r
147                         e.delay = cvar("g_balance_ricochet_nulltouches");\r
148                         e.wait = time + cvar("g_balance_ricochet_nulltime");\r
149                         e.think = W_RicochetRocket_Update;\r
150                         e.nextthink = time + 0.1;//4;\r
151                 }\r
152                 e.scale = 0.3 + 0.4*(1 - (self.cnt / bouncecount));\r
153                 num = num - 1;\r
154         }\r
155 \r
156         remove (self);\r
157 }\r
158 \r
159 void SoldierSpecial()\r
160 {\r
161         entity e;\r
162         if(self.special_time > time)\r
163                 return;\r
164         self.special_time = time + cvar("g_balance_ricochet_firerate");\r
165 \r
166         if (self.next_nuke > time)\r
167         {\r
168                 sprint(self, "You have to wait 2 minutes before you can use the Ricochet Rocket again\n");\r
169                 return;\r
170         }\r
171         if (self.no_grenades_2 < 2)\r
172         {\r
173                 sprint(self, "You need more type 2 grenades to use the Ricochet Rocket\n");\r
174                 return;\r
175         }\r
176         self.next_nuke = time + 120;\r
177 \r
178         local vector org;\r
179 \r
180         sound (self, CHAN_WEAPON, "weapons/rocket_fire.wav", 1, ATTN_NORM);\r
181         self.punchangle_x = -4;\r
182         org = self.origin + self.view_ofs + v_forward * 15 + v_right * 5 + v_up * -12;\r
183         e = W_Launch_RicochetRocket(org, v_forward * cvar("g_balance_ricochet_speed"), cvar("g_balance_ricochet_gravity"), 1, cvar("g_balance_ricochet_splitcount"));\r
184         // first rocket takes damage, others don't\r
185         e.takedamage = DAMAGE_YES;\r
186         e.damageforcescale = 4;\r
187         e.health = 30;\r
188         e.event_damage = W_RicochetRocket_Damage;\r
189 }\r
190 \r
191 \r
192 \r
193 void SoldierGrenade(float req)\r
194 {\r
195         if(req == WR_GRENADE1)\r
196         {\r
197                 if(W_ThrowGrenade(W_MirvGrenade))\r
198                         self.grenade_time = time + cvar("g_balance_grenade_mirv_refire");\r
199         }\r
200         else if(req == WR_GRENADE2)\r
201         {\r
202                 if(W_ThrowGrenade(W_FragGrenade))\r
203                         self.grenade_time = time + cvar("g_balance_grenade_frag_refire");\r
204         }\r
205 }\r
206 \r
207 void SoldierPreThink()\r
208 {\r
209 }\r
210 \r
211 void SoldierPostThink()\r
212 {\r
213 }\r
214 \r
215 void BecomeSoldier(float portion)\r
216 {\r
217         self.max_health = cvar("g_balance_class_soldier_health") * portion;\r
218 \r
219         self.max_armor = cvar("g_balance_class_soldier_armor") * portion;\r
220 \r
221         self.mass = cvar("g_balance_class_soldier_mass");\r
222 \r
223         SetPlayerSpeed(self);\r
224 \r
225         self.items = IT_WEP1 | IT_WEP2 | IT_WEP3 | IT_WEP4;\r
226         self.switchweapon = WEP4;               // used to be WEP3\r
227         self.ammo_shells = floor(20 * portion);\r
228         self.ammo_nails = floor(150 * portion);\r
229         self.ammo_rockets = floor(12 * portion);\r
230         self.ammo_cells = floor(0 * portion);\r
231         self.playerclass = TF_CLASS_SOLDIER;            // TF P.C.\r
232         SetMaxAmmoFor (CLASS_SOLDIER);\r
233 }\r