2276 lines
49 KiB
C++
2276 lines
49 KiB
C++
#include "StdAfx.h"
|
|
#include "GameLogic.h"
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
//静态变量
|
|
|
|
//扑克数据
|
|
const BYTE CGameLogic::m_cbCardDataArray[MAX_REPERTORY]=
|
|
{
|
|
0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09, //万子
|
|
0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09, //万子
|
|
0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09, //万子
|
|
0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09, //万子
|
|
0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19, //索子
|
|
0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19, //索子
|
|
0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19, //索子
|
|
0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19, //索子
|
|
0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29, //同子
|
|
0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29, //同子
|
|
0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29, //同子
|
|
0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29, //同子
|
|
0x31,0x32,0x33,0x34,0x35,0x36,0x37, //番子
|
|
0x31,0x32,0x33,0x34,0x35,0x36,0x37, //番子
|
|
0x31,0x32,0x33,0x34,0x35,0x36,0x37, //番子
|
|
0x31,0x32,0x33,0x34,0x35,0x36,0x37, //番子
|
|
};
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|
|
|
|
//构造函数
|
|
CGameLogic::CGameLogic()
|
|
{
|
|
}
|
|
|
|
//析构函数
|
|
CGameLogic::~CGameLogic()
|
|
{
|
|
}
|
|
|
|
//混乱扑克
|
|
void CGameLogic::RandCardData(BYTE cbCardData[], BYTE cbMaxCount)
|
|
{
|
|
//初始化种子
|
|
srand(GetTickCount() | (rand() << 8));
|
|
|
|
//混乱准备
|
|
BYTE cbCardDataTemp[CountArray(m_cbCardDataArray)];
|
|
CopyMemory(cbCardDataTemp,m_cbCardDataArray,sizeof(m_cbCardDataArray));
|
|
|
|
//混乱扑克
|
|
BYTE cbRandCount=0,cbPosition=0;
|
|
do
|
|
{
|
|
cbPosition=rand()%(cbMaxCount-cbRandCount);
|
|
cbCardData[cbRandCount++]=cbCardDataTemp[cbPosition];
|
|
cbCardDataTemp[cbPosition]=cbCardDataTemp[cbMaxCount-cbRandCount];
|
|
} while (cbRandCount<cbMaxCount);
|
|
|
|
return;
|
|
}
|
|
|
|
//删除扑克
|
|
bool CGameLogic::RemoveCard(BYTE cbCardIndex[MAX_INDEX], BYTE cbRemoveCard)
|
|
{
|
|
//效验扑克
|
|
ASSERT(IsValidCard(cbRemoveCard));
|
|
ASSERT(cbCardIndex[SwitchToCardIndex(cbRemoveCard)]>0);
|
|
|
|
//删除扑克
|
|
BYTE cbRemoveIndex=SwitchToCardIndex(cbRemoveCard);
|
|
if (cbCardIndex[cbRemoveIndex]>0)
|
|
{
|
|
cbCardIndex[cbRemoveIndex]--;
|
|
return true;
|
|
}
|
|
|
|
//失败效验
|
|
ASSERT(FALSE);
|
|
|
|
return false;
|
|
}
|
|
|
|
//删除扑克
|
|
bool CGameLogic::RemoveCard(BYTE cbCardIndex[MAX_INDEX], BYTE cbRemoveCard[], BYTE cbRemoveCount)
|
|
{
|
|
//删除扑克
|
|
for (BYTE i=0;i<cbRemoveCount;i++)
|
|
{
|
|
//效验扑克
|
|
ASSERT(IsValidCard(cbRemoveCard[i]));
|
|
ASSERT(cbCardIndex[SwitchToCardIndex(cbRemoveCard[i])]>0);
|
|
|
|
//删除扑克
|
|
BYTE cbRemoveIndex=SwitchToCardIndex(cbRemoveCard[i]);
|
|
if (cbCardIndex[cbRemoveIndex]==0)
|
|
{
|
|
//错误断言
|
|
ASSERT(FALSE);
|
|
|
|
//还原删除
|
|
for (BYTE j=0;j<i;j++)
|
|
{
|
|
ASSERT(IsValidCard(cbRemoveCard[j]));
|
|
cbCardIndex[SwitchToCardIndex(cbRemoveCard[j])]++;
|
|
}
|
|
|
|
return false;
|
|
}
|
|
else
|
|
{
|
|
//删除扑克
|
|
--cbCardIndex[cbRemoveIndex];
|
|
}
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
//删除扑克
|
|
bool CGameLogic::RemoveCard(BYTE cbCardData[], BYTE cbCardCount, BYTE cbRemoveCard[], BYTE cbRemoveCount)
|
|
{
|
|
//检验数据
|
|
ASSERT(cbCardCount<=MAX_COUNT);
|
|
ASSERT(cbRemoveCount<=cbCardCount);
|
|
|
|
//定义变量
|
|
BYTE cbDeleteCount=0,cbTempCardData[MAX_COUNT];
|
|
if (cbCardCount>CountArray(cbTempCardData)) return false;
|
|
|
|
CopyMemory(cbTempCardData,cbCardData,cbCardCount*sizeof(cbCardData[0]));
|
|
|
|
//置零扑克
|
|
for (BYTE i=0;i<cbRemoveCount;i++)
|
|
{
|
|
for (BYTE j=0;j<cbCardCount;j++)
|
|
{
|
|
if (cbRemoveCard[i]==cbTempCardData[j])
|
|
{
|
|
cbDeleteCount++;
|
|
cbTempCardData[j]=0;
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
//成功判断
|
|
if (cbDeleteCount!=cbRemoveCount)
|
|
{
|
|
ASSERT(FALSE);
|
|
return false;
|
|
}
|
|
|
|
//清理扑克
|
|
BYTE cbCardPos=0;
|
|
for (BYTE i=0;i<cbCardCount;i++)
|
|
{
|
|
if (cbTempCardData[i]!=0)
|
|
cbCardData[cbCardPos++]=cbTempCardData[i];
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
//有效判断
|
|
bool CGameLogic::IsValidCard(BYTE cbCardData)
|
|
{
|
|
BYTE cbValue=(cbCardData&MASK_VALUE);
|
|
BYTE cbColor=(cbCardData&MASK_COLOR)>>4;
|
|
return (((cbValue>=1)&&(cbValue<=9)&&(cbColor<=2))||((cbValue>=1)&&(cbValue<=7)&&(cbColor==3)));
|
|
}
|
|
|
|
//扑克数目
|
|
BYTE CGameLogic::GetCardCount(BYTE cbCardIndex[MAX_INDEX])
|
|
{
|
|
//数目统计
|
|
BYTE cbCardCount=0;
|
|
for (BYTE i=0;i<MAX_INDEX;i++)
|
|
cbCardCount+=cbCardIndex[i];
|
|
|
|
return cbCardCount;
|
|
}
|
|
|
|
//获取组合
|
|
BYTE CGameLogic::GetWeaveCard(WORD wWeaveKind, BYTE cbCenterCard, BYTE cbCardBuffer[4])
|
|
{
|
|
//组合扑克
|
|
switch (wWeaveKind)
|
|
{
|
|
case WIK_LEFT: //上牌操作
|
|
{
|
|
//设置变量
|
|
cbCardBuffer[1]=cbCenterCard+1;
|
|
cbCardBuffer[2]=cbCenterCard+2;
|
|
cbCardBuffer[0]=cbCenterCard;
|
|
|
|
return 3;
|
|
}
|
|
case WIK_RIGHT: //上牌操作
|
|
{
|
|
//设置变量
|
|
cbCardBuffer[1]=cbCenterCard-2;
|
|
cbCardBuffer[2]=cbCenterCard-1;
|
|
cbCardBuffer[0]=cbCenterCard;
|
|
|
|
return 3;
|
|
}
|
|
case WIK_CENTER: //上牌操作
|
|
{
|
|
//设置变量
|
|
cbCardBuffer[1]=cbCenterCard-1;
|
|
cbCardBuffer[0]=cbCenterCard;
|
|
cbCardBuffer[2]=cbCenterCard+1;
|
|
|
|
return 3;
|
|
}
|
|
case WIK_PENG: //碰牌操作
|
|
{
|
|
//设置变量
|
|
cbCardBuffer[0]=cbCenterCard;
|
|
cbCardBuffer[1]=cbCenterCard;
|
|
cbCardBuffer[2]=cbCenterCard;
|
|
|
|
return 3;
|
|
}
|
|
case WIK_GANG: //杠牌操作
|
|
{
|
|
//设置变量
|
|
cbCardBuffer[0]=cbCenterCard;
|
|
cbCardBuffer[1]=cbCenterCard;
|
|
cbCardBuffer[2]=cbCenterCard;
|
|
cbCardBuffer[3]=cbCenterCard;
|
|
|
|
return 4;
|
|
}
|
|
case WIK_DNBL: //东南北左
|
|
{
|
|
//设置变量
|
|
cbCardBuffer[1]=cbCenterCard+1;
|
|
cbCardBuffer[2]=cbCenterCard+3;
|
|
cbCardBuffer[0]=cbCenterCard;
|
|
|
|
return 3;
|
|
}
|
|
case WIK_DNBC: //东南北中
|
|
{
|
|
//设置变量
|
|
cbCardBuffer[1]=cbCenterCard-1;
|
|
cbCardBuffer[0]=cbCenterCard;
|
|
cbCardBuffer[2]=cbCenterCard+2;
|
|
|
|
return 3;
|
|
}
|
|
case WIK_DNBR: //东南北右
|
|
{
|
|
//设置变量
|
|
cbCardBuffer[1]=cbCenterCard-3;
|
|
cbCardBuffer[2]=cbCenterCard-2;
|
|
cbCardBuffer[0]=cbCenterCard;
|
|
|
|
return 3;
|
|
}
|
|
case WIK_DXBL: //东西北左
|
|
{
|
|
//设置变量
|
|
cbCardBuffer[1]=cbCenterCard+2;
|
|
cbCardBuffer[2]=cbCenterCard+3;
|
|
cbCardBuffer[0]=cbCenterCard;
|
|
|
|
return 3;
|
|
}
|
|
case WIK_DXBC: //东西北中
|
|
{
|
|
//设置变量
|
|
cbCardBuffer[1]=cbCenterCard-2;
|
|
cbCardBuffer[0]=cbCenterCard;
|
|
cbCardBuffer[2]=cbCenterCard+1;
|
|
|
|
return 3;
|
|
}
|
|
case WIK_DXBR: //东西北右
|
|
{
|
|
//设置变量
|
|
cbCardBuffer[1]=cbCenterCard-3;
|
|
cbCardBuffer[2]=cbCenterCard-1;
|
|
cbCardBuffer[0]=cbCenterCard;
|
|
|
|
return 3;
|
|
}
|
|
default:
|
|
{
|
|
ASSERT(FALSE);
|
|
}
|
|
}
|
|
|
|
return 0;
|
|
}
|
|
|
|
//动作等级
|
|
BYTE CGameLogic::GetUserActionRank(WORD wUserAction)
|
|
{
|
|
//胡牌等级
|
|
if (wUserAction&WIK_CHI_HU) { return 4; }
|
|
|
|
//杠牌等级
|
|
if (wUserAction&WIK_GANG) { return 3; }
|
|
|
|
//碰牌等级
|
|
if (wUserAction&WIK_PENG) { return 2; }
|
|
|
|
//上牌等级
|
|
if (wUserAction&(WIK_RIGHT|WIK_CENTER|WIK_LEFT|WIK_DNBL|WIK_DNBC|WIK_DNBR|WIK_DXBL|WIK_DXBC|WIK_DXBR)) { return 1; }
|
|
|
|
return 0;
|
|
}
|
|
|
|
//胡牌等级
|
|
BYTE CGameLogic::GetChiHuActionRank(tagChiHuResult & ChiHuResult)
|
|
{
|
|
//变量定义
|
|
BYTE cbChiHuOrder=0;
|
|
WORD wChiHuRight=ChiHuResult.wChiHuRight;
|
|
WORD wChiHuKind=(ChiHuResult.wChiHuKind&0xFF00)>>4;
|
|
|
|
//大胡升级
|
|
for (BYTE i=0;i<8;i++)
|
|
{
|
|
wChiHuKind>>=1;
|
|
if ((wChiHuKind&0x0001)!=0)
|
|
cbChiHuOrder++;
|
|
}
|
|
|
|
//权位升级
|
|
for (BYTE i=0;i<16;i++)
|
|
{
|
|
wChiHuRight>>=1;
|
|
if ((wChiHuRight&0x0001)!=0)
|
|
cbChiHuOrder++;
|
|
}
|
|
|
|
return cbChiHuOrder;
|
|
}
|
|
|
|
//吃牌判断
|
|
WORD CGameLogic::EstimateEatCard(BYTE cbCardIndex[MAX_INDEX], BYTE cbCurrentCard)
|
|
{
|
|
//参数效验
|
|
ASSERT(IsValidCard(cbCurrentCard));
|
|
|
|
|
|
//变量定义
|
|
BYTE cbExcursion[3]={0,1,2};
|
|
WORD wItemKind[3]={WIK_LEFT,WIK_CENTER,WIK_RIGHT};
|
|
|
|
//吃牌判断
|
|
WORD wEatKind=0;
|
|
BYTE cbFirstIndex=0;
|
|
BYTE cbCurrentIndex=SwitchToCardIndex(cbCurrentCard);
|
|
//中发白
|
|
if(cbCurrentIndex>=31)
|
|
{
|
|
for (BYTE i=0;i<CountArray(wItemKind);i++)
|
|
{
|
|
BYTE cbValueIndex=cbCurrentIndex%9;
|
|
if ((cbValueIndex>=cbExcursion[i])&&((cbValueIndex-cbExcursion[i])<=4))
|
|
{
|
|
//吃牌判断
|
|
cbFirstIndex=cbCurrentIndex-cbExcursion[i];
|
|
//过滤
|
|
if(cbFirstIndex<31) continue;
|
|
if ((cbCurrentIndex!=cbFirstIndex)&&(cbCardIndex[cbFirstIndex]==0))
|
|
continue;
|
|
if ((cbCurrentIndex!=(cbFirstIndex+1))&&(cbCardIndex[cbFirstIndex+1]==0))
|
|
continue;
|
|
if ((cbCurrentIndex!=(cbFirstIndex+2))&&(cbCardIndex[cbFirstIndex+2]==0))
|
|
continue;
|
|
|
|
//设置类型
|
|
wEatKind|=wItemKind[i];
|
|
}
|
|
}
|
|
|
|
}
|
|
else if(cbCurrentIndex>=27)
|
|
{
|
|
for (BYTE i=0;i<CountArray(wItemKind);i++)
|
|
{
|
|
BYTE cbValueIndex=cbCurrentIndex%9;
|
|
if ((cbValueIndex>=cbExcursion[i])&&((cbValueIndex-cbExcursion[i])<=1))
|
|
{
|
|
//吃牌判断
|
|
cbFirstIndex=cbCurrentIndex-cbExcursion[i];
|
|
if ((cbCurrentIndex!=cbFirstIndex)&&(cbCardIndex[cbFirstIndex]==0))
|
|
continue;
|
|
if ((cbCurrentIndex!=(cbFirstIndex+1))&&(cbCardIndex[cbFirstIndex+1]==0))
|
|
continue;
|
|
if ((cbCurrentIndex!=(cbFirstIndex+2))&&(cbCardIndex[cbFirstIndex+2]==0))
|
|
continue;
|
|
|
|
//设置类型
|
|
wEatKind|=wItemKind[i];
|
|
}
|
|
}
|
|
|
|
}
|
|
else
|
|
{
|
|
for (BYTE i=0;i<CountArray(wItemKind);i++)
|
|
{
|
|
BYTE cbValueIndex=cbCurrentIndex%9;
|
|
if ((cbValueIndex>=cbExcursion[i])&&((cbValueIndex-cbExcursion[i])<=6))
|
|
{
|
|
//吃牌判断
|
|
cbFirstIndex=cbCurrentIndex-cbExcursion[i];
|
|
if ((cbCurrentIndex!=cbFirstIndex)&&(cbCardIndex[cbFirstIndex]==0))
|
|
continue;
|
|
if ((cbCurrentIndex!=(cbFirstIndex+1))&&(cbCardIndex[cbFirstIndex+1]==0))
|
|
continue;
|
|
if ((cbCurrentIndex!=(cbFirstIndex+2))&&(cbCardIndex[cbFirstIndex+2]==0))
|
|
continue;
|
|
|
|
//设置类型
|
|
wEatKind|=wItemKind[i];
|
|
}
|
|
}
|
|
}
|
|
//东南西北中发白的组合
|
|
if(cbCurrentIndex>=27)
|
|
{
|
|
if(cbCurrentIndex==27)
|
|
{
|
|
if(cbCardIndex[28]>0&&cbCardIndex[30]>0)
|
|
wEatKind |=WIK_DNBL;
|
|
if(cbCardIndex[29]>0&&cbCardIndex[30]>0)
|
|
wEatKind |=WIK_DXBL;
|
|
}
|
|
if(cbCurrentIndex==28)
|
|
{
|
|
if(cbCardIndex[27]>0&&cbCardIndex[30]>0)
|
|
wEatKind |=WIK_DNBC;
|
|
}
|
|
if(cbCurrentIndex==29)
|
|
{
|
|
if(cbCardIndex[27]>0&&cbCardIndex[30]>0)
|
|
wEatKind |=WIK_DXBC;
|
|
}
|
|
if(cbCurrentIndex==30)
|
|
{
|
|
if(cbCardIndex[27]>0&&cbCardIndex[28]>0)
|
|
wEatKind |=WIK_DNBR;
|
|
if(cbCardIndex[27]>0&&cbCardIndex[29]>0)
|
|
wEatKind |=WIK_DXBR;
|
|
}
|
|
}
|
|
|
|
return wEatKind;
|
|
}
|
|
|
|
//碰牌判断
|
|
WORD CGameLogic::EstimatePengCard(BYTE cbCardIndex[MAX_INDEX], BYTE cbCurrentCard)
|
|
{
|
|
//参数效验
|
|
ASSERT(IsValidCard(cbCurrentCard));
|
|
|
|
//碰牌判断
|
|
return (cbCardIndex[SwitchToCardIndex(cbCurrentCard)]>=2)?WIK_PENG:WIK_NULL;
|
|
}
|
|
|
|
//杠牌判断
|
|
WORD CGameLogic::EstimateGangCard(BYTE cbCardIndex[MAX_INDEX], BYTE cbCurrentCard)
|
|
{
|
|
//参数效验
|
|
ASSERT(IsValidCard(cbCurrentCard));
|
|
|
|
//杠牌判断
|
|
return (cbCardIndex[SwitchToCardIndex(cbCurrentCard)]==3)?WIK_GANG:WIK_NULL;
|
|
}
|
|
|
|
//杠牌分析
|
|
WORD CGameLogic::AnalyseGangCard(BYTE cbCardIndex[MAX_INDEX], tagWeaveItem WeaveItem[], BYTE cbWeaveCount, tagGangCardResult & GangCardResult)
|
|
{
|
|
//设置变量
|
|
WORD wActionMask=WIK_NULL;
|
|
ZeroMemory(&GangCardResult,sizeof(GangCardResult));
|
|
|
|
//手上杠牌
|
|
for (BYTE i=0;i<MAX_INDEX;i++)
|
|
{
|
|
if (cbCardIndex[i]==4)
|
|
{
|
|
wActionMask|=WIK_GANG;
|
|
GangCardResult.cbCardData[GangCardResult.cbCardCount++]=SwitchToCardData(i);
|
|
}
|
|
}
|
|
|
|
//组合杠牌
|
|
for (BYTE i=0;i<cbWeaveCount;i++)
|
|
{
|
|
if (WeaveItem[i].wWeaveKind==WIK_PENG)
|
|
{
|
|
if (cbCardIndex[SwitchToCardIndex(WeaveItem[i].cbCenterCard)]==1)
|
|
{
|
|
wActionMask|=WIK_GANG;
|
|
GangCardResult.cbCardData[GangCardResult.cbCardCount++]=WeaveItem[i].cbCenterCard;
|
|
}
|
|
}
|
|
}
|
|
|
|
return wActionMask;
|
|
}
|
|
//分析扑克
|
|
bool CGameLogic::AnalyseCard(BYTE cbCardIndex[MAX_INDEX], tagWeaveItem WeaveItem[], BYTE cbWeaveCount, CAnalyseItemArray & AnalyseItemArray,BYTE cbCurrentCard,bool bZimo)
|
|
{
|
|
//计算数目
|
|
BYTE cbCardCount=0;
|
|
for (BYTE i=0;i<MAX_INDEX;i++)
|
|
cbCardCount+=cbCardIndex[i];
|
|
|
|
//拷贝数据
|
|
BYTE cbTempCardIndex[MAX_INDEX];
|
|
CopyMemory(cbTempCardIndex,cbCardIndex,sizeof(cbTempCardIndex));
|
|
|
|
//效验数目
|
|
ASSERT((cbCardCount>=2)&&(cbCardCount<=MAX_COUNT)&&((cbCardCount-2)%3==0));
|
|
if ((cbCardCount<2)||(cbCardCount>MAX_COUNT)||((cbCardCount-2)%3!=0)) return false;
|
|
|
|
//变量定义
|
|
BYTE cbKindItemCount=0;
|
|
tagKindItem KindItem[MAX_INDEX*2];
|
|
ZeroMemory(KindItem,sizeof(KindItem));
|
|
|
|
//需求判断
|
|
BYTE cbLessKindItem=(cbCardCount-2)/3;
|
|
ASSERT((cbLessKindItem+cbWeaveCount)==4);
|
|
|
|
//单吊判断
|
|
if (cbLessKindItem == 0)
|
|
{
|
|
//效验参数
|
|
ASSERT((cbCardCount == 2) && (cbWeaveCount == 4));
|
|
|
|
//牌眼判断
|
|
for (BYTE i = 0; i < MAX_INDEX; i++)
|
|
{
|
|
if (cbCardIndex[i] == 2)
|
|
{
|
|
//变量定义
|
|
tagAnalyseItem AnalyseItem;
|
|
ZeroMemory(&AnalyseItem, sizeof(AnalyseItem));
|
|
|
|
//设置结果
|
|
for (BYTE j = 0; j < cbWeaveCount; j++)
|
|
{
|
|
AnalyseItem.wWeaveKind[j] = WeaveItem[j].wWeaveKind;
|
|
AnalyseItem.cbCenterCard[j] = WeaveItem[j].cbCenterCard;
|
|
}
|
|
AnalyseItem.cbCardEye = SwitchToCardData(i);
|
|
|
|
//插入结果;
|
|
AnalyseItemArray.Add(AnalyseItem);
|
|
|
|
return true;
|
|
}
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
//拆分分析
|
|
if (cbCardCount>=3)
|
|
{
|
|
for (BYTE i=0;i<MAX_INDEX;i++)
|
|
{
|
|
//同牌判断
|
|
if (cbCardIndex[i]>=3)
|
|
{
|
|
ASSERT( cbKindItemCount < CountArray(KindItem) );
|
|
KindItem[cbKindItemCount].cbCenterCard=SwitchToCardData(i);
|
|
KindItem[cbKindItemCount].cbCardIndex[0]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[1]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[2]=i;
|
|
KindItem[cbKindItemCount++].wWeaveKind=WIK_PENG;
|
|
}
|
|
|
|
//连牌判断
|
|
if ((i<(MAX_INDEX-2-7))&&(cbCardIndex[i]>0)&&((i%9)<7))
|
|
{
|
|
for (BYTE j=1;j<=cbCardIndex[i];j++)
|
|
{
|
|
if ((cbCardIndex[i+1]>=j)&&(cbCardIndex[i+2]>=j))
|
|
{
|
|
ASSERT( cbKindItemCount < CountArray(KindItem) );
|
|
KindItem[cbKindItemCount].cbCenterCard=SwitchToCardData(i);
|
|
KindItem[cbKindItemCount].cbCardIndex[0]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[1]=i+1;
|
|
KindItem[cbKindItemCount].cbCardIndex[2]=i+2;
|
|
KindItem[cbKindItemCount++].wWeaveKind=WIK_LEFT;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
//东南西北
|
|
for (BYTE i=MAX_INDEX-7;i<MAX_INDEX-5;i++)
|
|
{
|
|
//变量定义
|
|
BYTE cbCardIndexTemp[MAX_INDEX];
|
|
|
|
//设置变量
|
|
CopyMemory(cbCardIndexTemp,cbCardIndex,sizeof(cbCardIndexTemp));
|
|
|
|
//东南西 南西北
|
|
for (BYTE j=1;j<=cbCardIndex[i]&&cbCardIndex[i]>0;j++)
|
|
{
|
|
if ((cbCardIndex[i+1]>=j)&&(cbCardIndex[i+2]>=j))
|
|
{
|
|
ASSERT( cbKindItemCount < CountArray(KindItem) );
|
|
KindItem[cbKindItemCount].cbCenterCard=SwitchToCardData(i);
|
|
KindItem[cbKindItemCount].cbCardIndex[0]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[1]=i+1;
|
|
KindItem[cbKindItemCount].cbCardIndex[2]=i+2;
|
|
KindItem[cbKindItemCount++].wWeaveKind=WIK_LEFT;
|
|
}
|
|
}
|
|
|
|
//东南北
|
|
if(i==MAX_INDEX-7)
|
|
{
|
|
for (BYTE j=1;j<=cbCardIndex[i]&&cbCardIndex[i]>0;j++)
|
|
{
|
|
if ((cbCardIndex[i+1]>=j)&&(cbCardIndex[i+3]>=j))
|
|
{
|
|
ASSERT( cbKindItemCount < CountArray(KindItem) );
|
|
KindItem[cbKindItemCount].cbCenterCard=SwitchToCardData(i);
|
|
KindItem[cbKindItemCount].cbCardIndex[0]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[1]=i+1;
|
|
KindItem[cbKindItemCount].cbCardIndex[2]=i+3;
|
|
KindItem[cbKindItemCount++].wWeaveKind=WIK_DNBL;
|
|
}
|
|
}
|
|
|
|
}
|
|
//东西北
|
|
if(i==MAX_INDEX-7)
|
|
{
|
|
for (BYTE j=1;j<=cbCardIndex[i]&&cbCardIndex[i]>0;j++)
|
|
{
|
|
if ((cbCardIndex[i+2]>=j)&&(cbCardIndex[i+3]>=j))
|
|
{
|
|
ASSERT( cbKindItemCount < CountArray(KindItem) );
|
|
KindItem[cbKindItemCount].cbCenterCard=SwitchToCardData(i);
|
|
KindItem[cbKindItemCount].cbCardIndex[0]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[1]=i+2;
|
|
KindItem[cbKindItemCount].cbCardIndex[2]=i+3;
|
|
KindItem[cbKindItemCount++].wWeaveKind=WIK_DXBL;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
//中发白
|
|
for (BYTE i=MAX_INDEX-3;i<MAX_INDEX;i++)
|
|
{
|
|
//连牌判断
|
|
if ((i<(MAX_INDEX-2))&&(cbCardIndex[i]>0)&&((i%9)<7))
|
|
{
|
|
for (BYTE j=1;j<=cbCardIndex[i];j++)
|
|
{
|
|
if ((cbCardIndex[i+1]>=j)&&(cbCardIndex[i+2]>=j))
|
|
{
|
|
KindItem[cbKindItemCount].cbCenterCard=SwitchToCardData(i);
|
|
KindItem[cbKindItemCount].cbCardIndex[0]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[1]=i+1;
|
|
KindItem[cbKindItemCount].cbCardIndex[2]=i+2;
|
|
KindItem[cbKindItemCount++].wWeaveKind=WIK_LEFT;
|
|
}
|
|
}
|
|
}
|
|
|
|
}
|
|
}
|
|
|
|
//组合分析
|
|
if (cbKindItemCount>=cbLessKindItem)
|
|
{
|
|
//变量定义
|
|
BYTE cbCardIndexTemp[MAX_INDEX];
|
|
ZeroMemory(cbCardIndexTemp,sizeof(cbCardIndexTemp));
|
|
|
|
//变量定义
|
|
BYTE cbIndex[MAX_WEAVE]={0,1,2,3};
|
|
tagKindItem * pKindItem[MAX_WEAVE];
|
|
ZeroMemory(&pKindItem,sizeof(pKindItem));
|
|
|
|
//开始组合
|
|
do
|
|
{
|
|
//设置变量
|
|
CopyMemory(cbCardIndexTemp,cbCardIndex,sizeof(cbCardIndexTemp));
|
|
for (BYTE i=0;i<cbLessKindItem;i++)
|
|
pKindItem[i]=&KindItem[cbIndex[i]];
|
|
|
|
//数量判断
|
|
bool bEnoughCard=true;
|
|
for (BYTE i=0;i<cbLessKindItem*3;i++)
|
|
{
|
|
//存在判断
|
|
BYTE cbCardIndex=pKindItem[i/3]->cbCardIndex[i%3];
|
|
if (cbCardIndexTemp[cbCardIndex]==0)
|
|
{
|
|
bEnoughCard=false;
|
|
break;
|
|
}
|
|
else
|
|
cbCardIndexTemp[cbCardIndex]--;
|
|
}
|
|
|
|
//德国判断
|
|
if (bEnoughCard == true)
|
|
{
|
|
//牌眼判断
|
|
BYTE cbCardEye = 0;
|
|
|
|
for (BYTE i = 0; i < MAX_INDEX; i++)
|
|
{
|
|
if (cbCardIndexTemp[i] == 2)
|
|
{ //眼牌数据;
|
|
cbCardEye = SwitchToCardData(i);
|
|
break;
|
|
}
|
|
}
|
|
|
|
|
|
//组合类型
|
|
if (cbCardEye != 0)
|
|
{
|
|
//变量定义
|
|
tagAnalyseItem AnalyseItem;
|
|
ZeroMemory(&AnalyseItem, sizeof(AnalyseItem));
|
|
|
|
//设置组合
|
|
for (BYTE i = 0; i < cbWeaveCount; i++)
|
|
{
|
|
AnalyseItem.wWeaveKind[i] = WeaveItem[i].wWeaveKind;
|
|
AnalyseItem.cbCenterCard[i] = WeaveItem[i].cbCenterCard;
|
|
}
|
|
|
|
//设置牌型
|
|
for (BYTE i = 0; i < cbLessKindItem; i++)
|
|
{
|
|
AnalyseItem.wWeaveKind[i + cbWeaveCount] = pKindItem[i]->wWeaveKind;
|
|
AnalyseItem.cbCenterCard[i + cbWeaveCount] = pKindItem[i]->cbCenterCard;
|
|
}
|
|
//精牌替换;
|
|
AnalyseItem.cbWeaveKingReplace = 0;
|
|
|
|
//设置牌眼;
|
|
AnalyseItem.cbCardEye = cbCardEye;
|
|
|
|
//精牌替换;
|
|
AnalyseItem.cbEyeKingReplace = 0;
|
|
|
|
//插入结果
|
|
AnalyseItemArray.Add(AnalyseItem);
|
|
}
|
|
}
|
|
|
|
//设置索引
|
|
if (cbIndex[cbLessKindItem-1]==(cbKindItemCount-1))
|
|
{
|
|
BYTE i = 0;
|
|
for ( i=cbLessKindItem-1;i>0;i--)
|
|
{
|
|
if ((cbIndex[i-1]+1)!=cbIndex[i])
|
|
{
|
|
BYTE cbNewIndex=cbIndex[i-1];
|
|
for (BYTE j=(i-1);j<cbLessKindItem;j++)
|
|
cbIndex[j]=cbNewIndex+j-i+2;
|
|
break;
|
|
}
|
|
}
|
|
if (i==0)
|
|
break;
|
|
}
|
|
else
|
|
cbIndex[cbLessKindItem-1]++;
|
|
|
|
} while (true);
|
|
|
|
}
|
|
|
|
|
|
//硬胡分析
|
|
if (AnalyseItemArray.GetCount()>0)
|
|
return true;
|
|
|
|
//硬胡清空
|
|
AnalyseItemArray.RemoveAll();
|
|
|
|
//变量定义
|
|
cbKindItemCount=0;
|
|
ZeroMemory(KindItem,sizeof(KindItem));
|
|
|
|
|
|
return false;
|
|
}
|
|
|
|
|
|
//吃胡分析
|
|
WORD CGameLogic::AnalyseChiHuCard(BYTE cbCardIndex[MAX_INDEX], tagWeaveItem WeaveItem[], BYTE cbWeaveCount, BYTE cbCurrentCard, WORD wChiHuRight, tagChiHuResult & ChiHuResult, BYTE cbHuRule, bool bZimo, bool bRealHu)
|
|
{
|
|
if (cbHuRule == eWNMJHURuleEnum_Invalid)
|
|
{
|
|
return WIK_NULL;
|
|
}
|
|
|
|
if (cbHuRule == eWNMJHURuleEnum_YingHU)
|
|
{
|
|
return AnalyseYingHuCard(cbCardIndex, WeaveItem, cbWeaveCount, cbCurrentCard, wChiHuRight, ChiHuResult, bZimo, bRealHu);
|
|
}
|
|
else if (cbHuRule == eWNMJHURuleEnum_YiBianDaoHU)
|
|
{
|
|
return AnalyseYiBianDaoHuCard(cbCardIndex, WeaveItem, cbWeaveCount, cbCurrentCard, wChiHuRight, ChiHuResult, bZimo, bRealHu);
|
|
}
|
|
else if (cbHuRule == eWNMJHURuleEnum_HunHU)
|
|
{
|
|
WORD wAction = AnalyseYiBianDaoHuCard(cbCardIndex, WeaveItem, cbWeaveCount, cbCurrentCard, wChiHuRight, ChiHuResult, bZimo, bRealHu);
|
|
if ( wAction != WIK_NULL )
|
|
{
|
|
return wAction;
|
|
}
|
|
|
|
return AnalyseYingHuCard(cbCardIndex, WeaveItem, cbWeaveCount, cbCurrentCard, wChiHuRight, ChiHuResult, bZimo, bRealHu);
|
|
}
|
|
|
|
return WIK_NULL;
|
|
}
|
|
|
|
|
|
//扑克转换
|
|
BYTE CGameLogic::SwitchToCardData(BYTE cbCardIndex)
|
|
{
|
|
ASSERT(cbCardIndex<MAX_INDEX);
|
|
|
|
ASSERT(cbCardIndex<34);
|
|
return ((cbCardIndex/9)<<4)|(cbCardIndex%9+1);
|
|
}
|
|
|
|
//扑克转换
|
|
BYTE CGameLogic::SwitchToCardIndex(BYTE cbCardData)
|
|
{
|
|
|
|
ASSERT(IsValidCard(cbCardData));
|
|
////计算位置
|
|
//BYTE cbValue=cbCardData&MASK_VALUE;
|
|
//BYTE cbColor=(cbCardData&MASK_COLOR)>>4;
|
|
return ((cbCardData&MASK_COLOR)>>4)*9+(cbCardData&MASK_VALUE)-1;
|
|
}
|
|
|
|
//扑克转换
|
|
BYTE CGameLogic::SwitchToCardData(BYTE cbCardIndex[MAX_INDEX], BYTE cbCardData[MAX_COUNT],BYTE bMaxCount)
|
|
{
|
|
//转换扑克 精牌放到原来位置
|
|
BYTE bPosition=0;
|
|
for (BYTE i=0;i<MAX_INDEX;i++)
|
|
{
|
|
|
|
if (cbCardIndex[i]!=0)
|
|
{
|
|
for (BYTE j=0;j<cbCardIndex[i];j++)
|
|
{
|
|
ASSERT(bPosition<bMaxCount);
|
|
cbCardData[bPosition++]=SwitchToCardData(i);
|
|
}
|
|
}
|
|
}
|
|
|
|
return bPosition;
|
|
}
|
|
|
|
//扑克转换
|
|
BYTE CGameLogic::SwitchToCardIndex(BYTE cbCardData[], BYTE cbCardCount, BYTE cbCardIndex[MAX_INDEX])
|
|
{
|
|
//设置变量
|
|
ZeroMemory(cbCardIndex,sizeof(BYTE)*MAX_INDEX);
|
|
|
|
//转换扑克
|
|
for (BYTE i=0;i<cbCardCount;i++)
|
|
{
|
|
cbCardIndex[SwitchToCardIndex(cbCardData[i])]++;
|
|
}
|
|
|
|
return cbCardCount;
|
|
}
|
|
|
|
|
|
//计算积分
|
|
LONG CGameLogic::CalScore(tagChiHuResult & ChihuResult, LONG &lScore, LONG &lTimes, LONG &lExtScore, BYTE cbFan, bool bZhiAnGangFanbei)
|
|
{
|
|
//胡牌校验
|
|
ASSERT(ChihuResult.wChiHuKind!=CHK_NULL);
|
|
if (ChihuResult.wChiHuKind== CHK_NULL) return 0;
|
|
|
|
//赋值初始化;
|
|
lTimes = 1L;
|
|
lExtScore = 0L;
|
|
|
|
//抢杠
|
|
if (ChihuResult.wChiHuRight&CHR_QIANG_GANG)
|
|
{
|
|
lTimes *= 1;
|
|
}
|
|
//杠开
|
|
if (ChihuResult.wChiHuRight&CHR_GANG_FLOWER)
|
|
{
|
|
lTimes *= 1;
|
|
}
|
|
//天胡
|
|
if (ChihuResult.wChiHuRight&CHR_TIAN)
|
|
{
|
|
lTimes *= 2;
|
|
}
|
|
//地胡
|
|
if (ChihuResult.wChiHuRight&CHR_DI)
|
|
{
|
|
lTimes *= 2;
|
|
}
|
|
|
|
//7对
|
|
if (ChihuResult.wChiHuKind&CHK_QI_DUI)
|
|
{
|
|
lTimes *= 2;
|
|
}
|
|
//13乱
|
|
if (ChihuResult.wChiHuKind&CHK_THIRTEEN)
|
|
{
|
|
lTimes *= 1;
|
|
}
|
|
//七星十三烂;
|
|
if (ChihuResult.wChiHuKind&CHK_SERVEN)
|
|
{
|
|
lTimes *= 2;
|
|
}
|
|
//碰碰胡;
|
|
if (ChihuResult.wChiHuKind&CHK_PENG_PENG)
|
|
{
|
|
lTimes *= 2;
|
|
}
|
|
//混一色;
|
|
if (ChihuResult.wChiHuKind&CHK_HUNYISE)
|
|
{
|
|
lTimes *= 2;
|
|
}
|
|
//清一色;
|
|
if (ChihuResult.wChiHuKind&CHK_QINYISE)
|
|
{
|
|
lTimes *= 4;
|
|
}
|
|
//字一色;
|
|
if (ChihuResult.wChiHuKind&CHK_ZIYISE)
|
|
{
|
|
lTimes *= 16;
|
|
}
|
|
|
|
if ( cbFan == eWNMJRuleEnum_OneTwoFAN )
|
|
{
|
|
if (ChihuResult.wChiHuRight&CHR_GANG_FLOWER)
|
|
{
|
|
lTimes *= 2;
|
|
}
|
|
else
|
|
{
|
|
if (ChihuResult.wChiHuRight&CHR_ZI_MO)
|
|
{
|
|
lTimes *= 1;
|
|
}
|
|
else
|
|
{
|
|
lTimes *= 2;
|
|
}
|
|
}
|
|
}
|
|
else if ( cbFan == eWNMJRuleEnum_TwoThreeFAN )
|
|
{
|
|
if (ChihuResult.wChiHuRight&CHR_GANG_FLOWER)
|
|
{
|
|
lTimes *= 3;
|
|
}
|
|
else
|
|
{
|
|
if (ChihuResult.wChiHuRight&CHR_ZI_MO)
|
|
{
|
|
lTimes *= 2;
|
|
}
|
|
else
|
|
{
|
|
lTimes *= 3;
|
|
}
|
|
}
|
|
}
|
|
|
|
//天胡,地胡,抢杠,杠开并且是真胡;
|
|
if (((ChihuResult.wChiHuRight&CHR_TIAN) || (ChihuResult.wChiHuRight&CHR_DI) || (ChihuResult.wChiHuRight&CHR_QIANG_GANG) || (ChihuResult.wChiHuRight&CHR_GANG_FLOWER))
|
|
&& ((ChihuResult.wChiHuRight&CHR_HAS_KING) != CHR_HAS_KING))
|
|
{
|
|
lTimes *= 2;
|
|
}
|
|
|
|
if (ChihuResult.wChiHuRight&CHR_GANG_FLOWER && !(ChihuResult.wChiHuRight&CHR_GANG_ZHONGSE))
|
|
{ //明暗杠,没杠到色情况下,获得特殊积分;
|
|
if ((ChihuResult.wChiHuKind&CHK_HUNYISE) || (ChihuResult.wChiHuKind&CHK_QINYISE))
|
|
{
|
|
if (cbFan == eWNMJRuleEnum_OneTwoFAN)
|
|
{
|
|
lTimes = 2;
|
|
}
|
|
else if (cbFan == eWNMJRuleEnum_TwoThreeFAN)
|
|
{
|
|
lTimes = 3;
|
|
}
|
|
}
|
|
else if (ChihuResult.wChiHuKind&CHK_ZIYISE)
|
|
{
|
|
if (cbFan == eWNMJRuleEnum_OneTwoFAN)
|
|
{
|
|
lTimes = 4;
|
|
}
|
|
else if (cbFan == eWNMJRuleEnum_TwoThreeFAN)
|
|
{
|
|
lTimes = 6;
|
|
}
|
|
}
|
|
}
|
|
|
|
int nMaxTimes = 0;
|
|
if (cbFan == eWNMJRuleEnum_OneTwoFAN)
|
|
{
|
|
nMaxTimes = 16;
|
|
}
|
|
else if (cbFan == eWNMJRuleEnum_TwoThreeFAN)
|
|
{
|
|
nMaxTimes = 24;
|
|
}
|
|
|
|
if (bZhiAnGangFanbei)
|
|
{
|
|
nMaxTimes *= 2;
|
|
}
|
|
|
|
if (lTimes > nMaxTimes)
|
|
{
|
|
lTimes = nMaxTimes;
|
|
}
|
|
|
|
return lTimes;
|
|
}
|
|
|
|
//13乱
|
|
bool CGameLogic::IsNeatAlone(BYTE cbCardIndex[MAX_INDEX],BYTE &cbGerman,BYTE cbCurrentCard,bool bZimo)
|
|
{
|
|
BYTE cbTempCardIndex[MAX_INDEX];
|
|
CopyMemory(cbTempCardIndex,cbCardIndex,sizeof(BYTE)*MAX_INDEX);
|
|
|
|
//计算数目
|
|
BYTE cbCardCount=0;
|
|
for (BYTE i=0;i<MAX_INDEX;i++)
|
|
cbCardCount+=cbTempCardIndex[i];
|
|
|
|
//满牌才能全不靠
|
|
if(cbCardCount<MAX_COUNT) return false;
|
|
|
|
|
|
//返回值判断
|
|
bool bRet=true;
|
|
|
|
|
|
//变量处理
|
|
const BYTE COMMON_TYPE_SUM = 9;
|
|
for (BYTE i = 0; i<MAX_INDEX; i++)
|
|
{
|
|
//重复字牌
|
|
if(cbTempCardIndex[i] > 1)
|
|
{
|
|
bRet=false;
|
|
break;
|
|
}
|
|
}
|
|
//牌值必须两两相隔;
|
|
if(bRet)
|
|
{
|
|
BYTE* pKingIndex = 0;
|
|
for(BYTE i=0; i<3; i++)
|
|
{
|
|
pKingIndex = &cbTempCardIndex[i*COMMON_TYPE_SUM];
|
|
for(BYTE j=0; j<COMMON_TYPE_SUM; j++)
|
|
{
|
|
if(pKingIndex[j] > 0)
|
|
{
|
|
for(BYTE k=0; k<2; k++)
|
|
{
|
|
j ++;
|
|
|
|
if(j<COMMON_TYPE_SUM)
|
|
{
|
|
if(pKingIndex[j] > 0)
|
|
{
|
|
bRet= false;
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if(bRet)
|
|
{
|
|
//德国判断
|
|
cbGerman=1;
|
|
|
|
return true;
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
//3顺 3刻
|
|
bool CGameLogic::IsNeat3(const BYTE cbCardIndex[MAX_INDEX],BYTE &cbGerman)
|
|
{
|
|
//德国
|
|
cbGerman=1;
|
|
|
|
BYTE cbCardIndexTemp[MAX_INDEX];
|
|
CopyMemory(cbCardIndexTemp,cbCardIndex,sizeof(cbCardIndexTemp));
|
|
|
|
//变量定义
|
|
BYTE cbIndex[4]={0,1,2,3};
|
|
tagKindItem * pKindItem[4];
|
|
ZeroMemory(&pKindItem,sizeof(pKindItem));
|
|
|
|
|
|
//需求判断
|
|
BYTE cbCardCount = 0;
|
|
for(BYTE i=0; i<MAX_INDEX; i++)
|
|
{
|
|
cbCardCount += cbCardIndexTemp[i];
|
|
}
|
|
//效验数目
|
|
ASSERT(cbCardCount<=14);
|
|
if((cbCardCount%3) != 0)
|
|
{
|
|
return false;
|
|
}
|
|
|
|
BYTE cbLessKindItem = cbCardCount/3;
|
|
if (cbLessKindItem == 0)
|
|
{
|
|
return true;
|
|
}
|
|
|
|
//变量定义
|
|
BYTE cbKindItemCount=0;
|
|
tagKindItem KindItem[MAX_INDEX-2];
|
|
ZeroMemory(KindItem,sizeof(KindItem));
|
|
|
|
for (BYTE i=0;i<MAX_INDEX;i++)
|
|
{
|
|
//同牌判断
|
|
if (cbCardIndex[i]>=3)
|
|
{
|
|
KindItem[cbKindItemCount].cbCenterCard=SwitchToCardData(i);
|
|
KindItem[cbKindItemCount].cbCardIndex[0]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[1]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[2]=i;
|
|
KindItem[cbKindItemCount++].wWeaveKind=WIK_PENG;
|
|
}
|
|
|
|
//连牌判断
|
|
if ((i<(MAX_INDEX-2-7))&&(cbCardIndex[i]>0)&&((i%9)<7))
|
|
{
|
|
for (BYTE j=1;j<=cbCardIndex[i];j++)
|
|
{
|
|
if ((cbCardIndex[i+1]>=j)&&(cbCardIndex[i+2]>=j))
|
|
{
|
|
KindItem[cbKindItemCount].cbCenterCard=SwitchToCardData(i);
|
|
KindItem[cbKindItemCount].cbCardIndex[0]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[1]=i+1;
|
|
KindItem[cbKindItemCount].cbCardIndex[2]=i+2;
|
|
KindItem[cbKindItemCount++].wWeaveKind=WIK_LEFT;
|
|
}
|
|
}
|
|
}
|
|
|
|
}
|
|
//东南西北
|
|
for (BYTE i=MAX_INDEX-7;i<MAX_INDEX-5;i++)
|
|
{
|
|
//变量定义
|
|
BYTE cbCardIndexTemp[MAX_INDEX];
|
|
|
|
//设置变量
|
|
CopyMemory(cbCardIndexTemp,cbCardIndex,sizeof(cbCardIndexTemp));
|
|
|
|
//东南西 南西北
|
|
for (BYTE j=1;j<=cbCardIndex[i]&&cbCardIndex[i]>0;j++)
|
|
{
|
|
if ((cbCardIndex[i+1]>=j)&&(cbCardIndex[i+2]>=j))
|
|
{
|
|
KindItem[cbKindItemCount].cbCenterCard=SwitchToCardData(i);
|
|
KindItem[cbKindItemCount].cbCardIndex[0]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[1]=i+1;
|
|
KindItem[cbKindItemCount].cbCardIndex[2]=i+2;
|
|
KindItem[cbKindItemCount++].wWeaveKind=WIK_LEFT;
|
|
}
|
|
}
|
|
|
|
//东南北
|
|
if(i==MAX_INDEX-7)
|
|
{
|
|
for (BYTE j=1;j<=cbCardIndex[i]&&cbCardIndex[i]>0;j++)
|
|
{
|
|
if ((cbCardIndex[i+1]>=j)&&(cbCardIndex[i+3]>=j))
|
|
{
|
|
KindItem[cbKindItemCount].cbCenterCard=SwitchToCardData(i);
|
|
KindItem[cbKindItemCount].cbCardIndex[0]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[1]=i+1;
|
|
KindItem[cbKindItemCount].cbCardIndex[2]=i+3;
|
|
KindItem[cbKindItemCount++].wWeaveKind=WIK_DNBL;
|
|
}
|
|
}
|
|
|
|
}
|
|
//东西北
|
|
if(i==MAX_INDEX-7)
|
|
{
|
|
for (BYTE j=1;j<=cbCardIndex[i]&&cbCardIndex[i]>0;j++)
|
|
{
|
|
if ((cbCardIndex[i+2]>=j)&&(cbCardIndex[i+3]>=j))
|
|
{
|
|
KindItem[cbKindItemCount].cbCenterCard=SwitchToCardData(i);
|
|
KindItem[cbKindItemCount].cbCardIndex[0]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[1]=i+2;
|
|
KindItem[cbKindItemCount].cbCardIndex[2]=i+3;
|
|
KindItem[cbKindItemCount++].wWeaveKind=WIK_DXBL;
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
}
|
|
//中发白
|
|
for (BYTE i=MAX_INDEX-3;i<MAX_INDEX;i++)
|
|
{
|
|
|
|
//连牌判断
|
|
if ((i<(MAX_INDEX-2))&&(cbCardIndex[i]>0)&&((i%9)<7))
|
|
{
|
|
for (BYTE j=1;j<=cbCardIndex[i];j++)
|
|
{
|
|
if ((cbCardIndex[i+1]>=j)&&(cbCardIndex[i+2]>=j))
|
|
{
|
|
KindItem[cbKindItemCount].cbCenterCard=SwitchToCardData(i);
|
|
KindItem[cbKindItemCount].cbCardIndex[0]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[1]=i+1;
|
|
KindItem[cbKindItemCount].cbCardIndex[2]=i+2;
|
|
KindItem[cbKindItemCount++].wWeaveKind=WIK_LEFT;
|
|
}
|
|
}
|
|
}
|
|
|
|
}
|
|
|
|
|
|
//组合分析
|
|
if (cbKindItemCount>=cbLessKindItem)
|
|
{
|
|
//变量定义
|
|
BYTE cbCardIndexTemp[MAX_INDEX];
|
|
ZeroMemory(cbCardIndexTemp,sizeof(cbCardIndexTemp));
|
|
|
|
//变量定义
|
|
BYTE cbIndex[4]={0,1,2,3};
|
|
tagKindItem * pKindItem[4];
|
|
ZeroMemory(&pKindItem,sizeof(pKindItem));
|
|
|
|
//开始组合
|
|
do
|
|
{
|
|
//设置变量
|
|
CopyMemory(cbCardIndexTemp,cbCardIndex,sizeof(cbCardIndexTemp));
|
|
for (BYTE i=0;i<cbLessKindItem;i++)
|
|
{
|
|
pKindItem[i]=&KindItem[cbIndex[i]];
|
|
}
|
|
|
|
//数量判断
|
|
bool bEnoughCard=true;
|
|
for (BYTE i=0;i<cbLessKindItem*3;i++)
|
|
{
|
|
//存在判断
|
|
BYTE cbCardIndex=pKindItem[i/3]->cbCardIndex[i%3];
|
|
if (cbCardIndexTemp[cbCardIndex]==0)
|
|
{
|
|
bEnoughCard=false;
|
|
break;
|
|
}
|
|
else
|
|
{
|
|
cbCardIndexTemp[cbCardIndex]--;
|
|
}
|
|
}
|
|
if(bEnoughCard)
|
|
{
|
|
return true;
|
|
}
|
|
|
|
//设置索引
|
|
if (cbIndex[cbLessKindItem-1] == (cbKindItemCount-1))
|
|
{
|
|
BYTE i = 0;
|
|
for (i=cbLessKindItem-1;i>0;i--)
|
|
{
|
|
if ((cbIndex[i-1]+1) != cbIndex[i])
|
|
{
|
|
BYTE cbNewIndex = cbIndex[i-1];
|
|
for (BYTE j=(i-1); j<cbLessKindItem; j++)
|
|
{
|
|
cbIndex[j]=cbNewIndex+j-i+2;
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
if (i==0)
|
|
{
|
|
break;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
cbIndex[cbLessKindItem-1]++;
|
|
}
|
|
|
|
} while (true);
|
|
|
|
}
|
|
|
|
//非德国
|
|
cbGerman=0;
|
|
|
|
//变量定义
|
|
cbKindItemCount=0;
|
|
ZeroMemory(KindItem,sizeof(KindItem));
|
|
|
|
//拆分分析
|
|
if (cbCardCount>=3)
|
|
{
|
|
for (BYTE i=0;i<MAX_INDEX;i++)
|
|
{
|
|
//同牌判断
|
|
if (cbCardIndex[i]>=3)
|
|
{
|
|
ASSERT( cbKindItemCount < CountArray(KindItem) );
|
|
KindItem[cbKindItemCount].cbCenterCard=SwitchToCardData(i);
|
|
KindItem[cbKindItemCount].cbCardIndex[0]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[1]=i;
|
|
KindItem[cbKindItemCount].cbCardIndex[2]=i;
|
|
KindItem[cbKindItemCount++].wWeaveKind=WIK_PENG;
|
|
}
|
|
}
|
|
}
|
|
|
|
//组合分析
|
|
if (cbKindItemCount>=cbLessKindItem)
|
|
{
|
|
//变量定义
|
|
BYTE cbCardIndexTemp[MAX_INDEX];
|
|
ZeroMemory(cbCardIndexTemp,sizeof(cbCardIndexTemp));
|
|
|
|
//变量定义
|
|
BYTE cbIndex[MAX_WEAVE]={0,1,2,3};
|
|
tagKindItem * pKindItem[MAX_WEAVE];
|
|
ZeroMemory(&pKindItem,sizeof(pKindItem));
|
|
|
|
//开始组合
|
|
do
|
|
{
|
|
//设置变量
|
|
CopyMemory(cbCardIndexTemp,cbCardIndex,sizeof(cbCardIndexTemp));
|
|
for (BYTE i=0;i<cbLessKindItem;i++)
|
|
pKindItem[i]=&KindItem[cbIndex[i]];
|
|
|
|
//设置索引
|
|
if (cbIndex[cbLessKindItem-1] == (cbKindItemCount-1))
|
|
{
|
|
BYTE i = 0;
|
|
for (i=cbLessKindItem-1;i>0;i--)
|
|
{
|
|
if ((cbIndex[i-1]+1) != cbIndex[i])
|
|
{
|
|
BYTE cbNewIndex = cbIndex[i-1];
|
|
for (BYTE j=(i-1); j<cbLessKindItem; j++)
|
|
{
|
|
cbIndex[j]=cbNewIndex+j-i+2;
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
if (i==0)
|
|
{
|
|
break;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
cbIndex[cbLessKindItem-1]++;
|
|
}
|
|
|
|
|
|
|
|
} while (true);
|
|
|
|
}
|
|
|
|
|
|
return false;
|
|
}
|
|
|
|
// 对子 豪华对子
|
|
//是否全2
|
|
bool CGameLogic::IsNeat2(BYTE cbCardIndex[MAX_INDEX],tagWeaveItem WeaveItem[], BYTE cbWeaveCount)
|
|
{
|
|
//倒牌过滤
|
|
if(cbWeaveCount>0) return false;
|
|
|
|
//德国判断
|
|
for(BYTE i=0; i<MAX_INDEX; i++)
|
|
{
|
|
if(cbCardIndex[i] != 0 && cbCardIndex[i] != 2 &&cbCardIndex[i] != 4)
|
|
{
|
|
return false;
|
|
}
|
|
}
|
|
|
|
return true;
|
|
}
|
|
//七小对牌
|
|
bool CGameLogic::IsQiXiaoDui(const BYTE cbCardIndex[MAX_INDEX], const tagWeaveItem WeaveItem[], const BYTE cbWeaveCount,const BYTE cbCurrentCard,BYTE &cbGerman,bool bZimo)
|
|
{
|
|
//组合判断;
|
|
if (cbWeaveCount!=0) return false;
|
|
|
|
//临时数据;
|
|
BYTE cbCardIndexTemp[MAX_INDEX];
|
|
CopyMemory(cbCardIndexTemp,cbCardIndex,sizeof(cbCardIndexTemp));
|
|
|
|
//数目验证;
|
|
ASSERT(GetCardCount(cbCardIndexTemp)%2==0);
|
|
if(GetCardCount(cbCardIndexTemp)%2 !=0) return false;
|
|
|
|
//当前索引;
|
|
BYTE cbCurrentIndex = SwitchToCardIndex(cbCurrentCard);
|
|
|
|
//计算单牌;
|
|
for (BYTE i=0;i<MAX_INDEX;i++)
|
|
{
|
|
BYTE cbCardCount=cbCardIndexTemp[i];
|
|
|
|
//单牌统计;
|
|
if( cbCardCount == 1 || cbCardCount == 3 ) return false;
|
|
}
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
//7星
|
|
bool CGameLogic::ServenStar(BYTE cbCardIndex[MAX_INDEX], BYTE &cbGerman, BYTE cbCurrentCard, bool bZimo, bool bChongfeng)
|
|
{
|
|
|
|
cbGerman=0;
|
|
//临时数据
|
|
BYTE cbCardIndexTemp[MAX_INDEX];
|
|
CopyMemory(cbCardIndexTemp,cbCardIndex,sizeof(cbCardIndexTemp));
|
|
|
|
if (!bChongfeng)
|
|
{ //全不靠;
|
|
bool bRet = false;
|
|
bool bAlone = IsNeatAlone(cbCardIndexTemp, cbGerman, cbCurrentCard, bZimo);
|
|
if (bAlone == false)
|
|
{
|
|
return false;
|
|
}
|
|
}
|
|
|
|
//7风记录
|
|
BYTE cbHasFeng[7];
|
|
ZeroMemory(cbHasFeng,sizeof(cbHasFeng));
|
|
for(int i=27; i<34; i++)
|
|
{
|
|
cbHasFeng[i-27]=cbCardIndexTemp[i];
|
|
|
|
if (!bChongfeng)
|
|
{
|
|
//重复风牌;
|
|
if (cbHasFeng[i - 27] > 1) return false;
|
|
}
|
|
}
|
|
|
|
//7星全
|
|
int j=0;
|
|
for (int i=0;i<7;i++)
|
|
{
|
|
if(cbHasFeng[i]>0)
|
|
j++;
|
|
}
|
|
if(j==7)
|
|
{
|
|
return true;
|
|
}
|
|
return false;
|
|
|
|
}
|
|
//计算副精
|
|
BYTE CGameLogic::GetKingFromBrother(BYTE cbBrotherData)
|
|
{
|
|
if(IsValidCard(cbBrotherData) == false)
|
|
{
|
|
return 0xFF;
|
|
}
|
|
BYTE cbColor = cbBrotherData & MASK_COLOR;
|
|
BYTE cbValue = (cbBrotherData & MASK_VALUE) + 1;
|
|
|
|
//万 索 筒
|
|
if(cbColor != 0x30)
|
|
{
|
|
if(cbValue > 0x09)
|
|
{
|
|
cbValue = 0x01;
|
|
}
|
|
}
|
|
else if(cbValue < 0x06)
|
|
{
|
|
if(cbValue > 0x04)
|
|
{
|
|
cbValue = 0x01;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if(cbValue > 0x07)
|
|
{
|
|
cbValue = 0x05;
|
|
}
|
|
}
|
|
|
|
return (cbColor | cbValue);
|
|
}
|
|
|
|
void CGameLogic::GetCardRemoveRepeat(BYTE cbCardIndex[MAX_INDEX], BYTE cbCardData[MAX_COUNT], BYTE &nCount)
|
|
{
|
|
nCount = 0;
|
|
for (BYTE i = 0; i < MAX_INDEX; ++i)
|
|
{
|
|
if (cbCardIndex[i] > 0)
|
|
{
|
|
cbCardData[nCount] = SwitchToCardData(i);
|
|
++nCount;
|
|
}
|
|
}
|
|
}
|
|
|
|
BYTE CGameLogic::AnalyseTingCard(const BYTE cbCardIndex[MAX_INDEX], tagWeaveItem WeaveItem[], BYTE cbWeaveCount, BYTE cbCurrentCard, WORD wChiHuRight, tagChiHuResult & ChiHuResult, BYTE cbHuRule, bool bZimo /*= false*/, bool bTurnAll, bool bRealTing)
|
|
{ //特殊停牌规则;
|
|
//变量定义;
|
|
WORD wChiHuKind = CHK_NULL;
|
|
|
|
//设置变量;
|
|
ZeroMemory(&ChiHuResult, sizeof(ChiHuResult));
|
|
|
|
//构造扑克;
|
|
BYTE cbCardIndexTemp[MAX_INDEX];
|
|
CopyMemory(cbCardIndexTemp, cbCardIndex, sizeof(cbCardIndexTemp));
|
|
|
|
BYTE cbRemoveRepeat = 0;
|
|
BYTE cbCardDataRemoveRepeat[MAX_COUNT] = { 0 };
|
|
|
|
GetCardRemoveRepeat(cbCardIndexTemp, cbCardDataRemoveRepeat, cbRemoveRepeat);
|
|
|
|
//插入扑克;
|
|
if (cbCurrentCard != 0)
|
|
cbCardIndexTemp[SwitchToCardIndex(cbCurrentCard)]++;
|
|
|
|
if ( bZimo )
|
|
{
|
|
cbCardDataRemoveRepeat[cbRemoveRepeat] = cbCurrentCard;
|
|
++cbRemoveRepeat;
|
|
}
|
|
|
|
if (!bTurnAll)
|
|
{
|
|
for (BYTE i = 0; i < cbRemoveRepeat; ++i)
|
|
{
|
|
RemoveCard(cbCardIndexTemp, cbCardDataRemoveRepeat[i]);
|
|
|
|
for (BYTE j = 0; j < MAX_INDEX; j++)
|
|
{
|
|
BYTE cbCurrentCardTemp = SwitchToCardData(j);
|
|
|
|
if (WIK_CHI_HU == AnalyseChiHuCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, cbCurrentCardTemp, wChiHuRight, ChiHuResult, cbHuRule, bZimo, false))
|
|
{
|
|
if (IsCheckZhongSe(cbCardIndex, WeaveItem, cbWeaveCount, cbCurrentCard, ChiHuResult, cbHuRule, bRealTing))
|
|
{
|
|
ChiHuResult.wChiHuRight |= CHR_HAS_KING;
|
|
return WIK_CHI_HU;
|
|
}
|
|
}
|
|
}
|
|
|
|
cbCardIndexTemp[SwitchToCardIndex(cbCardDataRemoveRepeat[i])]++;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
tagChiHuResult tempChiHuResult;
|
|
|
|
bool bHuPai = false;
|
|
for (BYTE i = 0; i < cbRemoveRepeat; ++i)
|
|
{
|
|
RemoveCard(cbCardIndexTemp, cbCardDataRemoveRepeat[i]);
|
|
|
|
for (BYTE j = 0; j < MAX_INDEX; j++)
|
|
{
|
|
BYTE cbCurrentCardTemp = SwitchToCardData(j);
|
|
|
|
if (WIK_CHI_HU == AnalyseChiHuCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, cbCurrentCardTemp, wChiHuRight, tempChiHuResult, cbHuRule, bZimo, false))
|
|
{
|
|
if (IsCheckZhongSe(cbCardIndex, WeaveItem, cbWeaveCount, cbCurrentCard, tempChiHuResult, cbHuRule, bRealTing))
|
|
{
|
|
bHuPai = true;
|
|
tempChiHuResult.wChiHuRight |= CHR_HAS_KING;
|
|
|
|
CompareChiHuResult( ChiHuResult, tempChiHuResult );
|
|
}
|
|
}
|
|
}
|
|
|
|
cbCardIndexTemp[SwitchToCardIndex(cbCardDataRemoveRepeat[i])]++;
|
|
}
|
|
if (bHuPai)
|
|
{
|
|
return WIK_CHI_HU;
|
|
}
|
|
}
|
|
|
|
return WIK_NULL;
|
|
}
|
|
|
|
bool CGameLogic::IsTingCard(const BYTE cbCardIndex[MAX_INDEX], tagWeaveItem WeaveItem[], BYTE cbWeaveCount,
|
|
BYTE cbCurrentCard, WORD wChiHuRight, tagChiHuResult& ChiHuResult, BYTE cbHuRule, bool bZimo /*= true*/, bool bTurnAll /*= false*/)
|
|
{
|
|
//复制数据;
|
|
BYTE cbCardIndexTemp[MAX_INDEX];
|
|
CopyMemory(cbCardIndexTemp, cbCardIndex, sizeof(cbCardIndexTemp));
|
|
|
|
if (!bTurnAll)
|
|
{
|
|
for (BYTE i = 0; i < MAX_INDEX; i++)
|
|
{
|
|
BYTE cbCurrentCardTemp = SwitchToCardData(i);
|
|
if (WIK_CHI_HU == AnalyseChiHuCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, cbCurrentCardTemp, wChiHuRight, ChiHuResult, cbHuRule, bZimo, false))
|
|
{
|
|
if (IsCheckZhongSe(cbCardIndex, WeaveItem, cbWeaveCount, cbCurrentCard, ChiHuResult, cbHuRule, true))
|
|
return true;
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
tagChiHuResult tempChiHuResult;
|
|
|
|
bool bHuPai = false;
|
|
|
|
for (BYTE i = 0; i < MAX_INDEX; i++)
|
|
{
|
|
BYTE cbCurrentCardTemp = SwitchToCardData(i);
|
|
if (WIK_CHI_HU == AnalyseChiHuCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, cbCurrentCardTemp, wChiHuRight, tempChiHuResult, cbHuRule, bZimo, false))
|
|
{
|
|
if (IsCheckZhongSe(cbCardIndex, WeaveItem, cbWeaveCount, cbCurrentCard, tempChiHuResult, cbHuRule, true))
|
|
{
|
|
bHuPai = true;
|
|
tempChiHuResult.wChiHuRight |= CHR_HAS_KING;
|
|
|
|
CompareChiHuResult(ChiHuResult, tempChiHuResult);
|
|
}
|
|
}
|
|
}
|
|
if (bHuPai)
|
|
{
|
|
return true;
|
|
}
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
//清一色牌
|
|
bool CGameLogic::IsQingYiSe(const BYTE cbCardIndex[MAX_INDEX], const tagWeaveItem WeaveItem[], const BYTE cbItemCount, const BYTE cbCurrentCard)
|
|
{
|
|
//胡牌后判断;
|
|
BYTE cbCardColor = 0xFF;
|
|
|
|
for (BYTE i = 0; i < MAX_INDEX; i++)
|
|
{
|
|
if (cbCardIndex[i] != 0)
|
|
{
|
|
//花色判断;
|
|
if (cbCardColor != 0xFF)
|
|
return false;
|
|
|
|
//设置花色;
|
|
cbCardColor = (SwitchToCardData(i)&MASK_COLOR);
|
|
|
|
//设置索引;(第一种花色颜色找到后,直接移9位,找到第二种牌值的颜色);
|
|
i = (i / 9 + 1) * 9 - 1;
|
|
}
|
|
}
|
|
|
|
if ((cbCurrentCard&MASK_COLOR) != cbCardColor) return false;
|
|
|
|
//组合判断;
|
|
for (BYTE i = 0; i < cbItemCount; i++)
|
|
{
|
|
BYTE cbCenterCard = WeaveItem[i].cbCenterCard;
|
|
if ((cbCenterCard&MASK_COLOR) != cbCardColor) return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
bool CGameLogic::IsHunYiSe(const BYTE cbCardIndex[MAX_INDEX], const tagWeaveItem WeaveItem[], const BYTE cbItemCount, const BYTE cbCurrentCard)
|
|
{
|
|
BYTE cbCardColor = 0xFF;
|
|
|
|
BYTE cbCardIndexTemp[MAX_INDEX] = {0};
|
|
memcpy(cbCardIndexTemp, cbCardIndex, sizeof(cbCardIndexTemp));
|
|
|
|
BYTE cbCardDataIndex = SwitchToCardIndex(cbCurrentCard);
|
|
cbCardIndexTemp[cbCardDataIndex]++;
|
|
|
|
//组合判断;
|
|
for (BYTE i = 0; i < cbItemCount; i++)
|
|
{
|
|
BYTE cbCenterCard = WeaveItem[i].cbCenterCard;
|
|
BYTE cbCardDataIndex = SwitchToCardIndex(cbCenterCard);
|
|
|
|
cbCardIndexTemp[cbCardDataIndex]++;
|
|
}
|
|
|
|
for (BYTE i = 0; i < (MAX_INDEX - 7); i++)
|
|
{
|
|
if (cbCardIndexTemp[i] != 0)
|
|
{
|
|
//花色判断;
|
|
if (cbCardColor != 0xFF)
|
|
return false;
|
|
|
|
//设置花色;
|
|
cbCardColor = (SwitchToCardData(i)&MASK_COLOR);
|
|
|
|
//设置索引;(第一种花色颜色找到后,直接移9位,找到第二种牌值的颜色);
|
|
i = (i / 9 + 1) * 9 - 1;
|
|
}
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
bool CGameLogic::IsZiPai(BYTE cbCardData)
|
|
{
|
|
return ((cbCardData&MASK_COLOR) == 0x30);
|
|
}
|
|
|
|
bool CGameLogic::IsZiYiSe(const BYTE cbCardIndex[MAX_INDEX], const tagWeaveItem WeaveItem[], const BYTE cbItemCount, const BYTE cbCurrentCard)
|
|
{
|
|
if (!IsZiPai(cbCurrentCard)) return false;
|
|
//组合判断;
|
|
for (BYTE i = 0; i < cbItemCount; i++)
|
|
{
|
|
BYTE cbCenterCard = WeaveItem[i].cbCenterCard;
|
|
if (!IsZiPai(cbCenterCard)) return false;
|
|
}
|
|
|
|
for (BYTE i = 0; i < (MAX_INDEX - 7); i++)
|
|
{
|
|
if (cbCardIndex[i] != 0)
|
|
{
|
|
return false;
|
|
}
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
WORD CGameLogic::AnalyseYingHuCard(BYTE cbCardIndex[MAX_INDEX], tagWeaveItem WeaveItem[], BYTE cbWeaveCount, BYTE cbCurrentCard, WORD wChiHuRight, tagChiHuResult & ChiHuResult, bool bZimo /*= false*/, bool bRealHu /*= true*/)
|
|
{
|
|
BYTE cbValue = cbCurrentCard&MASK_VALUE;
|
|
BYTE cbColor = (cbCurrentCard&MASK_COLOR) >> 4;
|
|
|
|
if (bRealHu && (cbColor < 3) && (cbValue < 5))
|
|
{ //5以下的不能胡;(东南西北中发白可以胡);
|
|
return WIK_NULL;
|
|
}
|
|
|
|
//变量定义
|
|
WORD wChiHuKind = CHK_NULL;
|
|
|
|
//设置变量
|
|
ZeroMemory(&ChiHuResult, sizeof(ChiHuResult));
|
|
|
|
//构造扑克
|
|
BYTE cbCardIndexTemp[MAX_INDEX];
|
|
CopyMemory(cbCardIndexTemp, cbCardIndex, sizeof(cbCardIndexTemp));
|
|
|
|
//插入扑克
|
|
if (cbCurrentCard != 0)
|
|
cbCardIndexTemp[SwitchToCardIndex(cbCurrentCard)]++;
|
|
|
|
//自模权位
|
|
if (bZimo)
|
|
{
|
|
wChiHuRight |= CHR_ZI_MO;
|
|
}
|
|
|
|
//权位调整 杠胡+自摸 = 杠上花
|
|
if ((wChiHuRight&CHR_QIANG_GANG) && (wChiHuRight&CHR_ZI_MO))
|
|
{
|
|
wChiHuRight &= ~CHR_QIANG_GANG;
|
|
wChiHuRight &= ~CHR_ZI_MO;
|
|
wChiHuRight |= CHR_GANG_FLOWER;
|
|
}
|
|
|
|
//德国七星
|
|
BYTE bGerman = 0;
|
|
|
|
//7星
|
|
if (cbWeaveCount == 0 && ServenStar(cbCardIndexTemp, bGerman, cbCurrentCard, bZimo) == true)
|
|
{
|
|
////真胡去掉有宝权位;
|
|
//wChiHuRight &= ~CHR_HAS_KING;
|
|
|
|
ChiHuResult.wChiHuKind = CHK_SERVEN;
|
|
ChiHuResult.wChiHuRight |= wChiHuRight;
|
|
|
|
return WIK_CHI_HU;
|
|
}
|
|
bGerman = 0;
|
|
|
|
//13离
|
|
if (cbWeaveCount == 0 && IsNeatAlone(cbCardIndexTemp, bGerman, cbCurrentCard, bZimo) == true)
|
|
{
|
|
ChiHuResult.wChiHuKind = CHK_THIRTEEN;
|
|
ChiHuResult.wChiHuRight |= wChiHuRight;
|
|
return WIK_CHI_HU;
|
|
}
|
|
|
|
bGerman = 0;
|
|
//7小对分析
|
|
if (cbWeaveCount == 0 && IsQiXiaoDui(cbCardIndexTemp, WeaveItem, cbWeaveCount, cbCurrentCard, bGerman, bZimo))
|
|
{
|
|
wChiHuKind = CHK_QI_DUI;
|
|
|
|
ChiHuResult.wChiHuKind = wChiHuKind;
|
|
ChiHuResult.wChiHuRight |= wChiHuRight;
|
|
|
|
return WIK_CHI_HU;
|
|
}
|
|
|
|
//牌型数组
|
|
static CAnalyseItemArray AnalyseItemArray;
|
|
|
|
//设置变量
|
|
AnalyseItemArray.RemoveAll();
|
|
ZeroMemory(&ChiHuResult, sizeof(ChiHuResult));
|
|
|
|
//分析扑克
|
|
AnalyseCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, AnalyseItemArray, cbCurrentCard, bZimo);
|
|
|
|
//胡牌分析
|
|
if (AnalyseItemArray.GetCount() > 0)
|
|
{
|
|
//牌型分析
|
|
for (INT_PTR i = 0; i < AnalyseItemArray.GetCount(); i++)
|
|
{
|
|
//变量定义
|
|
bool bLianCard = false, bPengCard = false;
|
|
bool bGerman = true;
|
|
tagAnalyseItem * pAnalyseItem = &AnalyseItemArray[i];
|
|
|
|
//牌型分析
|
|
for (BYTE j = 0; j < CountArray(pAnalyseItem->wWeaveKind); j++)
|
|
{
|
|
WORD wWeaveKind = pAnalyseItem->wWeaveKind[j];
|
|
bPengCard = ((wWeaveKind&(WIK_GANG | WIK_PENG)) != 0) ? true : bPengCard;
|
|
bLianCard = ((wWeaveKind&(WIK_CHI)) != 0) ? true : bLianCard;
|
|
}
|
|
bGerman = (pAnalyseItem->cbWeaveKingReplace || pAnalyseItem->cbEyeKingReplace) ? false : bGerman;
|
|
|
|
//牌型判断
|
|
ASSERT((bLianCard == true) || (bPengCard == true));
|
|
|
|
//基胡
|
|
if ((bLianCard == true) && (bPengCard == true))
|
|
wChiHuKind |= CHK_JI_HU;
|
|
if ((bLianCard == true) && (bPengCard == false))
|
|
wChiHuKind |= CHK_JI_HU;
|
|
if ((bLianCard == false) && (bPengCard == true))
|
|
wChiHuKind |= CHK_JI_HU; //wChiHuKind |= CHK_PENG_PENG;
|
|
}
|
|
}
|
|
|
|
//结果判断
|
|
if (wChiHuKind != CHK_NULL)
|
|
{
|
|
//设置结果
|
|
ChiHuResult.wChiHuKind = wChiHuKind;
|
|
ChiHuResult.wChiHuRight = wChiHuRight;
|
|
return WIK_CHI_HU;
|
|
}
|
|
|
|
return WIK_NULL;
|
|
}
|
|
|
|
|
|
WORD CGameLogic::AnalyseYiBianDaoHuCard(BYTE cbCardIndex[MAX_INDEX], tagWeaveItem WeaveItem[], BYTE cbWeaveCount, BYTE cbCurrentCard, WORD wChiHuRight, tagChiHuResult & ChiHuResult, bool bZimo /*= false*/, bool bRealHu /*= true*/)
|
|
{
|
|
BYTE cbValue = cbCurrentCard&MASK_VALUE;
|
|
BYTE cbColor = (cbCurrentCard&MASK_COLOR) >> 4;
|
|
|
|
if (bRealHu && (cbColor < 3) && (cbValue < 5))
|
|
{ //5以下的不能胡;(东南西北中发白可以胡);
|
|
return WIK_NULL;
|
|
}
|
|
|
|
//变量定义
|
|
WORD wChiHuKind = CHK_NULL;
|
|
|
|
//设置变量
|
|
ZeroMemory(&ChiHuResult, sizeof(ChiHuResult));
|
|
|
|
//构造扑克
|
|
BYTE cbCardIndexTemp[MAX_INDEX];
|
|
CopyMemory(cbCardIndexTemp, cbCardIndex, sizeof(cbCardIndexTemp));
|
|
|
|
//插入扑克
|
|
if (cbCurrentCard != 0)
|
|
cbCardIndexTemp[SwitchToCardIndex(cbCurrentCard)]++;
|
|
|
|
//自模权位
|
|
if (bZimo)
|
|
{
|
|
wChiHuRight |= CHR_ZI_MO;
|
|
}
|
|
|
|
//权位调整 杠胡+自摸 = 杠上花
|
|
if ((wChiHuRight&CHR_QIANG_GANG) && (wChiHuRight&CHR_ZI_MO))
|
|
{
|
|
wChiHuRight &= ~CHR_QIANG_GANG;
|
|
wChiHuRight &= ~CHR_ZI_MO;
|
|
wChiHuRight |= CHR_GANG_FLOWER;
|
|
}
|
|
|
|
//德国七星;
|
|
BYTE bGerman = 0;
|
|
|
|
//7星
|
|
if (cbWeaveCount == 0 && ServenStar(cbCardIndexTemp, bGerman, cbCurrentCard, bZimo) == true)
|
|
{
|
|
ChiHuResult.wChiHuKind = CHK_SERVEN;
|
|
ChiHuResult.wChiHuRight |= wChiHuRight;
|
|
|
|
return WIK_CHI_HU;
|
|
}
|
|
|
|
bGerman = 0;
|
|
//7小对分析
|
|
if (cbWeaveCount == 0 && IsQiXiaoDui(cbCardIndexTemp, WeaveItem, cbWeaveCount, cbCurrentCard, bGerman, bZimo))
|
|
{
|
|
if (IsZiYiSe(cbCardIndex, WeaveItem, cbWeaveCount, cbCurrentCard))
|
|
{
|
|
wChiHuKind = (CHK_QI_DUI | CHK_ZIYISE);
|
|
}
|
|
else if (IsQingYiSe(cbCardIndex, WeaveItem, cbWeaveCount, cbCurrentCard))
|
|
{
|
|
wChiHuKind = (CHK_QI_DUI | CHK_QINYISE);
|
|
}
|
|
else if (IsHunYiSe(cbCardIndex, WeaveItem, cbWeaveCount, cbCurrentCard))
|
|
{
|
|
wChiHuKind = (CHK_QI_DUI | CHK_HUNYISE);
|
|
}
|
|
else
|
|
{
|
|
wChiHuKind = CHK_QI_DUI;
|
|
}
|
|
|
|
ChiHuResult.wChiHuKind = wChiHuKind;
|
|
ChiHuResult.wChiHuRight |= wChiHuRight;
|
|
|
|
return WIK_CHI_HU;
|
|
}
|
|
|
|
//牌型数组
|
|
static CAnalyseItemArray AnalyseItemArray;
|
|
|
|
//设置变量
|
|
AnalyseItemArray.RemoveAll();
|
|
ZeroMemory(&ChiHuResult, sizeof(ChiHuResult));
|
|
|
|
//分析扑克
|
|
AnalyseCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, AnalyseItemArray, cbCurrentCard, bZimo);
|
|
|
|
//胡牌分析
|
|
if (AnalyseItemArray.GetCount() > 0)
|
|
{
|
|
//牌型分析
|
|
for (INT_PTR i = 0; i < AnalyseItemArray.GetCount(); i++)
|
|
{
|
|
//变量定义
|
|
bool bLianCard = false, bPengCard = false;
|
|
bool bGerman = true;
|
|
tagAnalyseItem * pAnalyseItem = &AnalyseItemArray[i];
|
|
|
|
//牌型分析
|
|
for (BYTE j = 0; j < CountArray(pAnalyseItem->wWeaveKind); j++)
|
|
{
|
|
WORD wWeaveKind = pAnalyseItem->wWeaveKind[j];
|
|
bPengCard = ((wWeaveKind&(WIK_GANG | WIK_PENG)) != 0) ? true : bPengCard;
|
|
bLianCard = ((wWeaveKind&(WIK_CHI)) != 0) ? true : bLianCard;
|
|
}
|
|
bGerman = (pAnalyseItem->cbWeaveKingReplace || pAnalyseItem->cbEyeKingReplace) ? false : bGerman;
|
|
|
|
//牌型判断
|
|
ASSERT((bLianCard == true) || (bPengCard == true));
|
|
|
|
//基胡;
|
|
if ((bLianCard == true) && (bPengCard == true))
|
|
wChiHuKind |= CHK_JI_HU;
|
|
if ((bLianCard == true) && (bPengCard == false))
|
|
wChiHuKind |= CHK_JI_HU;
|
|
if ((bLianCard == false) && (bPengCard == true))
|
|
wChiHuKind |= CHK_PENG_PENG;
|
|
}
|
|
}
|
|
|
|
//字一色分析;
|
|
if (IsZiYiSe(cbCardIndex, WeaveItem, cbWeaveCount, cbCurrentCard))
|
|
{
|
|
if (wChiHuKind == WIK_NULL)
|
|
{ //没有组成胡牌的字一色胡权位;
|
|
wChiHuRight |= CHR_INVALIDHU_ZIYISE;
|
|
}
|
|
|
|
wChiHuKind |= CHK_ZIYISE;
|
|
wChiHuKind &= (~CHK_JI_HU);
|
|
|
|
ChiHuResult.wChiHuKind = wChiHuKind;
|
|
ChiHuResult.wChiHuRight |= wChiHuRight;
|
|
|
|
return WIK_CHI_HU;
|
|
}
|
|
|
|
//清一色分析;
|
|
if ((wChiHuKind != CHK_NULL) && IsQingYiSe(cbCardIndex, WeaveItem, cbWeaveCount, cbCurrentCard))
|
|
{
|
|
wChiHuKind |= CHK_QINYISE;
|
|
wChiHuKind &= (~CHK_JI_HU);
|
|
|
|
ChiHuResult.wChiHuKind = wChiHuKind;
|
|
ChiHuResult.wChiHuRight |= wChiHuRight;
|
|
|
|
return WIK_CHI_HU;
|
|
}
|
|
|
|
//混一色分析;
|
|
if ((wChiHuKind != CHK_NULL) && IsHunYiSe(cbCardIndex, WeaveItem, cbWeaveCount, cbCurrentCard))
|
|
{
|
|
wChiHuKind |= CHK_HUNYISE;
|
|
wChiHuKind &= (~CHK_JI_HU);
|
|
|
|
ChiHuResult.wChiHuKind = wChiHuKind;
|
|
ChiHuResult.wChiHuRight |= wChiHuRight;
|
|
|
|
return WIK_CHI_HU;
|
|
}
|
|
|
|
if (wChiHuKind == CHK_JI_HU)
|
|
{ //只是基本胡,就不是一边倒胡;
|
|
wChiHuKind = CHK_NULL;
|
|
}
|
|
|
|
//结果判断;
|
|
if (wChiHuKind != CHK_NULL)
|
|
{
|
|
//设置结果
|
|
ChiHuResult.wChiHuKind = wChiHuKind;
|
|
ChiHuResult.wChiHuRight = wChiHuRight;
|
|
return WIK_CHI_HU;
|
|
}
|
|
|
|
return WIK_NULL;
|
|
}
|
|
|
|
bool CGameLogic::IsCheckZhongSe(const BYTE cbCardIndex[MAX_INDEX], const tagWeaveItem WeaveItem[], const BYTE cbItemCount, const BYTE cbCurrentCard, tagChiHuResult & ChiHuResult, BYTE cbRule, bool bTing)
|
|
{
|
|
if (ChiHuResult.wChiHuKind & CHK_ZIYISE)
|
|
{
|
|
if (IsZiYiSe(cbCardIndex, WeaveItem, cbItemCount, cbCurrentCard))
|
|
{
|
|
ChiHuResult.wChiHuRight &= (~CHR_INVALIDHU_ZIYISE);
|
|
ChiHuResult.wChiHuRight |= CHR_GANG_ZHONGSE;
|
|
}
|
|
else
|
|
{
|
|
if (ChiHuResult.wChiHuRight & CHR_INVALIDHU_ZIYISE)
|
|
{ //没杠到色,并且字一色不是胡牌(只是特殊的字一色胡,没有组合成胡牌)的情况下;
|
|
ChiHuResult.wChiHuKind = WIK_NULL;
|
|
}
|
|
else
|
|
{
|
|
if (!bTing)
|
|
{
|
|
ChiHuResult.wChiHuKind &= (~CHK_ZIYISE);
|
|
}
|
|
else
|
|
{
|
|
if (ChiHuResult.wChiHuKind & (~CHK_ZIYISE))
|
|
{ //如果有其他的大胡,去除字一色权位;
|
|
ChiHuResult.wChiHuKind &= (~CHK_ZIYISE);
|
|
}
|
|
}
|
|
|
|
//听牌后,如果是混一色,改变胡牌种类;
|
|
if (IsHunYiSe(cbCardIndex, WeaveItem, cbItemCount, cbCurrentCard))
|
|
{
|
|
ChiHuResult.wChiHuKind &= (~CHK_ZIYISE);
|
|
ChiHuResult.wChiHuKind |= CHK_HUNYISE;
|
|
ChiHuResult.wChiHuRight |= CHR_GANG_ZHONGSE;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
else if(ChiHuResult.wChiHuKind & CHK_QINYISE)
|
|
{
|
|
if (IsQingYiSe(cbCardIndex, WeaveItem, cbItemCount, cbCurrentCard))
|
|
{
|
|
ChiHuResult.wChiHuRight |= CHR_GANG_ZHONGSE;
|
|
}
|
|
else
|
|
{
|
|
if (!bTing)
|
|
{
|
|
ChiHuResult.wChiHuKind &= (~CHK_QINYISE);
|
|
}
|
|
else
|
|
{
|
|
if (ChiHuResult.wChiHuKind & (~CHK_QINYISE))
|
|
{ //如果有其他的大胡,去除清一色权位;
|
|
ChiHuResult.wChiHuKind &= (~CHK_QINYISE);
|
|
}
|
|
}
|
|
|
|
//如果是混一色,改变胡牌种类;
|
|
if (IsHunYiSe(cbCardIndex, WeaveItem, cbItemCount, cbCurrentCard))
|
|
{
|
|
ChiHuResult.wChiHuKind &= (~CHK_QINYISE);
|
|
ChiHuResult.wChiHuKind |= CHK_HUNYISE;
|
|
ChiHuResult.wChiHuRight |= CHR_GANG_ZHONGSE;
|
|
}
|
|
}
|
|
}
|
|
else if (ChiHuResult.wChiHuKind & CHK_HUNYISE)
|
|
{
|
|
if (IsHunYiSe(cbCardIndex, WeaveItem, cbItemCount, cbCurrentCard))
|
|
{
|
|
ChiHuResult.wChiHuRight |= CHR_GANG_ZHONGSE;
|
|
}
|
|
else
|
|
{
|
|
if (!bTing)
|
|
{
|
|
ChiHuResult.wChiHuKind &= (~CHK_HUNYISE);
|
|
}
|
|
else
|
|
{
|
|
if (ChiHuResult.wChiHuKind & (~CHK_HUNYISE))
|
|
{ //如果有其他的大胡,去除混一色权位;
|
|
ChiHuResult.wChiHuKind &= (~CHK_HUNYISE);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (ChiHuResult.wChiHuKind == CHK_SERVEN)
|
|
{
|
|
//构造扑克;
|
|
BYTE cbCardIndexTemp[MAX_INDEX];
|
|
CopyMemory(cbCardIndexTemp, cbCardIndex, sizeof(cbCardIndexTemp));
|
|
|
|
//插入扑克;
|
|
if (cbCurrentCard != 0)
|
|
cbCardIndexTemp[SwitchToCardIndex(cbCurrentCard)]++;
|
|
|
|
//再次判断时,七星时是可以重复风牌,能走到这里一般都是有宝牌替换的;
|
|
|
|
BYTE bGerman = 0;
|
|
bool bZimo = false;
|
|
bool bReal = ServenStar(cbCardIndexTemp, bGerman, cbCurrentCard, bZimo, true);
|
|
if (!bReal)
|
|
{ //假七星;
|
|
if (cbRule == eWNMJHURuleEnum_YiBianDaoHU)
|
|
{ //胡不了;
|
|
ChiHuResult.wChiHuKind = CHK_NULL;
|
|
}
|
|
else
|
|
{ //降成十三烂;
|
|
ChiHuResult.wChiHuKind = CHK_THIRTEEN;
|
|
}
|
|
}
|
|
}
|
|
|
|
if ( ChiHuResult.wChiHuKind == CHK_NULL )
|
|
{
|
|
ChiHuResult.wChiHuRight = 0;
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
void CGameLogic::CompareChiHuResult(tagChiHuResult& destChiHuResult, tagChiHuResult& tempChiHuResult)
|
|
{
|
|
if (destChiHuResult.wChiHuKind == CHK_NULL)
|
|
{
|
|
destChiHuResult = tempChiHuResult;
|
|
}
|
|
else
|
|
{
|
|
if (destChiHuResult.wChiHuKind < tempChiHuResult.wChiHuKind)
|
|
{
|
|
if (tempChiHuResult.wChiHuKind >= CHK_HUNYISE)
|
|
{
|
|
if (tempChiHuResult.wChiHuRight & CHR_GANG_ZHONGSE)
|
|
{
|
|
destChiHuResult = tempChiHuResult;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
destChiHuResult = tempChiHuResult;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if (destChiHuResult.wChiHuKind >= CHK_HUNYISE)
|
|
{
|
|
if (!(destChiHuResult.wChiHuRight & CHR_GANG_ZHONGSE))
|
|
{
|
|
destChiHuResult = tempChiHuResult;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
//////////////////////////////////////////////////////////////////////////
|