]> git.jsancho.org Git - lugaru.git/blob - Source/Weapons.cpp
some small cleanups
[lugaru.git] / Source / Weapons.cpp
1 /*
2 Copyright (C) 2003, 2010 - Wolfire Games
3
4 This file is part of Lugaru.
5
6 Lugaru is free software; you can redistribute it and/or
7 modify it under the terms of the GNU General Public License
8 as published by the Free Software Foundation; either version 2
9 of the License, or (at your option) any later version.
10
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
14
15 See the GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
20 */
21
22 /**> HEADER FILES <**/
23 #include "Weapons.h"
24 #include "openal_wrapper.h"
25 #include "Animation.h"
26 #include "Sounds.h"
27 #include "Game.h"
28 #include "Awards.h"
29
30 extern float multiplier;
31 extern Terrain terrain;
32 extern float gravity;
33 extern int environment;
34 extern int detail;
35 extern FRUSTUM frustum;
36 extern XYZ viewer;
37 extern float realmultiplier;
38 extern int slomo;
39 extern float slomodelay;
40 extern bool cellophane;
41 extern float texdetail;
42 extern GLubyte bloodText[512*512*3];
43 extern int bloodtoggle;
44 extern Objects objects;
45 extern bool osx;
46 extern bool autoslomo;
47 extern float camerashake;
48 extern float woozy;
49 extern float viewdistance;
50 extern float blackout;
51 extern int difficulty;
52 extern bool freeze;
53 extern int tutoriallevel;
54 extern int numthrowkill;
55
56 Model Weapon::throwingknifemodel;
57 GLuint Weapon::knifetextureptr = 0;
58 GLuint Weapon::lightbloodknifetextureptr = 0;
59 GLuint Weapon::bloodknifetextureptr = 0;
60
61 Model Weapon::swordmodel;
62 GLuint Weapon::swordtextureptr = 0;
63 GLuint Weapon::lightbloodswordtextureptr = 0;
64 GLuint Weapon::bloodswordtextureptr = 0;
65
66 Model Weapon::staffmodel;
67 GLuint Weapon::stafftextureptr = 0;
68
69 Weapon::Weapon(int t, int o) : owner(o) {
70         setType(t);
71         bloody=0;
72         blooddrip=0;
73         blooddripdelay=0;
74         onfire=0;
75         flamedelay=0;
76         damage=0;
77         position=-1000;
78         tippoint=-1000;
79 }
80
81 void Weapon::setType(int t) {
82         type = t;
83         if(type==sword){
84                 mass=1.5;
85                 tipmass=1;
86                 length=.8;
87         }
88         if(type==staff){
89                 mass=2;
90                 tipmass=1;
91                 length=1.5;
92         }
93         if(type==knife){
94                 mass=1;
95                 tipmass=1.2;
96                 length=.25;
97         }
98 }
99
100 void Weapon::DoStuff() {
101         static int i,whichpatchx,whichpatchz,j,k,whichhit,m;
102         static XYZ start,end,colpoint,normalrot,footvel,footpoint;
103         static XYZ terrainnormal;
104         static XYZ vel;
105         static XYZ midp;
106         static XYZ newpoint1,newpoint2;
107         static float friction=3.5;
108         static float elasticity=.4;
109         static XYZ bounceness;
110         static float frictionness;
111         static float closestdistance;
112         static float distance;
113         static XYZ point[3];
114         static XYZ closestpoint;
115         static XYZ closestswordpoint;
116         static XYZ extramove;
117         static float tempmult;
118         
119         if(owner!=-1){
120                 oldowner=owner;
121         }
122         if(damage>=2&&type==staff&&owner!=-1){
123                 emit_sound_at(staffbreaksound, tippoint);
124                 XYZ tempvel;
125                 XYZ speed;
126                 //speed=(tippoint-oldtippoint)/multiplier/6;
127                 speed=0;
128                 for(j=0;j<40;j++){
129                         tempvel.x=float(abs(Random()%100)-50)/20;
130                         tempvel.y=float(abs(Random()%100)-50)/20;
131                         tempvel.z=float(abs(Random()%100)-50)/20;
132                         tempvel+=speed;
133                         Sprite::MakeSprite(splintersprite, position+(tippoint-position)*((float)j-8)/32,tempvel*.5, 115/255,73/255,12/255, .1, 1);
134                 }
135                 int tempowner;
136                 tempowner=owner;
137                 owner=-1;
138                 hitsomething=0;
139                 missed=1;
140                 freetime=0;
141                 firstfree=1;
142                 position=0;
143                 physics=0;
144                 if(tempowner!=-1){
145                         player[tempowner].num_weapons--;
146                         if(player[tempowner].num_weapons){
147                                 player[tempowner].weaponids[0]=player[tempowner].weaponids[player[tempowner].num_weapons];
148                                 if(player[tempowner].weaponstuck==player[tempowner].num_weapons)player[tempowner].weaponstuck=0;
149                         }
150                         player[tempowner].weaponactive=-1;
151                 }
152         }
153         oldposition=position;
154         oldtippoint=tippoint;
155         if(owner==-1&&(velocity.x||velocity.y||velocity.z)&&!physics){
156                 position+=velocity*multiplier;
157                 tippoint+=velocity*multiplier;
158                 whichpatchx=position.x/(terrain.size/subdivision*terrain.scale);
159                 whichpatchz=position.z/(terrain.size/subdivision*terrain.scale);
160                 if(whichpatchx>0&&whichpatchz>0&&whichpatchx<subdivision&&whichpatchz<subdivision)
161                         if(terrain.patchobjectnum[whichpatchx][whichpatchz]){
162                                 for(j=0;j<terrain.patchobjectnum[whichpatchx][whichpatchz];j++){
163                                         k=terrain.patchobjects[whichpatchx][whichpatchz][j];
164                                         start=oldtippoint;
165                                         end=tippoint;
166                                         whichhit=objects.model[k].LineCheck(&start,&end,&colpoint,&objects.position[k],&objects.rotation[k]);
167                                         if(whichhit!=-1){
168                                                 if(objects.type[k]==treetrunktype){
169                                                         objects.model[k].MakeDecal(breakdecal,DoRotation(colpoint-objects.position[k],0,-objects.rotation[k],0),.1,1,Random()%360);
170                                                         normalrot=DoRotation(objects.model[k].facenormals[whichhit],0,objects.rotation[k],0);
171                                                         velocity=0;
172                                                         if(type==knife)position=colpoint-normalrot*.1;
173                                                         if(type==sword)position=colpoint-normalrot*.2;
174                                                         if(type==staff)position=colpoint-normalrot*.2;
175                                                         XYZ temppoint1,temppoint2,tempforward;
176                                                         float distance;
177
178                                                         temppoint1=0;
179                                                         temppoint2=normalrot;
180                                                         distance=findDistance(&temppoint1,&temppoint2);
181                                                         rotation2=asin((temppoint1.y-temppoint2.y)/distance);
182                                                         rotation2*=360/6.28;
183                                                         temppoint1.y=0;
184                                                         temppoint2.y=0;
185                                                         rotation1=acos((temppoint1.z-temppoint2.z)/findDistance(&temppoint1,&temppoint2));
186                                                         rotation1*=360/6.28;
187                                                         if(temppoint1.x>temppoint2.x)rotation1=360-rotation1;
188
189                                                         rotation3=0;
190                                                         smallrotation=90;
191                                                         smallrotation2=0;
192                                                         bigtilt=0;
193                                                         bigtilt2=0;
194                                                         bigrotation=0;
195
196                                                         emit_sound_at(knifesheathesound, position, 128.);
197
198                                                         bloody=0;
199
200                                                         Sprite::MakeSprite(cloudimpactsprite, position,velocity, 1,1,1, .8, .3);
201                                                 }
202                                                 else {
203                                                         physics=1;
204                                                         firstfree=1;
205                                                         position-=velocity*multiplier;
206                                                         tippoint-=velocity*multiplier;
207                                                         tipvelocity=velocity;
208                                                 }
209                                         }
210                                 }
211                         }
212                         if(velocity.x||velocity.y||velocity.z)
213                                 for(j=0;j<numplayers;j++){
214                                         footvel=0;
215                                         footpoint=DoRotation((player[j].skeleton.joints[player[j].skeleton.jointlabels[abdomen]].position+player[j].skeleton.joints[player[j].skeleton.jointlabels[neck]].position)/2,0,player[j].rotation,0)*player[j].scale+player[j].coords;
216                                         if(owner==-1&&findDistancefastflat(&position,&player[j].coords)<1.5&&findDistancefast(&position,&player[j].coords)<4&&player[j].weaponstuck==-1&&!player[j].skeleton.free&&j!=oldowner){
217                                                 if((player[j].aitype!=attacktypecutoff||abs(Random()%6)==0||(player[j].targetanimation!=backhandspringanim&&player[j].targetanimation!=rollanim&&player[j].targetanimation!=flipanim&&Random()%2==0))&&!missed){
218                                                         if((player[j].creature==wolftype&&Random()%3!=0&&player[j].weaponactive==-1&&(player[j].isIdle()||player[j].isRun()||player[j].targetanimation==walkanim))||(player[j].creature==rabbittype&&Random()%2==0&&player[j].aitype==attacktypecutoff&&player[j].weaponactive==-1)){
219                                                                 emit_sound_at(knifedrawsound, player[j].coords, 128.);
220
221                                                                 player[j].weaponactive=0;
222                                                                 player[j].targetanimation=removeknifeanim;
223                                                                 player[j].targetframe=1;
224                                                                 player[j].target=1;
225                                                                 owner=player[j].id;
226                                                                 if(player[j].num_weapons>0){
227                                                                         player[j].weaponids[player[j].num_weapons]=player[j].weaponids[0];
228                                                                 }
229                                                                 player[j].num_weapons++;
230                                                                 player[j].weaponids[0]=i;
231
232                                                                 player[j].aitype=attacktypecutoff;
233                                                         }
234                                                         else {
235                                                                 if(j!=0)numthrowkill++;
236                                                                 player[j].num_weapons++;
237                                                                 player[j].weaponstuck=player[j].num_weapons-1;
238                                                                 if(normaldotproduct(player[j].facing,velocity)>0)player[j].weaponstuckwhere=1;
239                                                                 else player[j].weaponstuckwhere=0;
240
241                                                                 player[j].weaponids[player[j].num_weapons-1]=i;
242
243                                                                 player[j].RagDoll(0);
244                                                                 player[j].skeleton.joints[player[j].skeleton.jointlabels[abdomen]].velocity+=velocity*2;
245                                                                 player[j].skeleton.joints[player[j].skeleton.jointlabels[neck]].velocity+=velocity*2;
246                                                                 player[j].skeleton.joints[player[j].skeleton.jointlabels[rightshoulder]].velocity+=velocity*2;
247                                                                 player[j].skeleton.joints[player[j].skeleton.jointlabels[leftshoulder]].velocity+=velocity*2;
248                                                                 //player[j].Puff(abdomen);
249                                                                 if(bloodtoggle&&tutoriallevel!=1)Sprite::MakeSprite(cloudimpactsprite, footpoint,footvel, 1,0,0, .8, .3);
250                                                                 if(tutoriallevel==1)Sprite::MakeSprite(cloudimpactsprite, footpoint,footvel, 1,1,1, .8, .3);
251                                                                 footvel=tippoint-position;
252                                                                 Normalise(&footvel);
253                                                                 if(bloodtoggle&&tutoriallevel!=1)Sprite::MakeSprite(bloodflamesprite, footpoint,footvel*-1, 1,0,0, .6, 1);
254
255                                                                 if(tutoriallevel!=1){
256                                                                         if(player[j].weaponstuckwhere==0)player[j].DoBloodBig(2,205);
257                                                                         if(player[j].weaponstuckwhere==1)player[j].DoBloodBig(2,200);
258                                                                         player[j].damage+=200/player[j].armorhigh;
259                                                                         player[j].deathbleeding=1;
260                                                                         player[j].bloodloss+=(200+abs((float)(Random()%40))-20)/player[j].armorhigh;
261                                                                         owner=j;
262                                                                         bloody=2;
263                                                                         blooddrip=5;
264                                                                 }
265
266                                                                 emit_sound_at(fleshstabsound, position, 128.);
267
268                                                                 if(animation[player[0].targetanimation].height==highheight)
269                                                                   award_bonus(0, ninja);
270                                                                 else
271                                                                   award_bonus(0, Bullseyebonus);
272                                                         }
273                                                 }
274                                                 else missed=1;
275                                         }
276                                 }
277                                 if(position.y<terrain.getHeight(position.x,position.z)){
278                                         if(terrain.getOpacity(position.x,position.z)<.2){
279                                                 velocity=0;
280                                                 if(terrain.lineTerrain(oldposition,position,&colpoint)!=-1){
281                                                         position=colpoint*terrain.scale;
282                                                 }
283                                                 else position.y=terrain.getHeight(position.x,position.z);
284
285                                                 terrain.MakeDecal(shadowdecalpermanent,position,.06,.5,0);
286                                                 normalrot=terrain.getNormal(position.x,position.z)*-1;
287                                                 velocity=0;
288                                                 //position-=normalrot*.1;
289                                                 glMatrixMode(GL_MODELVIEW);                                                     // Select The Modelview Matrix
290                                                 glPushMatrix();
291                                                         GLfloat M[16];
292                                                         glLoadIdentity();
293                                                         glRotatef(bigrotation,0,1,0);
294                                                         glRotatef(bigtilt2,1,0,0);
295                                                         glRotatef(bigtilt,0,0,1);
296                                                         glRotatef(-rotation1+90,0,1,0);
297                                                         glRotatef(-rotation2+90,0,0,1);
298                                                         glRotatef(-rotation3,0,1,0);
299                                                         glRotatef(smallrotation,1,0,0);
300                                                         glRotatef(smallrotation2,0,1,0);
301                                                         glTranslatef(0,0,1);
302                                                         glGetFloatv(GL_MODELVIEW_MATRIX,M);
303                                                         tippoint.x=M[12];
304                                                         tippoint.y=M[13];
305                                                         tippoint.z=M[14];
306                                                 glPopMatrix();
307                                                 position-=tippoint*.15;
308                                                 XYZ temppoint1,temppoint2,tempforward;
309
310                                                 rotation3=0;
311                                                 smallrotation=90;
312                                                 smallrotation2=0;
313                                                 bigtilt=0;
314                                                 bigtilt2=0;
315                                                 bigrotation=0;
316
317                                                 emit_sound_at(knifesheathesound, position, 128.);
318
319                                                 XYZ terrainlight;
320                                                 terrainlight=terrain.getLighting(position.x,position.z);
321                                                 if(environment==snowyenvironment){
322                                                         if(findDistancefast(&position,&viewer)<viewdistance*viewdistance/4)Sprite::MakeSprite(cloudsprite, position,velocity, terrainlight.x,terrainlight.y,terrainlight.z, .5, .7);
323                                                 }
324                                                 else if(environment==grassyenvironment){
325                                                         if(findDistancefast(&position,&viewer)<viewdistance*viewdistance/4)Sprite::MakeSprite(cloudsprite, position,velocity, terrainlight.x*90/255,terrainlight.y*70/255,terrainlight.z*8/255, .5, .5);
326                                                 }
327                                                 else if(environment==desertenvironment){
328                                                         if(findDistancefast(&position,&viewer)<viewdistance*viewdistance/4)Sprite::MakeSprite(cloudsprite, position,velocity, terrainlight.x*190/255,terrainlight.y*170/255,terrainlight.z*108/255, .5, .7);
329                                                 }
330
331                                                 bloody=0;
332                                         }
333                                         else {
334                                                 physics=1;
335                                                 firstfree=1;
336                                                 position-=velocity*multiplier;
337                                                 tippoint-=velocity*multiplier;
338                                                 tipvelocity=velocity;
339                                         }
340                                 }
341                                 if(velocity.x!=0||velocity.z!=0||velocity.y!=0){
342                                         velocity.y+=gravity*multiplier;
343
344                                         XYZ temppoint1,temppoint2,tempforward;
345                                         float distance;
346
347                                         temppoint1=0;
348                                         temppoint2=velocity;
349                                         distance=findDistance(&temppoint1,&temppoint2);
350                                         rotation2=asin((temppoint1.y-temppoint2.y)/distance);
351                                         rotation2*=360/6.28;
352                                         temppoint1.y=0;
353                                         temppoint2.y=0;
354                                         rotation1=acos((temppoint1.z-temppoint2.z)/findDistance(&temppoint1,&temppoint2));
355                                         rotation1*=360/6.28;
356                                         rotation3=0;
357                                         smallrotation=90;
358                                         smallrotation2=0;
359                                         bigtilt=0;
360                                         bigtilt2=0;
361                                         bigrotation=0;
362                                         if(temppoint1.x>temppoint2.x)rotation1=360-rotation1;
363                                 }
364         }
365         //Sword physics
366         XYZ mid;
367         XYZ oldmid;
368         XYZ oldmid2;
369
370         tempmult=multiplier;
371         multiplier/=10;
372         for(int l=0;l<10;l++){
373                 if(owner==-1&&(velocity.x||velocity.y||velocity.z)&&physics){
374                         //move
375                         position+=velocity*multiplier;
376                         tippoint+=tipvelocity*multiplier;
377
378                         //Length constrain
379                         midp=(position*mass+tippoint*tipmass)/(mass+tipmass);
380                         vel=tippoint-midp;
381                         Normalise(&vel);
382                         newpoint1=midp-vel*length*(tipmass/(mass+tipmass));
383                         newpoint2=midp+vel*length*(mass/(mass+tipmass));
384                         if(!freeze){
385                                 if(freetime>.04)velocity=velocity+(newpoint1-position)/multiplier;
386                                 if(freetime>.04)tipvelocity=tipvelocity+(newpoint2-tippoint)/multiplier;
387                         }
388                         position=newpoint1;
389                         tippoint=newpoint2;
390
391
392                         //Object collisions
393                         whichpatchx=(position.x)/(terrain.size/subdivision*terrain.scale);
394                         whichpatchz=(position.z)/(terrain.size/subdivision*terrain.scale);
395                         if(whichpatchx>0&&whichpatchz>0&&whichpatchx<subdivision&&whichpatchz<subdivision)
396                                 if(terrain.patchobjectnum[whichpatchx][whichpatchz]){
397                                         for(j=0;j<terrain.patchobjectnum[whichpatchx][whichpatchz];j++){
398                                                 k=terrain.patchobjects[whichpatchx][whichpatchz][j];
399
400                                                 if(firstfree){
401                                                         if(type!=staff){
402                                                                 start=position-(tippoint-position)/5;
403                                                                 end=tippoint+(tippoint-position)/30;
404                                                                 whichhit=objects.model[k].LineCheck(&start,&end,&colpoint,&objects.position[k],&objects.rotation[k]);
405                                                                 if(whichhit!=-1){
406                                                                         XYZ diff;
407                                                                         diff=(colpoint-tippoint);
408                                                                         Normalise(&diff);
409                                                                         hitsomething=1;
410
411                                                                         position+=(colpoint-tippoint)+diff*.05;
412                                                                         tippoint=colpoint+diff*.05;
413                                                                         oldposition=position;
414                                                                         oldtippoint=tippoint;
415                                                                 }
416                                                         }
417                                                         if(type==staff){
418                                                                 start=tippoint-(position-tippoint)/5;
419                                                                 end=position+(position-tippoint)/30;
420                                                                 whichhit=objects.model[k].LineCheck(&start,&end,&colpoint,&objects.position[k],&objects.rotation[k]);
421                                                                 if(whichhit!=-1){
422                                                                         XYZ diff;
423                                                                         diff=(colpoint-position);
424                                                                         Normalise(&diff);
425                                                                         hitsomething=1;
426
427                                                                         tippoint+=(colpoint-position)+diff*.05;
428                                                                         position=colpoint+diff*.05;
429                                                                         oldtippoint=tippoint;
430                                                                         oldposition=tippoint;
431                                                                 }
432                                                         }
433                                                 }
434
435                                                 start=oldposition;
436                                                 end=position;
437                                                 whichhit=objects.model[k].LineCheck(&start,&end,&colpoint,&objects.position[k],&objects.rotation[k]);
438                                                 if(whichhit!=-1){
439                                                         hitsomething=1;
440                                                         position=colpoint;
441                                                         terrainnormal=DoRotation(objects.model[k].facenormals[whichhit],0,objects.rotation[k],0)*-1;
442                                                         ReflectVector(&velocity,&terrainnormal);
443                                                         position+=terrainnormal*.002;
444
445                                                         bounceness=terrainnormal*findLength(&velocity)*(abs(normaldotproduct(velocity,terrainnormal)));
446                                                         if(findLengthfast(&velocity)<findLengthfast(&bounceness))bounceness=0;
447                                                         frictionness=abs(normaldotproduct(velocity,terrainnormal));
448                                                         velocity-=bounceness;
449                                                         if(1-friction*frictionness>0)velocity*=1-friction*frictionness;
450                                                         else velocity=0;
451                                                         velocity+=bounceness*elasticity;
452
453                                                         if(findLengthfast(&bounceness)>1){
454                                                                 int whichsound;
455                                                                 if(type==staff)whichsound=footstepsound3+abs(Random()%2);
456                                                                 if(type!=staff)whichsound=clank1sound+abs(Random()%4);
457                                                                 emit_sound_at(whichsound, position, 128*findLengthfast(&bounceness));
458                                                         }
459                                                 }
460                                                 start=oldtippoint;
461                                                 end=tippoint;
462                                                 whichhit=objects.model[k].LineCheck(&start,&end,&colpoint,&objects.position[k],&objects.rotation[k]);
463                                                 if(whichhit!=-1){
464                                                         hitsomething=1;
465                                                         tippoint=colpoint;
466                                                         terrainnormal=DoRotation(objects.model[k].facenormals[whichhit],0,objects.rotation[k],0)*-1;
467                                                         ReflectVector(&tipvelocity,&terrainnormal);
468                                                         tippoint+=terrainnormal*.002;
469
470                                                         bounceness=terrainnormal*findLength(&tipvelocity)*(abs(normaldotproduct(tipvelocity,terrainnormal)));
471                                                         if(findLengthfast(&tipvelocity)<findLengthfast(&bounceness))bounceness=0;
472                                                         frictionness=abs(normaldotproduct(tipvelocity,terrainnormal));
473                                                         tipvelocity-=bounceness;
474                                                         if(1-friction*frictionness>0)tipvelocity*=1-friction*frictionness;
475                                                         else tipvelocity=0;
476                                                         tipvelocity+=bounceness*elasticity;
477
478                                                         if(findLengthfast(&bounceness)>1){
479                                                                 int whichsound;
480                                                                 if(type==staff)whichsound=footstepsound3+abs(Random()%2);
481                                                                 if(type!=staff)whichsound=clank1sound+abs(Random()%4);
482                                                                 emit_sound_at(whichsound, position, 128*findLengthfast(&bounceness));
483                                                         }
484                                                 }
485
486                                                 if((objects.type[k]!=boxtype&&objects.type[k]!=platformtype&&objects.type[k]!=walltype&&objects.type[k]!=weirdtype)||objects.rotation2[k]!=0)
487                                                         for(m=0;m<2;m++){
488                                                                 mid=(position*(21+(float)m*10)+tippoint*(19-(float)m*10))/40;
489                                                                 oldmid2=mid;
490                                                                 oldmid=(oldposition*(21+(float)m*10)+oldtippoint*(19-(float)m*10))/40;
491
492                                                                 start=oldmid;
493                                                                 end=mid;
494                                                                 whichhit=objects.model[k].LineCheck(&start,&end,&colpoint,&objects.position[k],&objects.rotation[k]);
495                                                                 if(whichhit!=-1){
496                                                                         hitsomething=1;
497                                                                         mid=colpoint;
498                                                                         terrainnormal=DoRotation(objects.model[k].facenormals[whichhit],0,objects.rotation[k],0)*-1;
499                                                                         ReflectVector(&velocity,&terrainnormal);
500
501                                                                         bounceness=terrainnormal*findLength(&velocity)*(abs(normaldotproduct(velocity,terrainnormal)));
502                                                                         if(findLengthfast(&velocity)<findLengthfast(&bounceness))bounceness=0;
503                                                                         frictionness=abs(normaldotproduct(velocity,terrainnormal));
504                                                                         velocity-=bounceness;
505                                                                         if(1-friction*frictionness>0)velocity*=1-friction*frictionness;
506                                                                         else velocity=0;
507                                                                         velocity+=bounceness*elasticity;
508
509                                                                         if(findLengthfast(&bounceness)>1){
510                                                                                 int whichsound;
511                                                                                 if(type==staff)whichsound=footstepsound3+abs(Random()%2);
512                                                                                 if(type!=staff)whichsound=clank1sound+abs(Random()%4);
513                                                                                 emit_sound_at(whichsound, mid, 128*findLengthfast(&bounceness));
514                                                                         }
515                                                                         position+=(mid-oldmid2)*(20/(1+(float)m*10));
516                                                                 }
517
518                                                                 mid=(position*(19-(float)m*10)+tippoint*(21+(float)m*10))/40;
519                                                                 oldmid2=mid;
520                                                                 oldmid=(oldposition*(19-(float)m*10)+oldtippoint*(21+(float)m*10))/40;
521
522                                                                 start=oldmid;
523                                                                 end=mid;
524                                                                 whichhit=objects.model[k].LineCheck(&start,&end,&colpoint,&objects.position[k],&objects.rotation[k]);
525                                                                 if(whichhit!=-1){
526                                                                         hitsomething=1;
527                                                                         mid=colpoint;
528                                                                         terrainnormal=DoRotation(objects.model[k].facenormals[whichhit],0,objects.rotation[k],0)*-1;
529                                                                         ReflectVector(&tipvelocity,&terrainnormal);
530
531                                                                         bounceness=terrainnormal*findLength(&tipvelocity)*(abs(normaldotproduct(tipvelocity,terrainnormal)));
532                                                                         if(findLengthfast(&tipvelocity)<findLengthfast(&bounceness))bounceness=0;
533                                                                         frictionness=abs(normaldotproduct(tipvelocity,terrainnormal));
534                                                                         tipvelocity-=bounceness;
535                                                                         if(1-friction*frictionness>0)tipvelocity*=1-friction*frictionness;
536                                                                         else tipvelocity=0;
537                                                                         tipvelocity+=bounceness*elasticity;
538
539                                                                         if(findLengthfast(&bounceness)>1){
540                                                                                 int whichsound;
541                                                                                 if(type==staff)whichsound=footstepsound3+abs(Random()%2);
542                                                                                 if(type!=staff)whichsound=clank1sound+abs(Random()%4);
543                                                                                 emit_sound_at(whichsound, mid, 128*findLengthfast(&bounceness));
544                                                                         }
545                                                                         tippoint+=(mid-oldmid2)*(20/(1+(float)m*10));
546                                                                 }
547                                                         }
548                                                 else
549                                                 {
550                                                         start=position;
551                                                         end=tippoint;
552                                                         whichhit=objects.model[k].LineCheck(&start,&end,&colpoint,&objects.position[k],&objects.rotation[k]);
553                                                         if(whichhit!=-1){
554                                                                 hitsomething=1;
555                                                                 closestdistance=-1;
556                                                                 closestswordpoint=colpoint;//(position+tippoint)/2;
557                                                                 point[0]=DoRotation(objects.model[k].vertex[objects.model[k].Triangles[whichhit].vertex[0]],0,objects.rotation[k],0)+objects.position[k];
558                                                                 point[1]=DoRotation(objects.model[k].vertex[objects.model[k].Triangles[whichhit].vertex[1]],0,objects.rotation[k],0)+objects.position[k];
559                                                                 point[2]=DoRotation(objects.model[k].vertex[objects.model[k].Triangles[whichhit].vertex[2]],0,objects.rotation[k],0)+objects.position[k];
560                                                                 if(DistancePointLine(&closestswordpoint, &point[0], &point[1], &distance,&colpoint ))
561                                                                         if(distance<closestdistance||closestdistance==-1){
562                                                                                 closestpoint=colpoint;
563                                                                                 closestdistance=distance;
564                                                                         }
565                                                                         if(DistancePointLine(&closestswordpoint, &point[1], &point[2], &distance,&colpoint ))
566                                                                                 if(distance<closestdistance||closestdistance==-1){
567                                                                                         closestpoint=colpoint;
568                                                                                         closestdistance=distance;
569                                                                                 }
570                                                                                 if(DistancePointLine(&closestswordpoint, &point[2], &point[0], &distance,&colpoint ))
571                                                                                         if(distance<closestdistance||closestdistance==-1){
572                                                                                                 closestpoint=colpoint;
573                                                                                                 closestdistance=distance;
574                                                                                         }
575                                                                                         if(closestdistance!=-1&&isnormal(closestdistance)){
576                                                                                                 if(DistancePointLine(&closestpoint, &position, &tippoint, &distance,&colpoint )){
577                                                                                                         closestswordpoint=colpoint;
578                                                                                                         velocity+=(closestpoint-closestswordpoint);
579                                                                                                         tipvelocity+=(closestpoint-closestswordpoint);
580                                                                                                         position+=(closestpoint-closestswordpoint);
581                                                                                                         tippoint+=(closestpoint-closestswordpoint);
582                                                                                                 }
583                                                                                         }
584                                                         }
585                                                 }
586
587                                         }
588                                 }
589                                 //Terrain collisions
590                                 whichhit=terrain.lineTerrain(oldposition,position,&colpoint);
591                                 if(whichhit!=-1||position.y<terrain.getHeight(position.x,position.z)){
592                                         hitsomething=1;
593                                         if(whichhit!=-1)position=colpoint*terrain.scale;
594                                         else position.y=terrain.getHeight(position.x,position.z);
595
596                                         terrainnormal=terrain.getNormal(position.x,position.z);
597                                         ReflectVector(&velocity,&terrainnormal);
598                                         position+=terrainnormal*.002;
599                                         bounceness=terrainnormal*findLength(&velocity)*(abs(normaldotproduct(velocity,terrainnormal)));
600                                         if(findLengthfast(&velocity)<findLengthfast(&bounceness))bounceness=0;
601                                         frictionness=abs(normaldotproduct(velocity,terrainnormal));
602                                         velocity-=bounceness;
603                                         if(1-friction*frictionness>0)velocity*=1-friction*frictionness;
604                                         else velocity=0;
605                                         if(terrain.getOpacity(position.x,position.z)<.2)velocity+=bounceness*elasticity*.3;
606                                         else velocity+=bounceness*elasticity;
607 //if (type==knife) printf("velocity of knife %d now %f,%f,%f.\n", i, velocity.x, velocity.y, velocity.z);
608                                         if(findLengthfast(&bounceness)>1){
609                                                 int whichsound;
610                                                 if(terrain.getOpacity(position.x,position.z)>.2){
611                                                         if(type==staff)whichsound=footstepsound3+abs(Random()%2);
612                                                         if(type!=staff)whichsound=clank1sound+abs(Random()%4);
613                                                 }
614                                                 else whichsound=footstepsound+abs(Random()%2);
615                                                 emit_sound_at(whichsound, position,
616                                                                   findLengthfast(&bounceness)
617                                                                   * (terrain.getOpacity(position.x,position.z) > .2
618                                                                  ? 128.
619                                                                  : 32.));
620
621                                                 if(terrain.getOpacity(position.x,position.z)<.2){
622                                                         XYZ terrainlight;
623                                                         terrainlight=terrain.getLighting(position.x,position.z);
624                                                         if(environment==snowyenvironment){
625                                                                 if(findDistancefast(&position,&viewer)<viewdistance*viewdistance/4)Sprite::MakeSprite(cloudsprite, position,velocity, terrainlight.x,terrainlight.y,terrainlight.z, .5, .7);
626                                                         }
627                                                         else if(environment==grassyenvironment){
628                                                                 if(findDistancefast(&position,&viewer)<viewdistance*viewdistance/4)Sprite::MakeSprite(cloudsprite, position,velocity, terrainlight.x*90/255,terrainlight.y*70/255,terrainlight.z*8/255, .5, .5);
629                                                         }
630                                                         else if(environment==desertenvironment){
631                                                                 if(findDistancefast(&position,&viewer)<viewdistance*viewdistance/4)Sprite::MakeSprite(cloudsprite, position,velocity, terrainlight.x*190/255,terrainlight.y*170/255,terrainlight.z*108/255, .5, .7);
632                                                         }
633                                                 }
634                                         }
635                                 }
636                                 whichhit=terrain.lineTerrain(oldtippoint,tippoint,&colpoint);
637                                 if(whichhit!=-1||tippoint.y<terrain.getHeight(tippoint.x,tippoint.z)){
638                                         if(whichhit!=-1)tippoint=colpoint*terrain.scale;
639                                         else tippoint.y=terrain.getHeight(tippoint.x,tippoint.z);
640
641                                         terrainnormal=terrain.getNormal(tippoint.x,tippoint.z);
642                                         ReflectVector(&tipvelocity,&terrainnormal);
643                                         tippoint+=terrainnormal*.002;
644                                         bounceness=terrainnormal*findLength(&tipvelocity)*(abs(normaldotproduct(tipvelocity,terrainnormal)));
645                                         if(findLengthfast(&tipvelocity)<findLengthfast(&bounceness))bounceness=0;
646                                         frictionness=abs(normaldotproduct(tipvelocity,terrainnormal));
647                                         tipvelocity-=bounceness;
648                                         if(1-friction*frictionness>0)tipvelocity*=1-friction*frictionness;
649                                         else tipvelocity=0;
650                                         if(terrain.getOpacity(tippoint.x,tippoint.z)<.2)tipvelocity+=bounceness*elasticity*.3;
651                                         else tipvelocity+=bounceness*elasticity;
652 //if (type==knife) printf("tipvelocity of knife %d now %f,%f,%f.\n", i, tipvelocity.x, tipvelocity.y, tipvelocity.z);
653
654                                         if(findLengthfast(&bounceness)>1){
655                                                 int whichsound;
656                                                 if(terrain.getOpacity(tippoint.x,tippoint.z)>.2){
657                                                         if(type==staff)whichsound=footstepsound3+abs(Random()%2);
658                                                         if(type!=staff)whichsound=clank1sound+abs(Random()%4);
659                                                 }
660                                                 else whichsound=footstepsound+abs(Random()%2);
661                                                 emit_sound_at(whichsound, tippoint,
662                                                                   findLengthfast(&bounceness)
663                                                                   * (terrain.getOpacity(tippoint.x,tippoint.z) > .2
664                                                                  ? 128.
665                                                                  : 32.));
666
667                                                 if(terrain.getOpacity(tippoint.x,tippoint.z)<.2){
668                                                         XYZ terrainlight;
669                                                         terrainlight=terrain.getLighting(tippoint.x,tippoint.z);
670                                                         if(environment==snowyenvironment){
671                                                                 if(findDistancefast(&tippoint,&viewer)<viewdistance*viewdistance/4)Sprite::MakeSprite(cloudsprite, tippoint,tipvelocity, terrainlight.x,terrainlight.y,terrainlight.z, .5, .7);
672                                                         }
673                                                         else if(environment==grassyenvironment){
674                                                                 if(findDistancefast(&tippoint,&viewer)<viewdistance*viewdistance/4)Sprite::MakeSprite(cloudsprite, tippoint,tipvelocity, terrainlight.x*90/255,terrainlight.y*70/255,terrainlight.z*8/255, .5, .5);
675                                                         }
676                                                         else if(environment==desertenvironment){
677                                                                 if(findDistancefast(&tippoint,&viewer)<viewdistance*viewdistance/4)Sprite::MakeSprite(cloudsprite, tippoint,tipvelocity, terrainlight.x*190/255,terrainlight.y*170/255,terrainlight.z*108/255, .5, .7);
678                                                         }
679                                                 }
680                                         }
681                                 }
682
683                                 //Edges
684                                 mid=position+tippoint;
685                                 mid/=2;
686                                 mid+=(position-mid)/20;
687                                 oldmid=mid;
688                                 if(mid.y<terrain.getHeight(mid.x,mid.z)){
689                                         hitsomething=1;
690                                         mid.y=terrain.getHeight(mid.x,mid.z);
691
692                                         terrainnormal=terrain.getNormal(mid.x,mid.z);
693                                         ReflectVector(&velocity,&terrainnormal);
694                                         //mid+=terrainnormal*.002;
695                                         bounceness=terrainnormal*findLength(&velocity)*(abs(normaldotproduct(velocity,terrainnormal)));
696                                         if(findLengthfast(&velocity)<findLengthfast(&bounceness))bounceness=0;
697                                         frictionness=abs(normaldotproduct(velocity,terrainnormal));
698                                         velocity-=bounceness;
699                                         if(1-friction*frictionness>0)velocity*=1-friction*frictionness;
700                                         else velocity=0;
701                                         if(terrain.getOpacity(mid.x,mid.z)<.2)velocity+=bounceness*elasticity*.3;
702                                         else velocity+=bounceness*elasticity;
703
704                                         if(findLengthfast(&bounceness)>1){
705                                                 int whichsound;
706                                                 if(terrain.getOpacity(mid.x,mid.z)>.2){
707                                                         if(type==staff)whichsound=footstepsound3+abs(Random()%2);
708                                                         if(type!=staff)whichsound=clank1sound+abs(Random()%4);
709                                                 }
710                                                 else whichsound=footstepsound+abs(Random()%2);
711                                                 emit_sound_at(whichsound, mid,
712                                                                   findLengthfast(&bounceness)
713                                                                   * (terrain.getOpacity(position.x,position.z) > .2
714                                                                  ? 128.
715                                                                  : 32.));
716                                         }
717                                         position+=(mid-oldmid)*20;
718                                 }
719
720                                 mid=position+tippoint;
721                                 mid/=2;
722                                 mid+=(tippoint-mid)/20;
723                                 oldmid=mid;
724                                 if(mid.y<terrain.getHeight(mid.x,mid.z)){
725                                         hitsomething=1;
726                                         mid.y=terrain.getHeight(mid.x,mid.z);
727
728                                         terrainnormal=terrain.getNormal(mid.x,mid.z);
729                                         ReflectVector(&tipvelocity,&terrainnormal);
730                                         //mid+=terrainnormal*.002;
731                                         bounceness=terrainnormal*findLength(&tipvelocity)*(abs(normaldotproduct(tipvelocity,terrainnormal)));
732                                         if(findLengthfast(&tipvelocity)<findLengthfast(&bounceness))bounceness=0;
733                                         frictionness=abs(normaldotproduct(tipvelocity,terrainnormal));
734                                         tipvelocity-=bounceness;
735                                         if(1-friction*frictionness>0)tipvelocity*=1-friction*frictionness;
736                                         else tipvelocity=0;
737                                         if(terrain.getOpacity(mid.x,mid.z)<.2)tipvelocity+=bounceness*elasticity*.3;
738                                         else tipvelocity+=bounceness*elasticity;
739
740                                         if(findLengthfast(&bounceness)>1){
741                                                 int whichsound;
742                                                 if(terrain.getOpacity(mid.x,mid.z)>.2){
743                                                         if(type==staff)whichsound=footstepsound3+abs(Random()%2);
744                                                         if(type!=staff)whichsound=clank1sound+abs(Random()%4);
745                                                 }
746                                                 else whichsound=footstepsound+abs(Random()%2);
747                                                 emit_sound_at(whichsound, mid,
748                                                                   findLengthfast(&bounceness)
749                                                                   * (terrain.getOpacity(position.x,position.z) > .2
750                                                                  ? 128.
751                                                                  : 32.));
752                                         }
753                                         tippoint+=(mid-oldmid)*20;
754                                 }
755                                 //Gravity
756                                 velocity.y+=gravity*multiplier;
757                                 tipvelocity.y+=gravity*multiplier;
758                                 //position.y+=gravity*multiplier*multiplier;
759                                 //tippoint.y+=gravity*multiplier*multiplier;
760
761                                 //Rotation
762                                 XYZ temppoint1,temppoint2,tempforward;
763                                 float distance;
764
765                                 temppoint1=position;
766                                 temppoint2=tippoint;
767                                 distance=findDistance(&temppoint1,&temppoint2);
768                                 rotation2=asin((temppoint1.y-temppoint2.y)/distance);
769                                 rotation2*=360/6.28;
770                                 temppoint1.y=0;
771                                 temppoint2.y=0;
772                                 rotation1=acos((temppoint1.z-temppoint2.z)/findDistance(&temppoint1,&temppoint2));
773                                 rotation1*=360/6.28;
774                                 rotation3=0;
775                                 smallrotation=90;
776                                 smallrotation2=0;
777                                 bigtilt=0;
778                                 bigtilt2=0;
779                                 bigrotation=0;
780                                 if(temppoint1.x>temppoint2.x)rotation1=360-rotation1;
781
782                                 //Stop moving
783                                 if(findLengthfast(&velocity)<.3&&findLengthfast(&tipvelocity)<.3&&hitsomething){
784                                         freetime+=multiplier;
785                                 }
786
787                                 //velocity=(position-oldposition)/multiplier;
788                                 //tipvelocity==(tippoint[i-+oldtippoint)/multiplier;
789                                 if(freetime>.4){
790                                         velocity=0;
791                                         tipvelocity=0;
792                                 }
793                                 firstfree=0;
794                 }
795         }
796         multiplier=tempmult;
797         if(blooddrip&&bloody){
798                 blooddripdelay-=blooddrip*multiplier/2;
799                 blooddrip-=multiplier;
800                 if(blooddrip<0)blooddrip=0;
801                 if(blooddrip>5)blooddrip=5;
802                 if(blooddripdelay<0&&bloodtoggle){
803                         blooddripdelay=1;
804                         XYZ bloodvel;
805                         XYZ bloodloc;
806                         bloodloc=position+(tippoint-position)*.7;
807                         bloodloc.y-=.05;
808                         if(bloodtoggle){
809                                 bloodvel=0;
810                                 Sprite::MakeSprite(bloodsprite, bloodloc,bloodvel, 1,1,1, .03, 1);
811                         }
812                 }
813         }
814         if(onfire){
815                 flamedelay-=multiplier;
816                 if(onfire&&flamedelay<=0){
817                         flamedelay=.020;
818                         flamedelay-=multiplier;
819                         normalrot=0;
820                         if(owner!=-1){
821                                 normalrot=player[owner].velocity;
822                         }
823                         normalrot.y+=1;
824                         if(owner!=-1){
825                                 if(player[owner].onterrain){
826                                         normalrot.y=1;
827                                 }
828                         }
829                         Sprite::MakeSprite(weaponflamesprite, position+tippoint*(((float)abs(Random()%100))/600+.05),normalrot, 1,1,1, (.6+(float)abs(Random()%100)/200-.25)*1/3, 1);
830                         Sprite::setLastSpriteSpeed(4);
831                         Sprite::setLastSpriteAlivetime(.3);
832                 }
833         }
834
835         if(!onfire&&owner==-1&&type!=staff){
836                 flamedelay-=multiplier;
837                 if(flamedelay<=0){
838                         flamedelay=.020;
839                         flamedelay-=multiplier;
840                         normalrot=0;
841                         if(Random()%50==0&&findDistancefast(&position,&viewer)>80){
842                                 XYZ shinepoint;
843                                 shinepoint=position+(tippoint-position)*(((float)abs(Random()%100))/100);
844                                 Sprite::MakeSprite(weaponshinesprite, shinepoint,normalrot, 1,1,1, (.1+(float)abs(Random()%100)/200-.25)*1/3*fast_sqrt(findDistance(&shinepoint,&viewer)), 1);
845                                 Sprite::setLastSpriteSpeed(4);
846                                 Sprite::setLastSpriteAlivetime(.3);
847                         }
848                 }
849         }
850 }
851
852 void Weapons::DoStuff() {
853         //Move
854         for(std::vector<Weapon>::iterator weapon = begin(); weapon != end(); ++weapon) {
855                 weapon->DoStuff();
856         }
857 }
858
859 void Weapon::Draw() {
860         static int j;
861         static XYZ terrainlight;
862         static GLfloat M[16];
863         static bool draw;
864         
865         if((frustum.SphereInFrustum(position.x,position.y,position.z,1)&&findDistancefast(&viewer,&position)<viewdistance*viewdistance))
866         {
867                 draw=0;
868                 if(owner==-1)
869                 {
870                         draw=1;
871                         if(velocity.x&&!physics)drawhowmany=10;
872                         else drawhowmany=1;
873                 }
874                 if(owner!=-1)
875                 {
876                         if(player[owner].occluded<25)
877                                 if((frustum.SphereInFrustum(player[owner].coords.x,player[owner].coords.y+player[owner].scale*3,player[owner].coords.z,player[owner].scale*8)&&findDistancefast(&viewer,&player[owner].coords)<viewdistance*viewdistance)||player[owner].skeleton.free==3)
878                                         draw=1;
879                         if((player[owner].targetanimation==knifeslashstartanim||player[owner].targetanimation==swordsneakattackanim||(player[owner].currentanimation==staffhitanim&&player[owner].currentframe>1)||(player[owner].currentanimation==staffhitreversedanim&&player[owner].currentframe>1)||(player[owner].currentanimation==staffspinhitanim&&player[owner].currentframe>1)||(player[owner].currentanimation==staffspinhitreversedanim&&player[owner].currentframe>1)||(player[owner].currentanimation==staffgroundsmashanim&&player[owner].currentframe>1)||(player[owner].targetanimation==swordslashanim&&player[owner].targetframe<7)||player[owner].targetanimation==crouchstabanim||player[owner].targetanimation==swordslashreversalanim||player[owner].targetanimation==swordslashreversedanim||player[owner].targetanimation==knifefollowanim||player[owner].targetanimation==swordgroundstabanim||player[owner].targetanimation==knifethrowanim)&&player[owner].targetanimation==lastdrawnanim&&!player[owner].skeleton.free)
880                         {
881                                 drawhowmany=10;
882                         }
883                         else drawhowmany=1;
884                         if(player[owner].targetanimation==swordgroundstabanim)
885                         {
886                                 lastdrawnrotation1=rotation1;
887                                 lastdrawnrotation2=rotation2;
888                                 lastdrawnrotation3=rotation3;
889                                 lastdrawnbigrotation=bigrotation;
890                                 lastdrawnbigtilt=bigtilt;
891                                 lastdrawnbigtilt2=bigtilt2;
892                                 lastdrawnsmallrotation=smallrotation;
893                                 lastdrawnsmallrotation2=smallrotation2;
894                         }
895                 }
896                 if(draw)
897                 {
898                         terrainlight=terrain.getLighting(position.x,position.z);
899                         if(drawhowmany>0)
900                         {
901                                 glAlphaFunc(GL_GREATER, 0.01);
902                         }
903                         for(j=drawhowmany;j>0;j--)
904                         {
905                                 glMatrixMode(GL_MODELVIEW);                                                     // Select The Modelview Matrix
906                                 glPushMatrix();
907                                         glColor4f(terrainlight.x,terrainlight.y,terrainlight.z,j/drawhowmany);
908                                         if(owner!=-1)glTranslatef(position.x*(((float)(j))/drawhowmany)+lastdrawnposition.x*(1-((float)(j))/drawhowmany),position.y*(((float)(j))/drawhowmany)-.02+lastdrawnposition.y*(1-((float)(j))/drawhowmany),position.z*(((float)(j))/drawhowmany)+lastdrawnposition.z*(1-((float)(j))/drawhowmany));
909                                         if(owner==-1)glTranslatef(position.x*(((float)(j))/drawhowmany)+lastdrawnposition.x*(1-((float)(j))/drawhowmany),position.y*(((float)(j))/drawhowmany)+lastdrawnposition.y*(1-((float)(j))/drawhowmany),position.z*(((float)(j))/drawhowmany)+lastdrawnposition.z*(1-((float)(j))/drawhowmany));
910                                         //glTranslatef(position.x,position.y-.02,position.z);
911                                         glRotatef(bigrotation*(((float)(j))/drawhowmany)+lastdrawnbigrotation*(1-((float)(j))/drawhowmany),0,1,0);
912                                         glRotatef(bigtilt2*(((float)(j))/drawhowmany)+lastdrawnbigtilt2*(1-((float)(j))/drawhowmany),1,0,0);
913                                         glRotatef(bigtilt*(((float)(j))/drawhowmany)+lastdrawnbigtilt*(1-((float)(j))/drawhowmany),0,0,1);
914                                         glRotatef(-rotation1*(((float)(j))/drawhowmany)-lastdrawnrotation1*(1-((float)(j))/drawhowmany)+90,0,1,0);
915                                         glRotatef(-rotation2*(((float)(j))/drawhowmany)-lastdrawnrotation2*(1-((float)(j))/drawhowmany)+90,0,0,1);
916                                         glRotatef(-rotation3*(((float)(j))/drawhowmany)-lastdrawnrotation3*(1-((float)(j))/drawhowmany),0,1,0);
917                                         glRotatef(smallrotation*(((float)(j))/drawhowmany)+lastdrawnsmallrotation*(1-((float)(j))/drawhowmany),1,0,0);
918                                         glRotatef(smallrotation2*(((float)(j))/drawhowmany)+lastdrawnsmallrotation2*(1-((float)(j))/drawhowmany),0,1,0);
919
920                                         if(owner!=-1)
921                                         {
922                                                 if(player[owner].targetanimation==staffhitanim||player[owner].currentanimation==staffhitanim||player[owner].targetanimation==staffhitreversedanim||player[owner].currentanimation==staffhitreversedanim)
923                                                 {
924                                                         glTranslatef(0,0,-.3);
925                                                 }
926                                                 if(player[owner].targetanimation==staffgroundsmashanim||player[owner].currentanimation==staffgroundsmashanim||player[owner].targetanimation==staffspinhitreversedanim||player[owner].currentanimation==staffspinhitreversedanim||player[owner].targetanimation==staffspinhitanim||player[owner].currentanimation==staffspinhitanim)
927                                                 {
928                                                         glTranslatef(0,0,-.1);
929                                                 }
930                                         }
931
932                                         glEnable(GL_LIGHTING);
933                                         switch(type) {
934                                                 case knife:
935                                                         if(!bloody||!bloodtoggle)
936                                                                 throwingknifemodel.drawdifftex(knifetextureptr);
937                                                         if(bloodtoggle)
938                                                         {
939                                                                 if(bloody==1)
940                                                                         throwingknifemodel.drawdifftex(lightbloodknifetextureptr);
941                                                                 if(bloody==2)
942                                                                         throwingknifemodel.drawdifftex(bloodknifetextureptr);
943                                                         }
944                                                         break;
945                                                 case sword:
946                                                         if(!bloody||!bloodtoggle)
947                                                                 swordmodel.drawdifftex(swordtextureptr);
948                                                         if(bloodtoggle)
949                                                         {
950                                                                 if(bloody==1)
951                                                                         swordmodel.drawdifftex(lightbloodswordtextureptr);
952                                                                 if(bloody==2)
953                                                                         swordmodel.drawdifftex(bloodswordtextureptr);
954                                                         }
955                                                         break;
956                                                 case staff:
957                                                         staffmodel.drawdifftex(stafftextureptr);
958                                                         break;
959                                         }
960
961                                 glPopMatrix();
962                         }
963
964                         lastdrawnposition=position;
965                         lastdrawntippoint=tippoint;
966                         lastdrawnrotation1=rotation1;
967                         lastdrawnrotation2=rotation2;
968                         lastdrawnrotation3=rotation3;
969                         lastdrawnbigrotation=bigrotation;
970                         lastdrawnbigtilt=bigtilt;
971                         lastdrawnbigtilt2=bigtilt2;
972                         lastdrawnsmallrotation=smallrotation;
973                         lastdrawnsmallrotation2=smallrotation2;
974                         if(owner!=-1)lastdrawnanim=player[owner].currentanimation;
975                 }
976                 if(owner!=-1)
977                 {
978                         glMatrixMode(GL_MODELVIEW);                                                     // Select The Modelview Matrix
979                         glPushMatrix();
980                                 glLoadIdentity();
981                                 glTranslatef(position.x,position.y-.02,position.z);
982                                 glRotatef(bigrotation,0,1,0);
983                                 glRotatef(bigtilt2,1,0,0);
984                                 glRotatef(bigtilt,0,0,1);
985                                 glRotatef(-rotation1+90,0,1,0);
986                                 glRotatef(-rotation2+90,0,0,1);
987                                 glRotatef(-rotation3,0,1,0);
988                                 glRotatef(smallrotation,1,0,0);
989                                 glRotatef(smallrotation2,0,1,0);
990                                 glTranslatef(0,0,length);
991                                 glGetFloatv(GL_MODELVIEW_MATRIX,M);
992                                 tippoint.x=M[12];
993                                 tippoint.y=M[13];
994                                 tippoint.z=M[14];
995                         glPopMatrix();
996                 }
997         }
998 }
999
1000 int Weapons::Draw()
1001 {
1002         glAlphaFunc(GL_GREATER, 0.9);
1003         glEnable(GL_TEXTURE_2D);
1004         glEnable(GL_BLEND);
1005         glEnable(GL_CULL_FACE);
1006         glCullFace(GL_FRONT);
1007         glDepthMask(1);
1008         
1009         for(std::vector<Weapon>::iterator weapon = begin(); weapon != end(); ++weapon) {
1010                 weapon->Draw();
1011         }
1012         return 0;
1013 }
1014
1015 Weapons::Weapons()
1016 {
1017 }
1018
1019 Weapons::~Weapons()
1020 {
1021         if (Weapon::stafftextureptr) glDeleteTextures( 1, &Weapon::stafftextureptr );
1022         if (Weapon::knifetextureptr) glDeleteTextures( 1, &Weapon::knifetextureptr );
1023         if (Weapon::lightbloodknifetextureptr) glDeleteTextures( 1, &Weapon::lightbloodknifetextureptr );
1024         if (Weapon::bloodknifetextureptr) glDeleteTextures( 1, &Weapon::bloodknifetextureptr );
1025         if (Weapon::swordtextureptr) glDeleteTextures( 1, &Weapon::swordtextureptr );
1026         if (Weapon::lightbloodswordtextureptr) glDeleteTextures( 1, &Weapon::lightbloodswordtextureptr );
1027         if (Weapon::bloodswordtextureptr) glDeleteTextures( 1, &Weapon::bloodswordtextureptr );
1028 }
1029