传奇源码分析-客户端(游戏逻辑处理源分析四)

现在假设玩家开始操作游戏:
传奇的客户端源代码工程WindHorn
一、CWHApp派生CWHWindow和CWHDXGraphicWindow。
二、CWHDefProcess派生出CloginProcess、CcharacterProcess、CgameProcess
客户端WinMain调用CWHDXGraphicWindow g_xMainWnd;创建一个窗口。
客户端CWHDXGraphicWindow在自己的Create函数中调用了CWHWindow的Create来创建窗口,然后再调用自己的CreateDXG()来初始化DirectX。

消息循环:
因此,当客户端鼠标单击的时候,先调用CWHWindow窗口的回调函数WndProc,即: g_pWHApp->MainWndProc g_pWHApp定义为:static CWHApp* g_pWHApp = NULL;在CWHApp
构造函数中赋值为:g_pWHApp = this;
g_pWHApp->MainWndProc便调用了CWHApp::MainWndProc,这是一个虚函数,实际上则是调用它的派生类CWHDXGraphicWindow::MainWndProc。
if ( m_pxDefProcess )
return m_pxDefProcess->DefMainWndProc(hWnd, uMsg, wParam, lParam);
根据g_xMainWnd.m_pxDefProcess和全局变量g_bProcState标记当前的处理状态。调用
CLoginProcess->DefMainWndProc
CCharacterProcess->DefMainWndProc
CGameProcess->DefMainWndProc

当用户进行游戏之后,点击鼠标左键,来处理玩家走动的动作:
客户端执行流程:(玩家走动)
CGameProcess::OnLButtonDown(WPARAM wParam, LPARAM lParam)函数:该函数的处理流程:
1. g_xClientSocket.SendNoticeOK();如果点中CnoticeBox则m_xNotice.OnButtonDown
if m_xMsgBtn.OnLButtonDown则调用g_xClientSocket.SendNoticeOK()方法,发送还CM_LOGINNOTICEOK消息。
2.m_pxSavedTargetActor = NULL;设置为空。CInterface::OnLButtonDown函数会判断
鼠标点击的位置(CmirMsgBox, CscrlBar,CgameBtn,GetWindowInMousePos)
a. g_xClientSocket.SendItemIndex(CM_DROPITEM 丢弃物品)
游戏服务器执行流程m_pxPlayerObject->Operate()调用
m_pUserInfo->UserDropGenItem
m_pUserInfo->UserDropItem 删除普通物品。
SM_DROPITEM_SUCCESS 返回删除成功命令
SM_DROPITEM_FAIL 返回删除失败命令

b. 遍历m_stMapItemList列表(存储玩家,怪物,NPC), g_xClientSocket.SendPickUp 发送CM_PICKUP命令。
游戏服务器:m_pxPlayerObject->Operate()调用 PickUp(捡东西)消息处理:
m_pMap->GetItem(m_nCurrX, m_nCurrY) 返回地图里的物体(草药,物品,金子等)
1.memcmp(pMapItem->szName, g_szGoldName 如果是黄金:
m_pMap->RemoveObject从地图中移走该的品。
if (m_pUserInfo->IncGold(pMapItem->nCount))增加用户的金钱(向周转玩家发送RM_ITEMHIDE 消息,隐藏该物体,GoldChanged(),改变玩家的金钱。否则,把黄金返回地图中。
2.m_pUserInfo->IsEnoughBag()
如果玩家的还可以随身带装备(空间)。m_pMap->RemoveObject从地图中移走该的品。UpdateItemToDB,更新用户信息到数据库。(向周转玩家发送RM_ITEMHIDE 消息,隐藏该物体,SendAddItem(lptItemRcd)向本玩家发送捡到东西的消息。m_pUserInfo->m_lpTItemRcd.AddNewNode并把该物品加入自己的列表中。

c. if m_pxMouseTargetActor g_xClientSocket.SendNPCClick发送CM_CLICKNPC命令。
客户端RenderScene调用m_pxMouseTargetActor = NULL;
CheckMappedData(nLoopTime, bIsMoveTime)处理,如果鼠标在某个移动对象的区域内就会设置 m_pxMouseTargetActor为该对象。
如果是NPC:
if ( m_pxMouseTargetActor->m_stFeature.bGender == _GENDER_NPC )
g_xClientSocket.SendNPCClick(m_pxMouseTargetActor->m_dwIdentity);
CM_CLICKNPC消息:
否则:
m_xMyHero.OnLButtonDown

d. 否则m_xMyHero.OnLButtonDown
先判断m_xPacketQueue是否有数据,有则先处理。返回。
判断m_pxMap->GetNextTileCanMove 根据坐标,判断地图上该点属性是否可以移动到该位置:
可移动时:
人:SetMotionState(_MT_WALK
骑马:SetMotionState(_MT_HORSEWALK
不可移动时:
人:SetMotionState(_MT_STAND, bDir);
骑马:SetMotionState(_MT_HORSESTAND, bDir);
SetMotionState函数:
判断循环遍历目标点的周围八个坐标,如果发现是一扇门,则向服务器发送打开这扇门的命令。g_xClientSocket.SendOpenDoor,否则则发送CM_WALK命令到服务器。
m_bMotionLock = m_bInputLock = TRUE; 设置游戏状态
m_wOldPosX = m_wPosX; 保存玩家X点
m_wOldPosY = m_wPosY; 保存玩家Y点
m_bOldDir = m_bCurrDir; 保存玩家方向
然后调用SetMotionFrame设置m_bCurrMtn = _MT_WALK,方向等游戏状态。
设置m_bMoveSpeed = _SPEED_WALK(移动速度1)。m_pxMap->ScrollMap设置地图的偏移位置(m_shViewOffsetX, m_shViewOffsetY)。然后滚动地图,重绘玩家由CGameProcess::RenderScene CGameProcess::RenderObject->DrawActor重绘。



此文章来自网络,如有版权冲突请和我联系 [email protected]



传奇源码分析-客户端(游戏逻辑处理源分析四)

时间: 2024-08-07 04:32:18

传奇源码分析-客户端(游戏逻辑处理源分析四)的相关文章

传奇源码分析-客户端(游戏逻辑处理源分析五 服务器端响应)

器执行流程:(玩家走动) GameSrv服务器ProcessUserHuman线程处理玩家消息:遍历UserInfoList列表,依次调用每个UserInfo的Operate来处理命令队列中的所有操作; pUserInfo->Operate()调用m_pxPlayerObject->Operate()调用.判断玩家if (!m_fIsDead),如果已死,则发送_MSG_FAIL消息.我们在前面看到过,该消息是被优先处理的.否则则调用WalkTo,并发送_MSG_GOOD消息给客户端.Walk

传奇源码分析-客户端(游戏逻辑处理源分析三)

6. 接收怪物,商人,其它玩家的消息:ProcessUserHuman:(其它玩家-服务器处理)CPlayerObject->SearchViewRange();CPlayerObject->Operate();遍历UserInfoList列表,依次调用每个UserInfo的Operate来处理命令队列中的所有操作; pUserInfo->Operate()调用m_pxPlayerObject->Operate()调用.根据分发消息(RM_TURN)向客户端发送SM_TURN消息.

传奇源码分析-客户端(游戏逻辑处理源分析二)

5.接受登录成功后,接收GameSrv服务器发送的消息:接收GameGate发送的消息:CClientSocket::OnSocketMessage的FD_READ事件中,PacketQ.PushQ((BYTE*)pszPacket);把接收到的消息,压入PacketQ队列中.处理PacketQ队列数据是由CGameProcess::Load()时调用OnTimer在CGameProcess::OnTimer中处理的, 处理过程为:OnMessageReceive; ProcessPacket(

Java集合源码学习笔记(二)ArrayList分析

Java集合源码学习笔记(二)ArrayList分析 >>关于ArrayList ArrayList直接继承AbstractList,实现了List. RandomAccess.Cloneable.Serializable接口,为什么叫"ArrayList",因为ArrayList内部是用一个数组存储元素值,相当于一个可变大小的数组,也就是动态数组. (1)继承和实现继承了AbstractList,实现了List:ArrayList是一个数组队列,提供了相关的添加.删除.修

Apache Spark源码走读之7 -- Standalone部署方式分析

欢迎转载,转载请注明出处,徽沪一郎. 楔子 在Spark源码走读系列之2中曾经提到Spark能以Standalone的方式来运行cluster,但没有对Application的提交与具体运行流程做详细的分析,本文就这些问题做一个比较详细的分析,并且对在standalone模式下如何实现HA进行讲解. 没有HA的Standalone运行模式 先从比较简单的说起,所谓的没有ha是指master节点没有ha. 组成cluster的两大元素即Master和Worker.slave worker可以有1到

zookeeper源码之客户端

zookeeper自身提供了一个简易的客户端.主要包括一下几个模块: 1.启动模块. 2.核心执行模块. 3.网络通信模块. 启动模块 启动程序,接收和解析命令行.详见zookeeper源码之客户端启动模块. 核心执行模块 客户端操作ZooKeeper服务端的核心类,详见zookeeper源码之客户端核心执行模块. 类图   ZooKeeper ZooKeeper是客户端操作ZooKeeper服务端的核心类.当用户向ZooKeeperMain执行相关命令时,最终会交给ZooKeeper执行,其会

gomoblie flappy 源码分析:游戏逻辑

本文主要讨论游戏规则逻辑,具体绘制技术请参看相关文章: gomoblie flappy 源码分析:图片素材和大小的处理 http://www.cnblogs.com/ghj1976/p/5222289.html 绘制时间间隔控制 绘制是按照 60 FPS 的节奏绘制的(即每秒钟 60 帧),  FPS : frames per second(帧率) 代码中的控制注意是通过 golang.org/x/mobile/exp/sprite/clock 下的 Time 控制的.  Time实际是 int

Java集合源码学习笔记(三)LinkedList分析

前面学习了ArrayList的源码,数组是顺序存储结构,存储区间是连续的,占用内存严重,故空间复杂的很大.但数组的二分查找时间复杂度小,为O(1),数组的特点是寻址容易,插入和删除困难.今天学习另外的一种常用数据结构LinkedList的实现,LinkedList使用链表作为存储结构,链表是线性存储结构,在内存上不是连续的一段空间,占用内存比较宽松,故空间复杂度很小,但时间复杂度很大,达O(N),链表的特点是寻址困难,插入和删除容易.所有的代码都基于JDK 1.6. >>关于LinkedLis

《倾国倾城》全套源码:客户端+服务端+资源,鄙视复制帖子

郝萌主倾心贡献,尊重作者的劳动成果,请勿转载. 如果文章对您有所帮助,欢迎给作者捐赠,支持郝萌主,捐赠数额随意,重在心意^_^ 我要捐赠: 点击捐赠 Cocos2d-X源码下载:点我传送 游戏官方下载:http://dwz.cn/RwTjl 游戏视频预览:http://dwz.cn/RzHHd 游戏开发博客:http://dwz.cn/RzJzI 游戏源码传送:http://dwz.cn/Nret1 <倾国倾城>全套源码,MMORPG手游,客户端cocos2d-x开发,服务端erlang语言开