目标:游戏界面显示 拼图面板 、 提示面板(拼好的样子)、移动次数。

通过拖动小拼图片 进行拼图 ,最终拼成提示面板的样子。提示面板中的蓝色块表示空白块。

成功后提示成功!可通过点击重玩按钮,在任何时候选择重玩!

大致如图:

主要考虑四个问题:

1、界面的绘制  2、随机生成初始状态 3、拼图片移动的判断和实现 4、成功状态的判断

1、绘制界面

考虑到landscape的情况 ,还是用StackPanel爽点,将整个content放在一个StackPanel内,当方向改变的时候,只要改变StackPanel的Orientation就Ok了

然后将拼图面板用Grid 表示,主要是使用行列很方便,下面的 提示面板 、重玩按钮、 以及移动次数TextBlock放在一个StackPanel中

xaml中如下:

View Code

 <StackPanel x:Name="ContentPanel" Grid.Row="1" Margin="12,0,12,0" Orientation="Vertical" Loaded="ContentPanel_Loaded"><Grid Name="puzzlePanel" Margin="0 0" ></Grid><StackPanel Name="bottomStackPanel" Orientation="Horizontal" ><Grid  Name="TargetPanel"  Grid.Column="0" Margin="20 20 20 20" Width="180" Height="180">                 </Grid><Grid ><TextBlock Text="移动次数: 0" Name="moveTimesTextBlock" Grid.Column="1" HorizontalAlignment="Center" Margin="0 30 0 0" VerticalAlignment="Top"></TextBlock><Button Name="replayButton" Content="重玩" Margin="40,70,23,70" Click="replayButton_Click" Width="128"></Button></Grid> </StackPanel></StackPanel>

最重要的是拼图面板的绘制,我的思路是 根据需要的小拼图片数 给puzzlePanel添加相应数量的行和列,创建拼图面板的CreatePuzzlePanel如下:

View Code

//创建拼图面板//获取puzzlePanel 并为其设置宽高,背景色//然后为其定义指定的行列,用来存放 小拼图片        public void CreatePuzzlePanel()        {            puzzlePanel.Height = puzzlePanelHeight;            puzzlePanel.Width = puzzlePanelWidth;            puzzlePanel.Background = new SolidColorBrush(backgroundColor) ;for (int i = 0; i < rowNum; i++)            {                puzzlePanel.RowDefinitions.Add(new RowDefinition());                           }for (int j = 0; j < columNum; j++)            {                puzzlePanel.ColumnDefinitions.Add(new ColumnDefinition());            }            Grid.SetRow(puzzlePanel,0);        }

每个拼图片使用一个Grid 然后在Grid中放一个TextBlock 用来显示数字,拼图片的大小根据拼图面板的大小进行计算

最重要的还有需要设置一个空白的拼图片,这里通过随机生成一个空白的位置来实现,添加的时候这个空白的位置就设为空,就不会显示拼图片了,InitPuzzle方法会记录下该片对应的值,供创建提示面板使用。

然后将Grid添加到puzzlePanel容器中,这里通过设置Grid在puzzlePanel中的Row,Column来实现同时将Grid添加到一个List中,以便移懂拼图片的时候使用。这里设置Grid的Row和Column

通过Grid.SetRow和 Grid.SetColumn实现,当然这里显示的数字需要随机生成,是使用CreateRandNumArry方法实现的,这个后面再说。初始化拼图的  InitPuzzle方法如下

View Code

//初始化拼图面板//首先创建拼图片数组,数组大小等于rowNum*columNum //然后生成生成一个 大小 小于 拼图片数组大小 的随机数,该位置不显示拼图片//然后就是依次生成所需要的拼图片,在拼图片上显示 随机的数字        public int InitPuzzle()        {int emptyPieceValue = 0;int[] pieceValueArry = CreateRandNumArry();//int[] pieceValueArry = new int[] { 0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15};            int emptyValue = rand.Next(rowNum*columNum)+1;double pieceWidth=puzzlePanelWidth/columNum;double pieceHeight=puzzlePanelHeight/rowNum;int index=0;//重玩的时候需要先清空拼图面板,然后重新添加            puzzlePanel.Children.Clear();for (int i = 0; i < rowNum; i++)            {for (int j = 0; j < columNum; j++)                {//判断该位置是否需要显示拼图片                    if (getCorrectNum(i, j) != emptyValue)                    {                        Grid puzzlePiece = new Grid();                        Grid container = new Grid();                        container.Width = pieceWidth;                        container.Height = pieceHeight;                        container.Margin = new Thickness(1, 1, 1, 1);                        container.Name = (pieceValueArry[index] + 1).ToString();                        container.ManipulationDelta += new EventHandler<ManipulationDeltaEventArgs>(container_ManipulationDelta);                        container.ManipulationCompleted += new EventHandler<ManipulationCompletedEventArgs>(container_ManipulationCompleted);

                        container.Background = new SolidColorBrush(piecesColor);                        puzzlePanel.Children.Add(container);                        TextBlock content = new TextBlock();                        content.Text = (pieceValueArry[index] + 1).ToString();                        content.VerticalAlignment = VerticalAlignment.Center;                        content.HorizontalAlignment = HorizontalAlignment.Center;                        content.FontSize = 50;                        container.Children.Add(content);

                        Grid.SetRow(container, i);                        Grid.SetColumn(container, j);

                        puzzlePiecesArry.Add(puzzlePiece);

                    }else                    {//否则的话这个 拼图片肯定是空白的了,所以在数组中存储空//以标志此拼图片                        puzzlePiecesArry.Add(null);                        emptyPieceValue = pieceValueArry[index] + 1;                    }                                       index++;//获取下一个 拼图片上的 值                }            }//记录空白拼图片的 值是为了targetPanel中将空白拼图片显示为特别的颜色            return emptyPieceValue;        }

完了之后还要绘制 提示面板 其绘制方法和绘制拼图面板差不多,不过我把小片都放在Border元素中了,这里用到了InitPuzzle返回的空白片对应的值,创建提示面板的CreateTargetPanel如下:

View Code

//创建 目标面板 用来提示最终效果        public void CreateTargetPanel(int emptyPieceValue)        {            TargetPanel.Children.Clear();            TargetPanel.RowDefinitions.Clear();            TargetPanel.ColumnDefinitions.Clear();            TargetPanel.Background = new SolidColorBrush(backgroundColor);for (int i = 0; i < rowNum; i++)            {                TargetPanel.RowDefinitions.Add(new RowDefinition());            }for (int j = 0; j < columNum; j++)            {                TargetPanel.ColumnDefinitions.Add(new ColumnDefinition());            }

double targetPieceWidth = TargetPanel.Width / columNum;double targetPieceHeight = TargetPanel.Height / rowNum;int index = 0;for (int i = 0; i < rowNum; i++)            {for (int j = 0; j < columNum; j++)                {                    Border border = new Border();                    border.Width = targetPieceWidth;                    border.Height = targetPieceHeight;                    border.Margin = new Thickness(1, 1, 1, 1);

if (getCorrectNum(i, j) != emptyPieceValue)                    {                        border.Background = new SolidColorBrush(piecesColor);                    }else                    {                        border.Background = new SolidColorBrush(Color.FromArgb(10, 100, 100, 0));                    }                    TextBlock content = new TextBlock();                    content.Text = (++index).ToString();                    content.VerticalAlignment = VerticalAlignment.Center;                    content.HorizontalAlignment = HorizontalAlignment.Center;                    content.FontSize = 20;                    border.Child = content;                    Grid.SetRow(border, i);                    Grid.SetColumn(border, j);                    TargetPanel.Children.Add(border);                }            }        }

2、随机生成初始状态

这里我的思路是根据 拼图片的数目num,生成一个num大小的随机数组

我先定义一个   List<int> temp  依次存储0-(num-1)的整数,然后每次随机从该List中选择一个数添加到随机数组,同时将该数从List中删除,这样就生成了一个随机数组。

将随机数组交给上面的InitPuzzle处理,InitPuzzle 依次读取数组中的数 作为其显示的内容。

这样界面上显示的数字就是随机的了,并且有一个是空白 拼图片。

生成随机数组的   CreateRandNumArry  方法如下:

View Code

 //生成一个 随机的 拼图片值 数组,这些是拼图片上显示的数字//首先建立一个List 存储num个顺序的数字,//然后从中随机取出一个数 给randArry 并将该数从List中移除//重复此动作,直到生成所需的随机数组        public int[] CreateRandNumArry()        {

int num = columNum * rowNum;int []randArry=new int[num];            List<int> temp = new List<int>();         for (int i = 0; i < num; i++)            {                temp.Add(i);            }for (int j = 0; j < num; j++)            {int randValue=temp[rand.Next(temp.Count)];                randArry[j] =randValue;                temp.Remove(randValue);            }return randArry;        }

3、拼图片移动的判断和实现

这个应该是最重要的部分了,只有拼图片  相邻位置为空白片的时候 他才可以移动,所以可以通过判断元素的相邻位置是否为空,该判断可通过puzzlePiecesArry(存储当前所有拼图块Grid,通过获取Grid的Row和Column 很容易找到相邻元素)中存储的值来进行比较

若为空,将其与空元素交换位置,并且交换puzzlePiecesArry数组中的值,以便下一次继续比较

该比较应该在拼图片的   ManipulationDelta 方法中实现 该方法和ManipulationCompleted已经在每个拼图块创建的时候注册过, container_ManipulationDelta方法实现如下:

View Code

void container_ManipulationDelta(object sender, ManipulationDeltaEventArgs e)        {            Grid grid = sender as Grid;       int row=Grid.GetRow(grid);int colum=Grid.GetColumn(grid);            CompositeTransform transform = new CompositeTransform();            grid.RenderTransform = transform;

//因为puzzlePiecesArry中保存有各个 拼图片   且空拼图片对应的值为null// 所以可以直接判断要移动元素的相邻元素是否为空即可判断是否可以移动//若不为空,则不执行任何操作//若为空,将其与空元素交换位置,并且交换puzzlePiecesArry数组中的值,以便下一次继续比较

            Grid puzzlepiece=puzzlePiecesArry[getCorrectNum(row, colum) - 1];

double moveX = e.DeltaManipulation.Translation.X;double moveY = e.DeltaManipulation.Translation.Y;//向右            if (moveX > 0 && colum < (columNum - 1) && puzzlePiecesArry[getCorrectNum(row, colum + 1) - 1] == null)            {                Grid.SetRow(grid, row);                Grid.SetColumn(grid, colum + 1);                puzzlePiecesArry[getCorrectNum(row, colum + 1) - 1] = puzzlePiecesArry[getCorrectNum(row, colum) - 1];                puzzlePiecesArry[getCorrectNum(row, colum) - 1] = null;                moveTimes++;            }//向左            else if (moveX < 0 && colum > 0 && puzzlePiecesArry[getCorrectNum(row, colum-1) - 1] == null)            {                Grid.SetRow(grid, row);                Grid.SetColumn(grid, colum - 1);                puzzlePiecesArry[getCorrectNum(row, colum -1) - 1] = puzzlePiecesArry[getCorrectNum(row, colum) - 1];                puzzlePiecesArry[getCorrectNum(row, colum) - 1] = null;                moveTimes++;            }//向下            else if (moveY > 0 &&row < (rowNum - 1) && puzzlePiecesArry[getCorrectNum(row+1, colum) - 1] == null)            {                    Grid.SetRow(grid, row + 1);                    Grid.SetColumn(grid, colum);                    puzzlePiecesArry[getCorrectNum(row+1, colum) - 1] = puzzlePiecesArry[getCorrectNum(row, colum) - 1];                    puzzlePiecesArry[getCorrectNum(row, colum) - 1] = null;                    moveTimes++;            }//向上            else if (moveY < 0 && row > 0 && puzzlePiecesArry[getCorrectNum(row-1, colum ) - 1] == null)            {                    Grid.SetRow(grid, row - 1);                    Grid.SetColumn(grid, colum);                    puzzlePiecesArry[getCorrectNum(row-1, colum) - 1] = puzzlePiecesArry[getCorrectNum(row, colum) - 1];                    puzzlePiecesArry[getCorrectNum(row, colum) - 1] = null;                    moveTimes++;            }

//触发一次后立即结束,否则的话 拼图片会一直移动,//故此处一定要调用Complete方法            e.Complete();            e.Handled = true;        }

这里和上面用到的getCorrectNum方法是获取 row行colum列  应该对应的数字,即第0行0列应该对应1,0行1列对应2 等等,getCorrectNum如下:

View Code

//获取 row行colum列  应该对应的数字        private int getCorrectNum(int row, int colum)        {return row * columNum + colum + 1;        }

当然在移动拼图块的时候还要修改  移动次数值,这个可以在 ManipulationCompleted方法中实现

container_ManipulationCompleted方法如下:

View Code

void container_ManipulationCompleted(object sender, ManipulationCompletedEventArgs e)        {//更新移动次数            this.moveTimesTextBlock.Text = "移动次数: "+moveTimes.ToString();if (IsSuccess())            {                                MessageBoxResult result= MessageBox.Show("恭喜你,成功啦!再来一局?", "Congratulate", MessageBoxButton.OKCancel);if (result == MessageBoxResult.OK)                {                    replayButton_Click(sender, e);                }            }        }

4、成功状态的判断

每次操作完成后都要判断是否成功,  这个其实很简单了,根据拼图块所在的行和列可以很容易计算出该位置应该显示的数字 (通过getCorrectNum方法),和事实上显示的数字进行对比就可以

了,若除了空白块外都一样了,就成功了。判断成功的方法如下:

View Code

 //判断是否成功//分别判断每个PazzlePiece的数字是否与他应该对应的数字相等//他所对应的数字 可以通过getCorrectNum(int row, int colum) 获得        public bool IsSuccess()        {int row=0;int colum=0;foreach (Grid grid in puzzlePanel.Children)            {if (grid != null)                {                    row = Grid.GetRow(grid);                    colum = Grid.GetColumn(grid);//如果显示文本不等于 他应该对应的数字//且不是空白拼图片                    if (grid.Name != getCorrectNum(row, colum).ToString())                    {return false;                    }                }            }return true;        }

然后需要在 页面加载的时候 和 重玩按钮点击的时候  调用这些方法就可以了。

此外还有就是当屏幕方向改变的时候,需要调整这几部分显示的位置,这个我放在了PhoneApplicationPage_OrientationChanged 事件中:

View Code

 private void PhoneApplicationPage_OrientationChanged(object sender, OrientationChangedEventArgs e)        {if (e.Orientation == PageOrientation.PortraitUp)            {this.ContentPanel.Orientation = System.Windows.Controls.Orientation.Vertical;this.bottomStackPanel.Orientation = System.Windows.Controls.Orientation.Horizontal;            }else            {this.ContentPanel.Orientation = System.Windows.Controls.Orientation.Horizontal;this.bottomStackPanel.Orientation = System.Windows.Controls.Orientation.Vertical;

            }        }

就Ok了,当屏幕方向改变成landscape时候显示效果如下:

成功时候显示如下:

这个小程序我还要再进行修改 ,

就是实现图片拼图 、行列的选择、大小的选择、计算机解决等

代码下载:NumberPuzzle.rar

转载于:https://www.cnblogs.com/yinghuochong/archive/2011/09/10/2173438.html

windows phone 数字拼图小游戏相关推荐

  1. html数字拼图游戏,JavaScript_JS写的数字拼图小游戏代码[学习参考],复制代码 代码如下:html - phpStudy...

    JS写的数字拼图小游戏代码[学习参考] 复制代码 代码如下: 拼图 td.numTd{ width : 20px ; height : 20px ; } div.numDiv{ width : 100 ...

  2. 数字拼图java小程序_JS写的数字拼图小游戏代码[学习参考]

    昨天没事做,就用JS写了个数字拼图的小游戏,自娱自乐. 可惜关于逆序数的问题还没解决,现在有时是拼不成的,大家见谅了. 拼图 td.numTd{ width : 20px ; height : 20p ...

  3. JS写的数字拼图小游戏

    昨天没事做,就用JS写了个数字拼图的小游戏,自娱自乐. 可惜关于逆序数的问题还没解决,现在有时是拼不成的,大家见谅了. <html><head><title>拼图& ...

  4. 【java】JavaFX从零开始实现拼图小游戏

    最近java课老师布置了一个作业:制作一个拼图小游戏,关键老师自己说javaGUI编程没用,讲课的时候好像跳过了(没去上课不过我猜应该没讲吧),现在又叫我们做这些,实在是哭笑不得. 得了吧,老师的任务 ...

  5. CreateJS实现【益智类数字华容道小游戏】

    系列文章 微信小程序(游戏)----拖拽拼图(图片分块和打乱顺序) 微信小程序(游戏)----五子棋 [taro react](游戏) ---- 类2048游戏,看看在秦朝,功勋爵位你能到哪一级 [t ...

  6. JavaSE基础项目:拼图小游戏

    目录 学习资源: 源码和图片资源: 项目结构: 项目界面: 注册界面源码: 登录界面源码: 游戏界面源码: 学习资源: 视频资源: 黑马程序员拼图小游戏 源码和图片资源: 图片/源码资源: 百度网盘 ...

  7. 使用Vue做一个可自动拼图的拼图小游戏(二)

    背景以及最终效果 在上一篇文章中我们已经写完了一个可以正常玩的拼图小游戏,但是这还没有结束,我们还要接着试一下让拼图游戏可以自己完成拼图. 在线体验 本部分是这篇文章的第二部分,主要讲的是实现自动拼图 ...

  8. Android案例(1)——美女拼图小游戏

    视频地址: Android美女拼图小游戏 实现功能: (1)多个难度 第一关3*3. (2)倒计时 (3)图片切分 (4)图片位置变换 第一步: 在src下创建工具包com.imooc.game.ut ...

  9. Java项目之“拼图小游戏”

    文章目录 一.项目简介 二.游戏展示 三.程序设计 1. 创建游戏主界面( GameJFrame ) 2. 初始化界面 ( initJFrame ) 3. 初始化菜单 ( initJMenuBar ) ...

最新文章

  1. 语言学与计算机应用学什么,2016考研专业:语言学及应用语言学
  2. 代码片段--批量生产库以及可执行文件的依赖关系
  3. javascript学习系列(5):数组中的reduce方法
  4. 阿里巴巴提出Auto-Context R-CNN算法,刷出Faster RCNN目标检测新高度
  5. apache http php,性能-安装HTTP使用PHP和Apache使标头失效
  6. proxmoxve打造云桌面_[pve][vdi]用deskpool创建基于proxmoxVE的桌面云
  7. 制作软盘镜像文件的几种方法
  8. rtl8187L驱动在linux2.6.35上的编译
  9. windows U盘分区方法
  10. Redis 到底是怎么实现“附近的人”这个功能的呢?
  11. 个人信用报告今起可上网查询
  12. VC - vs2017里poco的websocket使用netssl
  13. 芦笋制品的全球与中国市场2022-2028年:技术、参与者、趋势、市场规模及占有率研究报告
  14. Python文本情感分析实战【源码】
  15. gvfsd-trash占用内存高时,清空回收站
  16. 简单易懂 LNMP 架构详解适合入门级别可跟做
  17. android layout html,layoutgravity
  18. 读书笔记:《程序员修炼之道:通向务实的最高境界》
  19. 在一个excel里面直接批量从谷歌地图抓取经纬度(vba部分)
  20. 如何用AVS Video Editor这款视频编辑软件消除音频噪音?

热门文章

  1. php音乐相册怎么打开,手机如何制作相册 手机音乐相册的制作方法
  2. 【JS】json导出到excel,自定义文件名和后缀名
  3. Linux云计算架构师进阶班-Docker-K8s-Devops-Openstack
  4. UOS其他分区及移动硬盘带锁问题处理
  5. JeeSite(2):导入数据,进入系统
  6. easyui支持ie8浏览器
  7. git的简介与基本使用远程仓库gitee的创建
  8. 使用vivado调用自定义IP的两种方法
  9. go get 命令介绍
  10. iOS: UIScrollView的属性zooming