⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 cgame.cpp

📁 一个个人开发的rpg游戏<亚特兰蒂斯传奇>的源码
💻 CPP
📖 第 1 页 / 共 5 页
字号:
//--------------------------------------------------------------------------------------------------------
//                        游戏主引擎模块
//CGame.cpp
//游戏引擎中的主引擎部分
//作者:吴振华(kylinx)(中国科大01级11系)
//E-mail:game-diy@163.com
//创建于:2003/6/19 by Kylinx
//最后修改于2003/7/28 by Kylinx
//--------------------------------------------------------------------------------------------------------
#include<time.h>
#include<stdio.h>
#include"CGame.h"
#include"CError.h"
#include"CGoods.h"
#include"CBattle.h"
#include"CGameData.h"
#include"CGraph.h"
#include"CMagic.h"
#include"CMessage.h"
#include"CMap.h"
#include"CButton.h"
#include"CTalk.h"
#include"CScript.h"
#include"CMenu.h"
#include"CMessageBox.h"
#include"CIniFile.h"
#include"CFont.h"
#include"CRenderPicture.h"
#include"CMacro.h"
#include"CBuyAndSell.h"
#include"CCursor.h"
#include"LoaMapEditor\\resource.h"

char CGame::s_szCurrentDir[1024];
////////////////////////////////////////////////////////////////////////////////////////////
//构造
////////////////////////////////////////////////////////////////////////////////////////////
CGame::CGame()
{
	memset(this,0,sizeof(CGame));
	m_bIsNight=false;
	m_pdbMagic=NULL;
	m_pdbGoods=NULL;
	m_pGameData=NULL;
	m_pDisplay=NULL;
	m_pPlayer=NULL;
	m_bShowFPS=false;
	m_bRandomBattle=false;
	m_bDitherScreen=false;
	m_bScriptControlling=true;
	m_nBattleFrequency=5;
	memset(s_szCurrentDir,0,1024);
	::GetCurrentDirectory(1024,s_szCurrentDir);

	m_pLog=new CLog("GameLog.txt");
	srand(time(0));
}
////////////////////////////////////////////////////////////////////////////////////////////
//析构
////////////////////////////////////////////////////////////////////////////////////////////
CGame::~CGame()
{
}
////////////////////////////////////////////////////////////////////////////////////////////
//调节Gamma,类似夜晚效果
////////////////////////////////////////////////////////////////////////////////////////////
void CGame::SetNight()
{
	m_bIsNight=true;
	DDGAMMARAMP	ddGammaRamp;
	DDGAMMARAMP ddGammaStart=m_pDisplay->GetGamma();
	for(int i=0;i<256;i++)
	{
		ddGammaRamp.blue[i]=ddGammaStart.blue[i];
		ddGammaRamp.red[i]=ddGammaStart.red[i]>>1;
		ddGammaRamp.green[i]=ddGammaStart.green[i]>>1;
	}	 
	m_pDisplay->SetGamma(ddGammaRamp);
	
}
////////////////////////////////////////////////////////////////////////////////////////////
//得到绝对路径
////////////////////////////////////////////////////////////////////////////////////////////
char*CGame::GetAbsolutePath(char*szRelativePath)
{
	LOA_ASSERT(szRelativePath!=NULL);

	return strcat(s_szCurrentDir,szRelativePath);
}
////////////////////////////////////////////////////////////////////////////////////////////
//初始化数据库
////////////////////////////////////////////////////////////////////////////////////////////
BOOL CGame::InitGameDataBase()
{
	
	m_pMapSurface=new CMapSurface();
	if(!m_pMapSurface)
	{
		m_pLog->WriteMessage("New CMapSurface() Failed!\n");
		return false;
	}
	m_pRoleBlock=KGDStack<POINT>::ForeCreate();


	m_pNpcList=KGDList<STRenderRole*>::ForeCreate();
	if(!m_pNpcList)
	{
		m_pLog->WriteMessage("New Npc List Failed!\n");
		return false;
	}
	m_pRoleQueue=CLagQueue<STRenderRole*>::ForeCreate();
	if(!m_pRoleQueue)
	{
		m_pLog->WriteMessage("New RenderRole Queue Failed!\n");
		return false;
	}
	m_pMap=new CMap(m_pLog);
	if(!m_pMap)
	{
		m_pLog->WriteMessage("New CMap Failed!\n");
		return false;
	}
	m_pRender=new CRender();
	if(!m_pRender)
	{
		m_pLog->WriteMessage("New CRender Failed!Out of memory!\n");
		return false;
	}
	m_pMsg=new CMessage();
	if(!m_pMsg)
	{
		m_pLog->WriteMessage("New CMessage Failed!Out of memory!\n");
		return false;
	}
	if(!m_pMsg->InitMessageQueue(m_pLog))
	{
		m_pLog->WriteMessage("Init Message Queue Failed!\n");
		return false;
	}
	m_pdbChangeMap=IDataBase<STChangeMapData>::ForeCreate();
	if(!m_pdbChangeMap )
	{
		m_pLog->WriteMessage("Create Change Map Database Failed!\n");
		return false;
	}
	m_pdbLoadScript=IDataBase<STLoadScriptData>::ForeCreate();
	if(!m_pdbLoadScript )
	{
		m_pLog->WriteMessage("Create Load Script Database Failed!\n");
		return false;
	}
	//查找所有的地图文件,创建地图文件数据库
	WIN32_FIND_DATA wfd;
	ZeroMemory(&wfd,sizeof(wfd));
	STChangeMapData*pCmd=NULL;
	STLoadScriptData*pScrdata=NULL;

	HANDLE hff=::FindFirstFile("map\\*.lmp",&wfd);
	char tmp[256];
	if(hff!=INVALID_HANDLE_VALUE)
	{
		memset(tmp,0,256);
		CMap map(NULL);
		STMapHead maphead;
		wsprintf(tmp,"map\\%s",wfd.cFileName);
		map.GetMapHead(tmp,&maphead);

		pCmd=new STChangeMapData;
		pCmd->ID=maphead.ID;
		strncpy(pCmd->szName,tmp,128);
		
		if(pCmd->ID!=0)
			m_pdbChangeMap->AddData(pCmd->ID,pCmd);
		
		while(::FindNextFile(hff,&wfd))
		{
			memset(tmp,0,256);
			wsprintf(tmp,"map\\%s",wfd.cFileName);
			map.GetMapHead(tmp,&maphead);
			pCmd=new STChangeMapData;
			pCmd->ID=maphead.ID;
			strncpy(pCmd->szName,tmp,128);

			if(pCmd->ID!=0)
				m_pdbChangeMap->AddData(pCmd->ID,pCmd);
		
		 
		}
		::FindClose(hff);
	}
	//查找所有脚本文件,创建脚本文件数据库
	hff=::FindFirstFile("script\\*.lsr",&wfd);
	if(hff!=INVALID_HANDLE_VALUE)
	{
		memset(tmp,0,256);
		CIniFile inifile;

		wsprintf(tmp,"script\\%s",wfd.cFileName);
		
		pScrdata=new STLoadScriptData;
		pScrdata->ID=::GetPrivateProfileInt("Info","ID",0,tmp);
	
		strncpy(pScrdata->szName,tmp,128);

		if(pScrdata->ID!=0)
			m_pdbLoadScript->AddData(pScrdata->ID,pScrdata);

		while(::FindNextFile(hff,&wfd))
		{
			memset(tmp,0,256);
			wsprintf(tmp,"script\\%s",wfd.cFileName);
			pScrdata=new STLoadScriptData;
			
			pScrdata->ID=::GetPrivateProfileInt("Info","ID",0,tmp);
		
			strncpy(pScrdata->szName,tmp,128);
			if(pScrdata->ID!=0)
				m_pdbLoadScript->AddData(pScrdata->ID,pScrdata);
		}
		::FindClose(hff);
	}

	m_pLog->WriteMessage("Create Change Map Database...OK!\n");
	m_pdbGoods=IDataBase<STGood>::ForeCreate();
	if(!m_pdbGoods)
	{
		m_pLog->WriteMessage("New GoodsDataBase Failed! Out of Memory!\n");
		return false;
	}
	m_pdbMagic=IDataBase<STMagic>::ForeCreate();
	if(!m_pdbMagic)
	{
		m_pLog->WriteMessage("New MagicDataBase Failed! Out of Memory!\n");
		return false;
	}
	

	m_pdbEffect=IDataBase<STEffect>::ForeCreate();
	if(!m_pdbEffect)
	{
		m_pLog->WriteMessage("New EffectDataBase Failed! Out of Memory!\n");
		return false;
	}

	m_pGameData=new CGameData(m_pLog);
	if(!m_pGameData)
	{
		m_pLog->WriteMessage("New Game Data Class Failed! Out of Memory!\n");
		return false;
	}
	
	
	char szGoodsDataFile[]="data\\goods.dat";

	m_pLog->WriteMessage("正在从物品数据文件%s获得物品数据...\n",szGoodsDataFile);
	if(!m_pGameData->CreateGoodsDataBase(szGoodsDataFile,&m_pdbGoods))
	{
		m_pLog->WriteMessage("初始化物品数据库...Failed!\n");
		return false;
	}
	m_pLog->WriteMessage("初始化物品数据库...OK!\n");
	

	m_pRenderMap=new CRenderMap();
	m_pRenderMap->CreateTask(true,true,0xffff);					//高优先级

	m_pRender->AddTask(m_pRenderMap);

	m_pRoleGraph=new CRoleGraph(m_pLog);
	if(!m_pRoleGraph)
	{
		m_pLog->WriteMessage("New CRole Graph Failed!\n");
		return false;
	}
	m_pLog->WriteMessage("New CRoleGraph OK!\n");


	m_pScriptData=new CScriptData;
	m_pScriptData->InitScriptVariable(m_pLog,4096);


	

	return true;
}
////////////////////////////////////////////////////////////////////////////////////////////
//设置显示模式
////////////////////////////////////////////////////////////////////////////////////////////
BOOL CGame::CreateDisplayMode(BOOL bWindowed)
{
	if(bWindowed)
	{
		if(FAILED(m_pDisplay->CreateWindowedDisplay(m_hWnd,640,480,WS_OVERLAPPED | WS_CAPTION| WS_MINIMIZEBOX)))
 			return false;
		else
			return true;
	}
	else
	{
 		if(FAILED(m_pDisplay->CreateFullScreenDisplay(m_hWnd,640,480,16)))
			return false;
		else
			return true;
	}
}
////////////////////////////////////////////////////////////////////////////////////////////
//截图
////////////////////////////////////////////////////////////////////////////////////////////
BOOL CGame::ScreenShot()
{
	//查找已经截下来的bmp文件,得到正确的一个索引,防止覆盖以前的文件
	WIN32_FIND_DATA wfd;
	ZeroMemory(&wfd,sizeof(wfd));
	HANDLE hff=::FindFirstFile("screenshot\\LOABMP*.bmp",&wfd);
	int index=0;
	if(hff!=INVALID_HANDLE_VALUE)
	{
		sscanf(wfd.cFileName,"LOABMP%d.bmp",&index);
		while(::FindNextFile(hff,&wfd))
		{
			sscanf(wfd.cFileName,"LOABMP%d.bmp",&index);
		}
		::FindClose(hff);
	}
	index++;
	char szBmpFile[256];
	wsprintf(szBmpFile,"screenshot\\LOABMP%d.bmp",index);

	FILE*fp=fopen(szBmpFile,"wb");
	if(!fp)
		return false;
	DDSURFACEDESC2 ddsd;
	ZeroMemory(&ddsd,sizeof(ddsd));
	ddsd.dwSize=sizeof(ddsd);
	m_pDisplay->GetBackBuffer()->Lock(NULL,&ddsd,DDLOCK_WAIT,NULL);

	WORD*pBuf=(WORD*)ddsd.lpSurface;
	BITMAPFILEHEADER bfh;
	BITMAPINFOHEADER bih;
	bfh.bfType=0x4d42;
	bfh.bfReserved1=0;
	bfh.bfReserved2=0;
	bfh.bfOffBits=sizeof(bfh)+sizeof(bih);
	bfh.bfSize=ddsd.dwWidth*ddsd.dwHeight*3+bfh.bfOffBits;								//保存为24位色的bmp,所以大小要*3

	bih.biBitCount=24;
	bih.biClrImportant=0;
	bih.biClrUsed=0;
	bih.biCompression=BI_RGB;
	bih.biHeight=ddsd.dwHeight;
	bih.biWidth=ddsd.dwWidth;
	bih.biPlanes=1;
	bih.biSize=sizeof(bih);
	bih.biSizeImage=ddsd.dwWidth*ddsd.dwHeight*3;
	bih.biXPelsPerMeter=0;
	bih.biYPelsPerMeter=0;

	fwrite(&bfh,sizeof(bfh),1,fp);
	fwrite(&bih,sizeof(bih),1,fp);

	pBuf=pBuf+ddsd.dwWidth*(ddsd.dwHeight-1);
	//倒着存放,从下到上
	if(m_pDisplay->Is565())						//如果表面是565格式
	{
		for(DWORD i=0;i<ddsd.dwHeight;i++)
		{
			for(DWORD j=0;j<ddsd.dwWidth;j++)
			{
				fputc((*pBuf & 0x1f)<<3,fp);	//b
				fputc((*pBuf >>3)&0xff,fp);		//g
				fputc((*pBuf >>8)&0xff,fp);		//r
				pBuf++;
			}
			pBuf-=ddsd.lPitch;//(ddsd.lPitch>>1)<<1;
		}
	}
	else
	{
		for(DWORD i=0;i<ddsd.dwHeight;i++)
		{
			for(DWORD j=0;j<ddsd.dwWidth;j++)
			{
				fputc((*pBuf & 0x1f)<<3,fp);	//b
				fputc((*pBuf >>2)&0xff,fp);		//g
				fputc((*pBuf >>7)&0xff,fp);		//r

				pBuf++;
			}
			pBuf-=ddsd.lPitch;//(ddsd.lPitch>>1)<<1;
		}
	}
	m_pDisplay->GetBackBuffer()->Unlock(NULL);
	fclose(fp);
	return true;
}
////////////////////////////////////////////////////////////////////////////////////////////
//窗口过程
////////////////////////////////////////////////////////////////////////////////////////////
LRESULT CALLBACK CGame::WinProc(HWND hWnd,UINT message,WPARAM wParam,LPARAM lParam)
{
	static CGame*pGame=NULL;
	switch(message)
    {
	case UM_SETGAME:
		pGame=(CGame*)wParam;
		break;
	case UM_GRAPHNOTIFY:					//DirectShow消息
		if(pGame)
		{
			pGame->m_pDShow->HandleGraphEvent();
			if(!pGame->m_pDShow->IsPlaying())
			{
				::SetActiveWindow(pGame->m_hWnd);
			}
		}
		break;
	case WM_SETCURSOR:
		ShowCursor(false);
		break;
    case WM_ACTIVATEAPP:
        if(pGame)
			pGame->m_bActive=wParam;
        break;
	case WM_MOVE:
	case WM_SIZE:
		{
			if(!pGame)
				break;
			pGame->m_pDisplay->UpdateBounds();
		}
		break;
	case WM_CLOSE:
		{
			if(pGame)
			{
				CMessageBox msgbox;
				if(LOA_MSG_BOX_IDYES==msgbox.ShowMessageBox(pGame,LOA_MSG_BOX_YESNO,"确实要退出么?"))
					DestroyWindow(hWnd);
			}
			else
			{
				DestroyWindow(hWnd);
			}
		}
		break;
    case WM_DESTROY:
		{
			if(pGame)
				pGame->m_bPlayGame=false;
	        PostQuitMessage(0);
		}
        break;
	case WM_KEYDOWN:
		{
			switch(LOWORD(wParam))
			{
			case VK_F9:
				{
					if(pGame)
						pGame->ScreenShot();
				}
				break;
			case VK_F8:
				{
					if(pGame)
						pGame->m_bShowFPS=!pGame->m_bShowFPS;
				}
				break;
			case VK_F5:
				{
					if(pGame)
					{
						if(pGame->m_bRandomBattle)
							pGame->m_bRandomBattle=false;
						else
							pGame->m_bRandomBattle=true;
					}
				}
				break;
			 
			default:
				break;

⌨️ 快捷键说明

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