From eb7cde2a10895da166cebe13452ca3b284eab78c Mon Sep 17 00:00:00 2001 From: "chirs241097@gmail.com" Date: Fri, 31 Jan 2014 15:41:18 +0000 Subject: AM resources/b_diff.png AM resources/b_inter.png AM resources/b_null.png D resources/bg.png AM resources/e_skyitem.png AM trunk/CHANGELOG.TXT AM trunk/VERSION.TXT M trunk/background.h M trunk/global.h A trunk/hge/sound.cpp D trunk/hge/sound_openal.cpp M trunk/levels.h M trunk/main.cpp M trunk/menus.h M trunk/towernbullet.h --- CHANGELOG.TXT | 245 ++++++++++++++++++++++++ VERSION.TXT | 1 + background.h | 342 +++++++++++++++++++++++++++------ global.h | 28 ++- hge/sound.cpp | 531 +++++++++++++++++++++++++++++++++++++++++++++++++++ hge/sound_openal.cpp | 531 --------------------------------------------------- levels.h | 17 +- main.cpp | 3 +- menus.h | 4 +- towernbullet.h | 89 +++++---- 10 files changed, 1143 insertions(+), 648 deletions(-) create mode 100755 CHANGELOG.TXT create mode 100755 VERSION.TXT create mode 100644 hge/sound.cpp delete mode 100644 hge/sound_openal.cpp diff --git a/CHANGELOG.TXT b/CHANGELOG.TXT new file mode 100755 index 0000000..3ed741a --- /dev/null +++ b/CHANGELOG.TXT @@ -0,0 +1,245 @@ +================================================================= +Next version: +0.7.0-8_PR (b61) +Improve the rendering code. (That code was a great fucking +resource consumer) + +Pre-Released versions: +0.7.0-7_PR (b60) +Spring Festival commit... +One level is rewritten. +Ready to sync this to svn... + +0.7.0-6_PR (b59) +Fixed 3D clouds background. New background components added. +Experimental FPS independent bullets. + +0.7.0-5_PR (b58) +Fixed another critical bug in laser collision detection +implementation... Laser is almost perfect now... + +0.7.0-4_PR (b57) +Fixed a critical bug in laser implementation and another awful +memory leak bug... + +0.7.0-3_PR (b56) +A new level is going to be complete... + +0.7.0-2_PR (b55) +Auto pause and do not make game suspend if focus is lost. + +0.7.0-1_PR (b54) +First two parts for level7. + +0.7.0-0_PR (b53) +New background for level7. Preparing interfaces for level7. + +0.6.2-2_PR (b52) +Level6 is frozen now. It's the longest level ever... (in blr!) + +0.6.2-1_PR (b51) +Completing level6! +Spring is coming? (Well, not really...) + +0.6.2-0_PR (b50) +Completing && improving hexagon. +Bumped the minor version for the sixth level is almost complete. + +0.6.1-4_PR (b49) +New level hexagon. + +0.6.1-3_PR (b48) +New level...(Avalanche) +Spotlight: Supporting BGM loop points(using my new hge +interfaces...)! +I have no idea on new levels (except "hyper fluid", that's a well- +planned part...). Maybe I've spent too much time staring at the +desktop? I feel like void these days. +The build count is bumped four times a day, you enough! + +0.6.1-2_PR (b47) +New level "Wriggle Nightbug-like"?... + +0.6.1-1_PR (b46) +Implemented several unimplemented audio interfaces of hge... +A Windows build to check compatibility is planned. + +0.6.1-0_PR (b45) +Now we have 11 parts in level6... +A BGM called Canon Techno is composed around here... + +0.6.0-0_PR (b44) +Starting level 6! +//We are in 2014 now. I'm regretful for I didn't have the dates +recorded. + +0.5.3-2_PR (b43) +Optimizing memory usage... (first step...)[*] +Borrowed "the unbreakable jail" from old code... +//[*]Note @ 0.6.1-3: +//1. I found this useless. +//2. This may cause SIGSEGV! + +0.5.3-1_PR (b42) +Final(the second last..) level for level 5, fish in a barrel? + +0.5.3-0_PR (b41) +Small fixes and levels as usual... + +0.5.2-3_PR (b40) +New minor parts for level5, fixed a bug in Player_Clear_Rotate. + +0.5.2-2_PR (b39) +Several patches on new clear range. +Changing interfaces for new levels. + +0.5.2-1_PR (b38) +New trigger method for clear range... + +0.4.4-0_PRG (b37a) +Regression version for releasing... + +0.5.2-0_PR (b37) +New part for level5. Now I'm working on the regression 0.4.x. + +0.5.1-1_PR (b36) +Several fixes including: +-Fading info panel when approaching. +-Sending multiplier layer up. + +0.5.1-0_PR (b35) +First two levels of level5. + +0.5.0-0_PR (b34) +Starting level5... Crazy Autumn... + +A regression is planned to release a 0.4.x-x_PR version as +official pre-released version. However it's still nowhere in sight +that if I could use Windows these days. + +0.4.3-0_PR (b33) +Level4 is almost complete. Now I'm using LOW FPS Mode for +development because I just want to cool my laptop down without +using my own power. //However I stopped that at the next version... + +0.4.2-0_PR (b32) +A new level... without using *ANY* old code (from level.h). + +0.4.1-2_PR (b31) +Level4 is now 18 parts... + +0.4.1-1_PR (b30) +Transfered sevel old levels here. + +0.4.1-0_PR (b29) +Optimizing old code for level4. + +0.4.0-0_PR (b28) +Now let's move to level4... + +0.3.2-0_PR (b27) +New levels for level3. In fact, it's almost completed now... + +0.3.1-2_PR (b26) +Improved bullet clearing method, avoiding hidden bullets +completely! + +0.3.1-1_PR (b25) +A new "big" level for level3. +Added several new interfaces to tower&bullet section. + +0.3.1-0_PR (b24) +Complete the first two parts of level3. + +0.3.0-0_PR (b23) +Starting the development of level3... + +0.2.9-2_PR (b22) +Completing level2... + +0.2.9-1_PR (b21) +New parts for level2. level2 is almost completed now. +PlayerLockX/Y implemented. +------------------------------------------------------------- +This will be released as a official Preview Release version. +------------------------------------------------------------- +BLR will be licensed under WTFPL from now. +(WTF?) + +0.2.9_PR (b20) +Level 2 is frozen "by heart". (How? By heart?) + +0.2.5_PR (b19) +Optimizing the second level to a "realistic" state... Added two +extra musics(although still remain not used). + +0.2.2_PR (b18) +The main development has been transferred to Linux. Optimizing +code for Linux. +//Revision count is not important. + +0.2.0_PR (b17) +Level 2?... + +0.1.7-2_PR (b16) +The first level is almost completed now... + +0.1.7-1_PR (b15) +Fixed several serious bug in Low FPS Mode. Fixed FPS Level option +code. + +0.1.7_PR (b14) +Updated the only level to synchronize with the In-Game Music. +Added "Multiplier +1" into the game system. Added an unimportant +loading screen.//In fact, it's loading nothing. May be unpacking +resource pack in Windows version... + +0.1.4_PR (b13) +libcghEx has been made independent and can apply to any other +projects. This is also the first BLR version that includes +In-Game Music. libcghEx has been extended with LinearProgresser +and HangUpText. + +0.1.1_PR (b12) +Added auto-multiplier system. libcghEx (Chrisoft Game Helper +Extras Library) is included in this version with CircleIndicator. + +0.1.0_PR (b11) +Creation of the Pre-Released Version. Removed all old level code. +Bourne-again!//Can you imagine what I was thinking when deleting +the result of 3 months' work?... +================================================================= +TestBed versions: + +TB130907 (b10) +A "Noname" level. Laser implementation partly rewritten. + +TB130903 (b9) +Additional backgrounds + +TB130827 (b8) +Laser implementation, Cheers! + +TB130818 (b7) +New Levels such as rainbow towers and squashing levels. + +TB130802 (b6) +Discarding old code, rewrite of most of the code. + +TB130718 (b5) +Bullet creation effects, sync code back to BLR1. + +TB130714 (b4) +Target indicator completed. + +TB130705 (b3) +New level and bullet creation code for orange bullets. + +TB130703 (b2) +Completing Orange Towers. + +TB130620 (b1) +Completing Deep Blue Towers. + +TB130610 (b0) +Creation of Testbed version. diff --git a/VERSION.TXT b/VERSION.TXT new file mode 100755 index 0000000..6ad3e29 --- /dev/null +++ b/VERSION.TXT @@ -0,0 +1 @@ +0.7.0-7_PR (b60) \ No newline at end of file diff --git a/background.h b/background.h index 0739e5f..718b42c 100644 --- a/background.h +++ b/background.h @@ -156,73 +156,307 @@ public: } }; //******************************************** -//3D-Clouds Background +//3D-sky Background +//Based on a hge tutorial //******************************************** -class TDClouds +class TDSky { +#define ScreenWidth 800 +#define ScreenHeight 600 +#define Stars 100 +#define SeaDisize 16 +#define SkyHeight (ScreenHeight*0.6f) +#define StarsHeight (SkyHeight*0.9f) +#define OrbitRadius (ScreenWidth*0.43f) private: - hgeQuad CQuad; - double DTime; - int alpha,lima; - bool onFadein,onFadeout; - void DoFadein() + const DWORD skyTopColors[3] = {0xFF15092A, 0xFF6C6480, 0xFF89B9D0}; + const DWORD skyBtmColors[3] = {0xFF303E57, 0xFFAC7963, 0xFFCAD7DB}; + const DWORD seaTopColors[3] = {0xFF3D546B, 0xFF927E76, 0xFF86A2AD}; + const DWORD seaBtmColors[3] = {0xFF1E394C, 0xFF2F4E64, 0xFF2F4E64}; + const int seq[9]={0, 0, 1, 2, 2, 2, 1, 0, 0}; + HTEXTURE skyitem; + hgeSprite *sky,*sun,*moon,*glow,*seaglow,*star; + hgeDistortionMesh *sea,*skylyr; + float timet,speed,skya,skylima,seq_residue; + int seq_id; + float starX[Stars],starY[Stars],starS[Stars],starA[Stars],seaP[SeaDisize]; + hgeColor colWhite,colSkyTop,colSkyBtm,colSeaTop,colSeaBtm; + hgeColor colSun,colSunGlow; + hgeColor colMoon,colMoonGlow,colSeaGlow; + float sunX,sunY,sunS,sunGlowS; + float moonX,moonY,moonS,moonGlowS; + float seaGlowX,seaGlowSX,seaGlowSY; + bool skyOnFadeIn,skyOnFadeOut; + float GetTime() { - int times=1; - if (LOWFPS)times=17; - for (int i=1;i<=times;++i)if (alphatm_sec; + tmp=t->tm_min+tmp/60.0f; + tmp=t->tm_hour+tmp/60.0f; + } + return tmp; } - void DoFadeout() + void SkyDoFadeIn() { - int times=1; - if (LOWFPS)times=17; - for (int i=1;i<=times;++i)if (alpha>0)--alpha; + float dlt=1.0f/hge->Timer_GetFPS(); + if (skya+dltTimer_GetFPS(); + if (skya-dlt>0)skya-=dlt; + else skya=0.0f,skyOnFadeOut=false; } public: - void Init(int _lima) - { - DTime=0.0f; - CQuad.tex=hge->Texture_Load("sky.png"); - CQuad.blend=BLEND_ALPHABLEND; - alpha=0;lima=_lima; - onFadein=onFadeout=false; - for (int i=0;i<4;++i) - CQuad.v[i].col=0x00FFFFFF; - CQuad.v[0].x=0,CQuad.v[0].y=300; - CQuad.v[1].x=800,CQuad.v[1].y=300; - CQuad.v[2].x=1000,CQuad.v[2].y=600; - CQuad.v[3].x=-200,CQuad.v[3].y=600; - CQuad.v[0].tx=0,CQuad.v[0].ty=0; - CQuad.v[0].tx=0.5,CQuad.v[0].ty=0; - CQuad.v[0].tx=0.5,CQuad.v[0].ty=0.5; - CQuad.v[0].tx=0,CQuad.v[0].ty=0.5; - } - void SetFadein() - { - onFadein=true; - onFadeout=false; - alpha=0; - } - void SetFadeout() - { - onFadeout=true; - onFadein=false; - alpha=lima; + bool Init() + { + skyitem=hge->Texture_Load("e_skyitem.png"); + if(!skyitem) return false; + sky=new hgeSprite(0, 0, 0, ScreenWidth, ScreenHeight); + sea=new hgeDistortionMesh(SeaDisize, SeaDisize); + sea->SetTextureRect(0, 0, ScreenWidth, ScreenHeight-SkyHeight); + sun=new hgeSprite(skyitem,81,0,114,114); + sun->SetHotSpot(57,57); + moon=new hgeSprite(skyitem,0,0,81,81); + moon->SetHotSpot(40,40); + star=new hgeSprite(skyitem,195,0,9,9); + star->SetHotSpot(5,5); + glow=new hgeSprite(skyitem,204,0,128,128); + glow->SetHotSpot(64,64); + glow->SetBlendMode(BLEND_COLORADD | BLEND_ALPHABLEND | BLEND_NOZWRITE); + seaglow=new hgeSprite(skyitem,204,96,128,32); + seaglow->SetHotSpot(64,0); + seaglow->SetBlendMode(BLEND_COLORADD | BLEND_ALPHAADD | BLEND_NOZWRITE); + skylyr=new hgeDistortionMesh(16, 16); + skylyr->SetTexture(skyitem); + skylyr->SetTextureRect(0,128,512,512); + skylyr->SetBlendMode(BLEND_ALPHAADD); + colWhite.SetHWColor(0xFFFFFFFF); + timet=GetTime(); + speed=skya=0.0f; + for(int i=0;iTexture_Free(skyitem); + } + void SetSpeed(float _speed){speed=_speed;} + void SetSkyA(float _skya){skya=_skya;} + void SkySetFadeIn(float _starta=0.0f,float _lima=1.0f) + { + skya=_starta;skylima=_lima; + skyOnFadeIn=true;skyOnFadeOut=false; + } + void SkySetFadeOut(float _starta=0.0f) + { + if (_starta>1E-4)skya=_starta; + skyOnFadeIn=false;skyOnFadeOut=true; } void Update() { - if (onFadein)DoFadein(); - if (onFadeout)DoFadeout(); - for (int i=0;i<4;++i) - CQuad.v[i].col=ARGB(alpha,0xFF,0xFF,0xFF); - DTime+=0.1*hge->Timer_GetDelta(); - CQuad.v[0].tx=cos(DTime),CQuad.v[0].ty=sin(DTime); - CQuad.v[1].tx=CQuad.v[0].tx+0.5f;CQuad.v[1].ty=CQuad.v[0].ty; - CQuad.v[2].tx=CQuad.v[0].tx+0.5f;CQuad.v[2].ty=CQuad.v[0].ty+0.5f; - CQuad.v[3].tx=CQuad.v[0].tx;CQuad.v[3].ty=CQuad.v[0].ty+0.5f; - hge->Gfx_RenderQuad(&CQuad); + int i, j, k; + float zenith,a,dy,fTime; + float posX,s1,s2; + const float cellw=ScreenWidth/(SeaDisize-1); + hgeColor col1,col2; + DWORD dwCol1,dwCol2; + if(speed==0.0f) timet=GetTime(); + else + { + timet+=hge->Timer_GetDelta()*speed; + if(timet>=24.0f) timet-=24.0f; + } + seq_id=(int)(timet/3); + seq_residue=timet/3-seq_id; + zenith=-(timet/12.0f*pi-pi/2.0f); + col1.SetHWColor(skyTopColors[seq[seq_id]]); + col2.SetHWColor(skyTopColors[seq[seq_id+1]]); + colSkyTop=col2*seq_residue + col1*(1.0f-seq_residue); + col1.SetHWColor(skyBtmColors[seq[seq_id]]); + col2.SetHWColor(skyBtmColors[seq[seq_id+1]]); + colSkyBtm=col2*seq_residue + col1*(1.0f-seq_residue); + col1.SetHWColor(seaTopColors[seq[seq_id]]); + col2.SetHWColor(seaTopColors[seq[seq_id+1]]); + colSeaTop=col2*seq_residue + col1*(1.0f-seq_residue); + col1.SetHWColor(seaBtmColors[seq[seq_id]]); + col2.SetHWColor(seaBtmColors[seq[seq_id+1]]); + colSeaBtm=col2*seq_residue + col1*(1.0f-seq_residue); + if(seq_id>=6 || seq_id<2) + for(int i=0; iRandom_Float(0.6f, 1.0f); + a*=(rand()%40+60.0f)/100.0f; + if(seq_id>=6) a*=sinf((timet-18.0f)/12.0f*pi); + else a*=sinf((1.0f-timet/6.0f)*pi/2); + starA[i]=a; + } + if(seq_id==2) a=sinf(seq_residue*pi/2); + else if(seq_id==5) a=cosf(seq_residue*pi/2); + else if(seq_id>2 && seq_id<5) a=1.0f; + else a=0.0f; + colSun.SetHWColor(0xFFEAE1BE); + colSun=colSun*(1-a)+colWhite*a; + a=(cosf(timet/6.0f*pi)+1.0f)/2.0f; + if(seq_id>=2 && seq_id<=6) + { + colSunGlow=colWhite*a; + colSunGlow.a=1.0f; + } + else colSunGlow.SetHWColor(0xFF000000); + sunX=ScreenWidth*0.5f+cosf(zenith)*OrbitRadius; + sunY=SkyHeight*1.2f+sinf(zenith)*OrbitRadius; + sunS=1.0f-0.3f*sinf((timet-6.0f)/12.0f*pi); + sunGlowS=3.0f*(1.0f-a)+3.0f; + if(seq_id>=6) a=sinf((timet-18.0f)/12.0f*pi); + else a=sinf((1.0f-timet/6.0f)*pi/2); + colMoon.SetHWColor(0x20FFFFFF); + colMoon=colMoon*(1-a)+colWhite*a; + colMoonGlow=colWhite; + colMoonGlow.a=0.5f*a; + moonX=ScreenWidth*0.5f+cosf(zenith-pi)*OrbitRadius; + moonY=SkyHeight*1.2f+sinf(zenith-pi)*OrbitRadius; + moonS=1.0f-0.3f*sinf((timet+6.0f)/12.0f*pi); + moonGlowS=a*0.4f+0.5f; + if(timet>19.0f || timet<4.5f) + { + a=0.2f; + if(timet>19.0f && timet<20.0f) a*=(timet-19.0f); + else if(timet>3.5f && timet<4.5f) a*=1.0f-(timet-3.5f); + colSeaGlow=colMoonGlow; + colSeaGlow.a=a; + seaGlowX=moonX; + seaGlowSX=moonGlowS*3.0f; + seaGlowSY=moonGlowS*2.0f; + } + else if(timet>6.5f && timet<19.0f) + { + a=0.3f; + if(timet<7.5f) a*=(timet-6.5f); + else if(timet>18.0f) a*=1.0f-(timet-18.0f); + colSeaGlow=colSunGlow; + colSeaGlow.a=a; + seaGlowX=sunX; + seaGlowSX=sunGlowS; + seaGlowSY=sunGlowS*0.6f; + } + else colSeaGlow.a=0.0f; + for(i=1; iTimer_GetTime(); + a*=20; + for(j=0; jSetColor(j, i, dwCol1); + dy=a*sinf(seaP[i]+(float(j)/(SeaDisize-1)-0.5f)*pi*16.0f-fTime); + sea->SetDisplacement(j, i, 0.0f, dy, HGEDISP_NODE); + } + } + float t=0.1*hge->Timer_GetTime(); + skylyr->SetTextureRect(128+sin(t)*128.0f,256+cos(t)*128.0f,256,128); + if (skyOnFadeIn)SkyDoFadeIn(); + if (skyOnFadeOut)SkyDoFadeOut(); + for (int i=-8;i<8;++i) + for (int j=-8;j<8;++j) + { + skylyr->SetColor(j+8,i+8,ARGB((int)(skya*((i+9)*16-16)),0xFF,0xFF,0xFF)); + skylyr->SetDisplacement(j+8,i+8,j*(16.0f*((i+9)/16.0f)+64.0f),i*24,HGEDISP_CENTER); + } + dwCol1=colSeaTop.GetHWColor(); + dwCol2=colSeaBtm.GetHWColor(); + for(j=0; jSetColor(j, 0, dwCol1); + sea->SetColor(j, SeaDisize-1, dwCol2); + } + if(timet>19.0f || timet<5.0f) + { + a=0.12f; + if(timet>19.0f && timet<20.0f) a*=(timet-19.0f); + else if(timet>4.0f && timet<5.0f) a*=1.0f-(timet-4.0f); + posX=moonX; + } + else if(timet>7.0f && timet<17.0f) + { + a=0.14f; + if(timet<8.0f) a*=(timet-7.0f); + else if(timet>16.0f) a*=1.0f-(timet-16.0f); + posX=sunX; + } + else a=0.0f; + if(a!=0.0f) + { + k=(int)floorf(posX/cellw); + s1=(1.0f-(posX-k*cellw)/cellw); + s2=(1.0f-((k+1)*cellw-posX)/cellw); + if(s1>0.7f) s1=0.7f; + if(s2>0.7f) s2=0.7f; + s1*=a;s2*=a; + for(i=0; iGetColor(k,i)); + col1+=colSun*s1*(1-a); + col1.Clamp(); + sea->SetColor(k, i, col1.GetHWColor()); + col1.SetHWColor(sea->GetColor(k+1,i)); + col1+=colSun*s2*(1-a); + col1.Clamp(); + sea->SetColor(k+1, i, col1.GetHWColor()); + } + } + } + void Render() + { + sky->SetColor(colSkyTop.GetHWColor(), 0); + sky->SetColor(colSkyTop.GetHWColor(), 1); + sky->SetColor(colSkyBtm.GetHWColor(), 2); + sky->SetColor(colSkyBtm.GetHWColor(), 3); + sky->Render(0, 0); + if(seq_id>=6 || seq_id<2) + for(int i=0; iSetColor((DWORD(starA[i]*255.0f)<<24) | 0xFFFFFF); + star->RenderEx(starX[i], starY[i], 0.0f, starS[i]); + } + glow->SetColor(colSunGlow.GetHWColor()); + glow->RenderEx(sunX, sunY, 0.0f, sunGlowS); + sun->SetColor(colSun.GetHWColor()); + sun->RenderEx(sunX, sunY, 0.0f, sunS); + glow->SetColor(colMoonGlow.GetHWColor()); + glow->RenderEx(moonX, moonY, 0.0f, moonGlowS); + moon->SetColor(colMoon.GetHWColor()); + moon->RenderEx(moonX, moonY, 0.0f, moonS); + sea->Render(0, SkyHeight); + seaglow->SetColor(colSeaGlow.GetHWColor()); + seaglow->RenderEx(seaGlowX, SkyHeight, 0.0f, seaGlowSX, seaGlowSY); + skylyr->Render(ScreenWidth/8*3,ScreenHeight/3*2); } }; -TDClouds Sky; +TDSky sky; DWORD ColorTransfer(DWORD a,DWORD t) { diff --git a/global.h b/global.h index f71df6c..fb8ea32 100644 --- a/global.h +++ b/global.h @@ -14,7 +14,7 @@ hgeGUI *gui; hgeFont *fnt; hgeSprite *spr,*titlespr; //Here are some Varibles in Bullet Lab -int Current_Position;//Where are we now. +int Current_Position;//Where we are now /*Scenes: 0: main menu 1: game scene @@ -28,7 +28,7 @@ int Current_Position;//Where are we now. 9: highscore view scene 10: highscore details scene 11: Pause scene -12: BackToTitle Confirm +12: BackToTitle Confirmation 13: Options scene 14: Player Profile scene */ @@ -71,17 +71,17 @@ bool LOWFPS=false,diffkey=false; inline double GetDist(vector2d,vector2d); struct Bullet { - hgeSprite *bulletspr; + hgeSprite *bulletspr;//This shit will be deprecated. vector2d bulletpos; vector2d bulletdir; double dist; int bullettype; int redexplo,redattrib,oriexplo,whicnt; - //In Orange bullets + /*In Orange bullets //redattrib also serves as oraattrib to determine if they will explode or change direction //redexplo also serves as orange explo //yelbrk serves as direction-change timer - //whicnt describes how much one will explode into (into an exactly circle) + //whicnt describes how much one will explode into (into an exactly circle)*/ double bulletspeed; double bulletaccel,limv; bool exist; @@ -104,10 +104,10 @@ struct Bullet dist=1; } }bullet[10000]; -//Something about bullets: +/*Something about bullets: //bullettype: -//1: dir-based green bullet -//2: degree-based blue bullet (for clocks only) +//1: player dir-based green bullet +//2: degree-based blue bullet (for clocks only)[are they clocks?] //3: 12direction-based blue bullet //4: yellow chaser bullet //5: purple slow down bullet @@ -116,10 +116,10 @@ struct Bullet //8: Orange Redir bullet //9: dark Blue bullet //254: Semi-collision effect -//255: Score point +//255: Score point*/ struct Tower { - hgeSprite *towerspr; + hgeSprite *towerspr;//So will this one. vector2d towerpos; int towertype; int towertimer,curtimer; @@ -138,7 +138,8 @@ struct Tower //1:four default directions //2:random left/right //3:random up/down -struct Target{ +struct Target//An annoying circle +{ hgeSprite *targspr; vector2d targpos,targdir; double rot,rotspd; @@ -323,12 +324,7 @@ void ShowTip(char *tip) DisableAllTower=true; DisablePlayer=true; if (hge->Input_GetKeyStateEx(HGEK_Z)==HGEKST_HIT) - { - //DisableAllTower=false; - //DisablePlayer=false; - //Current_Position=1; FadeTip=true; - } double width=TipFont->GetStringWidth(tip); TipFont->printf(400-width/2,400,HGETEXT_LEFT,tip); if (FadeTip) diff --git a/hge/sound.cpp b/hge/sound.cpp new file mode 100644 index 0000000..bd9a8d7 --- /dev/null +++ b/hge/sound.cpp @@ -0,0 +1,531 @@ +/* +** Haaf's Game Engine 1.8 +** Copyright (C) 2003-2007, Relish Games +** hge.relishgames.com +** +** Core functions implementation: audio routines +*/ + + +// This is just enough to get Hammerfight working without using libBA$$. +// If you want a full HGE audio implementation, you should either use the +// code in sound_libbass.cpp (and maybe pay for a BA$$ licen$e), or improve +// this code. +// Well, this code is now improved by Chris Xiong, adding several new interfaces. +// (Such as seeking in sample...) +// Channel functions are fully supported now. However music and streaming are +// still not supported. Some APIs changed for OpenAL is different from BA$$. + +#include "hge_impl.h" + +#include "AL/al.h" +#include "AL/alc.h" +#include "AL/alext.h" +#include "ogg/ogg.h" +#include "vorbis/vorbisfile.h" +static const char* SOUND_SRC_FN="hge/sound_openal.cpp"; +struct oggcbdata +{ + const BYTE *data; + DWORD size; + DWORD pos; +}; + +static size_t oggcb_read(void *ptr, size_t size, size_t nmemb, void *datasource) +{ + oggcbdata *data = (oggcbdata *) datasource; + const DWORD avail = data->size - data->pos; + size_t want = nmemb * size; + if (want > avail) + want = avail - (avail % size); + if (want > 0) + { + memcpy(ptr, data->data + data->pos, want); + data->pos += want; + } + return want / size; +} + +static int oggcb_seek(void *datasource, ogg_int64_t offset, int whence) +{ + oggcbdata *data = (oggcbdata *) datasource; + ogg_int64_t pos = 0; + switch (whence) + { + case SEEK_SET: pos = offset; break; + case SEEK_CUR: pos = ((ogg_int64_t) data->pos) + offset; break; + case SEEK_END: pos = ((ogg_int64_t) data->size) + offset; break; + default: return -1; + } + + if ( (pos < 0) || (pos > ((ogg_int64_t) data->size)) ) + return -1; + + data->pos = (DWORD) pos; + return 0; +} + +static int oggcb_close(void *datasource) +{ + return 0; +} + +static long oggcb_tell(void *datasource) +{ + oggcbdata *data = (oggcbdata *) datasource; + return (long) data->pos; +} + +static ov_callbacks oggcb = { oggcb_read, oggcb_seek, oggcb_close, oggcb_tell }; + +static void *decompress_vorbis(const BYTE *data, const DWORD size, ALsizei *decompressed_size, ALenum *fmt, ALsizei *freq) +{ +#ifdef __POWERPC__ + const int bigendian = 1; +#else + const int bigendian = 0; +#endif + + oggcbdata cbdata = { data, size, 0 }; + OggVorbis_File vf; + memset(&vf, '\0', sizeof (vf)); + if (ov_open_callbacks(&cbdata, &vf, NULL, 0, oggcb) == 0) + { + int bitstream = 0; + vorbis_info *info = ov_info(&vf, -1); + + *decompressed_size = 0; + *fmt = (info->channels == 1) ? AL_FORMAT_MONO16 : AL_FORMAT_STEREO16; + *freq = info->rate; + + if ((info->channels != 1) && (info->channels != 2)) + { + ov_clear(&vf); + return NULL; + } + + char buf[1024 * 16]; + long rc = 0; + size_t allocated = 64 * 1024; + BYTE *retval = (ALubyte *) malloc(allocated); + while ( (rc = ov_read(&vf, buf, sizeof (buf), bigendian, 2, 1, &bitstream)) != 0 ) + { + if (rc > 0) + { + *decompressed_size += rc; + if (*decompressed_size >= allocated) + { + allocated *= 2; + ALubyte *tmp = (ALubyte *) realloc(retval, allocated); + if (tmp == NULL) + { + free(retval); + retval = NULL; + break; + } + retval = tmp; + } + memcpy(retval + (*decompressed_size - rc), buf, rc); + } + } + ov_clear(&vf); + return retval; + } + + return NULL; +} + +#define MAX_SIDS 128 +static int sidcount = 0; +static ALuint sids[MAX_SIDS]; + +static ALuint get_source() +{ + for (int i = 0; i < sidcount; i++) + { + ALint state = AL_PLAYING; + alGetSourceiv(sids[i], AL_SOURCE_STATE, &state); + if ((state != AL_PLAYING) && (state != AL_PAUSED)) + return sids[i]; + } + if (sidcount >= MAX_SIDS) + return 0; + + ALuint sid = 0; + alGenSources(1, &sid); + if (sid == 0) + return 0; + sids[sidcount++] = sid; + return sid; +} + + +HEFFECT CALL HGE_Impl::Effect_Load(const char *filename, DWORD size) +{ + DWORD _size, length, samples; + void *data; + + if(hOpenAL) + { + if(bSilent) return 1; + + if(size) { data=(void *)filename; _size=size; } + else + { + data=Resource_Load(filename, &_size); + if(!data) return 0; + } + + const BYTE *magic = (const BYTE *) data; + const bool isOgg = ( (_size > 4) && + (magic[0] == 'O') && (magic[1] == 'g') && + (magic[2] == 'g') && (magic[3] == 'S') ); + if (!isOgg) + { + if(!size) Resource_Free(data); + return 0; + } + void *allocation_decompressed = NULL; + void *decompressed = NULL; + ALsizei decompressed_size = 0; + ALsizei freq = 0; + ALenum fmt = AL_FORMAT_STEREO16; + if (isOgg) + { + if (alIsExtensionPresent((const ALchar *) "AL_EXT_vorbis")) + { + fmt = alGetEnumValue((const ALchar *) "AL_FORMAT_VORBIS_EXT"); + decompressed = data; + decompressed_size = _size; + } + else + { + allocation_decompressed = decompress_vorbis((const BYTE *) data, _size, &decompressed_size, &fmt, &freq); + decompressed = allocation_decompressed; + } + } + + ALuint bid = 0; + alGenBuffers(1, &bid); + alBufferData(bid, fmt, decompressed, decompressed_size, freq); + free(allocation_decompressed); // not delete[] ! + if(!size) Resource_Free(data); + return (HEFFECT) bid; + } + else return 0; +} + +HCHANNEL CALL HGE_Impl::Effect_Play(HEFFECT eff) +{ + return Effect_PlayEx(eff, 100, 0, 1.0f, false); +} + +HCHANNEL CALL HGE_Impl::Effect_PlayEx(HEFFECT eff, int volume, int pan, float pitch, bool loop) +{ + if(hOpenAL) + { + const ALuint sid = get_source(); // find an unused sid, or generate a new one. + if (sid != 0) + { + if (volume < 0) volume = 0; else if (volume > 100) volume = 100; + if (pan < -100) pan = -100; else if (pan > 100) pan = 100; + alSourceStop(sid); + alSourcei(sid, AL_BUFFER, (ALint) eff); + alSourcef(sid, AL_GAIN, ((ALfloat) volume) / 100.0f); + alSourcef(sid, AL_PITCH, pitch); + alSource3f(sid, AL_POSITION, ((ALfloat) pan) / 100.0f, 0.0f, 0.0f); + alSourcei(sid, AL_LOOPING, loop ? AL_TRUE : AL_FALSE); + alSourcePlay(sid); + } + return sid; + } + else return 0; +} + +void CALL HGE_Impl::Effect_Free(HEFFECT eff) +{ + if(hOpenAL) + { + ALuint bid = (ALuint) eff; + alDeleteBuffers(1, &bid); + } +} +//Castrate!! +HMUSIC CALL HGE_Impl::Music_Load(const char *filename, DWORD size){return 0;} + +HCHANNEL CALL HGE_Impl::Music_Play(HMUSIC mus, bool loop, int volume, int order, int row){return 0;} + +void CALL HGE_Impl::Music_Free(HMUSIC mus){} + +void CALL HGE_Impl::Music_SetAmplification(HMUSIC music, int ampl){} + +int CALL HGE_Impl::Music_GetAmplification(HMUSIC music){return -1;} + +int CALL HGE_Impl::Music_GetLength(HMUSIC music){return -1;} + +void CALL HGE_Impl::Music_SetPos(HMUSIC music, int order, int row){} + +bool CALL HGE_Impl::Music_GetPos(HMUSIC music, int *order, int *row){return false;} + +void CALL HGE_Impl::Music_SetInstrVolume(HMUSIC music, int instr, int volume){} + +int CALL HGE_Impl::Music_GetInstrVolume(HMUSIC music, int instr){return -1;} + +void CALL HGE_Impl::Music_SetChannelVolume(HMUSIC music, int channel, int volume){} + +int CALL HGE_Impl::Music_GetChannelVolume(HMUSIC music, int channel){return -1;} + +HSTREAM CALL HGE_Impl::Stream_Load(const char *filename, DWORD size){return 0;} + +void CALL HGE_Impl::Stream_Free(HSTREAM stream){} + +HCHANNEL CALL HGE_Impl::Stream_Play(HSTREAM stream, bool loop, int volume){return 0;} + +void CALL HGE_Impl::Channel_SetPanning(HCHANNEL chn, int pan) +{ + assert(pan >= -100); + assert(pan <= 100); + if(hOpenAL) + { + alSource3f((ALuint) chn, AL_POSITION, ((ALfloat) pan) / 100.0f, 0.0f, 0.0f); + } +} + +void CALL HGE_Impl::Channel_SetVolume(HCHANNEL chn, int volume) +{ + if(hOpenAL) + { + if (volume < 0) volume = 0; else if (volume > 100) volume = 100; + alSourcef((ALuint) chn, AL_GAIN, ((ALfloat) volume) / 100.0f); + } +} + +void CALL HGE_Impl::Channel_SetPitch(HCHANNEL chn, float pitch) +{ + if(hOpenAL) + { + alSourcef((ALuint) chn, AL_PITCH, pitch); + } +} + +void CALL HGE_Impl::Channel_Pause(HCHANNEL chn) +{ + if(hOpenAL) + { + alSourcePause((ALuint) chn); + } +} + +void CALL HGE_Impl::Channel_Resume(HCHANNEL chn) +{ + if(hOpenAL) + { + alSourcePlay((ALuint) chn); + } +} + +void CALL HGE_Impl::Channel_Stop(HCHANNEL chn) +{ + if(hOpenAL) + { + alSourceStop((ALuint) chn); + } +} + +void CALL HGE_Impl::Channel_PauseAll() +{ + if(hOpenAL) + { + ALCcontext *ctx = alcGetCurrentContext(); + alcSuspendContext(ctx); + } +} + +void CALL HGE_Impl::Channel_ResumeAll() +{ + if(hOpenAL) + { + ALCcontext *ctx = alcGetCurrentContext(); + alcProcessContext(ctx); + } +} + +void CALL HGE_Impl::Channel_StopAll() +{ + if(hOpenAL) + { + for (int i = 0; i < sidcount; i++) + alSourceStop(sids[i]); + } +} + +bool CALL HGE_Impl::Channel_IsPlaying(HCHANNEL chn) +{ + if(hOpenAL) + { + ALint state = AL_STOPPED; + alGetSourceiv((ALuint) chn, AL_SOURCE_STATE, &state); + return state == AL_PLAYING; + } + else return false; +} +//The following features are ported to OpenAL by Chris +float CALL HGE_Impl::Channel_GetLength(HCHANNEL chn) +//WARNING!!:In OpenAL We pass HEFFECT insteat HCHANNEL in! +//This should be fixed. +{ + //Well, you developers should know this "by heart". + if (hOpenAL) + { + ALint sizeInBytes; + ALint channels; + ALint bits; + ALuint bufferID=chn; + alGetBufferi(bufferID, AL_SIZE, &sizeInBytes); + alGetBufferi(bufferID, AL_CHANNELS, &channels); + alGetBufferi(bufferID, AL_BITS, &bits); + int lengthInSamples = sizeInBytes * 8 / (channels * bits); + ALint frequency; + alGetBufferi(bufferID, AL_FREQUENCY, &frequency); + float durationInSeconds = (float)lengthInSamples / (float)frequency; + return durationInSeconds; + } + return -1; +} + +float CALL HGE_Impl::Channel_GetPos(HCHANNEL chn) +{ + if (hOpenAL) + { + ALfloat res; + alGetSourcef((ALuint)chn,AL_SEC_OFFSET,&res); + return (float)res; + } + else return -1.0f; +} + +void CALL HGE_Impl::Channel_SetPos(HCHANNEL chn, float fSeconds) +{ + if (hOpenAL) + { + alSourcef((ALuint)chn,AL_SEC_OFFSET,(ALfloat)fSeconds); + } +} + +int CALL HGE_Impl::Channel_GetPos_BySample(HCHANNEL chn) +{ + if (hOpenAL) + { + ALint res; + alGetSourcei((ALuint)chn,AL_SAMPLE_OFFSET,&res); + return (int)res; + } + else return -1.0f; +} + +void CALL HGE_Impl::Channel_SetPos_BySample(HCHANNEL chn, int iSample) +{ + if (hOpenAL) + { + alSourcei((ALuint)chn,AL_SAMPLE_OFFSET,(ALint)iSample); + } +} + +void CALL HGE_Impl::Channel_SlideTo(HCHANNEL channel, float time, int volume, int pan, float pitch){} + +bool CALL HGE_Impl::Channel_IsSliding(HCHANNEL channel){return false;} + + +//////// Implementation //////// + + +bool HGE_Impl::_SoundInit() +{ + if(!bUseSound || hOpenAL) return true; + + bSilent=false; + + sidcount = 0; + memset(sids, '\0', sizeof (sids)); + + System_Log("%s: Starting OpenAL init",SOUND_SRC_FN); + + ALCdevice *dev = alcOpenDevice(NULL); + if (!dev) + { + System_Log("%s: alcOpenDevice(NULL) failed, using no sound",SOUND_SRC_FN); + bSilent=true; + return true; + } + + ALint caps[] = { ALC_FREQUENCY, nSampleRate, 0 }; + ALCcontext *ctx = alcCreateContext(dev, caps); + if (!ctx) + { + alcCloseDevice(dev); + System_Log("%s: alcCreateContext(NULL) failed, using no sound",SOUND_SRC_FN); + bSilent=true; + return true; + } + + alcMakeContextCurrent(ctx); + alcProcessContext(ctx); + + System_Log("%s: OpenAL initialized successfully.",SOUND_SRC_FN); + System_Log("%s: AL_VENDOR: %s",SOUND_SRC_FN, (char *) alGetString(AL_VENDOR)); + System_Log("%s: AL_RENDERER: %s",SOUND_SRC_FN, (char *) alGetString(AL_RENDERER)); + System_Log("%s: AL_VERSION: %s",SOUND_SRC_FN,(char *) alGetString(AL_VERSION)); + System_Log("%s: AL_EXTENSIONS: %s",SOUND_SRC_FN,(char *) alGetString(AL_EXTENSIONS)); + + hOpenAL = (void *) 0x1; // something non-NULL (!!! FIXME: this should eventually be a library handle). + + _SetFXVolume(nFXVolume); + //_SetMusVolume(nMusVolume); + //_SetStreamVolume(nStreamVolume); + + return true; +} + +void HGE_Impl::_SoundDone() +{ + CStreamList *stmItem=streams, *stmNext; + + if(hOpenAL) + { + for (int i = 0; i < sidcount; i++) + alSourceStop(sids[i]); + alDeleteSources(sidcount, sids); + sidcount = 0; + memset(sids, '\0', sizeof (sids)); + + ALCcontext *ctx = alcGetCurrentContext(); + ALCdevice *dev = alcGetContextsDevice(ctx); + alcMakeContextCurrent(NULL); + alcSuspendContext(ctx); + alcDestroyContext(ctx); + alcCloseDevice(dev); + + hOpenAL=0; + + while(stmItem) + { + stmNext=stmItem->next; + Resource_Free(stmItem->data); + delete stmItem; + stmItem=stmNext; + } + streams=0; + } +} + +void HGE_Impl::_SetMusVolume(int vol){} + +void HGE_Impl::_SetStreamVolume(int vol){} + +void HGE_Impl::_SetFXVolume(int vol) +{ + if(hOpenAL) + { + alListenerf(AL_GAIN, ((ALfloat) vol) / 100.0f); + } +} diff --git a/hge/sound_openal.cpp b/hge/sound_openal.cpp deleted file mode 100644 index 7aea7cf..0000000 --- a/hge/sound_openal.cpp +++ /dev/null @@ -1,531 +0,0 @@ -/* -** Haaf's Game Engine 1.8 -** Copyright (C) 2003-2007, Relish Games -** hge.relishgames.com -** -** Core functions implementation: audio routines -*/ - - -// This is just enough to get Hammerfight working without using libBA$$. -// If you want a full HGE audio implementation, you should either use the -// code in sound_libbass.cpp (and maybe pay for a BA$$ licen$e), or improve -// this code. -// Well, this code is now improved by Chris Xiong, adding several new interfaces. -// (Such as seeking in sample...) -// Channel functions are fully supported now. However music and streaming are -// still not supported. Some APIs changed for OpenAL is different from BA$$. - -#include "hge_impl.h" - -#include "AL/al.h" -#include "AL/alc.h" -#include "AL/alext.h" -#include "ogg/ogg.h" -#include "vorbis/vorbisfile.h" -static const char* SOUND_SRC_FN="hge/sound_openal.cpp"; -struct oggcbdata -{ - const BYTE *data; - DWORD size; - DWORD pos; -}; - -static size_t oggcb_read(void *ptr, size_t size, size_t nmemb, void *datasource) -{ - oggcbdata *data = (oggcbdata *) datasource; - const DWORD avail = data->size - data->pos; - size_t want = nmemb * size; - if (want > avail) - want = avail - (avail % size); - if (want > 0) - { - memcpy(ptr, data->data + data->pos, want); - data->pos += want; - } - return want / size; -} - -static int oggcb_seek(void *datasource, ogg_int64_t offset, int whence) -{ - oggcbdata *data = (oggcbdata *) datasource; - ogg_int64_t pos = 0; - switch (whence) - { - case SEEK_SET: pos = offset; break; - case SEEK_CUR: pos = ((ogg_int64_t) data->pos) + offset; break; - case SEEK_END: pos = ((ogg_int64_t) data->size) + offset; break; - default: return -1; - } - - if ( (pos < 0) || (pos > ((ogg_int64_t) data->size)) ) - return -1; - - data->pos = (DWORD) pos; - return 0; -} - -static int oggcb_close(void *datasource) -{ - return 0; -} - -static long oggcb_tell(void *datasource) -{ - oggcbdata *data = (oggcbdata *) datasource; - return (long) data->pos; -} - -static ov_callbacks oggcb = { oggcb_read, oggcb_seek, oggcb_close, oggcb_tell }; - -static void *decompress_vorbis(const BYTE *data, const DWORD size, ALsizei *decompressed_size, ALenum *fmt, ALsizei *freq) -{ -#ifdef __POWERPC__ - const int bigendian = 1; -#else - const int bigendian = 0; -#endif - - oggcbdata cbdata = { data, size, 0 }; - OggVorbis_File vf; - memset(&vf, '\0', sizeof (vf)); - if (ov_open_callbacks(&cbdata, &vf, NULL, 0, oggcb) == 0) - { - int bitstream = 0; - vorbis_info *info = ov_info(&vf, -1); - - *decompressed_size = 0; - *fmt = (info->channels == 1) ? AL_FORMAT_MONO16 : AL_FORMAT_STEREO16; - *freq = info->rate; - - if ((info->channels != 1) && (info->channels != 2)) - { - ov_clear(&vf); - return NULL; - } - - char buf[1024 * 16]; - long rc = 0; - size_t allocated = 64 * 1024; - BYTE *retval = (ALubyte *) malloc(allocated); - while ( (rc = ov_read(&vf, buf, sizeof (buf), bigendian, 2, 1, &bitstream)) != 0 ) - { - if (rc > 0) - { - *decompressed_size += rc; - if (*decompressed_size >= allocated) - { - allocated *= 2; - ALubyte *tmp = (ALubyte *) realloc(retval, allocated); - if (tmp == NULL) - { - free(retval); - retval = NULL; - break; - } - retval = tmp; - } - memcpy(retval + (*decompressed_size - rc), buf, rc); - } - } - ov_clear(&vf); - return retval; - } - - return NULL; -} - -#define MAX_SIDS 128 -static int sidcount = 0; -static ALuint sids[MAX_SIDS]; - -static ALuint get_source() -{ - for (int i = 0; i < sidcount; i++) - { - ALint state = AL_PLAYING; - alGetSourceiv(sids[i], AL_SOURCE_STATE, &state); - if ((state != AL_PLAYING) && (state != AL_PAUSED)) - return sids[i]; - } - if (sidcount >= MAX_SIDS) - return 0; - - ALuint sid = 0; - alGenSources(1, &sid); - if (sid == 0) - return 0; - sids[sidcount++] = sid; - return sid; -} - - -HEFFECT CALL HGE_Impl::Effect_Load(const char *filename, DWORD size) -{ - DWORD _size, length, samples; - void *data; - - if(hOpenAL) - { - if(bSilent) return 1; - - if(size) { data=(void *)filename; _size=size; } - else - { - data=Resource_Load(filename, &_size); - if(!data) return 0; - } - - const BYTE *magic = (const BYTE *) data; - const bool isOgg = ( (_size > 4) && - (magic[0] == 'O') && (magic[1] == 'g') && - (magic[2] == 'g') && (magic[3] == 'S') ); - if (!isOgg) - { - if(!size) Resource_Free(data); - return 0; - } - void *allocation_decompressed = NULL; - void *decompressed = NULL; - ALsizei decompressed_size = 0; - ALsizei freq = 0; - ALenum fmt = AL_FORMAT_STEREO16; - if (isOgg) - { - if (alIsExtensionPresent((const ALchar *) "AL_EXT_vorbis")) - { - fmt = alGetEnumValue((const ALchar *) "AL_FORMAT_VORBIS_EXT"); - decompressed = data; - decompressed_size = _size; - } - else - { - allocation_decompressed = decompress_vorbis((const BYTE *) data, _size, &decompressed_size, &fmt, &freq); - decompressed = allocation_decompressed; - } - } - - ALuint bid = 0; - alGenBuffers(1, &bid); - alBufferData(bid, fmt, decompressed, decompressed_size, freq); - free(allocation_decompressed); // not delete[] ! - if(!size) Resource_Free(data); - return (HEFFECT) bid; - } - else return 0; -} - -HCHANNEL CALL HGE_Impl::Effect_Play(HEFFECT eff) -{ - return Effect_PlayEx(eff, 100, 0, 1.0f, false); -} - -HCHANNEL CALL HGE_Impl::Effect_PlayEx(HEFFECT eff, int volume, int pan, float pitch, bool loop) -{ - if(hOpenAL) - { - const ALuint sid = get_source(); // find an unused sid, or generate a new one. - if (sid != 0) - { - if (volume < 0) volume = 0; else if (volume > 100) volume = 100; - if (pan < -100) pan = -100; else if (pan > 100) pan = 100; - alSourceStop(sid); - alSourcei(sid, AL_BUFFER, (ALint) eff); - alSourcef(sid, AL_GAIN, ((ALfloat) volume) / 100.0f); - alSourcef(sid, AL_PITCH, pitch); - alSource3f(sid, AL_POSITION, ((ALfloat) pan) / 100.0f, 0.0f, 0.0f); - alSourcei(sid, AL_LOOPING, loop ? AL_TRUE : AL_FALSE); - alSourcePlay(sid); - } - return sid; - } - else return 0; -} - -void CALL HGE_Impl::Effect_Free(HEFFECT eff) -{ - if(hOpenAL) - { - ALuint bid = (ALuint) eff; - alDeleteBuffers(1, &bid); - } -} -//Castrate!! -HMUSIC CALL HGE_Impl::Music_Load(const char *filename, DWORD size){return 0;} - -HCHANNEL CALL HGE_Impl::Music_Play(HMUSIC mus, bool loop, int volume, int order, int row){return 0;} - -void CALL HGE_Impl::Music_Free(HMUSIC mus){} - -void CALL HGE_Impl::Music_SetAmplification(HMUSIC music, int ampl){} - -int CALL HGE_Impl::Music_GetAmplification(HMUSIC music){return -1;} - -int CALL HGE_Impl::Music_GetLength(HMUSIC music){return -1;} - -void CALL HGE_Impl::Music_SetPos(HMUSIC music, int order, int row){} - -bool CALL HGE_Impl::Music_GetPos(HMUSIC music, int *order, int *row){return false;} - -void CALL HGE_Impl::Music_SetInstrVolume(HMUSIC music, int instr, int volume){} - -int CALL HGE_Impl::Music_GetInstrVolume(HMUSIC music, int instr){return -1;} - -void CALL HGE_Impl::Music_SetChannelVolume(HMUSIC music, int channel, int volume){} - -int CALL HGE_Impl::Music_GetChannelVolume(HMUSIC music, int channel){return -1;} - -HSTREAM CALL HGE_Impl::Stream_Load(const char *filename, DWORD size){return 0;} - -void CALL HGE_Impl::Stream_Free(HSTREAM stream){} - -HCHANNEL CALL HGE_Impl::Stream_Play(HSTREAM stream, bool loop, int volume){return 0;} - -void CALL HGE_Impl::Channel_SetPanning(HCHANNEL chn, int pan) -{ - assert(pan >= -100); - assert(pan <= 100); - if(hOpenAL) - { - alSource3f((ALuint) chn, AL_POSITION, ((ALfloat) pan) / 100.0f, 0.0f, 0.0f); - } -} - -void CALL HGE_Impl::Channel_SetVolume(HCHANNEL chn, int volume) -{ - if(hOpenAL) - { - if (volume < 0) volume = 0; else if (volume > 100) volume = 100; - alSourcef((ALuint) chn, AL_GAIN, ((ALfloat) volume) / 100.0f); - } -} - -void CALL HGE_Impl::Channel_SetPitch(HCHANNEL chn, float pitch) -{ - if(hOpenAL) - { - alSourcef((ALuint) chn, AL_PITCH, pitch); - } -} - -void CALL HGE_Impl::Channel_Pause(HCHANNEL chn) -{ - if(hOpenAL) - { - alSourcePause((ALuint) chn); - } -} - -void CALL HGE_Impl::Channel_Resume(HCHANNEL chn) -{ - if(hOpenAL) - { - alSourcePlay((ALuint) chn); - } -} - -void CALL HGE_Impl::Channel_Stop(HCHANNEL chn) -{ - if(hOpenAL) - { - alSourceStop((ALuint) chn); - } -} - -void CALL HGE_Impl::Channel_PauseAll() -{ - if(hOpenAL) - { - ALCcontext *ctx = alcGetCurrentContext(); - alcSuspendContext(ctx); - } -} - -void CALL HGE_Impl::Channel_ResumeAll() -{ - if(hOpenAL) - { - ALCcontext *ctx = alcGetCurrentContext(); - alcProcessContext(ctx); - } -} - -void CALL HGE_Impl::Channel_StopAll() -{ - if(hOpenAL) - { - for (int i = 0; i < sidcount; i++) - alSourceStop(sids[i]); - } -} - -bool CALL HGE_Impl::Channel_IsPlaying(HCHANNEL chn) -{ - if(hOpenAL) - { - ALint state = AL_STOPPED; - alGetSourceiv((ALuint) chn, AL_SOURCE_STATE, &state); - return state == AL_PLAYING; - } - else return false; -} - -float CALL HGE_Impl::Channel_GetLength(HCHANNEL chn) -//WARNING!!:In OpenAL We pass HEFFECT insteat HCHANNEL in! -//This should be fixed. -{ - //Well, you developers should know this "by heart". - if (hOpenAL) - { - ALint sizeInBytes; - ALint channels; - ALint bits; - ALuint bufferID=chn; - alGetBufferi(bufferID, AL_SIZE, &sizeInBytes); - alGetBufferi(bufferID, AL_CHANNELS, &channels); - alGetBufferi(bufferID, AL_BITS, &bits); - int lengthInSamples = sizeInBytes * 8 / (channels * bits); - ALint frequency; - alGetBufferi(bufferID, AL_FREQUENCY, &frequency); - float durationInSeconds = (float)lengthInSamples / (float)frequency; - return durationInSeconds; - } - return -1; -} - -float CALL HGE_Impl::Channel_GetPos(HCHANNEL chn) -{ - if (hOpenAL) - { - ALfloat res; - alGetSourcef((ALuint)chn,AL_SEC_OFFSET,&res); - return (float)res; - } - else return -1.0f; -} - -void CALL HGE_Impl::Channel_SetPos(HCHANNEL chn, float fSeconds) -{ - if (hOpenAL) - { - alSourcef((ALuint)chn,AL_SEC_OFFSET,(ALfloat)fSeconds); - } -} - -int CALL HGE_Impl::Channel_GetPos_BySample(HCHANNEL chn) -{ - if (hOpenAL) - { - ALint res; - alGetSourcei((ALuint)chn,AL_SAMPLE_OFFSET,&res); - return (int)res; - } - else return -1.0f; -} - -void CALL HGE_Impl::Channel_SetPos_BySample(HCHANNEL chn, int iSample) -{ - if (hOpenAL) - { - alSourcei((ALuint)chn,AL_SAMPLE_OFFSET,(ALint)iSample); - } -} - -void CALL HGE_Impl::Channel_SlideTo(HCHANNEL channel, float time, int volume, int pan, float pitch){} - -bool CALL HGE_Impl::Channel_IsSliding(HCHANNEL channel){return false;} - - -//////// Implementation //////// - - -bool HGE_Impl::_SoundInit() -{ - if(!bUseSound || hOpenAL) return true; - - bSilent=false; - - sidcount = 0; - memset(sids, '\0', sizeof (sids)); - - System_Log("%s: Starting OpenAL init",SOUND_SRC_FN); - - ALCdevice *dev = alcOpenDevice(NULL); - if (!dev) - { - System_Log("%s: alcOpenDevice(NULL) failed, using no sound",SOUND_SRC_FN); - bSilent=true; - return true; - } - - ALint caps[] = { ALC_FREQUENCY, nSampleRate, 0 }; - ALCcontext *ctx = alcCreateContext(dev, caps); - if (!ctx) - { - alcCloseDevice(dev); - System_Log("%s: alcCreateContext(NULL) failed, using no sound",SOUND_SRC_FN); - bSilent=true; - return true; - } - - alcMakeContextCurrent(ctx); - alcProcessContext(ctx); - - System_Log("%s: OpenAL initialized successfully.",SOUND_SRC_FN); - System_Log("%s: AL_VENDOR: %s",SOUND_SRC_FN, (char *) alGetString(AL_VENDOR)); - System_Log("%s: AL_RENDERER: %s",SOUND_SRC_FN, (char *) alGetString(AL_RENDERER)); - System_Log("%s: AL_VERSION: %s",SOUND_SRC_FN,(char *) alGetString(AL_VERSION)); - System_Log("%s: AL_EXTENSIONS: %s",SOUND_SRC_FN,(char *) alGetString(AL_EXTENSIONS)); - - hOpenAL = (void *) 0x1; // something non-NULL (!!! FIXME: this should eventually be a library handle). - - _SetFXVolume(nFXVolume); - //_SetMusVolume(nMusVolume); - //_SetStreamVolume(nStreamVolume); - - return true; -} - -void HGE_Impl::_SoundDone() -{ - CStreamList *stmItem=streams, *stmNext; - - if(hOpenAL) - { - for (int i = 0; i < sidcount; i++) - alSourceStop(sids[i]); - alDeleteSources(sidcount, sids); - sidcount = 0; - memset(sids, '\0', sizeof (sids)); - - ALCcontext *ctx = alcGetCurrentContext(); - ALCdevice *dev = alcGetContextsDevice(ctx); - alcMakeContextCurrent(NULL); - alcSuspendContext(ctx); - alcDestroyContext(ctx); - alcCloseDevice(dev); - - hOpenAL=0; - - while(stmItem) - { - stmNext=stmItem->next; - Resource_Free(stmItem->data); - delete stmItem; - stmItem=stmNext; - } - streams=0; - } -} - -void HGE_Impl::_SetMusVolume(int vol){} - -void HGE_Impl::_SetStreamVolume(int vol){} - -void HGE_Impl::_SetFXVolume(int vol) -{ - if(hOpenAL) - { - alListenerf(AL_GAIN, ((ALfloat) vol) / 100.0f); - } -} diff --git a/levels.h b/levels.h index 12fe52e..17de738 100644 --- a/levels.h +++ b/levels.h @@ -1194,6 +1194,9 @@ void Level5Part2() } int pos,lsrbrk; bool rev; +/**********************\ + * Vortex of Leaves * +\**********************/ void Level5Part3() { frameleft=AMinute; @@ -2546,39 +2549,39 @@ void Level7Part4() } } } -BulletnLaser bnl[100];//Yukari... +BulletSine bnl[100];//Yukari... double ykbrk; void Level7Part5()//This should be another part. { memset(bnl,0,sizeof(bnl)); frameleft=AMinute; - ykbrk=1.0f;++part; + ykbrk=1.1f;++part; } void Level7Part6() { ykbrk-=hge->Timer_GetDelta(); if (ykbrk<0) { - ykbrk=1.0f; + ykbrk=(double)frameleft/AMinute+0.1; for (int i=0;i<100;++i) if (!bnl[i].active) { vector2d a,b; if (rand()%100>49) { - if (rand()%100>49)a=vector2d(rand()%780+10,590);else a=vector2d(rand()%780+10,10); + if (rand()%100>49)a=vector2d(rand()%780+10,610);else a=vector2d(rand()%780+10,-10); } else { - if (rand()%100>49)a=vector2d(10,rand()%580+10);else a=vector2d(790,rand()%580+10); + if (rand()%100>49)a=vector2d(-10,rand()%580+10);else a=vector2d(810,rand()%580+10); } if (rand()%100>49) { - if (rand()%100>49)b=vector2d(rand()%780+10,590);else b=vector2d(rand()%780+10,10); + if (rand()%100>49)b=vector2d(rand()%780+10,610);else b=vector2d(rand()%780+10,-10); } else { - if (rand()%100>49)b=vector2d(10,rand()%580+10);else b=vector2d(790,rand()%580+10); + if (rand()%100>49)b=vector2d(-10,rand()%580+10);else b=vector2d(810,rand()%580+10); } bnl[i].Init(a,b); break; diff --git a/main.cpp b/main.cpp index 89f8046..459f060 100644 --- a/main.cpp +++ b/main.cpp @@ -439,6 +439,7 @@ void CallLevels() if (level==3&&part==7)level=4,part=0; if (level==4&&part==26)level=5,part=0; if (level==5&&part==23)level=6,part=0; + if (level==6&&part==32)level=7,part=0; } bool ProcessCurCred() { @@ -771,7 +772,7 @@ int main() if(hge->System_Initiate()) { //nonamecnt=1; - quad.tex=hge->Texture_Load("./Resources/bg.png"); + quad.tex=hge->Texture_Load("./Resources/b_null.png"); SprSheet=hge->Texture_Load("./Resources/ss.png"); TLeaf=hge->Texture_Load("./Resources/e_leaf.png"); TSflake=hge->Texture_Load("./Resources/e_sflake.png"); diff --git a/menus.h b/menus.h index 953b03f..f5aa36c 100644 --- a/menus.h +++ b/menus.h @@ -94,8 +94,8 @@ void StartGUI_FrameFnk() frameleft=ThirtySeconds;infofade=0xFF;Dis8ref=false; level=1,part=1;frms=0,averfps=0.0;bsscale=1; towcnt=bulcnt=0;whrcnt=12; - score=0;Mult_Init();Music_Init("./Resources/Music/CanonTechno.ogg"); - lpst=4625568;lped=9234584;Music_Play(); + score=0;Mult_Init();//Music_Init("./Resources/Music/CanonTechno.ogg"); + lpst=4625568;lped=9234584;//Music_Play(); coll=semicoll=clrusg=0;playerLockX=playerLockY=false; Lock.Init(2); //Lock.SetTexture(SprSheet,151,264,2,8); diff --git a/towernbullet.h b/towernbullet.h index b38442f..b13bf1b 100644 --- a/towernbullet.h +++ b/towernbullet.h @@ -2,9 +2,10 @@ //Towers and Bullets Implementations //"Copyleft" Chrisoft 2013 //WANTED: -//Human-being which really knows what these mean, please contact Chirsno which is puzzled by these shitty codes.. +//Human-being who really knows what these mean, please contact Chirsno which is puzzled by these shitty codes.. //[Perfect Freeze]: code here for BLR2 won't change a lot since 30/08/2013 -//If you are expecting new code, please wait the full rewrite in BLR3... +//Sorry that I would break that... +//I found the rendering code stupid so I MUST rewrite it NOW. // --Announcement from Chirsno #include "effects.h" static const char* TOWERNBULLET_H_FN="towernbullet.h"; @@ -354,15 +355,18 @@ void ProcessBullet2(int i) if (LOWFPS) { if (bullet[i].bulletspeedTimer_GetFPS()); + bullet[i].bulletpos.y-=bsscale*bullet[i].bulletspeed*(bullet[i].bulletdir.y)/20*(1000.0f/hge->Timer_GetFPS()); } BulletEffect_Process(i); double dis=GetDist(bullet[i].bulletpos,playerpos);//Get distance between player and bullet @@ -1491,10 +1495,12 @@ public: box.x1=box.x2=data1[i].x+RenCtr.x,box.y1=box.y2=data1[i].y+RenCtr.y; //box.Encapsulate(data1[i].x+RenCtr.x,data1[i].y+RenCtr.y); box.Encapsulate(data1[i+1].x+RenCtr.x,data1[i+1].y+RenCtr.y); + box.Encapsulate(data2[i].x+RenCtr.x,data2[i].y+RenCtr.y); + box.Encapsulate(data2[i+1].x+RenCtr.x,data2[i+1].y+RenCtr.y); { //Debugging collision box hgeSprite colbox=*(new hgeSprite(0,0,0,0,0)); - colbox.SetColor(0x0FFFFFFF); + colbox.SetColor(0x20FFFFFF); colbox.RenderStretch(box.x1,box.y1,box.x2,box.y2); } if (box.TestPoint(playerpos.x,playerpos.y)) @@ -1571,12 +1577,14 @@ void ProcessBullet2(Bullet &xbul) if (xbul.bulletspeedTimer_GetFPS()); + xbul.bulletpos.y-=xbul.bulletspeed*(xbul.bulletdir.y/xbul.dist)/20*(1000.0f/hge->Timer_GetFPS()); double dis=GetDist(xbul.bulletpos,playerpos); /*if (xbul.bulletpos.x<=-100||xbul.bulletpos.x>=900||xbul.bulletpos.y<=-100||xbul.bulletpos.y>=700) { @@ -1849,41 +1857,48 @@ public: } } }; -class BulletnLaser +class BulletSine { private: - Laser line; Bullet headb; - vector2d a,b; - double lifetime; + vector2d a,b,lastgenerated; + double theta; + Bullet* generated[400]; + int gencnt; + bool OutOfBound() + { + if (headb.bulletpos.x<=-25||headb.bulletpos.x>=825||headb.bulletpos.y<=-25||headb.bulletpos.y>=625) + return true;return false; + } public: bool active; void Init(vector2d _a,vector2d _b) { - a=_a;b=_b; - line.Init(); - line.SetTexture(SprSheet,0,264,248,8); - line.RenCtr.x=line.RenCtr.y=0; - line.EnableColl=false; - CreateBullet2(headb,a.x,b.x,6,0); + a=_a;b=_b;lastgenerated=_a; + CreateBullet2(headb,a.x,a.y,6,0); headb.redir(b); - double theta=(a.y-b.y,a.x-b.x); - vector2d a2=vector2d(a.x+4*sin(theta),a.y+4*cos(theta)); - vector2d b2=vector2d(b.x+4*sin(theta),b.y+4*cos(theta)); - //line.InsPoint(a,a2,0xCC33CCFF); - //while(line.InsPoint(b,b2,0xCC33CCFF)); - line.SetRes(3); - line.Setdata(0,a,a2,0xCC33CCFF); - for (int i=1;i<80;++i)line.Setdata(i,b,b2,0xCC33CCFF); - active=true; - lifetime=0; + theta=(a.y-b.y,a.x-b.x); + active=true;memset(generated,0,sizeof(generated)); + gencnt=0; } void Update() { - lifetime+=hge->Timer_GetDelta(); - if (lifetime>1.0&&!line.EnableColl)line.EnableColl=true; - if (lifetime>4.0&&line.EnableColl)line.EnableColl=false; - if (lifetime>4.5)active=false; - ProcessBullet2(headb);line.Process(); + if (GetDist(lastgenerated,headb.bulletpos)>4.0f) + { + ++gencnt; + double rad=(gencnt&1)?(gencnt+1)/2*pi/18.0f:-gencnt/2*pi/18.0f; + generated[gencnt]=&bullet[CreateBullet2(headb.bulletpos.x,headb.bulletpos.y,0,rad,true)]; + lastgenerated=headb.bulletpos; + } + if (OutOfBound()) + { + active=false; + //Release them! + for (int i=1;i<=gencnt;++i) + if (generated[i])//explosion prevention + generated[i]->bulletaccel=0.005,generated[i]->limv=2; + memset(generated,0,sizeof(generated));//therefore we won't touch those fucking things accidently + } + ProcessBullet2(headb); } }; -- cgit v1.2.3