实例介绍
【实例简介】含扑克牌算法介绍文档以及完整源码 等
【实例截图】

【核心代码】
using System;
using System.Collections;
using System.Drawing;
using System.Threading;
using System.Windows.Forms;
//ArrayList类
namespace mycards
{
public partial class MainForm : Form
{
//Card[,] PlayersCard = new Card[4, 13];//记录4个玩家的牌
private readonly int[,] AllOutCard = new int[4,1]; //记录所有玩家一轮出的牌
private readonly int[,] GetScoreCard = new int[4,16]; //4位牌手获取的分牌
private readonly int[] PlayerScore = new int[4]; //记录4位牌手得分
private readonly int[] PlayerSelectCard = new int[2]; //记录牌手本次已出的牌
private readonly int[] ScoreCard = new int[16] {10, 24, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 51};
private readonly int[] key = new int[53]; //记录4个人牌的索引号(在1--52范围)
private int FirstPlayer; //记录本次首出牌者
private bool FisrtGame = true; //首次游戏
private int GetPigPlayer = -1; //记录得到猪牌的一方
private bool MyTurn; //是否该玩家出牌
private int Order; //轮到谁出牌
private int OuterPlayerNum; //本次已出牌的人数
private Card[] pic;
public MainForm()
{
InitializeComponent();
}
private void Form1_Load(object sender, EventArgs e)
{
pic = new Card[53];
//以下两句是为了设置控件样式为双缓冲,这可以有效减少闪烁的问题
SetStyle(
ControlStyles.OptimizedDoubleBuffer | ControlStyles.AllPaintingInWmPaint | ControlStyles.UserPaint, true);
UpdateStyles();
}
private void Clear() //清除上一局信息
{
listView1.Items.Clear();
listView2.Items.Clear();
Array.Clear(GetScoreCard, 0, 64);
Array.Clear(PlayerScore, 0, 4);
}
private void Btn_start_Click(object sender, EventArgs e) //洗牌按钮
{
Clear(); //清除上一局信息
toolStripStatusLabel1.Text = "开始新一局";
Btn_SendCard.Enabled = true;
Btn_start.Enabled = false;
Poke Poke1 = new Poke(); //Poke实例Poke1
int k;
//for (int j = 1; j <= 13; j )
//{
// for (int i = 0; i <= 3; i )
// {
// Card card1 = Poke1.Shuffle(); //获取一张牌
// if (card1 != null)
// {
// k=j i * 13;
// if (pic[k] != null)
// {
// pic[k].Dispose();
// pic[k] = null;
// }
// pic[k] = card1;
// key[k] = card1.pic_order();
// }
// }
//}
for (k = 1; k <= 52; k )
{
Card card1 = Poke1.Shuffle(); //获取一张牌
if (pic[k] != null)
{
pic[k].Dispose();
pic[k] = null;
}
pic[k] = card1;
key[k] = card1.pic_order();
}
Array.Sort(key, pic, 1, 13);
Array.Sort(key, pic, 14, 13);
Array.Sort(key, pic, 27, 13);
Array.Sort(key, pic, 40, 13);
for (int i = 1; i <= 52; i )
{
pic[i].Tag = i; //记录控件的索引号
Controls.Add(pic[i]);
pic[i].Visible = false;
if (FisrtGame)
{
if (pic[i].Suit == 1 && pic[i].FaceNum == 2) //是梅花2
{
Order = (i - 1)/13; //开局出牌者
FirstPlayer = (i - 1)/13;
AllOutCard[Order, 0] = i;
}
}
else
{
//根据上一局得到猪牌的一方首先出牌
Order = GetPigPlayer;
FirstPlayer = GetPigPlayer;
}
}
for (int j = 13; j >= 1; j--)
{
for (int i = 3; i >= 0; i--)
{
k = i*13 j;
pic[k].SetPosition(80 7*(j*4 i), 180);
pic[k].SetSize(71, 96);
pic[k].showBack();
pic[k].Visible = true;
pic[k].BringToFront();
}
}
}
private void Btn_SendCard_Click(object sender, EventArgs e) //随机给4人发牌
{
Btn_SendCard.Enabled = false;
//Btn_start.Enabled = true;
int k;
for (int j = 1; j <= 13; j )
{
for (int i = 0; i <= 3; i )
{
k = i*13 j;
switch (i)
{
case 0: //牌手自己
pic[k].show();
pic[k].MoveTo(150 20*j, 350);
//pic[k].Left = 150 20 * j;
//pic[k].Top = 350;
pic[k].BringToFront();
pic[k].Click = bt_Click;
//pic[k].DoubleClick = new System.EventHandler(Dbt_Click);
break;
case 1: //牌手的下家
if (checkBox1.Checked)
{
pic[k].show();
}
pic[k].MoveTo(50, 50 20*j);
pic[k].Left = 50;
pic[k].Top = 50 20*j;
Rotate_card(pic[k]); //90度旋转纸牌
pic[k].BringToFront();
break;
case 2: //牌手的对家
if (checkBox1.Checked)
{
pic[k].show();
}
pic[k].MoveTo(150 20*j, 50);
pic[k].Left = 150 20*j;
pic[k].Top = 50;
Rotate_card(pic[k], 180); //180度旋转纸牌
pic[k].BringToFront();
break;
case 3: //牌手的上家
if (checkBox1.Checked)
{
pic[k].show();
}
pic[k].MoveTo(500, 330 - 20*j);
pic[k].Top = 330 - 20*j;
pic[k].Left = 500;
pic[k].BringToFront();
Rotate_card(pic[k], 270); //270度旋转纸牌
break;
}
}
}
//btnOut.Visible = true;
//panel1.Enabled = false;
timer2.Enabled = true; //出牌顺序控制开始
OuterPlayerNum = 0; //出牌人数为0
}
private void bt_Click(object sender, EventArgs e) //这里处理单击事件过程
{
Card picBox1 = (Card) sender;
int k = Convert.ToInt16(picBox1.Tag); //被选中牌的控件索引号
if (PlayerSelectCard[0] == 0)
{
picBox1.Top -= 10;
PlayerSelectCard[0] = k;
}
else //取消已选中的此牌
{
int pre = PlayerSelectCard[0];
pic[pre].Top = 10;
picBox1.Top -= 10;
PlayerSelectCard[0] = k;
}
}
private void Dbt_Click(object sender, EventArgs e) //这里处理双击事件过程
{
PictureBox picBox1 = (PictureBox) sender;
int i = Convert.ToInt16(picBox1.Tag);
picBox1.Top = 260;
picBox1.Left = 300;
picBox1.BringToFront();
}
//90度旋转纸牌
private void Rotate_card(PictureBox picBox)
{
int w = picBox.Width;
int h = picBox.Height;
picBox.Image.RotateFlip(RotateFlipType.Rotate90FlipNone);
picBox.Height = w;
picBox.Width = h;
picBox.Refresh();
}
//90度倍数旋转纸牌
private void Rotate_card(PictureBox picBox, int Angle)
{
int w = picBox.Width;
int h = picBox.Height;
switch (Angle)
{
case 90:
picBox.Image.RotateFlip(RotateFlipType.Rotate90FlipNone);
picBox.Height = w;
picBox.Width = h;
picBox.Refresh();
break;
case 180:
picBox.Image.RotateFlip(RotateFlipType.Rotate180FlipNone);
picBox.Refresh();
break;
case 270:
picBox.Image.RotateFlip(RotateFlipType.Rotate270FlipNone);
picBox.Height = w;
picBox.Width = h;
picBox.Refresh();
break;
}
}
private void ComputerOut(int player)
{
int m = 0;
switch (player)
{
case 1: //牌手的下家
m = ComputerOnePlayerCards(1);
pic[m].SetSize(pic[m].Height, pic[m].Width);
pic[m].show();
pic[m].Left = 150;
pic[m].Top = 200;
Rotate_card(pic[m], 90); //90度旋转纸牌
pic[m].BringToFront();
break;
case 2: //牌手的对家
m = ComputerOnePlayerCards(2);
pic[m].show();
pic[m].Left = 260;
pic[m].Top = 150;
Rotate_card(pic[m], 180); //90度旋转纸牌
pic[m].BringToFront();
break;
case 3: //牌手的上家
m = ComputerOnePlayerCards(3);
pic[m].SetSize(pic[m].Height, pic[m].Width);
pic[m].show();
pic[m].Left = 400;
pic[m].Top = 200;
Rotate_card(pic[m], 270); //90度旋转纸牌
pic[m].BringToFront();
break;
}
AllOutCard[player, 0] = m; //保存出牌
}
//电脑自动计算选手的出牌
private int ComputerOnePlayerCards(int player)
{
if (FisrtGame) //游戏开始第一次出牌,梅花2先出 2011-7-11
{
FisrtGame = false;
//AllOutCard[player, 0]已存放梅花2牌的索引号
return AllOutCard[player, 0]; //返回梅花2牌的索引号
}
ArrayList CanOutCard = new ArrayList();
int BeginCard, EndCard;
BeginCard = 13*player 1;
EndCard = 13*player 13;
for (int j = BeginCard; j <= EndCard; j )
{
if (pic[j] == null) continue;
//int k = pre[0];
//if (k == 0)//没有上家出牌,可以按没有同花色的处理
// break;
if (player == FirstPlayer) //自己是首家出牌,可以按没有同花色的处理
break;
else //统计与首家出牌是否有同色的牌
{
int k = AllOutCard[FirstPlayer, 0];
if (pic[k].Suit == pic[j].Suit)
CanOutCard.Add(j);
}
}
int m;
if (CanOutCard.Count == 0) //没有同花色的
{
Random r = new Random();
do
{
//随机产生可以出的牌索引号
m = r.Next(BeginCard, EndCard 1);
} while (pic[m] == null);
}
else //有同花色的
{
Random r = new Random();
//随机产生可以出的牌索引号
m = (int) CanOutCard[r.Next(0, CanOutCard.Count)];
}
return m;
}
private void btnOut_Click(object sender, EventArgs e)
{
if (PlayerSelectCard[0] == 0)
{
MessageBox.Show("你未选中出的牌,请单击选择要出的牌!", "提醒");
return;
}
if (FisrtGame) //必须出梅花2
{
if (pic[PlayerSelectCard[0]].ToString() == "梅2")
FisrtGame = false;
else
{
MessageBox.Show("你必须出梅花2!", "提醒");
return;
}
}
int k = PlayerSelectCard[0]; //被选中牌的控件索引号
if (FirstPlayer == 0) //自己先出牌
{
//不用判断花色与上家相同问题
}
else
{
//判断花色与首家相同问题
int n = AllOutCard[FirstPlayer, 0];
bool flag = false;
for (int r = 1; r < 13; r )
{
if (pic[r] != null && pic[r].Suit == pic[n].Suit)
flag = true;
}
if (flag) //有与首家同花色的
{
if (!(MyTurn && pic[n].Suit == pic[k].Suit))
{
MessageBox.Show("花色不符合规则,请换牌!", "出牌错误");
return;
}
}
}
pic[k].Top = 250;
pic[k].Left = 260;
pic[k].BringToFront();
key[k] = 0;
panel1.Enabled = false;
MyTurn = false; //玩家等待直到轮到自己
AllOutCard[0, 0] = PlayerSelectCard[0];
OuterPlayerNum ;
if (OuterPlayerNum == 4) //4 个人都已经出过牌
{
OneQuanOver(); //处理4 个人一圈牌
}
else
{
Order = 1; //该下家
}
}
private void OneQuanOver() //处理4 个人一圈牌
{
Thread.Sleep(500); //延时0.5秒
Order = NextFirst(); //比较牌的大小,决定下次谁先出牌
FirstPlayer = Order; //FirstPlayer 记录首先出牌的代号
if (FirstPlayer == 0) MyTurn = true; //轮到玩家出牌
//处理所有牌手的出牌
ClearAllOutCard(); //清除所有牌手的出牌
OuterPlayerNum = 0;
if (listView1.Items.Count == 13)
{
CalcScore(); //计算每位牌手得分
int t;
t = int.Parse(lblPlayer0.Text) PlayerScore[0];
lblPlayer0.Text = t.ToString(); //玩家(南家)得分
lblPlayer0.Visible = true;
t = int.Parse(lblPlayer1.Text) PlayerScore[1];
lblPlayer1.Text = t.ToString(); //西家得分
lblPlayer1.Visible = true;
t = int.Parse(lblPlayer2.Text) PlayerScore[2];
lblPlayer2.Text = t.ToString(); //北家得分
lblPlayer2.Visible = true;
t = int.Parse(lblPlayer3.Text) PlayerScore[3];
lblPlayer3.Text = t.ToString(); //东家得分
lblPlayer3.Visible = true;
toolStripStatusLabel1.Text = "牌已经出完, 请开始下一局";
Btn_start.Enabled = true;
timer2.Enabled = false;
}
}
private void ClearAllOutCard() //清除所有牌手的出牌
{
String[] subItem; //记录4位牌手的一次出牌情况
subItem = new string[4];
for (int i = 0; i < 4; i )
{
int m = AllOutCard[i, 0];
subItem[i] = pic[m].ToString(); //得到所出牌的花色及点数
}
listView1.Items.Add(new ListViewItem(subItem));
ClearPlayerOutCard(); //清空玩家此次出的牌
ClearOtherOutCard(); //清除其他牌手的出牌
}
private int NextFirst()
{
int k = AllOutCard[FirstPlayer, 0];
int type = pic[k].Suit; //获取花色
int max = pic[k].Power;
int who = FirstPlayer;
for (int i = 0; i < 4; i )
{
int m = AllOutCard[i, 0];
if (max < pic[m].Power && pic[m].Suit == type)
{
who = i; //此次出牌最大者编号
max = pic[m].Power; //4张牌的实际最大值
}
}
String[] subItem2; //记录4位牌手的一次出牌得分牌情况
subItem2 = new string[4];
for (int i = 0; i < 4; i )
{
int m = AllOutCard[i, 0];
bool flag = false;
foreach (int t in ScoreCard)
{
if (t == pic[m].pic_order()) //牌手i出的牌是分牌
flag = true;
}
if (flag)
{
for (k = 0; k < 16; k )
if (GetScoreCard[who, k] == 0) break;
GetScoreCard[who, k] = pic[m].pic_order();
subItem2[who] = pic[m].ToString();
listView2.Items.Add(new ListViewItem(subItem2));
}
}
return who;
}
private void ClearPlayerOutCard() //清空玩家此次出的牌
{
for (int i = 1; i <= 13; i )
{
if (pic[i] != null && key[i] == 0)
{
pic[i].Dispose();
pic[i] = null;
}
}
for (int i = 0; i < PlayerSelectCard.Length; i ) //清空牌手此次出的牌记录
{
if (PlayerSelectCard[i] != 0)
{
PlayerSelectCard[i] = 0;
}
}
ChangePosition(0); //调整玩家牌的位置
}
private void ClearOtherOutCard() //清除其他牌手的出牌
{
for (int m = 1; m < 4; m )
{
int k = AllOutCard[m, 0]; //其他牌手所出牌的控件索引号
if (pic[k] != null)
{
pic[k].Visible = false;
pic[k].Dispose();
pic[k] = null;
key[k] = 0;
}
//调整m牌手牌的位置
ChangePosition(m);
}
}
private void ChangePosition(int m) //调整m牌手牌的位置
{
int n = 0;
int quan;
quan = listView1.Items.Count;
switch (m)
{
case 0:
for (int i = 1; i <= 13; i )
{
if (pic[i m*13] != null)
{
n ;
pic[i m*13].MoveTo(150 20*n quan*10, 350);
}
}
break;
case 1:
for (int i = 1; i <= 13; i )
{
if (pic[i m*13] != null)
{
n ;
pic[i m*13].MoveTo(50, 50 20*n quan*10);
}
}
break;
case 2:
for (int i = 1; i <= 13; i )
{
if (pic[i m*13] != null)
{
n ;
pic[i m*13].MoveTo(150 20*n quan*10, 50);
}
}
break;
case 3:
for (int i = 1; i <= 13; i )
{
if (pic[i m*13] != null)
{
n ;
pic[i m*13].MoveTo(500, 330 - 20*n - quan*10);
}
}
break;
}
}
private void CalcScore() //计算每位牌手得分
{
int m, Red = 0, AllGet;
for (int i = 0; i < 4; i )
{
AllGet = 0; //记录大满贯的情况
bool CanDouble = false; //记录是否有梅10变压器
Red = 0;
for (int j = 0; j < 16; j )
{
m = GetScoreCard[i, j];
if (m == 0) break; //不是分牌
switch (m)
{
case 24: //羊
PlayerScore[i] = 100;
AllGet = 1;
break;
case 51: //猪
PlayerScore[i] -= 200;
FirstPlayer = i;
GetPigPlayer = i; //下一局开始出牌者代号
AllGet = 1;
break;
case 10: //梅10变压器
CanDouble = true;
AllGet = 1;
break;
case 27: //红桃A
Red -= 50;
break;
case 28: //红桃2
case 29: //红桃3
case 30: //红桃4
Red -= 0;
break;
case 31: //红桃5
case 32: //红桃6
case 33: //红桃7
case 34: //红桃8
case 35: //红桃9
case 36: //红桃10
Red -= 10;
break;
case 37: //红桃J
Red -= 20;
break;
case 38: //红桃Q
Red -= 30;
break;
case 39: //红桃K
Red -= 40;
break;
}
}
if (Red == -200) //是收满红
{
PlayerScore[i] = 200;
AllGet = 1;
}
else
{
PlayerScore[i] = Red;
}
if (CanDouble) //有梅10变压器
{
if (GetScoreCard[i, 0] == 10 &&
GetScoreCard[i, 1] == 0) //什么分牌都没有得到
PlayerScore[i] = 50; //则变压器按50 分算
else
PlayerScore[i] *= 2;
}
if (AllGet == 4) //全收(大满贯)得 800分
PlayerScore[i] = 800;
}
}
private void timer2_Tick(object sender, EventArgs e) //出牌顺序控制开始
{
if (Order == 0) //是玩家
{
MyTurn = true; //轮到玩家出牌
panel1.Enabled = true;
btnOut.Visible = true;
return;
}
//2011-7-11
//if (FisrtGame) //第一轮出牌,梅花2先出
//{
// ComputerOut(Order);//电脑计算牌手Order的出牌
// Order ;
// OuterPlayerNum ;
// if (Order == 4) Order = 0;
// FisrtGame = false;
// return;
//}
ComputerOut(Order);
Order ;
if (Order == 4) Order = 0;
OuterPlayerNum ;
if (OuterPlayerNum == 4) //4 个人都已经出过牌
{
OneQuanOver(); //处理4 个人一圈牌
}
}
}
}
好例子网口号:伸出你的我的手 — 分享!
小贴士
感谢您为本站写下的评论,您的评论对其它用户来说具有重要的参考价值,所以请认真填写。
- 类似“顶”、“沙发”之类没有营养的文字,对勤劳贡献的楼主来说是令人沮丧的反馈信息。
- 相信您也不想看到一排文字/表情墙,所以请不要反馈意义不大的重复字符,也请尽量不要纯表情的回复。
- 提问之前请再仔细看一遍楼主的说明,或许是您遗漏了。
- 请勿到处挖坑绊人、招贴广告。既占空间让人厌烦,又没人会搭理,于人于己都无利。
关于好例子网
本站旨在为广大IT学习爱好者提供一个非营利性互相学习交流分享平台。本站所有资源都可以被免费获取学习研究。本站资源来自网友分享,对搜索内容的合法性不具有预见性、识别性、控制性,仅供学习研究,请务必在下载后24小时内给予删除,不得用于其他任何用途,否则后果自负。基于互联网的特殊性,平台无法对用户传输的作品、信息、内容的权属或合法性、安全性、合规性、真实性、科学性、完整权、有效性等进行实质审查;无论平台是否已进行审查,用户均应自行承担因其传输的作品、信息、内容而可能或已经产生的侵权或权属纠纷等法律责任。本站所有资源不代表本站的观点或立场,基于网友分享,根据中国法律《信息网络传播权保护条例》第二十二与二十三条之规定,若资源存在侵权或相关问题请联系本站客服人员,点此联系我们。关于更多版权及免责申明参见 版权及免责申明


网友评论
我要评论