]> icculus.org git repositories - divverent/nexuiz.git/blob - data/qcsrc/server/assault.qc
new: func_assault_destructible
[divverent/nexuiz.git] / data / qcsrc / server / assault.qc
1
2 // attacker spawn point
3 void info_player_attacker() {
4         self.team = COLOR_TEAM1; // red, gets swapped every round
5         info_player_deathmatch();
6 }
7
8 // defender spawn point
9 void info_player_defender() {
10         self.team = COLOR_TEAM2; // blue, gets swapped every round
11         info_player_deathmatch();
12 }
13
14 // reset this objective. Used when spawning an objective
15 // and when a new round starts
16 void assault_objective_reset() {
17         if(self.spawnflags) { // first objective
18                 self.health = 100;
19                 self.nextthink = time + 0.1;
20         } else {
21                 self.health = ASSAULT_VALUE_INACTIVE;
22         }
23 }
24
25 void assault_objective_use() {
26         // activate objective
27         self.health = 100; 
28         self.nextthink = time + 0.1;
29 }
30
31 void assault_objective_think() {
32         local entity oldself;   
33         if(self.health < 0) {
34                 self.effects = 0;
35                 local entity ent;
36                 ent = find(world, targetname, self.target);
37                 while(ent) {
38                         oldself = self;
39                         self = ent;
40                         self.use();
41                         self = oldself;
42                         ent = find(ent, targetname, self.target);
43                         
44                 }
45         } else {
46                 self.effects = EF_STARDUST;
47                 self.nextthink = time + 0.1;
48         }
49         
50 }
51
52 void target_objective() {
53         self.classname = "target_objective";
54         self.think = assault_objective_think;
55         self.use = assault_objective_use;
56         assault_objective_reset();
57 }
58
59 // decrease the health of targeted objectives
60 void assault_objective_decrease() {
61
62         local entity ent;
63         ent = find(world, targetname, self.target);
64         while(ent) {
65                 if(ent.health > 0 && ent.health < ASSAULT_VALUE_INACTIVE)
66                         ent.health = ent.health - self.dmg;
67                 ent = find(ent, targetname, self.target);
68         }
69
70         self.cnt = 1;
71 }
72
73 // this entity should target an objective and be targeted by triggers
74 void target_objective_decrease() {
75
76         self.classname = "target_objective_decrease";
77
78         if(!self.dmg) {
79                 self.dmg = 101;
80         }
81         self.use = assault_objective_decrease;
82 }
83
84
85 void assault_destructible_reset() {
86         self.health = self.max_health;
87         self.model = self.mdl;
88         self.solid = SOLID_BSP;
89         self.cnt = 0; // not active
90         if(self.spawnflags)
91                 self.use();
92 }
93
94 void assault_destructible_use() {
95         self.cnt = 1; // mark active
96         self.takedamage = DAMAGE_YES;
97         self.nextthink = time + 0.1;
98 }
99
100 void assault_destructible_damage(entity inflictor, entity attacker, float damage, float deathtype, vector hitloc, vector force) {
101         // TODO: check for teams        
102
103         if(self.cnt > 0)        
104                 self.health = self.health - damage;
105
106 }
107
108
109 void assault_destructible_think() {
110         local entity oldself;
111
112         if(self.cnt > 0 && self.health < 0) {
113                 self.model = "";
114                 self.takedamage = DAMAGE_NO;
115                 self.solid = SOLID_NOT;
116                 local entity ent;
117                 ent = find(world, targetname, self.target);
118                 while(ent) {
119                         oldself = self;
120                         self = ent;
121                         self.use();
122                         self = oldself;
123                         ent = find(ent, targetname, self.target);
124                 }
125         } else {
126                 self.nextthink = time + 0.1;
127         }
128 }
129
130 // destructible walls that can be used to trigger target_objective_decrease
131 void func_assault_destructible() {
132         if(!self.health)
133                 self.health = 100;
134
135         self.max_health = self.health;
136         
137         self.cnt = 0; // not yet activated
138
139         self.classname = "func_assault_destructible";
140         self.mdl = self.model;
141         setmodel(self, self.mdl);
142
143         self.solid = SOLID_BSP;
144         self.think = assault_destructible_think;
145         self.use = assault_destructible_use;
146         self.event_damage = assault_destructible_damage;
147
148         if(self.spawnflags) // active from start
149                 self.use();
150 }
151
152
153 // trigger new round
154 // reset objectives, toggle spawnpoints, reset triggers, ...
155 void assault_new_round() {
156         
157         // this assumes self.classname == "func_assault_roundend"!
158         self.cnt = self.cnt + 1;
159
160         // swap spawn point teams
161         local entity ent;
162         local entity oldself;
163
164         ent = find(world, classname, "info_player_deathmatch");
165         while (ent)
166         {
167                 oldself = self;
168                 self = ent;
169                 if(self.team == COLOR_TEAM1) {
170                         self.team = COLOR_TEAM2;
171                 } else {
172                         self.team = COLOR_TEAM1;
173                 }
174                 self = oldself;
175
176                 ent = find(ent, classname, "info_player_deathmatch");
177         } 
178
179         // reset all objectives
180         ent = find(world, classname, "target_objective");
181         while (ent)
182         {
183                 oldself = self;
184                 self = ent;
185                 assault_objective_reset();
186                 self = oldself;
187
188                 ent = find(ent, classname, "target_objective");
189         } 
190
191         // reset all func_assault_destructible
192         ent = find(world, classname, "func_assault_destructible");
193         while (ent)
194         {
195                 oldself = self;
196                 self = ent;
197                 assault_destructible_reset();
198                 self = oldself;
199                 ent = find(ent, classname, "func_assault_destructible");
200         }
201
202         // actually restart round... how to do that?
203 }
204
205 void target_assault_roundend() {
206         self.cnt = 0; // round counter
207         self.classname = "target_assault_roundend";
208         self.use = assault_new_round;
209 }
210
211