c# 构架WPF 纸牌游戏(斗地主2)

   在上一节中我们将资源全部都制作好了,现在开始构架游戏。为了不让代码那么难看,我们很有必要加入设计模式和面向对象思想。
   首先,我们可以将扑克的花色抽象为6个类:方块类(CardDiamond)、红桃类(CardHeart)、黑桃类(CardClub)、梅花类(CardSpader)、小王类(CardSmallJoker)、大王类(CardBigJoker),让他们全部继承抽象类CardBase。在基类中,CardType属性和SetCard()方法定义为抽象类型。CardType是一个枚举类型,在子类中必须指定当前扑克的花色。SetCard()是读取扑克的正面图片资源,一旦执行,扑克便可以显示出正面(发牌阶段为背面),此处定义为抽象方法后可以利用工厂模式进行调用,使用者不需要具体知道它内部是如何实现的。CardNumber为扑克点数从1到13。定义一个UserControl的属性,就是Card,通过初始化相关的控件,可以动态增加到主程序容器中去。注意:初始化的时候所有的扑克都是背面朝上的,因此可以将这一动作抽象出来放到基类的构造函数中去。

 

  这里唯一需要解决的技术问题就是,如何动态的将图片资源对象到每一张牌。参考如下代码,通过设置Background可以实现,但是需要通过FindResource来找到对应的图片资源名称(在上节中生成资源字典的时候会生成此名称)
 Brush brush = m_Card.FindResource("ImageBrushFaceDown") as Brush;
 m_Card.Background = brush; 

  在CardHelper类中,负责生成新牌和洗牌操作。我的思想是这样的,先通过算法按顺序生成54张牌,然后随机抽取这些牌,被抽取的牌从原来集合中删除,直到所有的牌都被抽取完毕为止,从而达到洗牌的目的。参考如下代码:可以看出生成新牌的时候使用了策略模式

 

    public class CardHelper
    {
        
/// <summary>
        
/// 初始化牌,并洗牌,通过此函数可以获得一副随机的扑克牌。
        
/// </summary>
        
/// <returns></returns>
        public static List<CardBase> GetCardCollection()
        {
            List
<CardBase> cardCollection = new List<CardBase>();

            
for (int i = 0; i < 4; i++)
            {
                
for (int j = 1; j <= 13; j++)
                {
                    CardBase card 
= null;
                    
switch (i)
                    {
                        
case 0:
                            card 
= new CardClub();
                            card.Card.Name 
= "CardClub" + j.ToString();
                            
break;
                        
case 1:
                            card 
= new CardDiamond();
                            card.Card.Name 
= "CardDiamond" + j.ToString();
                            
break;
                        
case 2:
                            card 
= new CardHeart();
                            card.Card.Name 
= "CardHeart" + j.ToString();
                            
break;
                        
case 3:
                            card 
= new CardSpader();
                            card.Card.Name 
= "CardSpader" + j.ToString();
                            
break;
                    }
                    card.CardNumber 
= j;
                    cardCollection.Add(card);
                }
            }
            
//最后来添加大小王
            cardCollection.Add(new CardBigJoker());
            cardCollection.Add(
new CardSmallJoker());
            
return SetCardRnd(cardCollection);
        }

        
/// <summary>
        
/// 将生成的扑克随机打乱(洗牌操作)
        
/// </summary>
        
/// <param name="oldCardCollection">已经生成的扑克牌集合</param>
        
/// <returns></returns>
        private static List<CardBase> SetCardRnd(List<CardBase> oldCardCollection)
        {
            Random ran 
= new Random();
            List
<CardBase> cardCollection = new List<CardBase>();
            
for (int i = 53; i >= 0; i--)
            {
                
int cardIndex = ran.Next(0, i + 1);//随机数可以取到下限值,但是不能取到上限值。
                cardCollection.Add(oldCardCollection[cardIndex]);
                oldCardCollection.RemoveAt(cardIndex);
            }
            
return cardCollection;
        }
    }

 

 

posted on 2010-03-29 12:52  程晨  阅读(2018)  评论(2编辑  收藏  举报

导航