isohex9_1.cpp

来自「一個遊戲教程」· C++ 代码 · 共 888 行 · 第 1/2 页

CPP
888
字号
	lpdsb[6][0]=LPDSB_LoadFromFile(lpds,"hit1.wav",0);
	lpdsb[7][0]=LPDSB_LoadFromFile(lpds,"hit0.wav",0);
	lpdsb[8][0]=LPDSB_LoadFromFile(lpds,"win.wav",0);

	//load music
	lpdsbMusic=LPDSB_LoadFromFile(lpds,"music.wav",0);

	//load vox
	lpdsbOoYeah=LPDSB_LoadFromFile(lpds,"ooyeah.wav",0);
	lpdsbGroovy=LPDSB_LoadFromFile(lpds,"groovy.wav",0);
	lpdsbLoveThing=LPDSB_LoadFromFile(lpds,"lovething.wav",0);
	
	//duplicate sounds
	for(int copy=1;copy<SOUNDCOPYCOUNT;copy++)
	{
		for(int sound=0;sound<SOUNDCOUNT;sound++)
		{
			lpds->DuplicateSoundBuffer(lpdsb[sound][0],&lpdsb[sound][copy]);
		}
	}

	//start music
	lpdsbMusic->Play(0,0,DSBPLAY_LOOPING);
}

//clean up directdraw vars
void DD_Done()
{
	//release surfaces
	LPDDS_Release(&lpddspaddle);
	LPDDS_Release(&lpddsbricks);
	LPDDS_Release(&lpddsball);
	LPDDS_Release(&lpddsprime);

	//release direct draw object
	LPDD_Release(&lpdd);

	//delete the font
	DeleteObject(hfntMain);

	//remove font resource
	RemoveFontResource("Paganini.ttf");
}

//clean up directsound vars
void DS_Done()
{
	//release all sounds and copies of sounds
	for(int copy=0;copy<SOUNDCOPYCOUNT;copy++)
	{
		for(int sound=0;sound<SOUNDCOUNT;sound++)
		{
			LPDSB_Release(&lpdsb[sound][copy]);
		}
	}

	//release music
	LPDSB_Release(&lpdsbMusic);

	//release vox
	LPDSB_Release(&lpdsbOoYeah);
	LPDSB_Release(&lpdsbLoveThing);
	LPDSB_Release(&lpdsbGroovy);

	//release directsound object
	if(lpds)
	{
		lpds->Release();
		lpds=NULL;
	}
}

void SetUpGame()
{
	//reinitialize brick count

	//loop through every board location
	for(int x=0;x<MAPCOLUMNCOUNT;x++)
	{
		for(int y=0;y<MAPROWCOUNT;y++)
		{
			//set the brick
			Board[x][y]=y/(MAPROWCOUNT/BRICKCOUNT);
			dwBrickCount++;
		}
	}
	//paddle position
	ptPaddle.x=SCREENWIDTH/2-PADDLEWIDTH/2;
	ptPaddle.y=SCREENHEIGHT-PADDLEHEIGHT;

	//ball position and speed
	ptBall.x=SCREENWIDTH/2-BALLWIDTH/2;
	ptBall.y=300;
	ptBallNext=ptBall;
	ptBallVel.x=3;
	ptBallVel.y=3;
	bHitTop=false;
}

//reset game after a death
void ResetGame()
{
	//ball position and speed
	ptBall.x=SCREENWIDTH/2-BALLWIDTH/2;
	ptBall.y=300;
	ptBallNext=ptBall;
	ptBallVel.x=3;
	ptBallVel.y=3;
	bHitTop=false;
}


void ShowBoard()
{
	//clear out back buffer
	DDBLTFX ddbltfx;
	DDBLTFX_ColorFill(&ddbltfx,0);
	lpddsback->Blt(NULL,NULL,NULL,DDBLT_WAIT | DDBLT_COLORFILL, &ddbltfx);

	//loop through every board location
	for(int x=0;x<MAPCOLUMNCOUNT;x++)
	{
		for(int y=0;y<MAPROWCOUNT;y++)
		{
			//draw the brick
			if(Board[x][y]!=-1) DrawBrick(x*BRICKWIDTH,y*BRICKHEIGHT+MAPOFFSET,Board[x][y]);
		}
	}

	//draw the paddle
	DrawPaddle();

	//draw the ball
	DrawBall();

	//show the score
	ShowScore();

	//show number of lives left
	ShowLives();
}

void DrawBrick(int x, int y, int bricknum)
{
	//source and destination rectangles
	RECT rcDst;
	RECT rcSrc;

	//set source rectangle
	SetRect(&rcSrc,0,BRICKHEIGHT*bricknum,BRICKWIDTH,BRICKHEIGHT*bricknum+BRICKHEIGHT);

	//set destination rectangle
	CopyRect(&rcDst,&rcSrc);
	OffsetRect(&rcDst,x-rcDst.left,y-rcDst.top);

	//blit the brick
	lpddsback->Blt(&rcDst,lpddsbricks,&rcSrc,DDBLT_WAIT,NULL);
}

void DrawPaddle()
{
	//set up source rect
	RECT rcSrc;
	SetRect(&rcSrc,0,0,PADDLEWIDTH,PADDLEHEIGHT);

	//set up dest rect
	RECT rcDst;
	CopyRect(&rcDst,&rcSrc);
	OffsetRect(&rcDst,ptPaddle.x,ptPaddle.y);

	//blit
	lpddsback->Blt(&rcDst,lpddspaddle,&rcSrc,DDBLT_WAIT,NULL);
}

void DrawBall()
{
	//declare rects
	RECT rcSrc;
	RECT rcDst;

	//set up source rect
	SetRect(&rcSrc,0,0,BALLWIDTH,BALLHEIGHT);

	//set up dest rect
	CopyRect(&rcDst,&rcSrc);
	OffsetRect(&rcDst,ptBall.x,ptBall.y);

	//blit
	lpddsback->Blt(&rcDst,lpddsball,&rcSrc,DDBLT_WAIT | DDBLT_KEYSRC,NULL);
}

void MoveBall()
{
	//determine next position of ball
	ptBallNext.x=ptBall.x+ptBallVel.x*(bHitTop?2:1);
	ptBallNext.y=ptBall.y+ptBallVel.y*(bHitTop?2:1);

	//bounds checking
	if(ptBallNext.y<=0)
	{
		bHitTop=true;
		ptBallNext.y=0;
		ptBallVel.y=abs(ptBallVel.y);
		SoundPlay(SND_BOUNCE);
	}
	if(ptBallNext.x<=0)
	{
		ptBallNext.x=0;
		ptBallVel.x=abs(ptBallVel.x);
		SoundPlay(SND_BOUNCE);
	}
	if(ptBallNext.y>=(SCREENHEIGHT-BALLHEIGHT))
	{
		ptBallNext.y=SCREENHEIGHT-BALLHEIGHT;
		ptBallVel.y=-abs(ptBallVel.y);
		SoundPlay(SND_LOSE);
		GameState=GS_DEAD;
	}
	if(ptBallNext.x>=(SCREENWIDTH-BALLWIDTH))
	{
		ptBallNext.x=SCREENWIDTH-BALLWIDTH;
		ptBallVel.x=-abs(ptBallVel.x);
		SoundPlay(SND_BOUNCE);
	}

	//collision test
	int x;
	int y;
	bool hit=false;
	RECT rcBall;
	RECT rcBrick;
	RECT rcIntersect;

	//bounding box for ball
	SetRect(&rcBall,ptBallNext.x,ptBallNext.y,ptBallNext.x+BALLWIDTH,ptBallNext.y+BALLHEIGHT);

	for(x=0;x<MAPCOLUMNCOUNT;x++)
	{
		for(y=0;y<MAPROWCOUNT;y++)
		{
			if(Board[x][y]!=-1)
			{
				//bounding rectangle
				SetRect(&rcBrick,x*BRICKWIDTH,y*BRICKHEIGHT+MAPOFFSET,x*BRICKWIDTH+BRICKWIDTH,y*BRICKHEIGHT+MAPOFFSET+BRICKHEIGHT);

				//check for collision
				IntersectRect(&rcIntersect,&rcBall,&rcBrick);

				//if collision detected
				if(!IsRectEmpty(&rcIntersect))
				{
					//play hit sound
					SoundPlay(Board[x][y]+SND_HIT);

					//add to scroe
					dwScore+=(6-Board[x][y]);

					//decrease brick count
					dwBrickCount--;

					//if no bricks remaining
					if(dwBrickCount==0)
					{
						SoundPlay(SND_WIN);
						GameState=GS_WINLEVEL;
					}

					//delete brick
					Board[x][y]=-1;

					//set hit flag
					hit=true;

					//increment bricks hit
					dwBricksHit++;

					if(dwBricksHit==10)
					{
					//depending on number hit, play sound
					switch(rand()%3)
					{
					case 0:
						{
							lpdsbOoYeah->Play(0,0,0);
						}break;
					case 1:
						{
							lpdsbGroovy->Play(0,0,0);
						}break;
					case 2:
						{
							lpdsbLoveThing->Play(0,0,0);
						}break;
					}
					}
				}
			}
		}
	}

	//if the hit flag was set
	if(hit)
	{
		//bounce the ball
		ptBallVel.y=-ptBallVel.y;
	}

	//check for paddle collision
	if(ptBallVel.y>0)
	{
		//paddle bounding rect
		SetRect(&rcBrick,ptPaddle.x,ptPaddle.y,ptPaddle.x+PADDLEWIDTH,ptPaddle.y+PADDLEHEIGHT);

		//check for collision
		IntersectRect(&rcIntersect,&rcBrick,&rcBall);

		//if collision detected
		if(!IsRectEmpty(&rcIntersect))
		{
			//reset the brick hit
			dwBricksHit=0;

			//calculate which part of paddle was hit
			x=ptBallNext.x+BALLWIDTH/2-ptPaddle.x;
			if(x<0) x=0;
			if(x>PADDLEWIDTH) x=PADDLEWIDTH-1;
			x/=8;

			//set velocites depending on section hit
			switch(x)
			{
			case 0:
				{
					ptBallVel.x=-4;
					ptBallVel.y=-2;
				}break;
			case 1:
				{
					ptBallVel.x=-3;
					ptBallVel.y=-3;
				}break;
			case 2:
				{
					ptBallVel.x=-2;
					ptBallVel.y=-4;
				}break;
			case 3:
				{
					ptBallVel.x=-1;
					ptBallVel.y=-4;
				}break;
			case 4:
				{
					ptBallVel.x=1;
					ptBallVel.y=-4;
				}break;
			case 5:
				{
					ptBallVel.x=2;
					ptBallVel.y=-4;
				}break;
			case 6:
				{
					ptBallVel.x=3;
					ptBallVel.y=-3;
				}break;
			case 7:
				{
					ptBallVel.x=4;
					ptBallVel.y=-2;
				}break;
			}
			SoundPlay(SND_BOUNCE);
		}
	}

	//update ball position
	ptBall=ptBallNext;
}

void SoundPlay(int sound)
{
	//increment the sound copy
	dwSoundCopy[sound]++;

	//make sure copy number is in range
	dwSoundCopy[sound]%=SOUNDCOPYCOUNT;

	//play sound
	lpdsb[sound][dwSoundCopy[sound]]->Play(0,0,0);
}

void ShowScore()
{
	//buffer for converting from DWORD to string
	char Buf[20];
	memset(Buf,0,20);

	//convert
	itoa(dwScore,Buf,10);

	//set up rectangle
	RECT rcText;
	SetRect(&rcText,0,0,SCREENWIDTH,60);

	//grab dc from back buffer
	HDC hdc;
	lpddsback->GetDC(&hdc);

	//set font, color, and background mode
	SelectObject(hdc,hfntMain);
	SetTextColor(hdc,RGB(255,255,255));
	SetBkMode(hdc,TRANSPARENT);

	//draw the text
	DrawText(hdc,Buf,strlen(Buf),&rcText,DT_RIGHT | DT_TOP | DT_SINGLELINE);

	//relese dc to back buffer
	lpddsback->ReleaseDC(hdc);
}

void ShowLives()
{
	//source and dest rect
	RECT rcSrc;
	RECT rcDst;

	//set up source rect
	SetRect(&rcSrc,0,0,BALLWIDTH,BALLHEIGHT);
	SetRect(&rcDst,0,0,BALLWIDTH,BALLHEIGHT);

	//show one ball for each life at upper left of screen
	for(int count=0;count<(int)dwLives;count++)
	{
		//move dest rect to right
		OffsetRect(&rcDst,count*BALLWIDTH,0);

		//blit
		lpddsback->Blt(&rcDst,lpddsball,&rcSrc,DDBLT_WAIT | DDBLT_KEYSRC,NULL);

		//move dest rect back to left
		OffsetRect(&rcDst,-count*BALLWIDTH,0);
	}
}

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?