连连看课程设计报告.docx
《连连看课程设计报告.docx》由会员分享,可在线阅读,更多相关《连连看课程设计报告.docx(48页珍藏版)》请在冰豆网上搜索。
连连看课程设计报告
《高级语言程序设计
(2)》课程设计报告
1、程序设计说明书
【设计题目】连连看程序
【问题描述】
小游戏连连看,玩家需要找出游戏中图片相同的两个方块,如果它们之间的连接线不多于3根直线,就可将这两个方块消除,当游戏中没有满足条件的图案时,还可以实现重新排序的功能,游戏中的倒计时结束时,游戏结束时,游戏结束即可得出所得分数。
【软件功能】
1通过找出游戏中图片相同的两个方块,将其消除
2游戏中没有满足条件的方块时,可重新排列
3可计算游戏总得分,有“下一局”和“退出游戏”的功能
4可通过倒计时控制游戏时间,每一局开始倒计时都重新开始
5利用SWING设计适合的图形用户界面
6能响应鼠标或者键盘事件
【算法思想】
在检验两个图片能否消掉的时候,要让两个图片同时满足两个条件才行,就是两者配对并且连线成功。
分3种情况:
这三种情况都需要三个检测,这三个检测分别检测一条直路经。
这样就会有三条路经。
若这三条路经上都是空按钮,那么就刚好是三种直线(两个转弯点)把两个按钮连接起来了。
(1)、相邻
(2)、若不相邻的先在第一个按钮的同行找一个空按钮。
1.找到后看第二个按钮横向到这个空按钮所在的列是否有按钮。
2.没有的话再看第一个按钮到与它同行的那个空按钮之间是否有按钮。
3.没有的话,再从与第一个按钮同行的那个空按钮竖向到与第二个按钮的同行看是否有按钮。
没有的话路经就通了可以消了.
(3)、若
(2)失败后,再在第一个按钮的同列找一个空按钮。
1.找到后看第二个按钮竖向到这个空按钮所在的行是否有按钮2.没有的话,再看第一个按钮到与它同列的那个空按钮之间是否有按钮。
3.没有的话,再从与第一个按钮同列的那个空按钮横向到与第二个按钮同列看是否有按钮。
没有的话路经就通了,可以消了。
若以上三步都失败,说明这两个按钮不可以消去
两图能相连的所有情况:
【类的设计】
图片连连看游戏程序中只有一个类,类名为LianLianKan,该类实现了接口ActionListener;该类总共有十三个方法,他们的功能分别是:
init()初始化;createImgBtn()传进两个String类型的参数,返回带有数字和图片的按钮;randomBuild(),产生十五对随机的数字;fraction()计算得分;reload()将游戏按钮重列;estimateEven()传进两个int型和一个JButton型的三个参数(分别是击中的按钮位置坐标和按钮),选中按钮信息的存储与操作;xiao()消去符合游戏规则的相同的两个按钮;linePassOne()在第一按钮同行有空按钮的条件下判断第二转折点出现的情况;rowPassOne()在第一按钮同列有空按钮的条件下判断第二转折点出现的情况;remove()将相同的两个按钮消去;actionPerformed()实现按钮事件的监听;timerDemo()时间提示;main()主方法;
【用户界面】
【程序技巧】
1.程序采用图形用户界面,简单大方,且易于操作;
2.连连看图片采用大家熟悉的图片,能激起玩家的游戏兴趣;
3.游戏功能较为齐全,可实现退出、重列和下一局的功能,重列功能可对游戏中剩余的图片进行重新排列,使游戏继续进行,下一局功能可以使游戏重新开始
4.游戏具有倒计时功能,能够控制游戏时限,使游戏具有一定难度,倒计时结束时显示“gameover”
5.游戏可以统计玩家的游戏得分
【模块划分及调用关系】
根据对“连连看”游戏的分析,该游戏可分为三个模块:
算法模块、界面显示模块、菜单控制模块。
【模块划分及调用关系】
根据对“连连看”游戏的分析,该游戏可分为三个模块:
算法模块、界面显示模块、菜单控制模块。
【模块流程图】
主模块流程图:
用户界面模块
菜单(按钮)模块
算法模块
连连看游戏
用户界面模块流程图:
Button
下一局
Button
重列
Button
退出
Label:
您的得分
Label:
得分
Label:
Time
Label:
剩余时间
EastPanel
BorderLayout布局
WestPanel
BorderLayout布局
thisContainer主界面
NorthPanel
BorderLayout布局
SouthPanel
BorderLayout布局
CenterPanel
GriLayout布局
(7x8)
算法模块:
不能消去
当两图不在一条直线上,则以两图在X\、Y方向的延长线上去找两个点,使其能连成直线
消去
消去
是否直线相连
消去
是否相邻
消去
是否直线相连
是否相邻
是否为同一图片
消去
不能消去
是否在一条竖线
是否在一条横线
是否在同一位置
否
是
是
否
是
否否
是
是是
否
是是否
否
是
否
【运行说明】
将图片和LianLianKan.java文件放到同一个文件夹里
javacLianLianKan.java
javaLianLianKan
或者在eclipse里面,将图片和LianLianKan.java文件放到同一个包中运行
2、程序上机调试报告
【语法错误及其排除】
将图片加载在按钮上,并在调用按钮时会出现随机的图片时出现错误,最后创建了一个方法JButtoncreateImgBtn(Stringing,Stringtxt),作用是传进两个String类型的参数,返回带有数字和图片的按钮,方法中的主要内容有ImageIconimage=newImageIcon(getClass().getResource(ing));JButtonbutton=newJButton(txt,image);通过调用这个方法就可以将图片与按钮固定在一起。
加载计时器时出现错误,即如果只在初始方法init()里调用timerDemo()方法时,在点击重列按钮或者下一局按钮时,时间提示里的时间是两次时间相掺杂的;改为只在main()方法里调用timerDemo()方法,在点击重列按钮时没有问题,但在点击下一局按钮时,时间还是相掺杂着出现;最后改为在main()方法里调用timerDemo()方法的同时在actionPerformed()方法里将if(e.getSource()==newlyButton)
{
intgrid[][]=newint[8][7];
this.grid=grid;
randomBuild();
mainFrame.setVisible(false);
pressInformation=false;
Init();
}
改为:
if(e.getSource()==newlyButton)
{
flag=true;
intgrid[][]=newint[8][7];
this.grid=grid;
randomBuild();
mainFrame.setVisible(false);
pressInformation=false;
init();
timerDemo();
}
【算法错误及其排除】
在编辑randomBuild()方法产生随机的两两相同的数字时,程序中会出现并非
两两相同的图片,达不到预期的效果,后改为在randomBuild()方法里添加如下
这样的程序:
while(grid[cols][rows]!
=0){
cols=(int)(Math.random()*6+1);
rows=(int)(Math.random()*5+1);
}
程序才正确。
在编辑程序时,定义了一个grid数组,用来存放游戏按钮的位置,刚开始定义的是6行5列,结果玩游戏时,周边的按钮不能被消去,后将数组改为8行7列时才可以,这样按钮周边的一圈就是空按钮,周边的按钮就可以被消去。
3、程序测试结果
【测试数据】
1、程序运行结果:
2、点击重列按钮结果:
3、点击下一局:
4、游戏结束界面:
【输出结果】
【收获及体会】
通过这次图片连连看游戏的设计使我懂得了理论与实际相结合是很重要的,只有理论知识是远远不够的,只有把所学的理论知识与实践相结合起来,从理论中得出结论,才能真正的提高自己的水平,从而提高自己的实际动手能力和独立思考的能力。
在设计的过程中遇到问题,可以说得是困难重重,并且还发现了自己的许多不足之处,对以前所学过的知识理解得不够深刻,掌握得不够牢固。
同时在这次的设计中也小小的体验了一下做项目的感受。
我完成了这次JAVA课程设计,不过这只是我学习路上的驿站。
我相信我在未来的学习中会记住从本次课程设计中所学到的东西,并将它用到未来的学习中去。
4、源程序代码
packagetest;
importjava.awt.BorderLayout;
importjava.awt.Color;
importjava.awt.Container;
importjava.awt.GridLayout;
importjava.awt.event.ActionEvent;
importjava.awt.event.ActionListener;
importjava.util.Timer;
importjava.util.TimerTask;
importjavax.swing.ImageIcon;
importjavax.swing.JButton;
importjavax.swing.JFrame;
importjavax.swing.JLabel;
importjavax.swing.JPanel;
publicclassLianLianKanimplementsActionListener
{
//主面板
JFramemainFrame;
//面板容器
ContainerthisContainer;
//子面板
JPanelcenterPanel,southPanel,northPanel,westPanel,eastPanel;
//游戏按钮数组
JButtondiamondsButton[][]=newJButton[6][5];
//开始,退出,重列,重新开始按钮
JButtonexitButton,resetButton,newlyButton;
//JButtonstartButton;
//分数标签
JLabelfractionLable=newJLabel("0");
//时间标签
JLabeltime=newJLabel("");
//分别记录两次被选中的按钮
JButtonfristButton,secondButton;
//储存游戏按钮位置
intgrid[][]=newint[8][7];
//判断是否有按钮被击中
staticbooleanpressInformation=false;
//被选中的两个游戏按钮的位置坐标(x0,y0),(x,y)
intx0=0,y0=0,x=0,y=0;
//两个被选中按钮上相应的数字
intfristMsg=0,secondMsg=0;
inti,j,k,n;
//ints=0;
finalTimert=newTimer();
Colorb=Color.orange;
Colorg=Color.cyan;
Colorm=Color.pink;
//Colorc=Color.blue;
booleanflag;
//初始化
publicvoidinit()
{//创建主面板,并命为连连看
mainFrame=newJFrame("连连看");
thisContainer=mainFrame.getContentPane();
//thisContainer.setBackground(c);
/**
*把thisContainer划分为Center、South、North三个区域
*North区域添加分数
*Center区域添加游戏按钮
*South区域添加退出、重列、下一局等按钮
*/
thisContainer.setLayout(newBorderLayout());
centerPanel=newJPanel();
centerPanel.setBackground(b);
southPanel=newJPanel();
southPanel.setBackground(g);
northPanel=newJPanel(newBorderLayout());
//northPanel.setBackground(m);
westPanel=newJPanel();
westPanel.setBackground(m);
eastPanel=newJPanel();
eastPanel.setBackground(m);
//Labeltime=newLabel("剩余时间:
");
thisContainer.add(centerPanel,"Center");
thisContainer.add(southPanel,"South");
thisContainer.add(northPanel,"North");
northPanel.add(westPanel,"West");
northPanel.add(eastPanel,"Center");
westPanel.add(BorderLayout.WEST,newJLabel("剩余时间:
"));
westPanel.add(BorderLayout.EAST,time);
eastPanel.add(BorderLayout.CENTER,newJLabel("您的得分:
"));
eastPanel.add(BorderLayout.EAST,fractionLable);
eastPanel.add(fractionLable,"Center");
//northPanel.add(fractionLable);
/**
*eastPanel.add(newJLabel("您的得分:
"));
*eastPanel.add(fractionLable);
*westPanel.add(BorderLayout.WEST,newJLabel("剩余时间:
"));
*westPanel.add(BorderLayout.EAST,newJLabel(time));
*northPanel.add(westPanel);
*/
//把CenterPanel区域设置为网格布局
centerPanel.setLayout(newGridLayout(6,5));
for(intcols=0;cols<6;cols++)
{
for(introws=0;rows<5;rows++)
{
if(grid[cols+1][rows+1]!
=0)
{//给指定按钮添加图片
diamondsButton[cols][rows]=createImgBtn(grid[cols+1][rows+1]+".jpg",String.valueOf(grid[cols+1][rows+1]));
}
else
{//当指定按钮为空时传空字符串即照片为传的照片为空
diamondsButton[cols][rows]=createImgBtn("",String.valueOf(grid[cols+1][rows+1]));
}
/**
*else
*{
*//当指定按钮为空时将其定义为新的按钮
*diamondsButton[cols][rows]=newJButton();
*}
*/
diamondsButton[cols][rows].addActionListener(this);
centerPanel.add(diamondsButton[cols][rows]);
}
}
//startButton=newJButton("开始");
//startButton.addActionListener(this);
exitButton=newJButton("退出");
exitButton.addActionListener(this);
resetButton=newJButton("重列");
resetButton.addActionListener(this);
newlyButton=newJButton("下一局");
newlyButton.addActionListener(this);
//southPanel.add(startButton);
southPanel.add(exitButton);
southPanel.add(resetButton);
southPanel.add(newlyButton);
/**
*为该标签设置一个文本字符串
*该字符串为标签字符串所显示的文本字符串作为有符号的十进制整数为参数的字符串
*/
fractionLable.setText(String.valueOf(Integer.parseInt(fractionLable.getText())));
mainFrame.setBounds(180,10,800,650);//设置主面板的位置和大小
mainFrame.setVisible(false);
mainFrame.setVisible(true);
//centerPanel.setVisible(false);
//timerDemo();
}
//创建带有图片的按钮
publicJButtoncreateImgBtn(Stringing,Stringtxt)
{//根据给定名称的资源创建一个ImageIcon。
ImageIconimage=newImageIcon(getClass().getResource(ing));
JButtonbutton=newJButton(txt,image);
//设置文本(即数字)相对于图标的垂直位置为底及水平位置为中心
button.setVerticalTextPosition(JButton.BOTTOM);
button.setHorizontalTextPosition(JButton.CENTER);
returnbutton;
}
/**
*产生游戏中的随机数字
*数字至少两两相同
*/
publicvoidrandomBuild()
{
intrandoms,cols,rows;
for(inttwins=1;twins<=15;twins++)
{
randoms=(int)(Math.random()*25+1);//随机产生一个1~25的数字
for(intalike=1;alike<=2;alike++)
{//产生两个随机的坐标来存放同一个数字
cols=(int)(Math.random()*6+1);
rows=(int)(Math.random()*5+1);
while(grid[cols][rows]!
=0)//避免出现重复的坐标
{
cols=(int)(Math.random()*6+1);
rows=(int)(Math.random()*5+1);
}
this.grid[cols][rows]=randoms;
}
}
}
//计算得分
publicvoidfraction()
{
fractionLable.setText(String.valueOf(Integer.parseInt(fractionLable.getText())+100));
}
//重列
publicvoidreload()
{
intsave[]=newint[30];
intn=0,cols,rows;
intgrid[][]=newint[8][7];
//time.setVisible(false);
for(inti=0;i<=6;i++)
{
for(intj=0;j<=5;j++)
{
if(this.grid[i][j]!
=0)
{//将未消去的图片的数字放在save数组中
save[n]=this.grid[i][j];
n++;
}
}
}
n=n-1;
this.grid=grid;//把grid数组全部初始化为零
while(n>=0)
{//将剩下的所有图片数字重新随机放在数组grid中
cols=(int)(Math.random()*6+1);
rows=(int)(Math.random()*5+1);
while(grid[cols][rows]!
=0)//避免出现重复的坐标
{
cols=(int)(Math.random()*6+1);
rows=(int)(Math.random()*5+1);
}
this.grid[cols][rows]=save[n];
n--;
}
mainFrame.setVisible(false);
//将按钮点击信息归为初始
pressInformation=false;
init();
for(inti=0;i<6;i++)
{