Files
wnmj/Classes/Games/PDK/PDK_GameScene.cpp
2026-03-01 13:48:24 +08:00

2614 lines
72 KiB
C++
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
#include "PDK_GameScene.h"
#include "PDK_Player.h"
#include "PDK_GameLogic.h"
#include "UserInfo.h"
#include "MainScene.h"
#include "MissionWeiXin.h"
#include "DismissScene.h"
#include "PopScene.h"
#include "ActionEx.h"
#include "JniFun.h"
#include "SetScene.h"
#include "ChatScene.h"
#include "PlayerScene.h"
#include "IpTipScene.h"
#include "SimpleAudioEngine.h"
#include "SelectShareScene.h"
using namespace PDK_SPACE;
bool PDKGameScene::init()
{
if (!GameFrameBase::init())
{
return false;
}
m_cbTimeOutCard = 0;
m_cbTimeCallScore = 0;
m_cbTimeStartGame = 0;
m_cbTimeHeadOutCard = 0;
//m_nCellScore = 0;
m_pVoiceNode = nullptr;
m_strGameRuleInfo = "";
zeromemory(&m_PrivateRoomInfo, sizeof(CMD_GF_Private_Room_Info));
initNet();
initScene();
return true;
}
//进场动画完成回调;
void PDKGameScene::onEnterTransitionDidFinish()
{
GameFrameBase::onEnterTransitionDidFinish();
if (true == GAME_MUISCBG)
{
CocosDenshion::SimpleAudioEngine::getInstance()->playBackgroundMusic("Games/DDZ/Sound/backmusic.mp3", true);
}
// 暂时停了测试;
#if CC_PLATFORM_WIN32 == CC_TARGET_PLATFORM
CocosDenshion::SimpleAudioEngine* pAudio = CocosDenshion::SimpleAudioEngine::getInstance();
pAudio->stopBackgroundMusic(true);
#endif
// 录像模式;
if (m_IsGameRecord)
{
StartRecord(PDK_GAME_PLAYER);
}
else
{
// 增加游戏内事件处理;
auto dispatcher = Director::getInstance()->getEventDispatcher();
dispatcher->addCustomEventListener(SHOW_PRIVATE_END, CC_CALLBACK_1(PDKGameScene::onEventShowPrivate, this));
CGameServerItem* pGameServerItem = GameMission::g_pGameServerItem;
CC_ASSERT(pGameServerItem != nullptr);
if (pGameServerItem != nullptr)
{
m_kGameMission.SetServerItem(pGameServerItem);
m_kGameMission.start();
}
}
}
//场景退出;
void PDKGameScene::onExit()
{
GameFrameBase::onExit();
for (int i = 0; i < PDK_GAME_PLAYER; i++)
{
SafeDelete(m_aryPlayer[i]);
}
auto dispatcher = Director::getInstance()->getEventDispatcher();
dispatcher->removeCustomEventListeners(SHOW_PRIVATE_END);
}
//场景初始化;
void PDKGameScene::initScene()
{
//根节点;
m_rootNode = CSLoader::createNodeWithVisibleSize("Games/PDK/GameScene.csb");
CC_ASSERT(m_rootNode != nullptr);
this->addChild(m_rootNode, ZO_DEFAULT);
// 公告;
auto ImageSytem = (ImageView*)m_rootNode->getChildByName("ImgRoll");
ASSERT(ImageSytem!=nullptr);
SetSystemNode(ImageSytem);
//桌子节点;
auto tablePanel = static_cast<Layout*>(m_rootNode->getChildByName("panelRoomBg"));
CC_ASSERT(tablePanel != nullptr);
for (int i = 0; i < PDK_GAME_PLAYER; i++)
{
const char* lpcStr = __String::createWithFormat("panelChair_%d", i)->getCString();
Layout* layout = static_cast<Layout*>(m_rootNode->getChildByName(lpcStr));
m_aryPlayer[i] = new PDKPlayer(i, layout);
m_aryPlayer[i]->setVisible(false);
// 自己不可点击;
if (i != PDK_SELF_VIEW_ID)
{
layout->addClickEventListener([i, this](Ref* pSender){
CC_ASSERT(pSender != nullptr);
if (nullptr == pSender) return;
if ((m_aryPlayer[i] != nullptr) && m_aryPlayer[i]->getUserItem(false)!=nullptr)
{
PlayerScene* playerScene = PlayerScene::create();
playerScene->showPlayerInfo(m_aryPlayer[i]);
this->addChild(playerScene, ZO_TRUSTEE);
}
});
}
}
m_pLocalPlayer = m_aryPlayer[PDK_SELF_VIEW_ID];
auto exitCallFunc = [=](Ref*){
auto callback = [=](){
onClickExitGameButton(nullptr);
this->runAction(Sequence::createWithTwoActions(DelayTime::create(0.2f), CallFunc::create([=]{
Director::getInstance()->getEventDispatcher()->dispatchCustomEvent(LEAVE_GAME);
})));
};
PopScene::Instance().show(utility::a_u8("您确定要退出游戏吗?"), callback, nullptr);
};
//退出按钮;
m_pBtnLeave = static_cast<Button*>(tablePanel->getChildByName("btnExit"));
CC_ASSERT(m_pBtnLeave != nullptr);
m_pBtnLeave->addClickEventListener(exitCallFunc);
//设置按钮;
auto btnSetting = static_cast<Button*>(tablePanel->getChildByName("btnSetting"));
CC_ASSERT(btnSetting != nullptr);
btnSetting->addClickEventListener([this](Ref*){
YSAudioEngine::Instance().playBtnClickEffect();
TipNode* pNode = SetScene::create();
CC_ASSERT(pNode != nullptr);
this->addChild(pNode, ZO_ANI);
pNode->pushScene();
});
//聊天按钮;
auto btnChat = static_cast<Button*>(tablePanel->getChildByName("btnChat"));
CC_ASSERT(btnChat != nullptr);
btnChat->addClickEventListener([this](Ref*){
YSAudioEngine::Instance().playBtnClickEffect();
#if CC_PLATFORM_WIN32 == CC_TARGET_PLATFORM
// 测试牌型;
//uint8 cbCardData[10] = { 0x31, 0x21, 0x01, 0x1d, 0x0d, 0x0d, 0x2c, 0x1c, 0x0c, 0x22};
//uint8 cbCardType = m_GameLogic.GetCardType(cbCardData, 10, false);
//uint8 cbCardData[10] = { 0x16, 0x16, 0x06, 0x35, 0x25, 0x05, 0x33, 0x23, 0x2c, 0x2b };
//uint8 cbCardType = m_GameLogic.GetCardType(cbCardData, 10, false);
//if (cbCardType == PDK_CT_ERROR)
//{
// ASSERT(false);
//}
//else
//{
// ASSERT(true);
//}
//uint8 cbHandCardData[10] = { 0x31, 0x21, 0x01, 0x1d, 0x0d, 0x0d, 0x2c, 0x1c, 0x0c, 0x22 };
//tagPDKSearchCardResult SearchCardResult;
//uint8 cbResultCount = m_GameLogic.SearchOutCard(cbHandCardData, 10, cbCardData, 10, &SearchCardResult);
//ASSERT(cbResultCount <= 0);
////搜索出牌;
//tagPDKSearchCardResult mCardResult;
//BYTE cbHandCardData[16] = {0};
//BYTE cbTurnCardData[16] = {0};
//cbHandCardData[0] = 0x01;
//cbHandCardData[1] = 0x3c;
//cbHandCardData[2] = 0x1c;
//cbHandCardData[3] = 0x0c;
//cbHandCardData[4] = 0x17;
//cbHandCardData[5] = 0x03;
//cbTurnCardData[0] = 0x3a;
//cbTurnCardData[1] = 0x2a;
//cbTurnCardData[2] = 0x1a;
//cbTurnCardData[3] = 0x15;
//cbTurnCardData[4] = 0x14;
//BYTE cbResultCount = m_GameLogic.SearchOutCard(cbHandCardData, 6,
// cbTurnCardData, 5, &mCardResult);
//ASSERT(cbResultCount <= 0);
#else
const std::vector<std::string>& chatList = getShortChatList();
auto chatLayer = ChatLayer::create(chatList);
CC_ASSERT(chatLayer != nullptr);
this->addChild(chatLayer, ZO_ANI);
chatLayer->pushScene();
#endif
});
auto imgRoomInfo = static_cast<Sprite*>(tablePanel->getChildByName("imgRoomInfo"));
CC_ASSERT(imgRoomInfo != nullptr);
//房间号;
m_txtPrivateRoomID = static_cast<Text*>(imgRoomInfo->getChildByName("txtRoomID"));
CC_ASSERT(m_txtPrivateRoomID != nullptr);
m_txtPrivateRoomID->setVisible(false);
//局数;
m_txtPrivatePlayCount = static_cast<Text*>(imgRoomInfo->getChildByName("txtRoundNum"));
CC_ASSERT(m_txtPrivatePlayCount != nullptr);
m_txtPrivatePlayCount->setVisible(false);
//规则;
m_txtCompareDesc = static_cast<Text*>(imgRoomInfo->getChildByName("txtCompareDesc"));
CC_ASSERT(m_txtCompareDesc != nullptr);
m_txtCompareDesc->setVisible(false);
//准备按钮;
m_pBtnReady = static_cast<Button*>(m_rootNode->getChildByName("btnReady"));
CC_ASSERT(m_pBtnReady != nullptr);
m_pBtnReady->setVisible(false);
m_pBtnReady->addClickEventListener([=](Ref*){
SendUserReady();
});
//叫分按钮面板;
auto panelCallScore = static_cast<Layout*>(m_rootNode->getChildByName("panelCallScore"));
CC_ASSERT(panelCallScore != nullptr);
m_pAryBtnCall = static_cast<Button*>(panelCallScore->getChildByName("btnCallScore"));
CC_ASSERT(m_pAryBtnCall != nullptr);
//m_pAryBtnCall->addClickEventListener([=](Ref*){
// SendCallScore(true);
//});
m_pAryBtnCall->addClickEventListener([=](Ref*){
YSAudioEngine::getInstance()->playBtnClickEffect();
PopScene::Instance().show(utility::a_u8("你确定要打独吗?"), [=](){
SendCallScore(true);
}, nullptr);
});
//不叫按钮;
m_pBtnNoCall = static_cast<Button*>(panelCallScore->getChildByName("btnPassCall"));
CC_ASSERT(m_pBtnNoCall != nullptr);
m_pBtnNoCall->addClickEventListener([=](Ref*){
SendCallScore(false);
});
//出牌按钮面板;
auto panelOutCard = static_cast<Layout*>(m_rootNode->getChildByName("panelOutCard"));
CC_ASSERT(panelOutCard != nullptr);
//不出按钮;
m_pBtnPass = static_cast<Button*>(panelOutCard->getChildByName("btnPass"));
CC_ASSERT(m_pBtnPass != nullptr);
m_pBtnPass->addClickEventListener([this](Ref*){
if (getSelfChairID() == m_wCurChairID)
{
// 有牌必出控制;
if (m_GameLogic.IsHasGameRule(ePDKRuleEnum_MustOutCard))
{
//搜索出牌;
tagPDKSearchCardResult mCardResult;
uint8 cbResultCount = m_GameLogic.SearchOutCard(m_aryHandCardData, m_aryHandCardCount[PDK_SELF_VIEW_ID],
m_cbTurnCardData, m_cbTurnCardCount, &mCardResult);
if (cbResultCount > 0) return;
}
SendSocketData(PDK_SUB_C_PASS_CARD);
m_pHandCardLayer->downAllCard();
}
});
//提示按钮;
m_pBtnTips = static_cast<Button*>(panelOutCard->getChildByName("btnTips"));
CC_ASSERT(m_pBtnTips != nullptr);
m_pBtnTips->addClickEventListener(CC_CALLBACK_1(PDKGameScene::onButtonTipClick, this));
//出牌按钮;
m_pBtnOutCard = static_cast<Button*>(panelOutCard->getChildByName("btnOutCard"));
CC_ASSERT(m_pBtnOutCard != nullptr);
m_pBtnOutCard->addClickEventListener([this](Ref*){
//播放出牌音效;
playSoundEffect(PDK_ST_OUT_CARD);
PDK_CMD_C_OutCard OutCard;
zeromemory(&OutCard, sizeof(PDK_CMD_C_OutCard));
m_pHandCardLayer->getShootCardData(OutCard.cbCardData, OutCard.cbCardCount);
if (OutCard.cbCardCount > 0)
{
uint16 wHeadSize = sizeof(PDK_CMD_C_OutCard) - sizeof(OutCard.cbCardData);
uint16 wSendSize = wHeadSize + sizeof(uint8)*OutCard.cbCardCount;
SendSocketData(PDK_SUB_C_OUT_CARD, &OutCard, wSendSize);
}
});
//提示文字;
m_pSprTips = static_cast<Sprite*>(m_rootNode->getChildByName("sprTips"));
CC_ASSERT(m_pSprTips != nullptr);
//手牌节点;
auto panelHandCard = static_cast<Layout*>(m_rootNode->getChildByName("panelHandCard"));
auto func = CC_CALLBACK_2(PDKGameScene::selectCardCallback, this);
m_pHandCardLayer = PDKHandCardLayer::create(panelHandCard->getContentSize(), func);
panelHandCard->addChild(m_pHandCardLayer);
//加载扑克牌缓存;
SpriteFrameCache* pSpriteFrameCache = SpriteFrameCache::getInstance();
pSpriteFrameCache->addSpriteFramesWithFile("Games/DDZ/Table/PinCard.plist");
//微信分享按钮;
m_btnWeiXin = (Button*)tablePanel->getChildByName("btnWeiXin");
CC_ASSERT(m_btnWeiXin != nullptr);
m_btnWeiXin->setVisible(false);
// 分享房间号;
m_btnWeiXin->addClickEventListener([=](Ref*){
//播放出牌音效;
playSoundEffect(PDK_ST_OUT_CARD);
bool bGameRuleIdex = ((m_PrivateRoomInfo.bGameRuleIdex & ePDKRuleEnum_HandCardCount) > 0);
uint8 cbCardCount = bGameRuleIdex ? PDK_MAX_COUNT : (PDK_MAX_COUNT - 1);
std::string strGameTitle = "跑得快";
std::string strUrl = GlobalJosn::getInstance()->getShareInfoByKind(SH_KIND_WEIXIN_URL);
std::string strUrlInfo = StringUtils::format("%s?param=%d", strUrl.c_str(), m_PrivateRoomInfo.dwRoomNum);
std::string strGameRuleInfo = getGameRule(m_PrivateRoomInfo.bGameRuleIdex);
std::string strShareRule = StringUtils::format("房间号:[%u], %d 局,%d张牌%s。", m_PrivateRoomInfo.dwRoomNum,
m_PrivateRoomInfo.dwPlayTotal, cbCardCount, strGameRuleInfo.c_str());
MissionWeiXin::Instance().shareUrlWeiXin(strUrlInfo, strGameTitle, strShareRule);
//SelectShareScene::Instance().shareRoomInfo(strUrlInfo, strUTFGameTitle, strShareRule, 0);
});
// 语音标志;
m_pVoiceNode = (Node*)m_rootNode->getChildByName("VoiceNode");
CC_ASSERT(m_pVoiceNode != nullptr);
m_pVoiceNode->setVisible(false);
//语音按钮;
auto btnVoice = (Button*)tablePanel->getChildByName("btnVoice");
CC_ASSERT(btnVoice != nullptr);
//注册触摸事件;
btnVoice->addTouchEventListener(CC_CALLBACK_2(PDKGameScene::OnButtonVoiceTouched, this));
// 解散房间函数;
auto callback = [this](){
onEventAgreeDismissRoom(true);
};
// 离开按钮;
m_btnDismissRoom = (Button*)tablePanel->getChildByName("btnDismiss");
CC_ASSERT(m_btnDismissRoom != nullptr);
m_btnDismissRoom->setVisible(false);
m_btnDismissRoom->addClickEventListener([=](Ref *pSender){
std::string strTip;
if (0 == m_PrivateRoomInfo.dwPlayCout && false == m_PrivateRoomInfo.bStartGame)
{
strTip = "解散房间不扣房卡,是否解散?";
}
else
{
strTip = "您确定要解散房间吗?";
}
PopScene::Instance().show(utility::a_u8(strTip.c_str()), callback, nullptr);
});
// 结算面板;
m_pResultLayer = PDKGameEndNode::create();
m_pResultLayer->setVisible(false);
this->addChild(m_pResultLayer, ZO_END);
// 私人场面皮;
m_pPrivateScene = PDKPrivateEndNode::create();
m_pPrivateScene->setVisible(false);
this->addChild(m_pPrivateScene, ZO_PRIVATE);
//对手机返回键的监听;
auto keyListener = EventListenerKeyboard::create();
//和回调函数绑定;
keyListener->onKeyReleased = [=](EventKeyboard::KeyCode keyCode, Event * pEvent){
//返回值处理;
if (keyCode == EventKeyboard::KeyCode::KEY_ESCAPE)
{
exitCallFunc(nullptr);
}
};
//添加到事件分发器中;
_eventDispatcher->addEventListenerWithSceneGraphPriority(keyListener, this);
loadShortChat("Games/DDZ/ShortChat/ChatInfo.json");
//重置场景;
resetScene();
//重置数据;
ResetAllData();
}
//重置场景;
void PDKGameScene::resetScene(bool bAll/* = false*/)
{
//重置玩家UI
for (uint8 i = 0; i < PDK_GAME_PLAYER; i++)
{
m_aryPlayer[i]->resetUI(bAll);
}
//隐藏所有按钮;
m_pAryBtnCall->setVisible(false);
m_pBtnNoCall->setVisible(false);
m_pBtnPass->setVisible(false);
m_pBtnTips->setVisible(false);
m_pBtnOutCard->setVisible(false);
//m_pBtnReady->setVisible(false);
//隐藏面板;
m_pSprTips->setVisible(false);
//清空手牌;
m_pHandCardLayer->setLordMode(false);
m_pHandCardLayer->initUIData();
}
//重置数据;
void PDKGameScene::resetData()
{
m_bGameStart = false;
m_cbGameStatus = PDK_GAME_SCENE_FREE;
m_wLandChairID = INVALID_CHAIR;
m_wCurChairID = INVALID_CHAIR;
m_cbMustOutCard = 0x0;
m_wTurnWiner = INVALID_CHAIR;
m_cbTurnCardCount = 0;
m_wLastWiner = INVALID_CHAIR;
m_cbLastCardCount = 0;
m_cbBombCount = 0;
m_cbCallScore = 0;
zeromemory(m_cbLastCardData, sizeof(m_cbLastCardData));
zeromemory(m_cbTurnCardData, sizeof(m_cbTurnCardData));
zeromemory(m_aryHandCardData, sizeof(m_aryHandCardData));
zeromemory(m_aryHandCardCount, sizeof(m_aryHandCardCount));
zeromemory(m_aryAllHandCardData, sizeof(m_aryAllHandCardData));
zeromemory(m_arySendCardCount, sizeof(m_arySendCardCount));
zeromemory(m_aryActiveStatus, sizeof(m_aryActiveStatus));
}
//重置数据(相当于玩家离开);
void PDKGameScene::ResetAllData()
{
resetScene();
resetData();
}
//重置桌子;
void PDKGameScene::ResetTable()
{
resetScene(true);
resetData();
}
//获取快捷语音文件路径;
const std::string PDKGameScene::getShortChatSoundPath(uint8 cbGender, int nIndex)
{
// 短语;
std::string strFilePath = "Games/DDZ/ShortChat/";
if (cbGender == enMan)
{
strFilePath += StringUtils::format("man/%d.mp3", nIndex);
}
else
{
strFilePath += StringUtils::format("woman/%d.mp3", nIndex);
}
return strFilePath;
}
//绑定网络消息;
void PDKGameScene::initNet()
{
addNetCBDefine(PDK_SUB_S_GAME_START, this, PDKGameScene::onSubGameStart);
addNetCBDefine(PDK_SUB_S_CALL_SCORE, this, PDKGameScene::onSubGameCallScore);
addNetCBDefine(PDK_SUB_S_BANKER_INFO, this, PDKGameScene::onSubGameBankerInfo);
addNetCBDefine(PDK_SUB_S_OUT_CARD, this, PDKGameScene::onSubGameOutCard);
addNetCBDefine(PDK_SUB_S_PASS_CARD, this, PDKGameScene::onSubGamePassCard);
addNetCBDefine(PDK_SUB_S_SET_BASESCORE, this, PDKGameScene::onSubGameSetBaseScore);
addNetCBDefine(PDK_SUB_S_GAME_CONCLUDE, this, PDKGameScene::onSubGameEnd);
addNetCBDefine(PDK_SUB_S_TRUSTEE, this, PDKGameScene::onSubGameTrustee);
addNetCBDefine(PDK_SUB_S_START_SCORE, this, PDKGameScene::onSubGameStartScore);
}
//按钮点击事件;
void PDKGameScene::onButtonTipClick(Ref*)
{
if (getSelfChairID() != m_wCurChairID) return;
if (m_cbTurnCardCount == 0) return;
//搜索出牌;
tagPDKSearchCardResult mCardResult;
uint8 cbResultCount = m_GameLogic.SearchOutCard(m_aryHandCardData, m_aryHandCardCount[PDK_SELF_VIEW_ID],
m_cbTurnCardData, m_cbTurnCardCount, &mCardResult);
if (cbResultCount > 0)
{
// 下家剩余一张牌的情况下,出单牌必须是手牌最大的一张。
if (1 == m_cbTurnCardCount)
{
uint16 wSelfChairID = getSelfChairID();
uint16 wNextChairID = getNextChairID(wSelfChairID);
// 只剩下一张牌;
uint16 wViewID = SwitchViewChairID(wNextChairID);
if (1 == m_aryHandCardCount[wViewID])
{
uint8 cbMaxCardData = m_GameLogic.GetMaxCardData(m_aryHandCardData, m_aryHandCardCount[PDK_SELF_VIEW_ID]);
m_pHandCardLayer->shootCardData(&cbMaxCardData, 1);
}
else
{
//弹起牌;
m_pHandCardLayer->shootCardData(mCardResult.cbResultCard[0], mCardResult.cbCardCount[0]);
}
}
else
{
//弹起牌;
m_pHandCardLayer->shootCardData(mCardResult.cbResultCard[0], mCardResult.cbCardCount[0]);
}
m_pBtnOutCard->setEnabled(true);
}
else
{
SendSocketData(PDK_SUB_C_PASS_CARD);
}
}
bool PDKGameScene::OnEventSceneMessage(uint8 cbGameStatus, bool bLookonUser, void* pData, int nDataSize)
{
m_cbGameStatus = cbGameStatus;
switch (cbGameStatus)
{
case PDK_GAME_SCENE_FREE:
{
return onGameSceneFree(pData, nDataSize);
}
case PDK_GAME_SCENE_SEND:
{
return onGameSceneSend(pData, nDataSize);
}
case PDK_GAME_SCENE_CALL:
{
return onGameSceneCall(pData, nDataSize);
}
case PDK_GAME_SCENE_PLAY:
{
return onGameScenePlay(pData, nDataSize);
}
default:
break;
}
return true;
}
//恢复空闭场景;
bool PDKGameScene::onGameSceneFree(void* pData, int nDataSize)
{
//校验数据;
CC_ASSERT(nDataSize == sizeof(PDK_CMD_S_StatusFree));
PDK_CMD_S_StatusFree* pStatusFree = (PDK_CMD_S_StatusFree*)pData;
m_cbTimeOutCard = pStatusFree->cbTimeOutCard;
m_cbTimeCallScore = pStatusFree->cbTimeCallScore;
m_cbTimeStartGame = pStatusFree->cbTimeStartGame;
m_cbTimeHeadOutCard = pStatusFree->cbTimeHeadOutCard;
if (getSelfGamePlayer()->GetUserStatus() < US_READY)
{
m_pBtnReady->setEnabled(true);
m_pBtnReady->setVisible(true);
}
return true;
}
//恢复空闭场景;
bool PDKGameScene::onGameSceneSend(void* pData, int nDataSize)
{
//校验数据;
CC_ASSERT(nDataSize == sizeof(PDK_CMD_S_StatusSend));
PDK_CMD_S_StatusSend* pStatusSend = (PDK_CMD_S_StatusSend*)pData;
m_cbTimeOutCard = pStatusSend->cbTimeOutCard;
m_cbTimeCallScore = pStatusSend->cbTimeCallScore;
m_cbTimeStartGame = pStatusSend->cbTimeStartGame;
m_cbTimeHeadOutCard = pStatusSend->cbTimeHeadOutCard;
// 设置游戏规则;
m_GameLogic.SetCardRule(pStatusSend->dwGameRule);
memcpy(m_aryActiveStatus, pStatusSend->bActiveStatus, sizeof(pStatusSend->bActiveStatus));
//拷贝手牌;
memcpy(m_aryHandCardData, pStatusSend->cbHandCardData, sizeof(pStatusSend->cbHandCardData));
//初始化牌数;
for (uint8 i = 0; i < PDK_GAME_PLAYER; i++)
{
if (!m_aryActiveStatus[i]) continue;
uint16 wViewID = SwitchViewChairID(i);
// 设置玩家手牌;
m_aryHandCardCount[wViewID] = pStatusSend->cbHandCardCount[i];
m_aryPlayer[wViewID]->setHandCardCount(m_aryHandCardCount[wViewID]);
}
m_GameLogic.SortCardList(m_aryHandCardData, PDK_NORMAL_COUNT, PDK_ST_ORDER);
m_pHandCardLayer->redrawHandCard(m_aryHandCardData, PDK_NORMAL_COUNT);
return true;
}
//恢复叫分场景;
bool PDKGameScene::onGameSceneCall(void* pData, int nDataSize)
{
//校验数据;
CC_ASSERT(nDataSize == sizeof(PDK_CMD_S_StatusCall));
PDK_CMD_S_StatusCall* pStatusCall = (PDK_CMD_S_StatusCall*)pData;
m_bGameStart = true;
m_cbTimeOutCard = pStatusCall->cbTimeOutCard;
m_cbTimeCallScore = pStatusCall->cbTimeCallScore;
m_cbTimeStartGame = pStatusCall->cbTimeStartGame;
m_cbTimeHeadOutCard = pStatusCall->cbTimeHeadOutCard;
// 设置游戏规则;
m_GameLogic.SetCardRule(pStatusCall->dwGameRule);
memcpy(m_aryActiveStatus, pStatusCall->bActiveStatus, sizeof(pStatusCall->bActiveStatus));
//拷贝手牌;
memcpy(m_aryHandCardData, pStatusCall->cbHandCardData, sizeof(pStatusCall->cbHandCardData));
//初始化牌数;
for (uint8 i = 0; i < PDK_GAME_PLAYER; i++)
{
if (!m_aryActiveStatus[i]) continue;
uint16 wViewID = SwitchViewChairID(i);
// 设置玩家手牌;
m_aryHandCardCount[wViewID] = pStatusCall->cbHandCardCount[i];
m_aryPlayer[wViewID]->setHandCardCount(m_aryHandCardCount[wViewID]);
// 叫分状态;
m_aryPlayer[wViewID]->setCallVisible(pStatusCall->bScoreActive[i], pStatusCall->bScoreInfo[i]);
}
m_GameLogic.SortCardList(m_aryHandCardData, PDK_NORMAL_COUNT, PDK_ST_ORDER);
m_pHandCardLayer->redrawHandCard(m_aryHandCardData, PDK_NORMAL_COUNT);
// 显示必出牌;
if (m_GameLogic.IsValidCard(pStatusCall->cbMustOutCard))
{
// 当前玩家显示牌;
uint16 wCurrentViewID = SwitchViewChairID(pStatusCall->wCurrentUser);
// 自己弹起,其他人显示在出牌位置;
if (wCurrentViewID == PDK_SELF_VIEW_ID)
{
m_pHandCardLayer->shootCardData(&pStatusCall->cbMustOutCard, 1);
}
else
{
m_aryPlayer[wCurrentViewID]->setOutCardData(&pStatusCall->cbMustOutCard, 1, true);
}
}
// 自己没叫分,显示叫分按钮;
uint16 wSelfChairID = getSelfChairID();
if (!pStatusCall->bScoreActive[wSelfChairID])
{
updateCallButtons();
}
else
{
m_pAryBtnCall->setVisible(false);
m_pBtnNoCall->setVisible(false);
}
return true;
}
//恢复游戏场景;
bool PDKGameScene::onGameScenePlay(void* pData, int nDataSize)
{
//校验数据;
CC_ASSERT(nDataSize == sizeof(PDK_CMD_S_StatusPlay));
PDK_CMD_S_StatusPlay* pStatusPlay = (PDK_CMD_S_StatusPlay*)pData;
m_bGameStart = true;
// 操作时间;
m_cbTimeOutCard = pStatusPlay->cbTimeOutCard;
m_cbTimeCallScore = pStatusPlay->cbTimeCallScore;
m_cbTimeStartGame = pStatusPlay->cbTimeStartGame;
m_cbTimeHeadOutCard = pStatusPlay->cbTimeHeadOutCard;
// 设置游戏规则;
m_GameLogic.SetCardRule(pStatusPlay->dwGameRule);
memcpy(m_aryActiveStatus, pStatusPlay->bActiveStatus, sizeof(pStatusPlay->bActiveStatus));
// 上家出牌信息;
m_wTurnWiner = pStatusPlay->wTurnWiner;
m_cbTurnCardCount = pStatusPlay->cbTurnCardCount;
memcpy(m_cbTurnCardData, pStatusPlay->cbTurnCardData, m_cbTurnCardCount);
// 地主信息;
m_wLandChairID = pStatusPlay->wBankerUser;
m_wCurChairID = pStatusPlay->wCurrentUser;
m_cbMustOutCard = pStatusPlay->cbMustOutCard;
//初始化牌数;
for (uint8 i = 0; i < PDK_GAME_PLAYER; i++)
{
if (!m_aryActiveStatus[i]) continue;
uint16 wViewID = SwitchViewChairID(i);
uint8 cbCardCount = pStatusPlay->cbHandCardCount[i];
m_aryHandCardCount[wViewID] = cbCardCount;
m_aryPlayer[wViewID]->setHandCardCount(cbCardCount);
//最后出牌玩家视图;
if (i == m_wTurnWiner)
{
BYTE cbTmpTurnCard[PDK_MAX_COUNT] = { 0 };
CopyMemory(cbTmpTurnCard, pStatusPlay->cbTurnCardData, sizeof(BYTE)*m_cbTurnCardCount);
m_GameLogic.SortOutCardList(cbTmpTurnCard, m_cbTurnCardCount, false);
m_aryPlayer[wViewID]->setOutCardData(cbTmpTurnCard, m_cbTurnCardCount);
}
if (PDK_SELF_VIEW_ID == wViewID)
{
//拷贝手牌;
memcpy(m_aryHandCardData, pStatusPlay->cbHandCardData, cbCardCount);
m_GameLogic.SortCardList(m_aryHandCardData, cbCardCount, PDK_ST_ORDER);
m_pHandCardLayer->redrawHandCard(m_aryHandCardData, cbCardCount);
}
bool bLandlord = (i == pStatusPlay->wBankerUser);
m_aryPlayer[wViewID]->setLand(bLandlord);
}
if (m_wLandChairID==getSelfChairID())
{
m_pHandCardLayer->setLordMode(true);
}
// 显示必出牌;
if (m_GameLogic.IsValidCard(pStatusPlay->cbMustOutCard))
{
// 当前玩家显示牌;
uint16 wCurrentViewID = SwitchViewChairID(pStatusPlay->wCurrentUser);
// 自己弹起,其他人显示在出牌位置;
if (wCurrentViewID == PDK_SELF_VIEW_ID)
{
m_pHandCardLayer->shootCardData(&pStatusPlay->cbMustOutCard, 1);
}
else
{
m_aryPlayer[wCurrentViewID]->setOutCardData(&pStatusPlay->cbMustOutCard, 1, true);
}
}
//更新按钮状态;
updateButtonsStatus(pStatusPlay->wCurrentUser, m_cbTimeOutCard, (0 == pStatusPlay->cbTurnCardCount));
return true;
}
void PDKGameScene::onSubGameStart(const void * pBuffer, uint16 wDataSize)
{
//校验数据;
CC_ASSERT(wDataSize == sizeof(PDK_CMD_S_GameStart));
PDK_CMD_S_GameStart* pGameStart = (PDK_CMD_S_GameStart*)pBuffer;
m_bGameStart = true;
//清除准备状态;
for (uint8 i = 0; i < PDK_GAME_PLAYER; i++)
{
m_aryPlayer[i]->setReadyVisible(false);
}
// 设置游戏规则;
m_GameLogic.SetCardRule(pGameStart->dwGameRule);
// 拷贝状态;
memcpy(m_aryActiveStatus, pGameStart->bActiveStatus, sizeof(pGameStart->bActiveStatus));
if (m_IsGameRecord)
{
for (uint8 i = 0; i < PDK_GAME_PLAYER; i++)
{
if (!m_aryActiveStatus[i]) continue;
uint16 _wViewID = SwitchViewChairID(i);
m_aryHandCardCount[_wViewID] = pGameStart->cbCardCount[i];
m_aryPlayer[_wViewID]->setHandCardCount(m_aryHandCardCount[_wViewID]);
if (_wViewID == PDK_SELF_VIEW_ID)
{
m_GameLogic.SortCardList(m_aryHandCardData, m_aryHandCardCount[_wViewID], PDK_ST_ORDER);
m_pHandCardLayer->redrawHandCard(m_aryHandCardData, m_aryHandCardCount[PDK_SELF_VIEW_ID]);
}
else
{
m_GameLogic.SortCardList(m_aryAllHandCardData[_wViewID], m_aryHandCardCount[_wViewID], PDK_ST_ORDER);
m_aryPlayer[_wViewID]->setHandCardData(m_aryAllHandCardData[_wViewID], m_aryHandCardCount[_wViewID]);
}
}
}
else
{
playSoundEffect(PDK_ST_DEAL_CARD);
//拷贝手牌;
memcpy(m_aryHandCardData, pGameStart->cbCardData, sizeof(pGameStart->cbCardData));
for (uint8 i = 0; i < PDK_GAME_PLAYER; i++)
{
if (!m_aryActiveStatus[i]) continue;
uint16 _wViewID = SwitchViewChairID(i);
m_arySendCardCount[_wViewID] = pGameStart->cbCardCount[i];
}
//发牌动画;
float fDelaySendTime = 0.01f;
SpriteFrameCache* pSpriteFrameCache = SpriteFrameCache::getInstance();
Size sizeWin = Director::getInstance()->getWinSize();
Vec2 ptInitCard;
ptInitCard.x = sizeWin.width / 2;
ptInitCard.y = sizeWin.height / 2;
for (int i = 0; i < pGameStart->cbCardCount[0]; i++)
{
for (int j = 0; j < PDK_GAME_PLAYER; j++)
{
if (m_aryActiveStatus[j])
{
Sprite* pCardSprite = Sprite::createWithSpriteFrameName("bCardBack.png");
pCardSprite->setTag(i);
pCardSprite->setScale(0.5f);
pCardSprite->setPosition(ptInitCard);
m_rootNode->addChild(pCardSprite);
uint16 wViewID = SwitchViewChairID(j);
CC_ASSERT(wViewID < PDK_GAME_PLAYER);
if (wViewID < PDK_GAME_PLAYER)
{
moveSendCardSprite(pCardSprite, wViewID, fDelaySendTime);
}
fDelaySendTime = fDelaySendTime + 0.03;
}
}
}
}
}
//玩家叫分
void PDKGameScene::onSubGameCallScore(const void * pBuffer, uint16 wDataSize)
{
//校验数据;
CC_ASSERT(wDataSize == sizeof(PDK_CMD_S_CallScore));
PDK_CMD_S_CallScore* pCallScore = (PDK_CMD_S_CallScore*)pBuffer;
//转换叫分玩家视图;
uint16 wViewID = SwitchViewChairID(pCallScore->wCallScoreUser);
//隐藏倒计时;
m_aryPlayer[wViewID]->killClock();
//不包牌的时候显示;
m_aryPlayer[wViewID]->setCallVisible(true, pCallScore->bCurrentScore);
//如果是自已叫分隐藏叫分按钮;
if (PDK_SELF_VIEW_ID==wViewID)
{
m_pAryBtnCall->setVisible(false);
m_pBtnNoCall->setVisible(false);
}
}
//开始叫分;
void PDKGameScene::onSubGameStartScore(const void * pBuffer, uint16 wDataSize)
{
//校验数据;
CC_ASSERT(wDataSize == sizeof(PDK_CMD_S_SendCallScore));
PDK_CMD_S_SendCallScore* pSendCa = (PDK_CMD_S_SendCallScore*)pBuffer;
if (pSendCa->cbMustOutCard != 0x0)
{
// 当前玩家显示牌;
uint16 wCurrentViewID = SwitchViewChairID(pSendCa->wBankerUser);
// 自己弹起,其他人显示在出牌位置;
if (wCurrentViewID == PDK_SELF_VIEW_ID)
{
m_pHandCardLayer->shootCardData(&pSendCa->cbMustOutCard, 1);
}
else
{
m_aryPlayer[wCurrentViewID]->setOutCardData(&pSendCa->cbMustOutCard, 1, true);
}
}
updateCallButtons();
}
//地主信息;
void PDKGameScene::onSubGameBankerInfo(const void * pBuffer, uint16 wDataSize)
{
//校验数据;
CC_ASSERT(wDataSize == sizeof(PDK_CMD_S_BankerInfo));
PDK_CMD_S_BankerInfo* pBankerInfo = (PDK_CMD_S_BankerInfo*)pBuffer;
m_wLandChairID = pBankerInfo->wBankerUser;
m_wCurChairID = pBankerInfo->wCurrentUser;
m_wTurnWiner = m_wCurChairID;
m_cbTurnCardCount = 0;
zeromemory(m_cbTurnCardData, sizeof(m_cbTurnCardData));
if (pBankerInfo->wCurrentUser == getSelfChairID())
{
m_cbMustOutCard = pBankerInfo->cbMustOutCard;
}
//清除玩家叫分信息;
for (uint8 i = 0; i < PDK_GAME_PLAYER; i++)
{
m_aryPlayer[i]->setCallVisible(false, false);
}
//转换叫分玩家视图;
uint16 wCurrentViewID = SwitchViewChairID(pBankerInfo->wCurrentUser);
// 没人打独,显示必出牌;
if (pBankerInfo->cbMustOutCard != 0x0 && pBankerInfo->bShowMustOutCard)
{
// 自己弹起,其他人显示在出牌位置;
if (wCurrentViewID == PDK_SELF_VIEW_ID)
{
m_pHandCardLayer->shootCardData(&pBankerInfo->cbMustOutCard, 1);
}
else
{
m_aryPlayer[wCurrentViewID]->setOutCardData(&pBankerInfo->cbMustOutCard, 1, true);
}
}
else // 有人打独,无必出牌;
{
for (uint8 i = 0; i < PDK_GAME_PLAYER; i++)
{
m_aryPlayer[i]->setOutCardData(nullptr, 0);
}
// 自己手牌落下;
m_pHandCardLayer->downAllCard();
if (pBankerInfo->wBankerUser != INVALID_CHAIR)
{
uint16 wBankerViewID = SwitchViewChairID(pBankerInfo->wBankerUser);
m_aryPlayer[wBankerViewID]->setLand(true);
}
}
if (PDK_SELF_VIEW_ID == wCurrentViewID)
{
updateButtonsStatus(pBankerInfo->wCurrentUser, m_cbTimeHeadOutCard, true);
}
}
//玩家出牌;
void PDKGameScene::onSubGameOutCard(const void * pBuffer, uint16 wDataSize)
{
//定义变量;
PDK_CMD_S_OutCard* pOutCard = (PDK_CMD_S_OutCard*)pBuffer;
uint16 wHeadSize = sizeof(PDK_CMD_S_OutCard) - sizeof(pOutCard->cbCardData);
//效验数据;
CC_ASSERT((wDataSize >= wHeadSize) && (wDataSize == (wHeadSize + pOutCard->cbCardCount*sizeof(uint8))));
if ((wDataSize < wHeadSize) || (wDataSize != (wHeadSize + pOutCard->cbCardCount*sizeof(uint8)))) return ;
m_cbMustOutCard = 0x0;
BYTE cbTmpTurnCard[PDK_MAX_COUNT] = { 0 };
CopyMemory(cbTmpTurnCard, pOutCard->cbCardData, sizeof(BYTE)*pOutCard->cbCardCount);
m_GameLogic.SortOutCardList(cbTmpTurnCard, pOutCard->cbCardCount, pOutCard->bLastCard);
//转换出牌玩家视图;
uint16 wViewID = SwitchViewChairID(pOutCard->wOutCardUser);
m_aryPlayer[wViewID]->setPassVisible(false);
//m_aryPlayer[wViewID]->setOutCardData(pOutCard->cbCardData, pOutCard->cbCardCount);
m_aryPlayer[wViewID]->setOutCardData(cbTmpTurnCard, pOutCard->cbCardCount);
m_aryPlayer[wViewID]->killClock();
//获取出牌类型;
uint8 cbCardType = m_GameLogic.GetCardType(pOutCard->cbCardData, pOutCard->cbCardCount, pOutCard->bLastCard);
//计算炸弹次数;
if (PDK_CT_BOMB_CARD == cbCardType || PDK_CT_3A_BOMB_CARD == cbCardType)
{
m_cbBombCount++;
}
playAnimate(cbCardType, pOutCard->wOutCardUser, m_wTurnWiner);
//播放出牌声音;
playSoundEffect(cbCardType, m_aryPlayer[wViewID]->GetGender(), pOutCard->cbCardData[0]);
if (wViewID == PDK_SELF_VIEW_ID)
{
hideOutCardButtons();
m_GameLogic.RemoveCard(pOutCard->cbCardData, pOutCard->cbCardCount, m_aryHandCardData, m_aryHandCardCount[PDK_SELF_VIEW_ID]);
m_aryHandCardCount[PDK_SELF_VIEW_ID] -= pOutCard->cbCardCount;
//剩余牌数大于1再排序;
if (m_aryHandCardCount[PDK_SELF_VIEW_ID]>1)
{
m_GameLogic.SortCardList(m_aryHandCardData, m_aryHandCardCount[PDK_SELF_VIEW_ID], PDK_ST_ORDER);
}
m_pHandCardLayer->redrawHandCard(m_aryHandCardData, m_aryHandCardCount[PDK_SELF_VIEW_ID]);
}
else
{
m_aryHandCardCount[wViewID] -= pOutCard->cbCardCount;
if (m_IsGameRecord)
{
m_GameLogic.RemoveCard(pOutCard->cbCardData, pOutCard->cbCardCount, m_aryAllHandCardData[wViewID], m_aryHandCardCount[wViewID] + pOutCard->cbCardCount);
m_GameLogic.SortCardList(m_aryAllHandCardData[wViewID], m_aryHandCardCount[wViewID], PDK_ST_ORDER);
m_aryPlayer[wViewID]->setHandCardData(m_aryAllHandCardData[wViewID], m_aryHandCardCount[wViewID]);
}
}
m_aryPlayer[wViewID]->setHandCardCount(m_aryHandCardCount[wViewID]);
//此时游戏结束;
if (INVALID_CHAIR == pOutCard->wCurrentUser)
{
// 记录最后一手牌;
m_wLastWiner = pOutCard->wOutCardUser;
m_cbLastCardCount = pOutCard->cbCardCount;
memcpy(m_cbLastCardData, pOutCard->cbCardData, pOutCard->cbCardCount);
return;
}
m_wCurChairID = pOutCard->wCurrentUser;
m_wTurnWiner = pOutCard->wOutCardUser;
for (uint8 i = 0; i < PDK_GAME_PLAYER; i++)
{
if (i != wViewID)
{
m_aryPlayer[i]->setPassVisible(false);
m_aryPlayer[i]->setOutCardData(nullptr, 0);
}
}
//出牌类型为火箭时出牌玩家等于下个出牌玩家;
if (pOutCard->wOutCardUser == pOutCard->wCurrentUser)
{
m_cbTurnCardCount = 0;
zeromemory(m_cbTurnCardData, sizeof(m_cbTurnCardData));
}
else
{
m_cbTurnCardCount = pOutCard->cbCardCount;
memcpy(m_cbTurnCardData, pOutCard->cbCardData, pOutCard->cbCardCount);
}
//更新出牌按钮状态;
updateButtonsStatus(pOutCard->wCurrentUser, m_cbTimeOutCard);
//只剩一张牌时播放音效;
if (1==m_aryHandCardCount[wViewID])
{
playSoundEffect(PDK_ST_LEFT_ONE_CARD, m_aryPlayer[wViewID]->GetGender());
}
}
//玩家不出;
void PDKGameScene::onSubGamePassCard(const void * pBuffer, uint16 wDataSize)
{
//校验数据;
CC_ASSERT(wDataSize == sizeof(PDK_CMD_S_PassCard));
PDK_CMD_S_PassCard* pPassCard = (PDK_CMD_S_PassCard*)pBuffer;
//转换不出玩家视图;
uint16 wViewID = SwitchViewChairID(pPassCard->wPassCardUser);
m_aryPlayer[wViewID]->setPassVisible(true);
m_aryPlayer[wViewID]->setOutCardData(nullptr, 0);
m_aryPlayer[wViewID]->killClock();
//播放不出声音;
playSoundEffect(PDK_ST_PASS, m_aryPlayer[wViewID]->GetGender());
m_wCurChairID = pPassCard->wCurrentUser;
//如果一轮结束清空本轮出牌;
if (pPassCard->cbTurnOver)
{
m_wTurnWiner = m_wCurChairID;
m_cbTurnCardCount = 0;
zeromemory(m_cbTurnCardData, sizeof(m_cbTurnCardData));
for (uint8 i = 0; i < PDK_GAME_PLAYER; i++)
{
m_aryPlayer[i]->setPassVisible(false);
m_aryPlayer[i]->setOutCardData(nullptr, 0);
}
}
//如果是自已不出隐藏出牌按钮;
if (wViewID == PDK_SELF_VIEW_ID)
{
hideOutCardButtons();
}
//更新出牌按钮状态;
updateButtonsStatus(pPassCard->wCurrentUser, m_cbTimeOutCard, pPassCard->cbTurnOver>0);
}
//更新叫分按钮;
void PDKGameScene::updateCallButtons()
{
m_pAryBtnCall->setVisible(true);
m_pBtnNoCall->setVisible(true);
//显示当前玩家倒计时;
m_aryPlayer[PDK_SELF_VIEW_ID]->showClock(m_cbTimeCallScore, [=](void){
//SendPassCall();
});
}
//更新按钮状态;
void PDKGameScene::updateButtonsStatus(uint16 wCurChairID, uint8 cbLeftSeconds, bool bTurnOver/* = false*/)
{
//转换当前玩家视图;
uint16 wCurViewID = SwitchViewChairID(wCurChairID);
CC_ASSERT(wCurViewID < PDK_GAME_PLAYER);
//如果当前玩家是自已则显示出牌面板;
if (PDK_SELF_VIEW_ID == wCurViewID)
{
m_aryPlayer[wCurViewID]->setPassVisible(false);
m_aryPlayer[wCurViewID]->setOutCardData(nullptr, 0);
m_pBtnPass->setVisible(true);
m_pBtnPass->setEnabled(!bTurnOver);
m_pBtnTips->setVisible(true);
m_pBtnOutCard->setVisible(true);
//m_pBtnOutCard->setEnabled(false);
//搜索出牌;
tagPDKSearchCardResult mCardResult;
uint8 cbResultCount = m_GameLogic.SearchOutCard(m_aryHandCardData, m_aryHandCardCount[PDK_SELF_VIEW_ID],
m_cbTurnCardData, m_cbTurnCardCount, &mCardResult);
if (cbResultCount == 0 && m_cbTurnCardCount > 0)
{
m_pSprTips->setVisible(true);
m_pSprTips->setTexture(PDK_TIPS_ONLY_PASS_PNG_FILE);
m_pBtnTips->setEnabled(false);
m_pBtnOutCard->setEnabled(false);
//// 没有牌能大过上家则2秒后自动点不出
//m_pSprTips->runAction(Sequence::create(DelayTime::create(2.f), [this](Ref*){
// if (getSelfChairID() == m_wCurChairID)
// {
// SendSocketData(PDK_SUB_C_PASS_CARD);
// m_pHandCardLayer->downAllCard();
// }
//}, nullptr));
}
else
{
m_pBtnTips->setEnabled(true);
// 有牌必出控制;
if (m_GameLogic.IsHasGameRule(ePDKRuleEnum_MustOutCard))
{
m_pBtnPass->setEnabled(false);
}
checkOutCardButton();
}
//不出回调函数;
auto callback = [=](){
if (getSelfChairID() != m_wCurChairID)
{
CC_ASSERT(false);
return;
}
};
//显示自已倒计时;
m_aryPlayer[wCurViewID]->showClock(cbLeftSeconds, callback);
}
else
{
//显示其它玩家倒计时;
m_aryPlayer[wCurViewID]->showClock(cbLeftSeconds);
}
}
//隐藏出牌按钮;
void PDKGameScene::hideOutCardButtons()
{
m_pSprTips->setVisible(false);
m_pBtnPass->setVisible(false);
m_pBtnTips->setVisible(false);
m_pBtnOutCard->setVisible(false);
}
//隐藏出牌按钮;
void PDKGameScene::checkOutCardButton()
{
uint8 aryShootCardData[PDK_MAX_COUNT] = { 0 };
uint8 cbShootCardCount = 0;
m_pHandCardLayer->getShootCardData(aryShootCardData, cbShootCardCount);
if (cbShootCardCount==0)
{
m_pSprTips->setVisible(true);
m_pSprTips->setTexture(PDK_TIPS_CHOOSECARD_PNG_FILE);
m_pBtnOutCard->setEnabled(false);
return;
}
bool bLastCard = (cbShootCardCount == m_aryHandCardCount[PDK_SELF_VIEW_ID]);
uint8 cbCardType = m_GameLogic.GetCardType(aryShootCardData, cbShootCardCount, bLastCard);
if (cbCardType == PDK_CT_ERROR)
{
m_pSprTips->setVisible(true);
m_pSprTips->setTexture(PDK_TIPS_OUT_ERROR_PNG_FILE);
m_pBtnOutCard->setEnabled(false);
return;
}
else
{
m_pSprTips->setVisible(false);
}
// 必出牌判断;
if (m_cbMustOutCard != 0x0 && !m_GameLogic.SearchMustOutCard(aryShootCardData, cbShootCardCount, m_cbMustOutCard))
{
m_pSprTips->setVisible(true);
m_pSprTips->setTexture(PDK_TIPS_OUT_ERROR_PNG_FILE);
m_pBtnOutCard->setEnabled(false);
return;
}
// 下家剩余一张牌的情况下,出单牌必须是手牌最大的一张。
if (cbCardType == PDK_CT_SINGLE)
{
uint16 wSelfChairID = getSelfChairID();
uint16 wNextChairID = getNextChairID(wSelfChairID);
// 只剩下一张牌;
uint16 wViewID = SwitchViewChairID(wNextChairID);
if (1 == m_aryHandCardCount[wViewID])
{
if (m_GameLogic.GetCardLogicValue(aryShootCardData[0]) != m_GameLogic.GetMaxLogicValue(m_aryHandCardData, m_aryHandCardCount[PDK_SELF_VIEW_ID]))
{
m_pSprTips->setVisible(true);
m_pSprTips->setTexture(PDK_TIPS_OUT_ERROR_PNG_FILE);
m_pBtnOutCard->setEnabled(false);
return ;
}
}
}
if (m_cbTurnCardCount > 0)
{
bool bRet = m_GameLogic.CompareCard(m_cbTurnCardData, aryShootCardData, m_cbTurnCardCount, cbShootCardCount, bLastCard);
if (bRet)
{
m_pBtnOutCard->setEnabled(true);
}
else
{
m_pBtnOutCard->setEnabled(false);
}
}
else
{
m_pBtnOutCard->setEnabled(true);
}
}
//设置基分;
void PDKGameScene::onSubGameSetBaseScore(const void * pBuffer, uint16 wDataSize)
{
LONG lBaseScore = *(LONG*)pBuffer;
}
//游戏结束;
void PDKGameScene::onSubGameEnd(const void * pBuffer, uint16 wDataSize)
{
//校验数据;
CC_ASSERT(wDataSize == sizeof(PDK_CMD_S_GameConclude));
PDK_CMD_S_GameConclude* pGameEnd = (PDK_CMD_S_GameConclude*)pBuffer;
m_bGameStart = false;
m_cbGameStatus = PDK_GAME_SCENE_FREE;
std::string aryNickName[PDK_GAME_PLAYER];
for (uint8 i = 0; i < PDK_GAME_PLAYER; i++)
{
uint16 wViewID = SwitchViewChairID(i);
aryNickName[i] = m_aryPlayer[wViewID]->GetNickName();
m_aryPlayer[wViewID]->killClock();
}
uint16 wMyChairID = getSelfChairID();
if (pGameEnd->lGameScore[wMyChairID] > 0)
{
playSoundEffect(PDK_ST_WIN);
}
else
{
playSoundEffect(PDK_ST_LOSE);
}
int nScoreTimes = 1;
for (uint8 i = 0; i < m_cbBombCount; i++)
{
nScoreTimes *= 2;
}
m_pResultLayer->show(m_wLandChairID, wMyChairID, aryNickName, pGameEnd, m_wLastWiner, m_cbLastCardCount, m_cbLastCardData);
}
//玩家托管;
void PDKGameScene::onSubGameTrustee(const void * pBuffer, uint16 wDataSize)
{
////校验数据;
//CC_ASSERT(wDataSize == sizeof(PDK_CMD_S_Trustee));
//PDK_CMD_S_Trustee* pTrustee = (PDK_CMD_S_Trustee*)pBuffer;
//uint16 wViewID = SwitchViewChairID(pTrustee->wTrusteeUser);
//m_aryTrustee[wViewID] = (pTrustee->bTrustee>0);
//if (PDK_SELF_VIEW_ID == wViewID)
//{
// if (m_aryTrustee[wViewID])
// {
// m_pPanelTrustee->setVisible(true);
// m_pHandCardLayer->downAllCard();
// }
// else
// {
// m_pPanelTrustee->setVisible(false);
// }
//}
}
//用户进入;
void PDKGameScene::OnEventUserEnter(GamePlayer * pPlayer)
{
if (pPlayer == nullptr) return;
uint8 cbUserStatus = pPlayer->GetUserStatus();
if (pPlayer->GetChairID() == getSelfChairID())
{
//更新准备按钮状态;
if (cbUserStatus >= US_READY)
{
m_pBtnReady->setEnabled(false);
m_pBtnReady->setVisible(false);
}
}
}
//玩家状态改变;
void PDKGameScene::OnEventUserStatus(GamePlayer * pPlayer)
{
if ( pPlayer->GetChairID() == getSelfChairID() )
{
//更新准备按钮状态;
if (pPlayer->GetUserStatus() > US_READY)
{
m_pBtnReady->setEnabled(false);
}
else if (pPlayer->GetUserStatus() == US_READY)
{
m_pBtnReady->setEnabled(false);
}
}
std::string strIps[PDK_GAME_PLAYER] = {};
std::string strNickNames[PDK_GAME_PLAYER] = {};
// 同IP判断;
if ((m_PrivateRoomInfo.dwPlayCout <= 0) && !m_PrivateRoomInfo.bStartGame)
{
IsSameIp();
}
}
// 同IP判断;
void PDKGameScene::IsSameIp()
{
std::string strIps[PDK_GAME_PLAYER] = {};
std::string strNickNames[PDK_GAME_PLAYER] = {};
// 同IP判断;
for (WORD i = 0; i < PDK_GAME_PLAYER; i++)
{
GamePlayer* pPlayer = getPlayerByChairID(i);
if (pPlayer)
{
strIps[i] = pPlayer->GetLogonIp();
strNickNames[i] = pPlayer->GetNickName();
}
}
bool bSameIp = false;
for (WORD i = 0; i < PDK_GAME_PLAYER; i++)
{
WORD wNext = (i + 1) % PDK_GAME_PLAYER;
if ((strIps[i] != "") && (strIps[i] == strIps[wNext]))
{
bSameIp = true;
break;
}
}
//if (bSameIp)
//{
// IpTipScene::Instance().show(strNickNames, strIps, PDK_GAME_PLAYER);
//}
//else if (IpTipScene::Instance().isVisible())
//{
// IpTipScene::Instance().setVisible(false);
//}
}
//玩家金币改变;
void PDKGameScene::OnUserScore(GamePlayer* pPlayer)
{
CC_ASSERT(pPlayer!=nullptr);
if (pPlayer == nullptr) return;
// 不再桌子上;
CC_ASSERT(pPlayer->GetTableID() != INVALID_TABLE && pPlayer->GetChairID() != INVALID_CHAIR);
if (pPlayer->GetTableID() == INVALID_TABLE || pPlayer->GetChairID() == INVALID_CHAIR) return;
// 不是同一桌子玩家;
CC_ASSERT(pPlayer->GetTableID() == getSelfGamePlayer()->GetTableID());
if (pPlayer->GetTableID() != getSelfGamePlayer()->GetTableID()) return;
cocos2d::log(a_u8c("用户%sscore = %d"), pPlayer->GetNickName().c_str(), pPlayer->GetUserScore());
((PDKPlayer*)pPlayer)->updateScore();
}
// 玩家坐标;
Vec2 PDKGameScene::GetPlayerPosByUserID(uint32 dwUserID)
{
PDKPlayer* pPlayer = (PDKPlayer*)getPlayerByUserID(dwUserID);
if (pPlayer == nullptr)
{
return Vec2();
}
const Vec2& ptHeadPos = pPlayer->getHeadPos();
Vec2 ptWorldPos = pPlayer->convertToWorldSpace(ptHeadPos);
return Vec2(ptWorldPos);
}
//调用;
GamePlayer* PDKGameScene::CreatePlayer(IClientUserItem * pIClientUserItem)
{
if (pIClientUserItem->GetChairID() == INVALID_CHAIR)
{
return NULL;
}
if (pIClientUserItem->GetUserID() == UserInfo::Instance().getUserID())
{
m_pLocalPlayer->setUserItem(pIClientUserItem);
return m_pLocalPlayer;
}
else
{
WORD wViewID = SwitchViewChairID(pIClientUserItem->GetChairID());
CC_ASSERT(wViewID!=INVALID_CHAIR);
PDKPlayer* pPlayer = m_aryPlayer[wViewID];
pPlayer->setUserItem(pIClientUserItem);
return pPlayer;
}
return NULL;
}
//椅子号视图转换;
WORD PDKGameScene::SwitchViewChairID(WORD wChairID)
{
//参数判断;
if (wChairID == INVALID_CHAIR) return INVALID_CHAIR;
WORD wSelfChairID = getSelfChairID();
if (wSelfChairID == INVALID_CHAIR) return INVALID_CHAIR;
////转换椅子;
//WORD wChairCount = PDK_GAME_PLAYER;
//WORD wViewChairID = (wChairID + wChairCount * 3 / 2 - wSelfChairID) % wChairCount;
WORD wViewChairID = INVALID_CHAIR;
//转换椅子
if ((m_PrivateRoomInfo.bGameRuleIdex&ePDKRuleEnum_PlayCount) == 0)
{
if (wSelfChairID == wChairID)
{
return PDK_SELF_VIEW_ID;
}
else
{
return PDK_LEFT_VIEW_ID;
}
}
else
{
WORD wChairCount = PDK_GAME_PLAYER;
wViewChairID = (wChairID + wChairCount * 3 / 2 - wSelfChairID) % wChairCount;
}
return wViewChairID;
}
//本人进入游戏 GameFrameBase.cpp调用;
void PDKGameScene::upSelfPlayerInfo()
{
log("Self Enter!!");
return;
}
//不叫消息;
void PDKGameScene::SendCallScore(bool bCallScore)
{
PDK_CMD_C_CallScore call;
call.bCallScore = bCallScore;
SendSocketData(PDK_SUB_C_CALL_SCORE, &call, sizeof(PDK_CMD_C_CallScore));
}
//发牌;
void PDKGameScene::moveSendCardSprite(Sprite* pCardSprite, uint16 wViewID, float fDelayTime)
{
float fEndPosX = 0.f, fEndPosY = 0.f;
uint8 cbSendCardCount = m_arySendCardCount[wViewID];
if (wViewID == PDK_SELF_VIEW_ID)
{
Node* pHandCardPanel = m_pHandCardLayer->getParent();
CC_ASSERT(pHandCardPanel!=nullptr);
int iHandCardSpace = m_pHandCardLayer->getHandCardSpace(cbSendCardCount);
int iStartPosX = pHandCardPanel->getPositionX();
fEndPosX = iStartPosX + pCardSprite->getContentSize().width*0.35f + pCardSprite->getTag() / 3 * iHandCardSpace;
fEndPosY = pHandCardPanel->getPositionY() + pHandCardPanel->getContentSize().height / 2;
}
else
{
fEndPosX = m_aryPlayer[wViewID]->getCardPos().x;
fEndPosY = m_aryPlayer[wViewID]->getCardPos().y;
}
auto pAction = MoveTo::create(0.2f, Vec2(fEndPosX, fEndPosY));
auto fnShowAllCard = [=](Node * pNode)
{
pNode->stopAllActions();
m_GameLogic.SortCardList(m_aryHandCardData, m_aryHandCardCount[PDK_SELF_VIEW_ID], PDK_ST_ORDER);
m_pHandCardLayer->redrawHandCard(m_aryHandCardData, m_aryHandCardCount[PDK_SELF_VIEW_ID]);
};
auto callback = [=](Node* pNode)
{
m_aryHandCardCount[wViewID]++;
m_aryPlayer[wViewID]->setHandCardCount(m_aryHandCardCount[wViewID]);
pNode->removeFromParent();
if (wViewID == PDK_SELF_VIEW_ID) //玩家自己
{
m_pHandCardLayer->addSendCard2Panel();
//发牌完成延时0.2秒显示手牌数据
if (m_aryHandCardCount[wViewID] == cbSendCardCount)
{
this->runAction(Sequence::create(DelayTime::create(0.2f), CallFuncN::create(fnShowAllCard), nullptr));
}
}
};
Action* pCardAction = Sequence::create(DelayTime::create(fDelayTime), pAction, CallFuncN::create(callback), nullptr);
pCardSprite->runAction(pCardAction);
}
//选牌回调;
void PDKGameScene::selectCardCallback(uint8* arySelCardData, uint8 cbSelCardCount)
{
//播放点牌音效;
playSoundEffect(PDK_ST_CLICK_CARD);
if ( getSelfChairID()!=m_wCurChairID )
{
return;
}
checkOutCardButton();
}
//显示底牌;
void PDKGameScene::drawBackCardData()
{
//for (uint8 i = 0; i < PDK_BACK_COUNT; i++)
//{
// uint8 cbCardData = m_aryBackCardData[i];
// PDKSmallCardSprite* pCardSprite = PDKSmallCardSprite::create(cbCardData);
// pCardSprite->ignoreAnchorPointForPosition(false);
// pCardSprite->setAnchorPoint(Vec2(0.5f, 0.5f));
// pCardSprite->setPosition(29, 33);
// pCardSprite->setName(StringUtils::format("BackCardSprite%d", i));
// m_pPanelBackCard->addChild(pCardSprite);
// pCardSprite->runAction(MoveBy::create(0.4f, Vec2(i * 59, 0)));
//}
}
//翻转底牌;
void PDKGameScene::flipBackCard()
{
//for (uint8 i = 0; i < PDK_BACK_COUNT; i++)
//{
// CallFuncN* callback = CallFuncN::create([=](Node* pNode){
// PDKSmallCardSprite* pCardSprite = static_cast<PDKSmallCardSprite*>(pNode);
// pCardSprite->updateUIData(m_aryBackCardData[i]);
// });
//
// Node* pBackCard = m_pPanelBackCard->getChildByName(StringUtils::format("BackCardSprite%d", i));
// CC_ASSERT(pBackCard!=nullptr);
// Action* pAction = Sequence::create(OrbitCamera::create(0.25f, 1, 0, 0, 90, 0, 0), callback, OrbitCamera::create(0.25f, 1, 0, 270, 90, 0, 0), nullptr);
// pBackCard->runAction(pAction);
//}
}
//播放动画
void PDKGameScene::playAnimate(uint8 cbCardType, uint16 wFromChair, uint16 wToChair)
{
SpriteFrameCache* pSpriteFrameCache = SpriteFrameCache::getInstance();
uint16 wFromViewID = SwitchViewChairID(wFromChair);
uint16 wToViewID = SwitchViewChairID(wToChair);
PDKPlayer* pFromUserItem = (wFromViewID != INVALID_CHAIR)?m_aryPlayer[wFromViewID]:nullptr;
PDKPlayer* pToUserItem = (wToViewID != INVALID_CHAIR) ? m_aryPlayer[wToViewID] : nullptr;
const Size& winSize = Director::getInstance()->getWinSize();
//顺子类型;
if (cbCardType == PDK_CT_SINGLE_LINE)
{
if (pFromUserItem!=nullptr)
{
pSpriteFrameCache->addSpriteFramesWithFile("Games/DDZ/Ani/AniLine.plist");
Sprite* pImgLineAni = Sprite::createWithSpriteFrameName("imgAniLine1.png");
if (wFromViewID == PDK_LEFT_VIEW_ID)
{
pImgLineAni->setAnchorPoint(Vec2(0.0f, 0.5f));
}
else if (wFromViewID == PDK_SELF_VIEW_ID)
{
pImgLineAni->setAnchorPoint(Vec2(0.5f, 0.5f));
}
else if (wFromViewID == PDK_RIGHT_VIEW_ID)
{
pImgLineAni->setAnchorPoint(Vec2(1.0f, 0.5f));
}
pImgLineAni->setPosition(pFromUserItem->getOutCardPos());
pFromUserItem->addChild(pImgLineAni);
auto pLineAni = Animation::create();
pLineAni->setDelayPerUnit(0.1f);
for (uint8 i = 1; i <= 10; i++)
{
SpriteFrame* pSpriteFrame = pSpriteFrameCache->getSpriteFrameByName(StringUtils::format("imgAniLine%d.png", i));
pLineAni->addSpriteFrame(pSpriteFrame);
}
pImgLineAni->runAction(Sequence::create(Animate::create(pLineAni), RemoveSelf::create(), nullptr));
}
}
else if (cbCardType == PDK_CT_DOUBLE_LINE) //;
{
if (pFromUserItem != nullptr)
{
pSpriteFrameCache->addSpriteFramesWithFile("Games/DDZ/Ani/AniDouble.plist");
auto pImgDoubleAni = Sprite::createWithSpriteFrameName("imgAniDouble1.png");
if (wFromViewID == PDK_LEFT_VIEW_ID)
{
pImgDoubleAni->setAnchorPoint(Vec2(0, 0.5f));
}
else if (wFromViewID == PDK_SELF_VIEW_ID)
{
pImgDoubleAni->setAnchorPoint(Vec2(0.5f, 0.5f));
}
else if (wFromViewID == PDK_RIGHT_VIEW_ID)
{
pImgDoubleAni->setAnchorPoint(Vec2(1.0f, 0.5f));
}
pImgDoubleAni->setPosition(pFromUserItem->getOutCardPos());
pFromUserItem->addChild(pImgDoubleAni);
auto pDoubleAni = Animation::create();
pDoubleAni->setDelayPerUnit(0.15f);
for (uint8 i = 1; i <= 9; i++)
{
SpriteFrame* pSpriteFrame = pSpriteFrameCache->getSpriteFrameByName(StringUtils::format("imgAniDouble%d.png", i));
pDoubleAni->addSpriteFrame(pSpriteFrame);
}
pImgDoubleAni->runAction(Sequence::create(Animate::create(pDoubleAni), RemoveSelf::create(), nullptr));
}
}
else if (cbCardType == PDK_CT_THREE_LINE) //飞机类型
{
pSpriteFrameCache->addSpriteFramesWithFile("Games/DDZ/Ani/AniPlane.plist");
auto pImgPlaneSprite = Sprite::createWithSpriteFrameName("imgAniPlane1.png");
pImgPlaneSprite->setAnchorPoint(Vec2(1.0f, 0.5f));
pImgPlaneSprite->setPosition(0.0f, winSize.height/2);
m_rootNode->addChild(pImgPlaneSprite);
auto pImgPlaneAni1 = Sprite::createWithSpriteFrameName("imgAniPlane2.png");
pImgPlaneAni1->setPosition(390, 130);
pImgPlaneSprite->addChild(pImgPlaneAni1);
auto pPlaneAni1 = Animation::create();
pPlaneAni1->setDelayPerUnit(0.1f);
pPlaneAni1->addSpriteFrame(pSpriteFrameCache->getSpriteFrameByName("imgAniPlane2.png"));
pPlaneAni1->addSpriteFrame(pSpriteFrameCache->getSpriteFrameByName("imgAniPlane3.png"));
pImgPlaneAni1->runAction(RepeatForever::create(Animate::create(pPlaneAni1)));
auto pImgPlaneAni2 = Sprite::createWithSpriteFrameName("imgAniPlane4.png");
pImgPlaneAni2->setPosition(-55, 150);
pImgPlaneSprite->addChild(pImgPlaneAni2);
auto pPlaneAni2 = Animation::create();
pPlaneAni2->setDelayPerUnit(0.1f);
pPlaneAni2->addSpriteFrame(pSpriteFrameCache->getSpriteFrameByName("imgAniPlane4.png"));
pPlaneAni2->addSpriteFrame(pSpriteFrameCache->getSpriteFrameByName("imgAniPlane5.png"));
pPlaneAni2->addSpriteFrame(pSpriteFrameCache->getSpriteFrameByName("imgAniPlane6.png"));
pImgPlaneAni2->runAction(RepeatForever::create(Animate::create(pPlaneAni2)));
Action* pAction = Sequence::create(MoveBy::create(1.5f, Vec2(winSize.width + 380, 0)), RemoveSelf::create(), nullptr);
pImgPlaneSprite->runAction(pAction);
}
else if (cbCardType == PDK_CT_BOMB_CARD || cbCardType == PDK_CT_3A_BOMB_CARD) //炸弹类型
{
Vec2 ptEndBombPos = Vec2::ZERO;
if (wFromChair == wToChair)
{
ptEndBombPos.x = winSize.width / 2;
ptEndBombPos.y = winSize.height / 2;
}
else
{
if (pToUserItem != nullptr)
{
ptEndBombPos = pToUserItem->getHeadPos();
ptEndBombPos = pToUserItem->convertToWorldSpace(ptEndBombPos);
}
}
if (pFromUserItem != nullptr )
{
pSpriteFrameCache->addSpriteFramesWithFile("Games/DDZ/Ani/AniBomb.plist");
Vec2 ptBeginBombPos = pFromUserItem->getHeadPos();
ptBeginBombPos = pFromUserItem->convertToWorldSpace(ptBeginBombPos);
Sprite* pImgBombAni = Sprite::createWithSpriteFrameName("imgAniBomb1.png");
pImgBombAni->setPosition(ptBeginBombPos);
m_rootNode->addChild(pImgBombAni);
ccBezierConfig tabMovePos = { ptEndBombPos, Vec2(winSize.width / 2, winSize.height / 2), ptBeginBombPos };
EaseSineIn* pMoveAction = EaseSineIn::create(BezierTo::create(0.5f, tabMovePos));
Spawn* pSpawnAction = Spawn::create(RotateBy::create(0.5f, 720), pMoveAction, nullptr);
auto bombFunc = [=](){
if (wFromChair == wToChair)
{
for (uint8 i = 0; i < PDK_GAME_PLAYER; i++)
{
if (i != wFromViewID)
{
Sprite* pImgBombAni2 = Sprite::createWithSpriteFrameName("imgAniBomb15.png");
const Vec2& ptHeadPos = m_aryPlayer[i]->getHeadPos();
pImgBombAni2->setScale(1.4f);
pImgBombAni2->setPositionX(ptHeadPos.x);
pImgBombAni2->setPositionY(ptHeadPos.y + 4);
m_aryPlayer[i]->addChild(pImgBombAni2);
auto pBombAni2 = Animation::create();
pBombAni2->setDelayPerUnit(0.1f);
pBombAni2->addSpriteFrame(pSpriteFrameCache->getSpriteFrameByName("imgAniBomb15.png"));
pBombAni2->addSpriteFrame(pSpriteFrameCache->getSpriteFrameByName("imgAniBomb16.png"));
pBombAni2->addSpriteFrame(pSpriteFrameCache->getSpriteFrameByName("imgAniBomb17.png"));
Action* pAction = Sequence::create(Repeat::create(Animate::create(pBombAni2), 2), RemoveSelf::create(), nullptr);
pImgBombAni2->runAction(pAction);
}
}
}
else
{
if (pToUserItem != nullptr)
{
Sprite* pImgBombAni2 = Sprite::createWithSpriteFrameName("imgAniBomb15.png");
const Vec2& ptHeadPos = pToUserItem->getHeadPos();
pImgBombAni2->setScale(1.4f);
pImgBombAni2->setPositionX(ptHeadPos.x);
pImgBombAni2->setPositionY(ptHeadPos.y + 4);
pToUserItem->addChild(pImgBombAni2);
auto pBombAni2 = Animation::create();
pBombAni2->setDelayPerUnit(0.1f);
pBombAni2->addSpriteFrame(pSpriteFrameCache->getSpriteFrameByName("imgAniBomb15.png"));
pBombAni2->addSpriteFrame(pSpriteFrameCache->getSpriteFrameByName("imgAniBomb16.png"));
pBombAni2->addSpriteFrame(pSpriteFrameCache->getSpriteFrameByName("imgAniBomb17.png"));
Action* pAction = Sequence::create(Repeat::create(Animate::create(pBombAni2), 2), RemoveSelf::create(), nullptr);
pImgBombAni2->runAction(pAction);
}
}
};
auto callback = [=](){
//震动/闪屏
m_rootNode->runAction(ShakeBy::create(0.5f, Vec2(10, 10)));
Device::vibrate(0.5f);
Sprite* pImgBombAni1 = Sprite::createWithSpriteFrameName("imgAniBomb3.png");
if (wFromChair == wToChair)
{
pImgBombAni1->setPosition(ptEndBombPos);
m_rootNode->addChild(pImgBombAni1);
}
else
{
if (pToUserItem != nullptr)
{
pImgBombAni1->setPosition(pToUserItem->getHeadPos());
}
pToUserItem->addChild(pImgBombAni1);
}
auto pBombAni1 = Animation::create();
pBombAni1->setDelayPerUnit(0.1f);
for (uint8 i = 3; i <= 14; i++)
{
SpriteFrame* pSpriteFrame = pSpriteFrameCache->getSpriteFrameByName(StringUtils::format("imgAniBomb%d.png", i));
pBombAni1->addSpriteFrame(pSpriteFrame);
}
Action* pAction = Sequence::create(Animate::create(pBombAni1), RemoveSelf::create(), CallFunc::create(bombFunc), nullptr);
pImgBombAni1->runAction(pAction);
};
pImgBombAni->runAction(Sequence::create(pSpawnAction, RemoveSelf::create(), CallFunc::create(callback), nullptr));
}
}
//else if (cbCardType == PDK_CT_MISSILE_CARD) //火箭类型
//{
// pSpriteFrameCache->addSpriteFramesWithFile("Games/DDZ/Ani/AniRocket.plist");
// //auto pImgRocketBg = Sprite::createWithSpriteFrameName("imgAniRocket1.png");
// //pImgRocketBg->setPosition(winSize.width/2,winSize.height/2);
// //pImgRocketBg->setScaleX(winSize.width/pImgRocketBg->getContentSize().width);
// //pImgRocketBg->setScaleY(winSize.height/pImgRocketBg->getContentSize().height);
// //m_rootNode->addChild(pImgRocketBg);
// //pImgRocketBg->runAction(RepeatForever::create(cBlink::create(0.5f,1)));
// Sprite* pImgRocketSprite = Sprite::createWithSpriteFrameName("imgAniRocket2.png");
// pImgRocketSprite->setAnchorPoint(Vec2(0.5f, 0.0f));
// pImgRocketSprite->setPosition(winSize.width / 2, 85);
// m_rootNode->addChild(pImgRocketSprite);
// Sprite* pImgRocketAni1 = Sprite::createWithSpriteFrameName("imgAniRocket5.png");
// pImgRocketAni1->setAnchorPoint(Vec2(0.5f, 1.0f));
// pImgRocketAni1->setPosition(177, 85);
// pImgRocketSprite->addChild(pImgRocketAni1);
// auto pRocketAni1 = Animation::create();
// pRocketAni1->setDelayPerUnit(0.1f);
// pRocketAni1->addSpriteFrame(pSpriteFrameCache->getSpriteFrameByName("imgAniRocket5.png"));
// pRocketAni1->addSpriteFrame(pSpriteFrameCache->getSpriteFrameByName("imgAniRocket6.png"));
// pImgRocketAni1->runAction(RepeatForever::create(Animate::create(pRocketAni1)));
// Sprite* pImgRocketAni2 = Sprite::createWithSpriteFrameName("imgAniRocket3.png");
// pImgRocketAni2->setAnchorPoint(Vec2(0.5f, 1.0f));
// pImgRocketAni2->setPosition(177, -30);
// pImgRocketSprite->addChild(pImgRocketAni2);
// auto pRocketAni2 = Animation::create();
// pRocketAni2->setDelayPerUnit(0.1f);
// pRocketAni2->addSpriteFrame(pSpriteFrameCache->getSpriteFrameByName("imgAniRocket3.png"));
// pRocketAni2->addSpriteFrame(pSpriteFrameCache->getSpriteFrameByName("imgAniRocket4.png"));
// pImgRocketAni2->runAction(RepeatForever::create(Animate::create(pRocketAni2)));
// auto callback = [=](){
// pImgRocketSprite->runAction(Sequence::create(MoveBy::create(1.0f, Vec2(0, winSize.height + 610)), RemoveSelf::create(), nullptr));
// };
// pImgRocketAni2->runAction(Sequence::create(DelayTime::create(0.5f), RemoveSelf::create(), CallFunc::create(callback), nullptr));
// //震动/闪屏
// m_rootNode->runAction(ShakeBy::create(0.5f, Vec2(10, 10)));
// Device::vibrate(0.5f);
//}
//else if (cbCardType == PDK_RLT_SPRING)//春天
//{
// pSpriteFrameCache->addSpriteFramesWithFile("Games/PDK/Ani/AniSpring.plist");
// auto pSpringNode = CSLoader::createNodeWithVisibleSize("Games/PDK/Table/SpringAniScene.csb");
// m_rootNode->addChild(pSpringNode);
// auto pMainPanel = pSpringNode->getChildByName("MainPanel");
// auto img9FloweBg = pMainPanel->getChildByName("img9FloweBg");
// img9FloweBg->setScale(0.0f);
// img9FloweBg->stopAllActions();
// img9FloweBg->runAction(ScaleTo::create(0.3f, 1.2f));
// for (uint8 i=1; i<=8; i++)
// {
// auto flower = pMainPanel->getChildByName(StringUtils::format("imgFlower%d", i));
// flower->setOpacity(0);
// flower->runAction(FadeIn::create(0.3f));
// flower->runAction(RepeatForever::create(RotateBy::create(0.5f, 180)));
// auto star = pMainPanel->getChildByName(StringUtils::format("imgStar%d", i));
// star->runAction(RepeatForever::create(Blink::create(0.5f, 1)));
// }
// pSpringNode->runAction(Sequence::create(DelayTime::create(1.5f), RemoveSelf::create(), nullptr));
//}
}
void PDKGameScene::playSoundEffect(const uint8 cbCardType, uint8 cbSex/*=1*/, const uint8 cbData/*=0*/)
{
CocosDenshion::SimpleAudioEngine* pAudio = CocosDenshion::SimpleAudioEngine::getInstance();
std::string strSoundFile;
if (cbSex > 0)
{
cbSex--;
}
switch (cbCardType)
{
case PDK_CT_SINGLE:
{
int nFlagID = 0;
if (CARD_LITTLE_JOKER == cbData) //小王
{
nFlagID = 14;
}
else if (CARD_LITTLE_JOKER == cbData) //大王
{
nFlagID = 15;
}
else
{
nFlagID = m_GameLogic.GetCardValue(cbData);
}
strSoundFile = StringUtils::format(PDK_DANZHANG_FILE, cbSex, nFlagID);
break;
}
case PDK_CT_DOUBLE:
{
int nFlagID = m_GameLogic.GetCardValue(cbData);
strSoundFile = StringUtils::format(PDK_LIANGZHANG_FILE, cbSex, nFlagID);
break;
}
//case PDK_CT_THREE:
//{
// strSoundFile = StringUtils::format(PDK_3ZHANG_FILE, cbSex);
// break;
//}
case PDK_CT_SINGLE_LINE:
{
pAudio->playEffect(PDK_SHUNZI_EFF_FILE);
strSoundFile = StringUtils::format(PDK_SHUNZI_FILE, cbSex);
break;
}
case PDK_CT_DOUBLE_LINE:
{
pAudio->playEffect(PDK_LIANDUI_EFF_FILE);
strSoundFile = StringUtils::format(PDK_LIANDUI_FILE, cbSex);
break;
}
case PDK_CT_THREE_LINE:
{
strSoundFile = StringUtils::format(PDK_FEIJI_FILE, cbSex);
pAudio->playEffect(PDK_FEIJI_EFF_FILE);
break;
}
case PDK_CT_THREE_TAKE_TWO:
{
strSoundFile = StringUtils::format(PDK_3DAI2_FILE, cbSex);
break;
}
case PDK_CT_FOUR_TAKE_THREE:
{
strSoundFile = StringUtils::format(PDK_4DAI2_FILE, cbSex);
break;
}
case PDK_CT_BOMB_CARD:
case PDK_CT_3A_BOMB_CARD:
{
pAudio->playEffect(PDK_ZHADAN_EFF_FILE);
strSoundFile = StringUtils::format(PDK_ZHADAN_FILE, cbSex);
break;
}
case PDK_ST_DEAL_CARD:
{
strSoundFile = PDK_FAPAI_EFF_FILE;
break;
}
case PDK_ST_PASS:
{
int nSoundID = (rand() % 4) + 1;
strSoundFile = StringUtils::format(PDK_PASS_FILE, cbSex, nSoundID);
break;
}
case PDK_ST_CALL:
{
if (cbData <= 3)
{
strSoundFile = StringUtils::format(PDK_JIAO_FEN_FILE, cbSex, cbData);
}
else
{
strSoundFile = StringUtils::format(PDK_BUJIAO_FILE, cbSex);
}
break;
}
case PDK_ST_CLICK_CARD:
{
strSoundFile = PDK_DIANPAI_EFF_FILE;
break;
}
case PDK_ST_OUT_CARD:
{
strSoundFile = PDK_CHUPAI_EFF_FILE;
break;
}
case PDK_ST_LEFT_ONE_CARD:
{
strSoundFile = StringUtils::format(PDK_ZUIHOUYIZHANG_FILE, cbSex);
break;
}
case PDK_ST_WIN:
{
strSoundFile = PDK_WIN_EFF_FILE;
break;
}
case PDK_ST_LOSE:
{
strSoundFile = PDK_LOSE_EFF_FILE;
break;
}
}
CC_ASSERT(!strSoundFile.empty());
pAudio->playEffect(strSoundFile.c_str());
//SimpleAudioEngine::getInstance()->playEffect(fillpath,isRe);
}
/************************************* 语音 ***********************************************************/
// 按住语音按钮
void PDKGameScene::OnButtonVoiceTouched(Ref*, Widget::TouchEventType type)
{
if (Widget::TouchEventType::BEGAN == type)
{
// 暂停播放背景音乐;
CocosDenshion::SimpleAudioEngine::getInstance()->pauseBackgroundMusic();
if (m_pVoiceNode->isVisible())
{
m_pVoiceNode->setVisible(false);
m_pVoiceNode->stopAllActions();
YvVoiceManager::GetInstance()->StopRecord();
return;
}
m_pVoiceNode->setVisible(true);
// 启动帧动画;
auto action = CSLoader::createTimeline("Games/DDZ/VoiceNode.csb");
action->gotoFrameAndPlay(0);
m_pVoiceNode->runAction(action);
YvVoiceManager::GetInstance()->StartRecord();
}
else if ((Widget::TouchEventType::CANCELED == type) || (Widget::TouchEventType::ENDED == type))
{
// 继续播放背景音乐;
CocosDenshion::SimpleAudioEngine::getInstance()->resumeBackgroundMusic();
if (!m_pVoiceNode->isVisible())
{
return;
}
m_pVoiceNode->setVisible(false);
m_pVoiceNode->stopAllActions();
YvVoiceManager::GetInstance()->StopRecord();
}
}
// 获取下家椅子号;
uint16 PDKGameScene::getNextChairID(uint16 wChairID)
{
//下家剩余一张牌的情况下,出单牌必须是手牌最大的一张;
uint16 wNextChairID = (wChairID + 1) % PDK_GAME_PLAYER;
// 如果当前玩家为空,继续下一个玩家(一共3个位置最少2个人打牌不可能存在连续两个为空只判断一次就好了);
if (!m_aryActiveStatus[wNextChairID])
{
wNextChairID = (wNextChairID + 1) % PDK_GAME_PLAYER;
}
ASSERT(m_aryActiveStatus[wNextChairID]);
return wNextChairID;
}
/************************************* 房间信息 ***********************************************************/
// 房间信息消息
void PDKGameScene::OnSocketSubPrivateRoomInfo(CMD_GF_Private_Room_Info* pNetInfo)
{
m_PrivateRoomInfo = *pNetInfo;
m_dwRoomID = pNetInfo->dwRoomNum;
string strRoomID = StringUtils::format("%d", m_dwRoomID);
m_txtPrivateRoomID->setString(utility::a_u8(strRoomID));
m_txtPrivateRoomID->setVisible(true);
uint32 dwPlayCout = __max(pNetInfo->dwPlayCout+1, 1);
dwPlayCout = __min(dwPlayCout, pNetInfo->dwPlayTotal);
string strPlayCount = StringUtils::format("%u/%u", dwPlayCout, pNetInfo->dwPlayTotal);
cocos2d::log("dwPlayCout = %d", pNetInfo->dwPlayCout);
m_txtPrivatePlayCount->setString(utility::a_u8(strPlayCount.c_str()));
m_txtPrivatePlayCount->setVisible(true);
std::string strGameRule = getGameRule(pNetInfo->bGameRuleIdex);
m_txtCompareDesc->setString(utility::a_u8(strGameRule));
m_txtCompareDesc->setVisible(true);
SetChairs();
if (pNetInfo->bStartGame)
{
//如果游戏已开始则隐藏“返回大厅”按钮,显示“解散房间”按钮
m_btnWeiXin->setVisible(false);
m_pBtnLeave->setVisible(false);
m_pBtnReady->setVisible(false);
m_btnDismissRoom->setVisible(true);
//私人场已经开始,重连上游戏自带发送准备消息;
GamePlayer* pSelfPlayer = getSelfGamePlayer();
if (!m_pResultLayer->isVisible() && (pSelfPlayer != nullptr) && (pSelfPlayer->GetUserStatus() == US_SIT) && (m_cbGameStatus == PDK_GAME_SCENE_FREE))
{
SendUserReady();
}
}
else
{
GamePlayer* pPlayer = getSelfGamePlayer();
//如果房间主人是自已则隐藏“返回大厅”按钮,显示“解散房间”按钮
if (pPlayer != nullptr && pNetInfo->dwCreateUserID == pPlayer->GetUserID())
{
m_pBtnLeave->setVisible(false);
m_btnDismissRoom->setVisible(true);
}
//游戏未开始显示微信分享按钮
if (pNetInfo->dwPlayCout <= 0)
{
m_btnWeiXin->setVisible(true);
m_pBtnReady->setVisible(true);
}
}
}
// 私人场结束
void PDKGameScene::OnSocketSubPrivateEnd(void* data, int dataSize)
{
m_bPrivateEnd = true;
// 申请解散界面
DismissScene::Instance().hide();
GamePlayer* players[PDK_GAME_PLAYER];
for (int i = 0; i < PDK_GAME_PLAYER; i++)
{
players[i] = getPlayerByChairID(i);
}
if (m_pPrivateScene)
{
DataStream kDataStream(data, dataSize);
PDK_CMD_S_Private_End_Info kNetInfo;
kNetInfo.StreamValue(kDataStream, false);
//SCORE lGameGold = m_PrivateRoomInfo.lGameGold*m_PrivateRoomInfo.dwPlayCost;
//m_pPrivateScene->ShowGameResult(&kNetInfo, players, (m_PrivateRoomInfo.cbUnionGoldOpen == 1), lGameGold, m_PrivateRoomInfo.lScoreMultiple);
// 欢乐场
if (m_PrivateRoomInfo.cbUnionGoldOpen == 1)
{/*
SCORE lGameGold = m_PrivateRoomInfo.lGameGold*m_PrivateRoomInfo.dwPlayCost;
m_pPrivateScene->ShowGameResult(&kNetInfo, players, (m_PrivateRoomInfo.cbUnionGoldOpen == 1), lGameGold, m_PrivateRoomInfo.lScoreMultiple);*/
m_pPrivateScene->ShowGameResult(&kNetInfo, players, m_PrivateRoomInfo, m_PrivateScoreInfo);
}
else
{
m_pPrivateScene->ShowGameResult(&kNetInfo, players, m_PrivateRoomInfo.cbBaseScore);
}
m_pResultLayer->SetShowPrivate();
if (m_pResultLayer->isVisible() == false)
{
m_pPrivateScene->pushScene();
}
}
}
void PDKGameScene::onEventShowPrivate(cocos2d::EventCustom *event)
{
if (m_pPrivateScene)
{
m_pPrivateScene->pushScene();
}
}
// 请求解散房间
void PDKGameScene::OnSocketSubPrivateDismissInfo(CMD_GF_Private_Dismiss_Info* pNetInfo)
{
std::string aryName[PDK_GAME_PLAYER];
BYTE aryResult[PDK_GAME_PLAYER] = { 0 }; // 0 未选择 1 同意 2 不同意
bool bHasSelf = false;
uint32 dwMyChairID = getSelfChairID();
for (uint32 i = 0; i < pNetInfo->dwDissUserCout; i++)
{
uint32 dwChairID = pNetInfo->dwDissChairID[i];
GamePlayer* pPlayer = getPlayerByChairID(dwChairID);
if (pPlayer != nullptr && dwChairID < PDK_GAME_PLAYER)
{
aryResult[dwChairID] = 1;
}
if (dwMyChairID == dwChairID)
{
bHasSelf = true;
}
}
for (uint32 i = 0; i < pNetInfo->dwNotAgreeUserCout; i++)
{
uint32 dwChairID = pNetInfo->dwNotAgreeChairID[i];
GamePlayer* pPlayer = getPlayerByChairID(dwChairID);
if (pPlayer != nullptr && dwChairID < PDK_GAME_PLAYER)
{
aryResult[dwChairID] = 2;
}
if (dwMyChairID == dwChairID)
{
bHasSelf = true;
}
}
GamePlayer* players[PDK_GAME_PLAYER];
for (int i = 0; i < PDK_GAME_PLAYER; i++)
{
players[i] = getPlayerByChairID(i);
}
DismissScene::Instance().show(aryResult, players, !bHasSelf, PDK_GAME_PLAYER);
//DismissScene::Instance().show(aryName, aryResult, !bHasSelf);
}
void PDKGameScene::OnSocketSubPrivateDismissResult(CMD_GF_Private_Dismiss_Result* pNetInfo)
{
if (pNetInfo->bSuccess && false == m_PrivateRoomInfo.bStartGame)
{
Director::getInstance()->popScene();
}
else
{
DismissScene::Instance().hide();
}
}
//////////////////////////////// 游戏录像 //////////////////////////////////////////
// 开始录像播放
void PDKGameScene::StartGameRecord()
{
if (m_GameRecord.playersVec.size() < 2)
{
return;
}
// 初始化房间信息;
OnSocketSubPrivateRoomInfo(&m_GameRecord.roomInfo);
m_iActRecordIdex = 0;
m_txtRecordPercent->setString(utility::toString(m_iActRecordIdex * 100 / m_GameRecord.actionVec.size(), "%"));
schedule(schedule_selector(GameFrameBase::NextRecordAction), m_RecordTime);
return;
}
void PDKGameScene::NextRecordAction(float dt)
{
cocos2d::log("NextRecordAction...m_iActRecordIdex = %d", m_iActRecordIdex);
// 已经播放完了
if (m_iActRecordIdex >= (int)m_GameRecord.actionVec.size() || !isVisible())
{
m_txtRecordPercent->setString("100%");
m_btnPlay->setVisible(true);
m_btnPause->setVisible(false);
unschedule(schedule_selector(GameFrameBase::NextRecordAction));
return;
}
// 下一个操作记录;
tagGameRecordOperateResult& kAction = m_GameRecord.actionVec[m_iActRecordIdex];
// 游戏开始;
if (kAction.wSubCmdID == PDK_SUB_S_GAME_START)
{
m_cbTimeOutCard = 15;
m_cbTimeCallScore = 15;
m_cbTimeStartGame = 15;
m_cbTimeHeadOutCard = 15;
PDK_CMD_S_GameStart gameStart;
kAction.subMessageData.popValue(&gameStart, sizeof(PDK_CMD_S_GameStart));
CC_ASSERT(m_wRecordSelfChairID != INVALID_CHAIR);
for (uint8 i = 0; i < m_GameRecord.playersVec.size(); i++)
{
if (!gameStart.bActiveStatus[i])continue;
tagGameRecordPlayer& kRecordPlayer2 = m_GameRecord.playersVec[i];
if (kRecordPlayer2.wChairID == m_wRecordSelfChairID)
{
for (int j = 0; j < kRecordPlayer2.cbCardData.size(); j++)
{
m_aryHandCardData[j] = kRecordPlayer2.cbCardData[j];
}
}
else
{
uint16 wViewID = SwitchViewChairID(kRecordPlayer2.wChairID);
for (int j = 0; j < kRecordPlayer2.cbCardData.size(); j++)
{
m_aryAllHandCardData[wViewID][j] = kRecordPlayer2.cbCardData[j];
}
}
}
onSubGameStart(&gameStart, sizeof(PDK_CMD_S_GameStart));
}
// 玩家叫分;
else if (kAction.wSubCmdID == PDK_SUB_S_CALL_SCORE)
{
PDK_CMD_S_CallScore callCard;
kAction.subMessageData.popValue(&callCard, sizeof(PDK_CMD_S_CallScore));
onSubGameCallScore(&callCard, sizeof(PDK_CMD_S_CallScore));
}
// 确认地主;
else if (kAction.wSubCmdID == PDK_SUB_S_BANKER_INFO)
{
PDK_CMD_S_BankerInfo bankerInfo;
kAction.subMessageData.popValue(&bankerInfo, sizeof(PDK_CMD_S_BankerInfo));
onSubGameBankerInfo(&bankerInfo, sizeof(PDK_CMD_S_BankerInfo));
}
// 玩家出牌;
else if (kAction.wSubCmdID == PDK_SUB_S_OUT_CARD)
{
PDK_CMD_S_OutCard outCard;
kAction.subMessageData.popValue(outCard.cbCardCount);
kAction.subMessageData.popValue(outCard.wCurrentUser);
kAction.subMessageData.popValue(outCard.wOutCardUser);
kAction.subMessageData.popValue(outCard.bLastCard);
kAction.subMessageData.popValue(outCard.cbCardData, outCard.cbCardCount);
uint16 wHeadSize = sizeof(PDK_CMD_S_OutCard) - sizeof(outCard.cbCardData);
onSubGameOutCard(&outCard, (wHeadSize + outCard.cbCardCount*sizeof(uint8)));
}
// 玩家放弃出牌;
else if (kAction.wSubCmdID == PDK_SUB_S_PASS_CARD)
{
PDK_CMD_S_PassCard passCard;
kAction.subMessageData.popValue(&passCard, sizeof(PDK_CMD_S_PassCard));
onSubGamePassCard(&passCard, sizeof(PDK_CMD_S_PassCard));
}
// 游戏结束;
else if (kAction.wSubCmdID == PDK_SUB_S_GAME_CONCLUDE)
{
PDK_CMD_S_GameConclude GameEnd;
kAction.subMessageData.popValue(&GameEnd, sizeof(PDK_CMD_S_GameConclude));
onSubGameEnd(&GameEnd, sizeof(PDK_CMD_S_GameConclude));
}
m_iActRecordIdex++;
m_txtRecordPercent->setString(utility::toString(m_iActRecordIdex * 100 / m_GameRecord.actionVec.size(), "%"));
}
std::string PDKGameScene::getGameRule(uint32 dwGameRule)
{
std::string strGameRule = "";
// 不带王规则;
if ((dwGameRule&ePDKRuleEnum_MustOutCard) > 0)
{
strGameRule += "有牌必押";
}
if ((dwGameRule&ePDKRuleEnum_PlayCount) > 0)
{
if (strGameRule.length() > 0)
{
strGameRule += "";
}
strGameRule += "3人";
}
else
{
if (strGameRule.length() > 0)
{
strGameRule += "";
}
strGameRule += "2人";
}
if ((dwGameRule&ePDKRuleEnum_3ABomb) > 0)
{
if (strGameRule.length() > 0)
{
strGameRule += "";
}
strGameRule += "3A炸弹";
}
if ((dwGameRule&ePDKRuleEnum_FOUR_TAKE_THREE) > 0)
{
if (strGameRule.length() > 0)
{
strGameRule += "";
}
strGameRule += "四带三";
}
if ((dwGameRule&ePDKRuleEnum_DADU) > 0)
{
if (strGameRule.length() > 0)
{
strGameRule += "";
}
strGameRule += "打独";
}
if ((dwGameRule&ePDKRuleEnum_Bomb_Score) > 0)
{
if (strGameRule.length() > 0)
{
strGameRule += "";
}
strGameRule += "炸弹+10";
}
return strGameRule;
}
int PDKGameScene::getRealChairCount(uint32 dwGameRule)
{
if ((dwGameRule&ePDKRuleEnum_PlayCount) > 0)
{
return PDK_GAME_PLAYER;
}
else
{
return 2;
}
}
// 根据配置显示椅子;
void PDKGameScene::SetChairs()
{
WORD wChairID = getRealChairCount(m_PrivateRoomInfo.bGameRuleIdex);
for (WORD i = 0; i < wChairID; i++)
{
PDKPlayer* pPlayer = m_aryPlayer[i];
if (pPlayer == nullptr)continue;
pPlayer->setVisible(true);
}
}