诸暨麻将添加redis
No puede seleccionar más de 25 temas Los temas deben comenzar con una letra o número, pueden incluir guiones ('-') y pueden tener hasta 35 caracteres de largo.
 
 
 
 
 
 

1587 líneas
40 KiB

  1. #include "StdAfx.h"
  2. #include "GameLogic.h"
  3. #include "math.h"
  4. #include "TableFrameSink.h"
  5. #include "fstream"
  6. //////////////////////////////////////////////////////////////////////////
  7. //静态变量
  8. bool CChiHuRight::m_bInit = false;
  9. DWORD CChiHuRight::m_dwRightMask[MAX_RIGHT_COUNT];
  10. //构造函数
  11. CChiHuRight::CChiHuRight()
  12. {
  13. ZeroMemory( m_dwRight,sizeof(m_dwRight) );
  14. if( !m_bInit )
  15. {
  16. m_bInit = true;
  17. for( BYTE i = 0; i < CountArray(m_dwRightMask); i++ )
  18. {
  19. if( 0 == i )
  20. m_dwRightMask[i] = 0;
  21. else
  22. m_dwRightMask[i] = (DWORD(pow(2.0,i-1)))<<28;
  23. }
  24. }
  25. }
  26. //赋值符重载
  27. CChiHuRight & CChiHuRight::operator = ( DWORD dwRight )
  28. {
  29. DWORD dwOtherRight = 0;
  30. //验证权位
  31. if( !IsValidRight( dwRight ) )
  32. {
  33. //验证取反权位
  34. ASSERT( IsValidRight( ~dwRight ) );
  35. if( !IsValidRight( ~dwRight ) ) return *this;
  36. dwRight = ~dwRight;
  37. dwOtherRight = MASK_CHI_HU_RIGHT;
  38. }
  39. for( BYTE i = 0; i < CountArray(m_dwRightMask); i++ )
  40. {
  41. if( (dwRight&m_dwRightMask[i]) || (i==0&&dwRight<0x10000000) )
  42. m_dwRight[i] = dwRight&MASK_CHI_HU_RIGHT;
  43. else m_dwRight[i] = dwOtherRight;
  44. }
  45. return *this;
  46. }
  47. //与等于
  48. CChiHuRight & CChiHuRight::operator &= ( DWORD dwRight )
  49. {
  50. bool bNavigate = false;
  51. //验证权位
  52. if( !IsValidRight( dwRight ) )
  53. {
  54. //验证取反权位
  55. ASSERT( IsValidRight( ~dwRight ) );
  56. if( !IsValidRight( ~dwRight ) ) return *this;
  57. //调整权位
  58. DWORD dwHeadRight = (~dwRight)&0xF0000000;
  59. DWORD dwTailRight = dwRight&MASK_CHI_HU_RIGHT;
  60. dwRight = dwHeadRight|dwTailRight;
  61. bNavigate = true;
  62. }
  63. for( BYTE i = 0; i < CountArray(m_dwRightMask); i++ )
  64. {
  65. if( (dwRight&m_dwRightMask[i]) || (i==0&&dwRight<0x10000000) )
  66. {
  67. m_dwRight[i] &= (dwRight&MASK_CHI_HU_RIGHT);
  68. }
  69. else if( !bNavigate )
  70. m_dwRight[i] = 0;
  71. }
  72. return *this;
  73. }
  74. //或等于
  75. CChiHuRight & CChiHuRight::operator |= ( DWORD dwRight )
  76. {
  77. //验证权位
  78. if( !IsValidRight( dwRight ) ) return *this;
  79. for( BYTE i = 0; i < CountArray(m_dwRightMask); i++ )
  80. {
  81. if( (dwRight&m_dwRightMask[i]) || (i==0&&dwRight<0x10000000) )
  82. m_dwRight[i] |= (dwRight&MASK_CHI_HU_RIGHT);
  83. }
  84. return *this;
  85. }
  86. //与
  87. CChiHuRight CChiHuRight::operator & ( DWORD dwRight )
  88. {
  89. CChiHuRight chr = *this;
  90. return (chr &= dwRight);
  91. }
  92. //与
  93. CChiHuRight CChiHuRight::operator & ( DWORD dwRight ) const
  94. {
  95. CChiHuRight chr = *this;
  96. return (chr &= dwRight);
  97. }
  98. //或
  99. CChiHuRight CChiHuRight::operator | ( DWORD dwRight )
  100. {
  101. CChiHuRight chr = *this;
  102. return chr |= dwRight;
  103. }
  104. //或
  105. CChiHuRight CChiHuRight::operator | ( DWORD dwRight ) const
  106. {
  107. CChiHuRight chr = *this;
  108. return chr |= dwRight;
  109. }
  110. //是否权位为空
  111. bool CChiHuRight::IsEmpty()
  112. {
  113. for( BYTE i = 0; i < CountArray(m_dwRight); i++ )
  114. if( m_dwRight[i] ) return false;
  115. return true;
  116. }
  117. //设置权位为空
  118. void CChiHuRight::SetEmpty()
  119. {
  120. ZeroMemory( m_dwRight,sizeof(m_dwRight) );
  121. return;
  122. }
  123. //获取权位数值
  124. BYTE CChiHuRight::GetRightData( DWORD dwRight[], BYTE cbMaxCount )
  125. {
  126. ASSERT( cbMaxCount >= CountArray(m_dwRight) );
  127. if( cbMaxCount < CountArray(m_dwRight) ) return 0;
  128. CopyMemory( dwRight,m_dwRight,sizeof(DWORD)*CountArray(m_dwRight) );
  129. return CountArray(m_dwRight);
  130. }
  131. //设置权位数值
  132. bool CChiHuRight::SetRightData( const DWORD dwRight[], BYTE cbRightCount )
  133. {
  134. ASSERT( cbRightCount <= CountArray(m_dwRight) );
  135. if( cbRightCount > CountArray(m_dwRight) ) return false;
  136. ZeroMemory( m_dwRight,sizeof(m_dwRight) );
  137. CopyMemory( m_dwRight,dwRight,sizeof(DWORD)*cbRightCount );
  138. return true;
  139. }
  140. //检查仅位是否正确
  141. bool CChiHuRight::IsValidRight( DWORD dwRight )
  142. {
  143. DWORD dwRightHead = dwRight & 0xF0000000;
  144. for( BYTE i = 0; i < CountArray(m_dwRightMask); i++ )
  145. if( m_dwRightMask[i] == dwRightHead ) return true;
  146. return false;
  147. }
  148. //////////////////////////////////////////////////////////////////////////
  149. //////////////////////////////////////////////////////////////////////////
  150. //静态变量
  151. //扑克数据,一脚癞油的基础数据
  152. const BYTE CGameLogic::m_cbCardDataArray[MAX_REPERTORY]=
  153. {
  154. 0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09, //万子
  155. 0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09, //万子
  156. 0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09, //万子
  157. 0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09, //万子
  158. 0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19, //索子
  159. 0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19, //索子
  160. 0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19, //索子
  161. 0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19, //索子
  162. 0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29, //同子
  163. 0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29, //同子
  164. 0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29, //同子
  165. 0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29, //同子
  166. };
  167. //三人两房 扑克数据
  168. const BYTE CGameLogic::m_cbCardDataArray_SRLF[MAX_REPERTORY_SRLF] =
  169. {
  170. 0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19, //索子
  171. 0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19, //索子
  172. 0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19, //索子
  173. 0x11,0x12,0x13,0x14,0x15,0x16,0x17,0x18,0x19, //索子
  174. 0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29, //同子
  175. 0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29, //同子
  176. 0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29, //同子
  177. 0x21,0x22,0x23,0x24,0x25,0x26,0x27,0x28,0x29, //同子
  178. };
  179. //////////////////////////////////////////////////////////////////////////
  180. //构造函数
  181. CGameLogic::CGameLogic(CTableFrameSink* pTableFramSink)
  182. {
  183. m_cbMagicIndex = MAX_INDEX;
  184. m_pTableFramSink = pTableFramSink;
  185. }
  186. //析构函数
  187. CGameLogic::~CGameLogic()
  188. {
  189. }
  190. //混乱扑克
  191. BYTE CGameLogic::RandCardData(BYTE cbCardData[])
  192. {
  193. BYTE cbCardDataTemp[MAX_REPERTORY];
  194. BYTE cbMaxCount = 0;
  195. //混乱准备
  196. //if (srlf == m_pTableFramSink->m_gameConfig.wSubGameID)
  197. //{
  198. // CopyMemory(cbCardDataTemp, m_cbCardDataArray_SRLF, sizeof(m_cbCardDataArray_SRLF));
  199. // cbMaxCount = MAX_REPERTORY_SRLF;
  200. //}
  201. //else {
  202. CopyMemory(cbCardDataTemp, m_cbCardDataArray, sizeof(m_cbCardDataArray));
  203. cbMaxCount = MAX_REPERTORY;
  204. //}
  205. //混乱扑克
  206. BYTE cbRandCount = 0, cbPosition = 0;
  207. do
  208. {
  209. cbPosition = rand() % (cbMaxCount - cbRandCount);
  210. cbCardData[cbRandCount++] = cbCardDataTemp[cbPosition];
  211. cbCardDataTemp[cbPosition] = cbCardDataTemp[cbMaxCount - cbRandCount];
  212. } while (cbRandCount < cbMaxCount);
  213. cbRandCount = 0, cbPosition = 0;
  214. ZeroMemory(cbCardDataTemp, sizeof(cbCardDataTemp));
  215. CopyMemory(cbCardDataTemp, cbCardData, sizeof(cbCardDataTemp));
  216. ZeroMemory(cbCardData, sizeof(cbCardData));
  217. do
  218. {
  219. cbPosition = rand() % (cbMaxCount - cbRandCount);
  220. cbCardData[cbRandCount++] = cbCardDataTemp[cbPosition];
  221. cbCardDataTemp[cbPosition] = cbCardDataTemp[cbMaxCount - cbRandCount];
  222. } while (cbRandCount < cbMaxCount);
  223. return cbMaxCount;
  224. }
  225. //删除扑克
  226. bool CGameLogic::RemoveCard(BYTE cbCardIndex[MAX_INDEX], BYTE cbRemoveCard)
  227. {
  228. //效验扑克
  229. ASSERT(IsValidCard(cbRemoveCard));
  230. ASSERT(cbCardIndex[SwitchToCardIndex(cbRemoveCard)]>0);
  231. //删除扑克
  232. BYTE cbRemoveIndex=SwitchToCardIndex(cbRemoveCard);
  233. if (cbCardIndex[cbRemoveIndex]>0)
  234. {
  235. cbCardIndex[cbRemoveIndex]--;
  236. return true;
  237. }
  238. //失败效验
  239. ASSERT(FALSE);
  240. return false;
  241. }
  242. //删除扑克
  243. bool CGameLogic::RemoveCard(BYTE cbCardIndex[MAX_INDEX], const BYTE cbRemoveCard[], BYTE cbRemoveCount)
  244. {
  245. //删除扑克
  246. for (BYTE i=0;i<cbRemoveCount;i++)
  247. {
  248. //效验扑克
  249. ASSERT(IsValidCard(cbRemoveCard[i]));
  250. ASSERT(cbCardIndex[SwitchToCardIndex(cbRemoveCard[i])]>0);
  251. //删除扑克
  252. BYTE cbRemoveIndex=SwitchToCardIndex(cbRemoveCard[i]);
  253. if (cbCardIndex[cbRemoveIndex]==0)
  254. {
  255. //错误断言
  256. ASSERT(FALSE);
  257. //还原删除
  258. for (BYTE j=0;j<i;j++)
  259. {
  260. ASSERT(IsValidCard(cbRemoveCard[j]));
  261. cbCardIndex[SwitchToCardIndex(cbRemoveCard[j])]++;
  262. }
  263. return false;
  264. }
  265. else
  266. {
  267. //删除扑克
  268. --cbCardIndex[cbRemoveIndex];
  269. }
  270. }
  271. return true;
  272. }
  273. //删除扑克
  274. bool CGameLogic::RemoveCard(BYTE cbCardData[], BYTE cbCardCount, const BYTE cbRemoveCard[], BYTE cbRemoveCount)
  275. {
  276. //检验数据
  277. ASSERT(cbCardCount<=14);
  278. ASSERT(cbRemoveCount<=cbCardCount);
  279. //定义变量
  280. BYTE cbDeleteCount=0,cbTempCardData[14];
  281. if (cbCardCount>CountArray(cbTempCardData))
  282. return false;
  283. CopyMemory(cbTempCardData,cbCardData,cbCardCount*sizeof(cbCardData[0]));
  284. //置零扑克
  285. for (BYTE i=0;i<cbRemoveCount;i++)
  286. {
  287. for (BYTE j=0;j<cbCardCount;j++)
  288. {
  289. if (cbRemoveCard[i]==cbTempCardData[j])
  290. {
  291. cbDeleteCount++;
  292. cbTempCardData[j]=0;
  293. break;
  294. }
  295. }
  296. }
  297. //成功判断
  298. if (cbDeleteCount!=cbRemoveCount)
  299. {
  300. ASSERT(FALSE);
  301. return false;
  302. }
  303. //清理扑克
  304. BYTE cbCardPos=0;
  305. for (BYTE i=0;i<cbCardCount;i++)
  306. {
  307. if (cbTempCardData[i]!=0)
  308. cbCardData[cbCardPos++]=cbTempCardData[i];
  309. }
  310. return true;
  311. }
  312. //有效判断
  313. bool CGameLogic::IsValidCard(BYTE cbCardData)
  314. {
  315. BYTE cbValue=(cbCardData&MASK_VALUE);
  316. BYTE cbColor=(cbCardData&MASK_COLOR)>>4;
  317. return (((cbValue>=1)&&(cbValue<=9)&&(cbColor<=2))||((cbValue>=1)&&(cbValue<=7)&&(cbColor==3)));
  318. }
  319. //扑克数目
  320. BYTE CGameLogic::GetCardCount(const BYTE cbCardIndex[MAX_INDEX])
  321. {
  322. //数目统计
  323. BYTE cbCardCount=0;
  324. for (BYTE i=0;i<MAX_INDEX;i++)
  325. cbCardCount+=cbCardIndex[i];
  326. return cbCardCount;
  327. }
  328. //获取组合
  329. BYTE CGameLogic::GetWeaveCard(int cbWeaveKind, BYTE cbCenterCard, BYTE cbCardBuffer[4])
  330. {
  331. //组合扑克
  332. switch (cbWeaveKind)
  333. {
  334. case WIK_LEFT: //上牌操作
  335. {
  336. //设置变量
  337. cbCardBuffer[0]=cbCenterCard;
  338. cbCardBuffer[1]=cbCenterCard+1;
  339. cbCardBuffer[2]=cbCenterCard+2;
  340. return 3;
  341. }
  342. case WIK_RIGHT: //上牌操作
  343. {
  344. //设置变量
  345. cbCardBuffer[0]=cbCenterCard;
  346. cbCardBuffer[1]=cbCenterCard-1;
  347. cbCardBuffer[2]=cbCenterCard-2;
  348. return 3;
  349. }
  350. case WIK_CENTER: //上牌操作
  351. {
  352. //设置变量
  353. cbCardBuffer[0]=cbCenterCard;
  354. cbCardBuffer[1]=cbCenterCard-1;
  355. cbCardBuffer[2]=cbCenterCard+1;
  356. return 3;
  357. }
  358. case WIK_PENG: //碰牌操作
  359. {
  360. //设置变量
  361. cbCardBuffer[0]=cbCenterCard;
  362. cbCardBuffer[1]=cbCenterCard;
  363. cbCardBuffer[2]=cbCenterCard;
  364. return 3;
  365. }
  366. case WIK_GANG: //杠牌操作
  367. {
  368. //设置变量
  369. cbCardBuffer[0]=cbCenterCard;
  370. cbCardBuffer[1]=cbCenterCard;
  371. cbCardBuffer[2]=cbCenterCard;
  372. cbCardBuffer[3]=cbCenterCard;
  373. return 4;
  374. }
  375. case WIK_MING_GANG: //明杠牌操作
  376. {
  377. //设置变量
  378. cbCardBuffer[0] = cbCenterCard;
  379. cbCardBuffer[1] = cbCenterCard;
  380. cbCardBuffer[2] = cbCenterCard;
  381. cbCardBuffer[3] = cbCenterCard;
  382. return 4;
  383. }
  384. case WIK_AN_GANG: //暗杠牌操作
  385. {
  386. //设置变量
  387. cbCardBuffer[0] = cbCenterCard;
  388. cbCardBuffer[1] = cbCenterCard;
  389. cbCardBuffer[2] = cbCenterCard;
  390. cbCardBuffer[3] = cbCenterCard;
  391. return 4;
  392. }
  393. case WIK_AN_PIGANG: //暗皮杠牌操作
  394. {
  395. //设置变量
  396. cbCardBuffer[0] = cbCenterCard;
  397. cbCardBuffer[1] = cbCenterCard;
  398. cbCardBuffer[2] = cbCenterCard;
  399. return 3;
  400. }
  401. case WIK_MING_PIGANG: //明皮杠牌操作
  402. {
  403. //设置变量
  404. cbCardBuffer[0] = cbCenterCard;
  405. cbCardBuffer[1] = cbCenterCard;
  406. cbCardBuffer[2] = cbCenterCard;
  407. return 3;
  408. }
  409. case WIK_BU_GANG:
  410. {
  411. cbCardBuffer[0] = cbCenterCard;
  412. cbCardBuffer[1] = cbCenterCard;
  413. cbCardBuffer[2] = cbCenterCard;
  414. cbCardBuffer[3] = cbCenterCard;
  415. return 4;
  416. }
  417. default:
  418. {
  419. ASSERT(FALSE);
  420. }
  421. }
  422. return 0;
  423. }
  424. //动作等级,只有碰,杠
  425. BYTE CGameLogic::GetUserActionRank(BYTE cbUserAction)
  426. {
  427. //胡牌等级
  428. //if (cbUserAction&WIK_CHI_HU) { return 4; }
  429. //杠牌等级
  430. if (cbUserAction&WIK_GANG) { return 3; }
  431. //碰牌等级
  432. if (cbUserAction&WIK_PENG) { return 2; }
  433. //上牌等级
  434. //if (cbUserAction&(WIK_RIGHT|WIK_CENTER|WIK_LEFT)) { return 1; }
  435. return 0;
  436. }
  437. //胡牌等级
  438. //WORD CGameLogic::GetChiHuActionRank(const CChiHuRight & ChiHuRight)
  439. //{
  440. // WORD wFanShu = 0;
  441. //
  442. // if (!(ChiHuRight&CHR_YING_LAIYOU).IsEmpty())
  443. // wFanShu = 4;
  444. // else if( !(ChiHuRight&CHR_RUAN_LAIYOU).IsEmpty() )
  445. // wFanShu = 2;
  446. // else if (!(ChiHuRight&CHR_YING_ZIMO).IsEmpty())
  447. // wFanShu = 2;
  448. // else if (!(ChiHuRight&CHR_RUAN_ZIMO).IsEmpty())
  449. // wFanShu = 1;
  450. // ASSERT( wFanShu > 0 );
  451. // return wFanShu;
  452. //}
  453. //吃牌判断 一脚耐油不需要
  454. /*
  455. BYTE CGameLogic::EstimateEatCard(const BYTE cbCardIndex[MAX_INDEX], BYTE cbCurrentCard)
  456. {
  457. //参数效验
  458. ASSERT(IsValidCard(cbCurrentCard));
  459. //过滤判断
  460. if ( cbCurrentCard>=0x31 || IsMagicCard(cbCurrentCard) )
  461. return WIK_NULL;
  462. //变量定义
  463. BYTE cbExcursion[3]={0,1,2};
  464. BYTE cbItemKind[3]={WIK_LEFT,WIK_CENTER,WIK_RIGHT};
  465. //吃牌判断
  466. BYTE cbEatKind=0,cbFirstIndex=0;
  467. BYTE cbCurrentIndex=SwitchToCardIndex(cbCurrentCard);
  468. for (BYTE i=0;i<CountArray(cbItemKind);i++)
  469. {
  470. BYTE cbValueIndex=cbCurrentIndex%9;
  471. if ((cbValueIndex>=cbExcursion[i])&&((cbValueIndex-cbExcursion[i])<=6))
  472. {
  473. //吃牌判断
  474. cbFirstIndex=cbCurrentIndex-cbExcursion[i];
  475. //吃牌不能包含有王霸
  476. if( m_cbMagicIndex != MAX_INDEX &&
  477. m_cbMagicIndex >= cbFirstIndex && m_cbMagicIndex <= cbFirstIndex+2 ) continue;
  478. if ((cbCurrentIndex!=cbFirstIndex)&&(cbCardIndex[cbFirstIndex]==0))
  479. continue;
  480. if ((cbCurrentIndex!=(cbFirstIndex+1))&&(cbCardIndex[cbFirstIndex+1]==0))
  481. continue;
  482. if ((cbCurrentIndex!=(cbFirstIndex+2))&&(cbCardIndex[cbFirstIndex+2]==0))
  483. continue;
  484. //设置类型
  485. cbEatKind|=cbItemKind[i];
  486. }
  487. }
  488. return cbEatKind;
  489. }*/
  490. //碰牌判断
  491. int CGameLogic::EstimatePengCard(const BYTE cbCardIndex[MAX_INDEX], BYTE cbCurrentCard, BYTE LaiZiPiData)
  492. {
  493. //参数效验
  494. ASSERT(IsValidCard(cbCurrentCard));
  495. //过滤判断
  496. if (IsMagicCard(cbCurrentCard))
  497. return WIK_NULL;
  498. if (cbCurrentCard == LaiZiPiData)
  499. {
  500. BYTE index = SwitchToCardIndex(cbCurrentCard);
  501. BYTE zhi = cbCardIndex[index];
  502. return (zhi == 2) ? WIK_MING_PIGANG : WIK_NULL;
  503. }
  504. //碰牌判断
  505. return (cbCardIndex[SwitchToCardIndex(cbCurrentCard)] >= 2) ? WIK_PENG : WIK_NULL;
  506. }
  507. //杠牌判断
  508. int CGameLogic::EstimateGangCard(const BYTE cbCardIndex[MAX_INDEX], BYTE cbCurrentCard)
  509. {
  510. //参数效验
  511. ASSERT(IsValidCard(cbCurrentCard));
  512. //过滤判断
  513. if ( IsMagicCard(cbCurrentCard) )
  514. return WIK_NULL;
  515. BYTE index = SwitchToCardIndex(cbCurrentCard);
  516. BYTE zhi = cbCardIndex[index];
  517. //杠牌判断
  518. return (zhi==3)?WIK_MING_GANG:WIK_NULL;
  519. }
  520. //杠牌分析
  521. int CGameLogic::AnalyseGangCard(const BYTE cbCardIndex[MAX_INDEX], const BYTE m_cbLaiZiData, const BYTE m_cbLaiZiPiData, const tagWeaveItem WeaveItem[], BYTE cbWeaveCount, tagGangCardResult & GangCardResult, BYTE bProvideCard, bool bCanAnGang /* = true */)
  522. {
  523. //设置变量
  524. int cbActionMask = WIK_NULL;
  525. ZeroMemory(&GangCardResult, sizeof(GangCardResult));
  526. if (cbCardIndex[SwitchToCardIndex(m_cbLaiZiPiData)] == 3)
  527. {
  528. cbActionMask |= (WIK_GANG | WIK_AN_PIGANG);
  529. GangCardResult.cbCardData[GangCardResult.cbCardCount++] = m_cbLaiZiPiData;//癞子皮杠
  530. }
  531. //手上杠牌
  532. for (BYTE i = 0; i < MAX_INDEX; i++)
  533. {
  534. if (i == m_cbMagicIndex) continue;
  535. if (i == SwitchToCardIndex(m_cbLaiZiData))continue;
  536. //if (cbCardIndex[i] == 3)
  537. //{
  538. // BYTE cbCardLaiZiData = SwitchToCardData(i);//用户手上牌有3个一样的牌,把这个牌复制给临时变量
  539. // if (cbCardLaiZiData == m_cbLaiZiPiData)//判断是否是癞子皮
  540. // {
  541. // cbActionMask |= WIK_GANG;
  542. // GangCardResult.cbCardData[GangCardResult.cbCardCount++] = cbCardLaiZiData;//癞子皮杠
  543. // }
  544. //}
  545. if (cbCardIndex[i] == 4)
  546. {
  547. BYTE cbCardData = SwitchToCardData(i);
  548. cbActionMask |= (WIK_GANG | WIK_AN_GANG);
  549. GangCardResult.cbCardData[GangCardResult.cbCardCount++] = cbCardData;
  550. }
  551. }
  552. //组合杠牌
  553. for (BYTE i = 0; i < cbWeaveCount; i++)
  554. {
  555. if (WeaveItem[i].cbWeaveKind == WIK_PENG && WeaveItem[i].cbCenterCard == bProvideCard)
  556. {
  557. cbActionMask |= WIK_BU_GANG;
  558. GangCardResult.cbCardData[GangCardResult.cbCardCount++] = WeaveItem[i].cbCenterCard;
  559. }
  560. }
  561. return cbActionMask;
  562. }
  563. int CGameLogic::AnalyseChiHuCard(const BYTE cbCardIndex[MAX_INDEX], const tagWeaveItem WeaveItem[], BYTE cbWeaveCount, BYTE cbCurrentCard, CChiHuRight &ChiHuRight, BYTE m_cbLaiZi, BYTE bSubMit)
  564. {
  565. if (bSubMit == OneStepLaiYou || bSubMit == BanLai)
  566. {
  567. //变量定义
  568. int cbChiHuKind = WIK_NULL;
  569. CAnalyseItemArray AnalyseItemArray;
  570. //设置变量
  571. AnalyseItemArray.RemoveAll();
  572. ChiHuRight.SetEmpty();
  573. //构造扑克
  574. BYTE cbCardIndexTemp[MAX_INDEX];
  575. CopyMemory(cbCardIndexTemp, cbCardIndex, sizeof(cbCardIndexTemp));
  576. //cbCurrentCard一定不为0 !!!!!!!!!
  577. ASSERT(cbCurrentCard != 0);
  578. if (cbCurrentCard == 0) return WIK_NULL;
  579. if (!ChiHuRight.IsEmpty())
  580. cbChiHuKind = WIK_ZI_MO;
  581. //插入扑克
  582. if (cbCurrentCard == 0)
  583. {
  584. ASSERT(false);
  585. return false;
  586. }
  587. cbCardIndexTemp[SwitchToCardIndex(cbCurrentCard)]++;
  588. BYTE LaiZiIndex = SwitchToCardIndex(m_cbLaiZi);//癞子在牌里面的索引
  589. if (cbCardIndexTemp[LaiZiIndex] > 1)//手上癞子超过2个或者2个,就不能胡牌,必须打掉一个
  590. {
  591. return WIK_NULL;
  592. }
  593. BYTE isHuPaiCount = 0;
  594. if (cbCardIndexTemp[LaiZiIndex] == 1 && cbCurrentCard != m_cbLaiZi)
  595. {
  596. AnalyseCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, AnalyseItemArray);
  597. if (AnalyseItemArray.GetCount() > 0)
  598. {
  599. return WIK_ZI_MO | WIK_YING_ZIMO;
  600. }
  601. AnalyseItemArray.RemoveAll();
  602. cbCardIndexTemp[LaiZiIndex]--;
  603. cbCardIndexTemp[SwitchToCardIndex(cbCurrentCard)]--;
  604. for (BYTE i = 0; i < MAX_INDEX; i++)
  605. {
  606. if (i == LaiZiIndex)continue;
  607. cbCardIndexTemp[i] += 2;
  608. if (cbCardIndexTemp[i]>5)
  609. {
  610. isHuPaiCount++;
  611. cbCardIndexTemp[i] -= 2;
  612. continue;
  613. }
  614. AnalyseCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, AnalyseItemArray);
  615. if (AnalyseItemArray.GetCount() > 0)
  616. {
  617. isHuPaiCount++;
  618. }
  619. AnalyseItemArray.RemoveAll();
  620. cbCardIndexTemp[i] -= 2;
  621. }
  622. if (isHuPaiCount >= 26)
  623. {
  624. return WIK_NULL;
  625. }
  626. cbCardIndexTemp[SwitchToCardIndex(cbCurrentCard)]++;
  627. //分析扑克,cbCardIndexTemp是用户手上的牌,WeaveItem,
  628. for (BYTE i = 0; i < MAX_INDEX; i++)
  629. {
  630. if (i == LaiZiIndex)continue;
  631. if (cbCardIndexTemp[i]>4)continue;
  632. cbCardIndexTemp[i]++;
  633. AnalyseCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, AnalyseItemArray);
  634. //胡牌分析
  635. if (AnalyseItemArray.GetCount()>0)
  636. {
  637. cbChiHuKind = WIK_ZI_MO;
  638. return cbChiHuKind;
  639. }
  640. AnalyseItemArray.RemoveAll();
  641. cbCardIndexTemp[i]--;
  642. }
  643. //if (cbChiHuKind&WIK_ZI_MO)
  644. //{
  645. // cbCardIndexTemp[SwitchToCardIndex(cbCurrentCard)]--;
  646. // for (BYTE i = 0; i < MAX_INDEX; i++)
  647. // {
  648. // if (i == LaiZiIndex)continue;
  649. // cbCardIndexTemp[i] += 2;
  650. // AnalyseCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, AnalyseItemArray);
  651. // if (AnalyseItemArray.GetCount()>0)
  652. // {
  653. // isHuPaiCount++;
  654. // }
  655. // cbCardIndexTemp[i] -= 2;
  656. // }
  657. // if (isHuPaiCount >= 26) //当有癞子时,且癞子是个万能和牌时,需要打掉,或者改牌
  658. // {
  659. // isHuPaiCount = 0;
  660. // return WIK_NULL;
  661. // }
  662. // cbCardIndexTemp[SwitchToCardIndex(cbCurrentCard)]++;
  663. //}
  664. cbCardIndexTemp[LaiZiIndex]++;
  665. return cbChiHuKind;
  666. }
  667. else
  668. {
  669. if (cbCurrentCard == m_cbLaiZi)
  670. {
  671. if (cbCardIndexTemp[LaiZiIndex] != 1)
  672. {
  673. ASSERT(false);
  674. return false;
  675. }
  676. AnalyseCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, AnalyseItemArray);
  677. if (AnalyseItemArray.GetCount() > 0)
  678. {
  679. return WIK_ZI_MO | WIK_YING_ZIMO;
  680. }
  681. cbCardIndexTemp[LaiZiIndex]--;
  682. //分析扑克,cbCardIndexTemp是用户手上的牌,WeaveItem,
  683. for (BYTE i = 0; i < MAX_INDEX; i++)
  684. {
  685. if (i == LaiZiIndex)continue;
  686. cbCardIndexTemp[i]++;
  687. AnalyseCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, AnalyseItemArray);
  688. //胡牌分析
  689. if (AnalyseItemArray.GetCount()>0)
  690. {
  691. cbChiHuKind = WIK_ZI_MO;
  692. return cbChiHuKind;
  693. }
  694. AnalyseItemArray.RemoveAll();
  695. cbCardIndexTemp[i]--;
  696. }
  697. cbCardIndexTemp[LaiZiIndex]++;
  698. return cbChiHuKind;
  699. }
  700. else
  701. {
  702. AnalyseCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, AnalyseItemArray);
  703. //胡牌分析
  704. if (AnalyseItemArray.GetCount() > 0)
  705. {
  706. cbChiHuKind |= WIK_ZI_MO;
  707. cbChiHuKind |= WIK_YING_ZIMO;
  708. }
  709. return cbChiHuKind;
  710. }
  711. }
  712. return false;
  713. }
  714. if (bSubMit == WuLaiDaoDi)
  715. {
  716. //变量定义
  717. int cbChiHuKind = WIK_NULL;
  718. CAnalyseItemArray AnalyseItemArray;
  719. //设置变量
  720. AnalyseItemArray.RemoveAll();
  721. ChiHuRight.SetEmpty();
  722. //构造扑克
  723. BYTE cbCardIndexTemp[MAX_INDEX];
  724. CopyMemory(cbCardIndexTemp, cbCardIndex, sizeof(cbCardIndexTemp));
  725. //cbCurrentCard一定不为0 !!!!!!!!!
  726. ASSERT(cbCurrentCard != 0);
  727. if (cbCurrentCard == 0) return WIK_NULL;
  728. if (!ChiHuRight.IsEmpty())
  729. cbChiHuKind = WIK_ZI_MO;
  730. //插入扑克
  731. if (cbCurrentCard == 0)
  732. {
  733. ASSERT(false);
  734. return false;
  735. }
  736. cbCardIndexTemp[SwitchToCardIndex(cbCurrentCard)]++;
  737. BYTE LaiZiIndex = SwitchToCardIndex(m_cbLaiZi);//癞子在牌里面的索引
  738. if (cbCardIndexTemp[LaiZiIndex] > 0)
  739. {
  740. return WIK_NULL;
  741. }
  742. AnalyseCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, AnalyseItemArray);
  743. if (AnalyseItemArray.GetCount() > 0)
  744. {
  745. cbChiHuKind |= WIK_ZI_MO;
  746. cbChiHuKind |= WIK_YING_ZIMO;
  747. }
  748. return cbChiHuKind;
  749. }
  750. return false;
  751. }
  752. //听牌分析,
  753. bool CGameLogic::AnalyseTingCard(const BYTE cbCardIndex[MAX_INDEX], const tagWeaveItem WeaveItem[], BYTE cbWeaveCount, BYTE *m_cbTingPaiData, BYTE m_cbLaiZi, BYTE subMit,BYTE LaiZiCount)
  754. {
  755. //复制数据
  756. BYTE cbCardIndexTemp[MAX_INDEX];
  757. CopyMemory(cbCardIndexTemp, cbCardIndex, sizeof(cbCardIndexTemp));
  758. BYTE cbCardCount = GetCardCount(cbCardIndexTemp);
  759. if (cbCardCount > 1 && (cbCardCount - 1) % 3 != 0)
  760. {
  761. ASSERT(false);
  762. return false;
  763. }
  764. CChiHuRight chr;
  765. for (BYTE i = 0; i < MAX_INDEX; i++)
  766. {
  767. BYTE cbCurrentCard = SwitchToCardData(i);
  768. if (cbCurrentCard == m_cbLaiZi&&subMit == WuLaiDaoDi)continue;
  769. if (subMit == BanLai)
  770. {
  771. int wikChiHu = AnalyseChiHuCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, cbCurrentCard, chr, m_cbLaiZi, subMit);
  772. if ((LaiZiCount == 0 && (wikChiHu&WIK_YING_ZIMO) == WIK_YING_ZIMO) || (LaiZiCount > 0 && (wikChiHu&WIK_ZI_MO) == WIK_ZI_MO))
  773. m_cbTingPaiData[i] = 1;
  774. else
  775. {
  776. m_cbTingPaiData[i] = 0;
  777. }
  778. }
  779. else
  780. {
  781. if (WIK_ZI_MO & AnalyseChiHuCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, cbCurrentCard, chr, m_cbLaiZi, subMit))
  782. m_cbTingPaiData[i] = 1;
  783. else
  784. {
  785. m_cbTingPaiData[i] = 0;
  786. }
  787. }
  788. }
  789. return true;
  790. }
  791. //是否听牌
  792. bool CGameLogic::IsTingCard(const BYTE cbCardIndex[MAX_INDEX], const tagWeaveItem WeaveItem[], BYTE cbWeaveCount, BYTE m_cbLaiZi, BYTE subMit, BYTE LaiZiCount)
  793. {
  794. //复制数据
  795. BYTE cbCardIndexTemp[MAX_INDEX];
  796. CopyMemory(cbCardIndexTemp, cbCardIndex, sizeof(cbCardIndexTemp));
  797. BYTE LaiZiIndex = SwitchToCardIndex(m_cbLaiZi);
  798. CChiHuRight chr;
  799. for (BYTE i = 0; i < MAX_INDEX; i++)
  800. {
  801. BYTE cbCurrentCard = SwitchToCardData(i);
  802. if (((i == LaiZiIndex) && (cbCardIndexTemp[i] > 0) && (subMit == OneStepLaiYou || subMit == BanLai)) || (i == LaiZiIndex&& subMit == WuLaiDaoDi))
  803. continue;
  804. if (subMit == BanLai && LaiZiCount == 0)
  805. {
  806. int wikChiHu = AnalyseChiHuCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, cbCurrentCard, chr, m_cbLaiZi, subMit);
  807. if (WIK_YING_ZIMO & wikChiHu)
  808. {
  809. return true;
  810. }
  811. else
  812. continue;
  813. }
  814. if (WIK_ZI_MO & AnalyseChiHuCard(cbCardIndexTemp, WeaveItem, cbWeaveCount, cbCurrentCard, chr, m_cbLaiZi, subMit))
  815. return true;
  816. }
  817. return false;
  818. }
  819. //扑克转换
  820. BYTE CGameLogic::SwitchToCardData(BYTE cbCardIndex)
  821. {
  822. //ASSERT(cbCardIndex<34);
  823. return ((cbCardIndex/9)<<4)|(cbCardIndex%9+1);
  824. }
  825. //扑克转换
  826. BYTE CGameLogic::SwitchToCardIndex(BYTE cbCardData)
  827. {
  828. ASSERT(IsValidCard(cbCardData));
  829. return ((cbCardData&MASK_COLOR)>>4)*9+(cbCardData&MASK_VALUE)-1;
  830. }
  831. //扑克转换
  832. BYTE CGameLogic::SwitchToCardData(const BYTE cbCardIndex[MAX_INDEX], BYTE cbCardData[MAX_COUNT])
  833. {
  834. //转换扑克
  835. BYTE cbPosition=0;
  836. //钻牌
  837. if( m_cbMagicIndex != MAX_INDEX )
  838. {
  839. for( BYTE i = 0; i < cbCardIndex[m_cbMagicIndex]; i++ )
  840. cbCardData[cbPosition++] = SwitchToCardData(m_cbMagicIndex);
  841. }
  842. for (BYTE i=0;i<MAX_INDEX;i++)
  843. {
  844. if( i == m_cbMagicIndex ) continue;
  845. if (cbCardIndex[i]!=0)
  846. {
  847. for (BYTE j=0;j<cbCardIndex[i];j++)
  848. {
  849. ASSERT(cbPosition<MAX_COUNT);
  850. cbCardData[cbPosition++]=SwitchToCardData(i);
  851. }
  852. }
  853. }
  854. return cbPosition;
  855. }
  856. //扑克转换
  857. BYTE CGameLogic::SwitchToCardIndex(const BYTE cbCardData[], BYTE cbCardCount, BYTE cbCardIndex[MAX_INDEX])
  858. {
  859. //设置变量
  860. ZeroMemory(cbCardIndex,sizeof(BYTE)*MAX_INDEX);
  861. //转换扑克
  862. for (BYTE i=0;i<cbCardCount;i++)
  863. {
  864. ASSERT(IsValidCard(cbCardData[i]));
  865. cbCardIndex[SwitchToCardIndex(cbCardData[i])]++;
  866. }
  867. return cbCardCount;
  868. }
  869. //分析扑克
  870. bool CGameLogic::AnalyseCard(const BYTE cbCardIndex[MAX_INDEX], const tagWeaveItem WeaveItem[], BYTE cbWeaveCount, CAnalyseItemArray & AnalyseItemArray)
  871. {
  872. //计算数目
  873. BYTE cbCardCount = GetCardCount(cbCardIndex);
  874. //效验数目
  875. //ASSERT((cbCardCount>=2)&&(cbCardCount<=MAX_COUNT)&&((cbCardCount-2)%3==0));
  876. if ((cbCardCount<2) || (cbCardCount>MAX_COUNT) || ((cbCardCount - 2) % 3 != 0))
  877. return false;
  878. //变量定义
  879. BYTE cbKindItemCount = 0;
  880. tagKindItem KindItem[27 * 2 + 7 + 14];
  881. ZeroMemory(KindItem, sizeof(KindItem));
  882. //需求判断
  883. BYTE cbLessKindItem = (cbCardCount - 2) / 3;
  884. ASSERT((cbLessKindItem + cbWeaveCount) == 4);
  885. //单吊判断
  886. if (cbLessKindItem == 0)
  887. {
  888. //效验参数
  889. ASSERT((cbCardCount == 2) && (cbWeaveCount == 4));
  890. //牌眼判断
  891. for (BYTE i = 0; i < MAX_INDEX; i++)
  892. {
  893. if (cbCardIndex[i] == 2 ||
  894. (m_cbMagicIndex != MAX_INDEX && i != m_cbMagicIndex && cbCardIndex[m_cbMagicIndex] + cbCardIndex[i] == 2))
  895. {
  896. //变量定义
  897. tagAnalyseItem AnalyseItem;
  898. ZeroMemory(&AnalyseItem, sizeof(AnalyseItem));
  899. //设置结果
  900. for (BYTE j = 0; j < cbWeaveCount; j++)
  901. {
  902. AnalyseItem.cbWeaveKind[j] = WeaveItem[j].cbWeaveKind;
  903. AnalyseItem.cbCenterCard[j] = WeaveItem[j].cbCenterCard;
  904. GetWeaveCard(WeaveItem[j].cbWeaveKind, WeaveItem[j].cbCenterCard, AnalyseItem.cbCardData[j]);
  905. }
  906. AnalyseItem.cbCardEye = SwitchToCardData(i);
  907. if (cbCardIndex[i] < 2 || i == m_cbMagicIndex)
  908. AnalyseItem.bMagicEye = true;
  909. else AnalyseItem.bMagicEye = false;
  910. //插入结果
  911. AnalyseItemArray.Add(AnalyseItem);
  912. return true;
  913. }
  914. }
  915. return false;
  916. }
  917. //拆分分析,用户手上的临时牌变量
  918. BYTE cbMagicCardIndex[MAX_INDEX];
  919. CopyMemory(cbMagicCardIndex, cbCardIndex, sizeof(cbMagicCardIndex));
  920. BYTE cbMagicCardCount = 0;//用来干什么的不知道
  921. if (m_cbMagicIndex != MAX_INDEX)
  922. {
  923. cbMagicCardCount = cbCardIndex[m_cbMagicIndex];
  924. if (cbMagicCardIndex[m_cbMagicIndex]) cbMagicCardIndex[m_cbMagicIndex] = 1; //减小多余组合
  925. }
  926. if (cbCardCount >= 3)
  927. {
  928. for (BYTE i = 0; i < MAX_INDEX; i++)
  929. {
  930. //同牌判断
  931. if (cbMagicCardIndex[i] + cbMagicCardCount >= 3)
  932. {
  933. ASSERT(cbKindItemCount < CountArray(KindItem));
  934. KindItem[cbKindItemCount].cbCardIndex[0] = i;
  935. KindItem[cbKindItemCount].cbCardIndex[1] = i;
  936. KindItem[cbKindItemCount].cbCardIndex[2] = i;
  937. KindItem[cbKindItemCount].cbWeaveKind = WIK_PENG;
  938. KindItem[cbKindItemCount].cbCenterCard = SwitchToCardData(i);
  939. KindItem[cbKindItemCount].cbValidIndex[0] = cbMagicCardIndex[i] > 0 ? i : m_cbMagicIndex;
  940. KindItem[cbKindItemCount].cbValidIndex[1] = cbMagicCardIndex[i] > 1 ? i : m_cbMagicIndex;
  941. KindItem[cbKindItemCount].cbValidIndex[2] = cbMagicCardIndex[i] > 2 ? i : m_cbMagicIndex;
  942. cbKindItemCount++;
  943. if (cbMagicCardIndex[i] + cbMagicCardCount >= 6)
  944. {
  945. ASSERT(cbKindItemCount < CountArray(KindItem));
  946. KindItem[cbKindItemCount].cbCardIndex[0] = i;
  947. KindItem[cbKindItemCount].cbCardIndex[1] = i;
  948. KindItem[cbKindItemCount].cbCardIndex[2] = i;
  949. KindItem[cbKindItemCount].cbWeaveKind = WIK_PENG;
  950. KindItem[cbKindItemCount].cbCenterCard = SwitchToCardData(i);
  951. KindItem[cbKindItemCount].cbValidIndex[0] = cbMagicCardIndex[i] > 3 ? i : m_cbMagicIndex;
  952. KindItem[cbKindItemCount].cbValidIndex[1] = m_cbMagicIndex;
  953. KindItem[cbKindItemCount].cbValidIndex[2] = m_cbMagicIndex;
  954. cbKindItemCount++;
  955. }
  956. }
  957. //连牌判断
  958. if ((i < (MAX_INDEX - 2)) && ((i % 9) < 7))
  959. {
  960. //只要财神牌数加上3个顺序索引的牌数大于等于3,则进行组合
  961. if (cbMagicCardCount + cbMagicCardIndex[i] + cbMagicCardIndex[i + 1] + cbMagicCardIndex[i + 2] >= 3)
  962. {
  963. BYTE cbIndex[3] = { i == m_cbMagicIndex ? 0 : cbMagicCardIndex[i], (i + 1) == m_cbMagicIndex ? 0 : cbMagicCardIndex[i + 1],
  964. (i + 2) == m_cbMagicIndex ? 0 : cbMagicCardIndex[i + 2] };
  965. int nMagicCountTemp = cbMagicCardCount;
  966. BYTE cbValidIndex[3];
  967. while (nMagicCountTemp + cbIndex[0] + cbIndex[1] + cbIndex[2] >= 3)
  968. {
  969. for (BYTE j = 0; j < CountArray(cbIndex); j++)
  970. {
  971. if (cbIndex[j] > 0)
  972. {
  973. cbIndex[j]--;
  974. cbValidIndex[j] = i + j;
  975. }
  976. else
  977. {
  978. nMagicCountTemp--;
  979. cbValidIndex[j] = m_cbMagicIndex;
  980. }
  981. }
  982. if (nMagicCountTemp >= 0)
  983. {
  984. ASSERT(cbKindItemCount < CountArray(KindItem));
  985. KindItem[cbKindItemCount].cbCardIndex[0] = i;
  986. KindItem[cbKindItemCount].cbCardIndex[1] = i + 1;
  987. KindItem[cbKindItemCount].cbCardIndex[2] = i + 2;
  988. KindItem[cbKindItemCount].cbWeaveKind = WIK_LEFT;
  989. KindItem[cbKindItemCount].cbCenterCard = SwitchToCardData(i);
  990. CopyMemory(KindItem[cbKindItemCount].cbValidIndex, cbValidIndex, sizeof(cbValidIndex));
  991. cbKindItemCount++;
  992. }
  993. else break;
  994. }
  995. }
  996. }
  997. }
  998. }
  999. //组合分析
  1000. if (cbKindItemCount >= cbLessKindItem)
  1001. {
  1002. //变量定义
  1003. BYTE cbCardIndexTemp[MAX_INDEX];
  1004. ZeroMemory(cbCardIndexTemp, sizeof(cbCardIndexTemp));
  1005. //变量定义
  1006. BYTE cbIndex[4] = { 0, 1, 2, 3 };
  1007. tagKindItem * pKindItem[4];
  1008. ZeroMemory(&pKindItem, sizeof(pKindItem));
  1009. //开始组合
  1010. do
  1011. {
  1012. //设置变量
  1013. CopyMemory(cbCardIndexTemp, cbCardIndex, sizeof(cbCardIndexTemp));
  1014. for (BYTE i = 0; i < cbLessKindItem; i++)
  1015. pKindItem[i] = &KindItem[cbIndex[i]];
  1016. //数量判断
  1017. bool bEnoughCard = true;
  1018. for (BYTE i = 0; i < cbLessKindItem * 3; i++)
  1019. {
  1020. //存在判断
  1021. BYTE cbCardIndex = pKindItem[i / 3]->cbValidIndex[i % 3];
  1022. if (cbCardIndexTemp[cbCardIndex] == 0)
  1023. {
  1024. bEnoughCard = false;
  1025. break;
  1026. }
  1027. else
  1028. cbCardIndexTemp[cbCardIndex]--;
  1029. }
  1030. //胡牌判断
  1031. if (bEnoughCard == true)
  1032. {
  1033. //牌眼判断
  1034. BYTE cbCardEye = 0;
  1035. bool bMagicEye = false;
  1036. for (BYTE i = 0; i < MAX_INDEX; i++)
  1037. {
  1038. if (cbCardIndexTemp[i] == 2)
  1039. {
  1040. cbCardEye = SwitchToCardData(i);
  1041. if (i == m_cbMagicIndex) bMagicEye = true;
  1042. break;
  1043. }
  1044. else if (i != m_cbMagicIndex &&
  1045. m_cbMagicIndex != MAX_INDEX && cbCardIndexTemp[i] + cbCardIndexTemp[m_cbMagicIndex] == 2)
  1046. {
  1047. cbCardEye = SwitchToCardData(i);
  1048. bMagicEye = true;
  1049. }
  1050. }
  1051. //组合类型
  1052. if (cbCardEye != 0)
  1053. {
  1054. //变量定义
  1055. tagAnalyseItem AnalyseItem;
  1056. ZeroMemory(&AnalyseItem, sizeof(AnalyseItem));
  1057. //设置组合
  1058. for (BYTE i = 0; i < cbWeaveCount; i++)
  1059. {
  1060. AnalyseItem.cbWeaveKind[i] = WeaveItem[i].cbWeaveKind;
  1061. AnalyseItem.cbCenterCard[i] = WeaveItem[i].cbCenterCard;
  1062. GetWeaveCard(WeaveItem[i].cbWeaveKind, WeaveItem[i].cbCenterCard,
  1063. AnalyseItem.cbCardData[i]);
  1064. }
  1065. //设置牌型
  1066. for (BYTE i = 0; i < cbLessKindItem; i++)
  1067. {
  1068. AnalyseItem.cbWeaveKind[i + cbWeaveCount] = pKindItem[i]->cbWeaveKind;
  1069. AnalyseItem.cbCenterCard[i + cbWeaveCount] = pKindItem[i]->cbCenterCard;
  1070. AnalyseItem.cbCardData[cbWeaveCount + i][0] = SwitchToCardData(pKindItem[i]->cbValidIndex[0]);
  1071. AnalyseItem.cbCardData[cbWeaveCount + i][1] = SwitchToCardData(pKindItem[i]->cbValidIndex[1]);
  1072. AnalyseItem.cbCardData[cbWeaveCount + i][2] = SwitchToCardData(pKindItem[i]->cbValidIndex[2]);
  1073. }
  1074. //设置牌眼
  1075. AnalyseItem.cbCardEye = cbCardEye;
  1076. AnalyseItem.bMagicEye = bMagicEye;
  1077. //插入结果
  1078. AnalyseItemArray.Add(AnalyseItem);
  1079. }
  1080. }
  1081. //设置索引
  1082. if (cbIndex[cbLessKindItem - 1] == (cbKindItemCount - 1))
  1083. {
  1084. BYTE i = cbLessKindItem - 1;
  1085. for (; i > 0; i--)
  1086. {
  1087. if ((cbIndex[i - 1] + 1) != cbIndex[i])
  1088. {
  1089. BYTE cbNewIndex = cbIndex[i - 1];
  1090. for (BYTE j = (i - 1); j < cbLessKindItem; j++)
  1091. cbIndex[j] = cbNewIndex + j - i + 2;
  1092. break;
  1093. }
  1094. }
  1095. if (i == 0)
  1096. break;
  1097. }
  1098. else
  1099. cbIndex[cbLessKindItem - 1]++;
  1100. } while (true);
  1101. }
  1102. return (AnalyseItemArray.GetCount() > 0);
  1103. }
  1104. //钻牌
  1105. bool CGameLogic::IsMagicCard( BYTE cbCardData )
  1106. {
  1107. if( m_cbMagicIndex != MAX_INDEX )
  1108. return SwitchToCardIndex(cbCardData) == m_cbMagicIndex;
  1109. return false;
  1110. }
  1111. //获取手牌癞子数量
  1112. BYTE CGameLogic::GetLaiZiCount(const BYTE cbCardIndex[MAX_INDEX], BYTE m_cbLaiZi)
  1113. {
  1114. BYTE LaiZiCount = 0;//判断玩家手上是否有癞子
  1115. for (BYTE i = 0; i < MAX_INDEX; i++)
  1116. {
  1117. if (cbCardIndex[i] == 0)continue;
  1118. if (SwitchToCardData(i) == m_cbLaiZi)//癞子不能有多个,否则需要打出去
  1119. {
  1120. if (cbCardIndex[i] == 1)
  1121. {
  1122. LaiZiCount = 1;
  1123. }
  1124. else
  1125. {
  1126. LaiZiCount = 2;
  1127. }
  1128. }
  1129. }
  1130. return LaiZiCount;
  1131. }
  1132. //排序,根据牌值排序
  1133. bool CGameLogic::SortCardList( BYTE cbCardData[MAX_COUNT], BYTE cbCardCount )
  1134. {
  1135. //数目过虑
  1136. if (cbCardCount==0||cbCardCount>MAX_COUNT) return false;
  1137. //排序操作
  1138. bool bSorted=true;
  1139. BYTE cbSwitchData=0,cbLast=cbCardCount-1;
  1140. do
  1141. {
  1142. bSorted=true;
  1143. for (BYTE i=0;i<cbLast;i++)
  1144. {
  1145. if (cbCardData[i]>cbCardData[i+1])
  1146. {
  1147. //设置标志
  1148. bSorted=false;
  1149. //扑克数据
  1150. cbSwitchData=cbCardData[i];
  1151. cbCardData[i]=cbCardData[i+1];
  1152. cbCardData[i+1]=cbSwitchData;
  1153. }
  1154. }
  1155. cbLast--;
  1156. } while(bSorted==false);
  1157. return true;
  1158. }
  1159. byte CGameLogic::GetValue(USHORT uNum, byte PaiZhi)
  1160. {
  1161. byte bRet = 0;
  1162. switch (uNum)
  1163. {
  1164. case 0:
  1165. return PaiZhi;
  1166. case 1:
  1167. return PaiZhi + 41;
  1168. case 2:
  1169. return PaiZhi + 82;
  1170. case 3:
  1171. return PaiZhi + 123;
  1172. case 4:
  1173. return PaiZhi + 164;
  1174. default:
  1175. ASSERT(FALSE);
  1176. return 0;
  1177. throw _T("非法数值");
  1178. break;
  1179. }
  1180. return bRet + PaiZhi;
  1181. }
  1182. bool CGameLogic::PeiPai(BYTE ParZhi[MAX_REPERTORY])
  1183. {
  1184. std::ifstream in;
  1185. std::string filename = "zuopai.dat";
  1186. in.open(filename);
  1187. if (!in.is_open())
  1188. {
  1189. return false;
  1190. //ASSERT(false);
  1191. }
  1192. static BYTE TempCardData[MAX_REPERTORY];
  1193. //static BYTE TempCardDatar[MAX_REPERTORY];
  1194. ZeroMemory(TempCardData, sizeof(TempCardData));
  1195. //ZeroMemory(TempCardDatar, sizeof(TempCardDatar));
  1196. BYTE tempCount = 0;
  1197. char ch[1];
  1198. while (!in.eof())
  1199. {
  1200. in.read(ch, 1);
  1201. TempCardData[tempCount++] = ch[0];
  1202. }
  1203. in.close();
  1204. //TempCardData[108] = 0;
  1205. for (BYTE i = 0; i < MAX_REPERTORY; i++)
  1206. {
  1207. ASSERT(i < MAX_REPERTORY);
  1208. ParZhi[i] = TempCardData[MAX_REPERTORY - i - 1];
  1209. }
  1210. //TempCardDatar[MAX_REPERTORY] = 0;
  1211. return true;
  1212. }
  1213. BYTE CGameLogic::GetEndCard(const BYTE cbCardIndex[MAX_INDEX],BYTE mLaiZiData)
  1214. {
  1215. for (int i = MAX_INDEX - 1; i >= 0; i--)
  1216. {
  1217. if (cbCardIndex[i] > 0 && SwitchToCardData(i) != mLaiZiData)
  1218. {
  1219. return SwitchToCardData(i);
  1220. }
  1221. }
  1222. ASSERT(false);
  1223. return mLaiZiData;
  1224. }
  1225. /*
  1226. // 胡法分析函数
  1227. */
  1228. //中张(不带1和9)
  1229. //bool CGameLogic::IsZhongZhang(const BYTE cbCardIndex[], const tagWeaveItem WeaveItem[], BYTE cbWeaveCount)
  1230. //{
  1231. // for (BYTE i = 0; i < MAX_INDEX; i++)
  1232. // {
  1233. // if (cbCardIndex[i] > 0)
  1234. // {
  1235. // BYTE cbCardValue = SwitchToCardData(i) & MASK_VALUE;
  1236. // if (cbCardValue == 1 || cbCardValue == 9) return false;
  1237. // }
  1238. // }
  1239. //
  1240. // for (BYTE i = 0; i < cbWeaveCount; i++)
  1241. // {
  1242. // BYTE cbCardValue = WeaveItem[i].cbCenterCard & MASK_VALUE;
  1243. //
  1244. // if (WeaveItem[i].cbWeaveKind & WIK_LEFT)
  1245. // {
  1246. // if (cbCardValue == 1 || cbCardValue == 7) return false;
  1247. // }
  1248. // else if (WeaveItem[i].cbWeaveKind & WIK_CENTER)
  1249. // {
  1250. // if (cbCardValue == 2 || cbCardValue == 8) return false;
  1251. // }
  1252. // else if (WeaveItem[i].cbWeaveKind & WIK_RIGHT)
  1253. // {
  1254. // if (cbCardValue == 3 || cbCardValue == 9) return false;
  1255. // }
  1256. // else
  1257. // {
  1258. // if (cbCardValue == 1 || cbCardValue == 9) return false;
  1259. // }
  1260. // }
  1261. //
  1262. // return true;
  1263. //}
  1264. //大对子
  1265. //bool CGameLogic::IsPengPeng( const tagAnalyseItem *pAnalyseItem )
  1266. //{
  1267. // for( BYTE i = 0; i < CountArray(pAnalyseItem->cbWeaveKind); i++ )
  1268. // {
  1269. // if( pAnalyseItem->cbWeaveKind[i]&(WIK_LEFT|WIK_CENTER|WIK_RIGHT) )
  1270. // return false;
  1271. // }
  1272. // return true;
  1273. //}
  1274. //清一色牌
  1275. //bool CGameLogic::IsQingYiSe(const BYTE cbCardIndex[MAX_INDEX], const tagWeaveItem WeaveItem[], const BYTE cbItemCount,const BYTE cbCurrentCard)
  1276. //{
  1277. // //胡牌判断
  1278. // BYTE cbCardColor=0xFF;
  1279. //
  1280. // for (BYTE i=0;i<MAX_INDEX;i++)
  1281. // {
  1282. // if(i==m_cbMagicIndex) continue;
  1283. // if (cbCardIndex[i]!=0)
  1284. // {
  1285. // //花色判断
  1286. // if (cbCardColor!=0xFF)
  1287. // return false;
  1288. //
  1289. // //设置花色
  1290. // cbCardColor=(SwitchToCardData(i)&MASK_COLOR);
  1291. //
  1292. // //设置索引
  1293. // i=(i/9+1)*9-1;
  1294. // }
  1295. // }
  1296. //
  1297. // //如果手上只有王霸
  1298. // if( cbCardColor == 0xFF )
  1299. // {
  1300. // ASSERT( m_cbMagicIndex != MAX_INDEX && cbCardIndex[m_cbMagicIndex] > 0 );
  1301. // //检查组合
  1302. // ASSERT( cbItemCount > 0 );
  1303. // cbCardColor = WeaveItem[0].cbCenterCard&MASK_COLOR;
  1304. // }
  1305. //
  1306. // if((cbCurrentCard&MASK_COLOR)!=cbCardColor && !IsMagicCard(cbCurrentCard) ) return false;
  1307. //
  1308. // //组合判断
  1309. // for (BYTE i=0;i<cbItemCount;i++)
  1310. // {
  1311. // BYTE cbCenterCard=WeaveItem[i].cbCenterCard;
  1312. // if ((cbCenterCard&MASK_COLOR)!=cbCardColor) return false;
  1313. // }
  1314. //
  1315. // return true;
  1316. //}
  1317. //七小对牌
  1318. //bool CGameLogic::IsQiXiaoDui(const BYTE cbCardIndex[MAX_INDEX], const tagWeaveItem WeaveItem[], const BYTE cbWeaveCount,const BYTE cbCurrentCard)
  1319. //{
  1320. // //组合判断
  1321. // if (cbWeaveCount!=0) return false;
  1322. //
  1323. // //单牌数目
  1324. // BYTE cbReplaceCount = 0;
  1325. //
  1326. // //临时数据
  1327. // BYTE cbCardIndexTemp[MAX_INDEX];
  1328. // CopyMemory(cbCardIndexTemp,cbCardIndex,sizeof(cbCardIndexTemp));
  1329. //
  1330. // //插入数据
  1331. // BYTE cbCurrentIndex = SwitchToCardIndex(cbCurrentCard);
  1332. // cbCardIndexTemp[cbCurrentIndex]++;
  1333. //
  1334. // //计算单牌
  1335. // for (BYTE i=0;i<MAX_INDEX;i++)
  1336. // {
  1337. // BYTE cbCardCount=cbCardIndexTemp[i];
  1338. //
  1339. // //王牌过滤
  1340. // if( i == m_cbMagicIndex ) continue;
  1341. //
  1342. // //单牌统计
  1343. // if( cbCardCount == 1 || cbCardCount == 3 ) cbReplaceCount++;
  1344. // }
  1345. //
  1346. // //王牌不够
  1347. // if( m_cbMagicIndex != MAX_INDEX && cbReplaceCount > cbCardIndexTemp[m_cbMagicIndex] ||
  1348. // m_cbMagicIndex == MAX_INDEX && cbReplaceCount > 0 )
  1349. // return false;
  1350. //
  1351. // return true;
  1352. //
  1353. //}
  1354. //带幺
  1355. //bool CGameLogic::IsDaiYao( const tagAnalyseItem *pAnalyseItem )
  1356. //{
  1357. // //检查牌眼
  1358. // BYTE cbCardValue = pAnalyseItem->cbCardEye&MASK_VALUE;
  1359. // if( cbCardValue != 1 && cbCardValue != 9 ) return false;
  1360. //
  1361. // for( BYTE i = 0; i < CountArray(pAnalyseItem->cbWeaveKind); i++ )
  1362. // {
  1363. // if( pAnalyseItem->cbWeaveKind[i]&(WIK_LEFT|WIK_CENTER|WIK_RIGHT) )
  1364. // {
  1365. // BYTE j = 0;
  1366. // for( ; j < 3; j++ )
  1367. // {
  1368. // cbCardValue = pAnalyseItem->cbCardData[i][j]&MASK_VALUE;
  1369. // if( cbCardValue == 1 || cbCardValue == 9 ) break;
  1370. // }
  1371. // if( j == 3 ) return false;
  1372. // }
  1373. // else
  1374. // {
  1375. // cbCardValue = pAnalyseItem->cbCenterCard[i]&MASK_VALUE;
  1376. // if( cbCardValue != 1 && cbCardValue != 9 ) return false;
  1377. // }
  1378. // }
  1379. // return true;
  1380. //}
  1381. //将对
  1382. //bool CGameLogic::IsJiangDui( const tagAnalyseItem *pAnalyseItem )
  1383. //{
  1384. // //是否大对子
  1385. // if( !IsPengPeng(pAnalyseItem) ) return false;
  1386. //
  1387. // //检查牌眼
  1388. // BYTE cbCardValue = pAnalyseItem->cbCardEye&MASK_VALUE;
  1389. // if( cbCardValue != 2 && cbCardValue != 5 && cbCardValue != 8 ) return false;
  1390. //
  1391. // for( BYTE i = 0; i < CountArray(pAnalyseItem->cbWeaveKind); i++ )
  1392. // {
  1393. // if( pAnalyseItem->cbWeaveKind[i]&(WIK_LEFT|WIK_CENTER|WIK_RIGHT) )
  1394. // {
  1395. // BYTE j = 0;
  1396. // for( ; j < 3; j++ )
  1397. // {
  1398. // cbCardValue = pAnalyseItem->cbCardData[i][j]&MASK_VALUE;
  1399. // if( cbCardValue == 2 || cbCardValue == 5 || cbCardValue == 8 ) break;
  1400. // }
  1401. // if( j == 3 ) return false;
  1402. // }
  1403. // else
  1404. // {
  1405. // cbCardValue = pAnalyseItem->cbCenterCard[i]&MASK_VALUE;
  1406. // if( cbCardValue != 2 && cbCardValue != 5 && cbCardValue != 8 ) return false;
  1407. // }
  1408. // }
  1409. // return true;
  1410. //}
  1411. //是否花猪,一脚耐油不需要判断花猪牌型
  1412. /*bool CGameLogic::IsHuaZhu( const BYTE cbCardIndex[], const tagWeaveItem WeaveItem[], BYTE cbWeaveCount, BYTE cbDingque)
  1413. {
  1414. BYTE cbColor[3] = { 0,0,0 };
  1415. for( BYTE i = 0; i < MAX_INDEX; i++ )
  1416. {
  1417. if( cbCardIndex[i] > 0 )
  1418. {
  1419. BYTE cbCardColor = SwitchToCardData(i)&MASK_COLOR;
  1420. cbColor[cbCardColor>>4]++;
  1421. i = (i/9+1)*9-1;
  1422. }
  1423. }
  1424. for( BYTE i = 0; i < cbWeaveCount; i++ )
  1425. {
  1426. BYTE cbCardColor = WeaveItem[i].cbCenterCard&MASK_COLOR;
  1427. cbColor[cbCardColor>>4]++;
  1428. }
  1429. if (INVALID_BYTE != cbDingque && 0 != cbColor[cbDingque])
  1430. return true;
  1431. //缺一门就不是花猪
  1432. for( BYTE i = 0; i < CountArray(cbColor); i++ )
  1433. if( cbColor[i] == 0 ) return false;
  1434. return true;
  1435. }*/
  1436. //////////////////////////////////////////////////////////////////////////