cocos2dx《单机斗地主》源码解剖之六 玩家(人)的出牌(2)

前端之家收集整理的这篇文章主要介绍了cocos2dx《单机斗地主》源码解剖之六 玩家(人)的出牌(2)前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。

下面分析//牌的张数大于等于5张的类型判断,原代码如下:

int GameScene::PaiDuanPaiXing(){  
    //对出的牌进行排序  
    PlayerOutPaiXu(m_arrPlayerOut);  
    //牌型判断  
    int lengh = m_arrPlayerOut->count();  
    PaiXing px;  
    //牌的张数少于5张类型判断 单,对,三张,四张  
    if(lengh<5 && lengh>0){  
        Poker* pk = (Poker *)m_arrPlayerOut->objectAtIndex(0);  
        Poker* pk1 = (Poker *)m_arrPlayerOut->objectAtIndex(lengh-1);  
        if(pk->getNum() == pk1->getNum())  
            return lengh;  
        //三带一  
        pk1 = (Poker *)m_arrPlayerOut->objectAtIndex(lengh-2);  
        if(pk->getNum() == pk1->getNum() && lengh == 4)  
            return THREE_ONE_CARD;  
        //双鬼  
        if(pk->getHuaSe()==Gui && pk1->getHuaSe()==Gui)  
            return BOMB_CARD;  
    }  
    //牌的张数大于等于5张的类型判断  
    if(lengh>=5)  
    {  
        //是否为连牌牌型(单)  
        if(IsLianPai())  
            return CONNECT_CARD;  
        if(IsLianDui())   //判断连对  
            return COMPANY_CARD;  
        //判断飞机类型  
        return IsFeiJi();  
    }  
    return ERROR_CARD;  
}  
首先看一下IsLianPai()这个代码,这个是判断是否为连牌,比如34567.下面贴上代码

bool GameScene::IsLianPai(){
	int lengh = m_arrPlayerOut->count();
	CCArray * arr = m_arrPlayerOut;
	//所有牌值必须小于2
	CCObject* object;
	CCARRAY_FOREACH(arr,object){
		if (((Poker *)object)->getNum() >= 12)//12代表牌值2,下面解释为什么
			return false;
	}
	//必须是连续的(前一张牌值加1是否等于后一张牌值)
	for(int i=0; i<lengh-1; ++i){
		Poker* pk = (Poker *)arr->objectAtIndex(i);
		Poker* pk1 = (Poker *)arr->objectAtIndex(i+1);
		if(pk->getNum()+1 != pk1->getNum())
			return false;
	}
	return true;
}
大家一定会对上面的12数值感到疑惑,下面截个图来解释:

牌值我是从0开始设置的,比如3的牌值为0,4为1。。。。。。

接下来放上判断是否是连对 IsLianDui() 代码

bool GameScene::IsLianDui(){
	int lengh = m_arrPlayerOut->count();
	CCArray * arr = m_arrPlayerOut;
	//所有牌值必须小于2
	CCObject* object;
	CCARRAY_FOREACH(arr,object){
		if (((Poker *)object)->getNum() >= 12)
			return false;
	}
	//大于等于6张牌并且数量为偶数
	if(lengh < 6 && lengh%2 != 0)
		return false;
	//必须是连续的
	for(int i=0; i<lengh-2; i+=2){
		Poker* pk = (Poker *)arr->objectAtIndex(i);
		Poker* pk1 = (Poker *)arr->objectAtIndex(i+2);
		if(pk->getNum()+1 != pk1->getNum())
			return false;
	}
	return true;
}
判断飞机类型 IsFeiJi()代码,函数名取的有点不合适,它返回的是一种飞机的类型,而不是bool值,所以很抱歉:

int GameScene::IsFeiJi(){
	int lengh = m_arrPlayerOut->count();
	CRAD_INDEX card_index = FenXiFeiJi();//分析牌是否是飞机,下面解释
	//判断三带二
	if(card_index.three_index.size()*3+card_index.duble_index.size()*2==lengh && card_index.three_index.size()==1 && card_index.duble_index.size()==1)
		return THREE_TWO_CARD;
	//判断飞机
	if(card_index.three_index.size()>1 && card_index.four_index.empty() && IsFeiJiLian(card_index.three_index)){
		//飞机不带
		if(card_index.three_index.size()*3 == lengh && card_index.duble_index.size()+card_index.single_index.size() == 0)
			return AIRCRAFT_CARD;
		//飞机带单
		if(card_index.three_index.size()*3+card_index.single_index.size() == lengh && card_index.duble_index.size() == 0)
			return AIRCRAFT_SINGLE_CARD;
		//飞机带双
		if(card_index.three_index.size()*3+card_index.duble_index.size()*2 == lengh && card_index.single_index.size() == 0)
			return AIRCRAFT_DOBULE_CARD;
	}
	//判断四带
	if(card_index.three_index.empty() && !card_index.four_index.empty() && lengh%2 == 0)
	{
		//四带单
		if(card_index.four_index.size()*4+card_index.single_index.size() == lengh && card_index.four_index.size()==1 && card_index.single_index.size()==2)
			return BOMB_TWO_CARD;
		//四带对
		if(card_index.four_index.size()*4+card_index.duble_index.size()*2 == lengh && card_index.four_index.size()==1 && card_index.duble_index.size()==1)
			return BOMB_TWOOO_CARD;
	}
	return ERROR_CARD;
}
这里注意CRAD_INDEX card_index = FenXiFeiJi(); 这句代码

CRAD_INDEX为一种结构体:

struct CRAD_INDEX//分析飞机
{
	std::vector<int> single_index;//单张
	std::vector<int> duble_index;//双张
	std::vector<int> three_index;//三张
	std::vector<int> four_index;//四张
};
以上的结构体是为了 对出的牌进行分类用,下面看看是如何对牌分类的,下面是FenXiFeiJi()的代码

CRAD_INDEX GameScene::FenXiFeiJi(){
	//分析牌型结构
	CCArray* arr = m_arrPlayerOut;
	//飞机的类型
	CRAD_INDEX m_cardIndex; 
	for(int i=0; i<arr->count();)
	{
		int time = 0;//相同牌的个数
		Poker* pk = (Poker *)arr->objectAtIndex(i);
		//找出相同牌
		for(int j=i; j<arr->count(); ++j)
		{
			Poker* pk1 = (Poker *)arr->objectAtIndex(j);
			if(pk->getNum() == pk1->getNum()){
				++time;
				++i;
			}
		}
		//单张
		if(time == 1)
			m_cardIndex.single_index.push_back(pk->getNum());
		else if(time == 2)
			m_cardIndex.duble_index.push_back(pk->getNum());
		else if(time == 3)
			m_cardIndex.three_index.push_back(pk->getNum());
		else if(time == 4)
			m_cardIndex.four_index.push_back(pk->getNum());
	}
	return m_cardIndex;
}

本章至此结束,下面就可以判断玩家(人)出的牌是否合法了。

源码请往前三章下载!

猜你在找的Cocos2d-x相关文章