这篇文章主要介绍了Java编写掷骰子游戏,需要的朋友可以参考下

废话不多说了,直接奔主题。

**多线程&&观察者模式

题目要求:《掷骰子》窗体小游戏,在该游戏中,玩家初始拥有1000的金钱,每次输入押大还是押小,以及下注金额,随机3个骰子的点数,如果3个骰子的总点数小于等于9,则开小,否则开大,然后判断玩家是否押对,如果未押对则扣除下注金额,如果押对则奖励和玩家下注金额相同的金钱。

分析:这个题目要求灵活运用多线程的相关知识,达到点击开始按钮时,有3个线程启动,分别控制3颗骰子的转动,在3颗骰子全部转完以后,回到主线程计算游戏结果。

//个线程控制颗骰子

Thread t = new Thread();

Thread t = new Thread();

Thread t = new Thread();

//启动个线程

t.start();

t.start();

t.start();

//将个线程加入主线程

t.join();

t.join();

t.join();

But,,,写完代码以后发现,这样做虽然能够保证游戏能够正确运行,但是当我点击开始按钮时,由于3个骰子线程都是直接开在主线程上的,点击开始按钮时,按钮出现下沉情况,子线程一直在后台运行,我窗体中的图片根本不会发生改变,而是直接显示最后的结果,意思就是骰子一直在后台转动,不在前台的窗体中及时更新显示。后来在网上苦苦找寻,大神们说如果想要通过点击JButton使窗体中的JLabel/JTextFeild等其他组件及时更新,直接在JButton的监听事件的实现方法里面直接创建匿名线程,也就是说直接在actionPerformed()方法中修改代码即可,这样能保证你的组件中内容的及时变换,实现非常炫酷的效果。

代码如下:

public void actionPerformed(ActionEvent e) {

new Thread(new Runnable() {

@Override

public void run() {

//将外部线程类转移到窗体内部

}

}).start();

}

But,,,But,,,   虽然非常炫酷了,能够实现图片的及时更新了,游戏结果却错了,每次我的骰子还在转动呢,我的游戏结果却早早的就出来了。

原因:3根骰子线程属于子线程,窗体线程属于主线程,问题就在于:子线程可以通过变成精灵线程来保持与主线程的同生死,但是主线程却无法控制子线程何时死亡,只有等待子线程执行完所属的run()方法,结束线程后才知道。

解决方法:在主线程(main)中开3个子线程(t1,t2,t3),在每个子线程上再开一个子子线程(t11,t21,t31)。

t1,t2,t3只运行一次,负责创建子子线程;t11,t21,t31每个线程运行多次,负责控制窗体中的图标及时更新。

这样主线程就不受子线程的影响,开始按钮也不回出现下沉的情况。

但是同样在此处使用join方法也是hold不住子线程的,毕竟t1,t2,t3只运行了一次,join对他们来说根本不起作用,想要掌控t11,t21,t31,最容易理解的办法,就是使用观察者模式了。

将窗体看做观察者,子线程看做被观察者。子线程运行完时,通知观察者我已经运行完成,当观察者观察到子线程全都运行完时,才开始运行后续步骤。

全部代码:

1.窗体

package com.sxt.dice;

import java.awt.Color;

public class DiceFrame extends JFrame implements ActionListener, Observer {

/**

* 《掷骰子》控制台小游戏,在该游戏中,玩家初始拥有的金钱,每次输入押大还是押小,

* 以及下注金额,随机个骰子的点数,如果个骰子的总点数小于等于,则开小,否则开大,

* 然后判断玩家是否押对,如果未押对则扣除下注金额,如果押对则奖励和玩家下注金额相同的金钱。

*

* 运用观察者模式 个子线程分别控制个骰子,都已经结束时,通知观察者窗体,窗体观察到所有子线程都结束时,计算游戏结果

*

*/

private static final long serialVersionUID = L;

private JTextField txtPut;

private JButton btnStart;

private JLabel labResult;

private JComboBox comboBox;

private JLabel labBigOrSmall;

private JLabel labPut;

private JLabel labSumMoney;

private JLabel labDice;

private JLabel labDice;

private JLabel labDice;

private JLabel labSum;

private JLabel labMes;

private static List imgs = new ArrayList();

public static void main(String[] args) {

new DiceFrame();

}

public DiceFrame() {

this.setLocationRelativeTo(null);

this.setBounds(, , , );

this.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);

getContentPane().setLayout(null);

this.setResizable(false);

labDice = new JLabel("");

labDice.setIcon(new ImageIcon("img/dices.jpg"));

labDice.setBounds(, , , );

getContentPane().add(labDice);

labSum = new JLabel("\u\uF\uD\uD\uFFA");

labSum.setBounds(, , , );

getContentPane().add(labSum);

labDice = new JLabel("");

labDice.setIcon(new ImageIcon("img/dices.jpg"));

labDice.setBounds(, , , );

getContentPane().add(labDice);

labDice = new JLabel("");

labDice.setIcon(new ImageIcon("img/dices.jpg"));

labDice.setBounds(, , , );

getContentPane().add(labDice);

labSumMoney = new JLabel("");

labSumMoney.setForeground(Color.red);

labSumMoney.setBounds(, , , );

getContentPane().add(labSumMoney);

labPut = new JLabel("\uC\uB\uEB\uCE\uFFA");

labPut.setToolTipText(".");

labPut.setBounds(, , , );

getContentPane().add(labPut);

txtPut = new JTextField();

txtPut.setBounds(, , , );

getContentPane().add(txtPut);

txtPut.setColumns();

labBigOrSmall = new JLabel("\uBC\uFFA");

labBigOrSmall.setBounds(, , , );

getContentPane().add(labBigOrSmall);

comboBox = new JComboBox();

comboBox.setBounds(, , , );

getContentPane().add(comboBox);

comboBox.addItem("大");

comboBox.addItem("小");

labResult = new JLabel("");

labResult.setBounds(, , , );

getContentPane().add(labResult);

btnStart = new JButton("START");

btnStart.setBounds(, , , );

getContentPane().add(btnStart);

labMes = new JLabel("*");

labMes.setBounds(, , , );

getContentPane().add(labMes);

this.setVisible(true);

imgs.add(new ImageIcon("img/.png"));

imgs.add(new ImageIcon("img/.png"));

imgs.add(new ImageIcon("img/.png"));

imgs.add(new ImageIcon("img/.png"));

imgs.add(new ImageIcon("img/.png"));

imgs.add(new ImageIcon("img/.png"));

btnStart.addActionListener(this);

}

@Override

public void actionPerformed(ActionEvent e) {

if (e.getSource() == btnStart) {

// 清除上次游戏的结果

labResult.setText("");

// 获取当前下注金额,用户余额,用户押大还是押小

String txt = txtPut.getText().trim();

String remain = labSumMoney.getText().trim();

// 余额不足,不能开始游戏,提示用户充值

if (Integer.parseInt(remain) <= ) {

JOptionPane.showMessageDialog(null, "当前余额不足,请充值!");

return;

}

// 下注金额合法性检查

if (txt.length() == ) {

// 提示用户输入

labMes.setText("*请输入下注金额");

labMes.setForeground(Color.RED);

return;

}

// 检查用户下注金额是否在有效范围内

if (Integer.parseInt(txt) <=

|| Integer.parseInt(txt) > Integer.parseInt(remain)) {

txtPut.setText("");

labMes.setText("下注金额应在~" + remain + "之间");

return;

}

// 游戏开始后相关项不可更改

txtPut.setEnabled(false);

labMes.setText("");

comboBox.setEnabled(false);

//在主线程上开t,t,t 个子线程

Thread t = new Thread() {

@Override

public void run() {

//每个子线程上再开子子线程,控制图标变换

IconThread t = new IconThread(labDice, imgs);

//给t添加观察者,即当前窗体

t.addObserver(DiceFrame.this);

new Thread(t).start();

}

};

Thread t = new Thread() {

@Override

public void run() {

IconThread t = new IconThread(labDice, imgs);

t.addObserver(DiceFrame.this);

new Thread(t).start();

}

};

Thread t = new Thread() {

@Override

public void run() {

IconThread t = new IconThread(labDice, imgs);

t.addObserver(DiceFrame.this);

new Thread(t).start();

}

};

t.start();

t.start();

t.start();

}

}

/**

* 获取骰子点数和

*

* @param lab

* @return sum

*/

private int result(JLabel lab) {

// 获取当前骰子图片

Icon icon = lab.getIcon();

int sum = ;

for (int i = ; i < imgs.size(); i++) {

if (icon.equals(imgs.get(i))) {

sum += (i + );

break;

}

}

return sum;

}

// 构建所有被观察者的集合

Vector allObservables = new Vector();

@Override

public void update(Observable o, Object arg) {

System.out.println(o + ".................");

// 如果集合中不包含当前被观察者,将此被观察者加入集合

if (allObservables.contains(o) == false) {

allObservables.add(o);

}

// 如果集合中被观察者个数为,说明个骰子线程已经全部结束

if (allObservables.size() == ) {

// 获取当前下注金额,用户余额,用户押大还是押小

String txt = txtPut.getText().trim();

String remain = labSumMoney.getText().trim();

String bigOrSmall = comboBox.getSelectedItem().toString();

// 获取每个骰子点数

int sum = result(labDice);

int sum = result(labDice);

int sum = result(labDice);

System.out.println(sum + "-" + sum + "-" + sum);

int sum = sum + sum + sum;

System.out.println(sum);

if (sum > && "大".equals(bigOrSmall) || sum <=

&& "小".equals(bigOrSmall)) {

// 奖励玩家相应金额

remain = String.valueOf(Integer.parseInt(remain)

+ Integer.parseInt(txt));

labSumMoney.setText(remain);

// 显示游戏结果

labResult.setText("WIN");

labResult.setForeground(Color.GREEN);

labResult.setFont(new Font("宋体", Font.BOLD, ));

} else {

// 扣除玩家相应金额

remain = String.valueOf(Integer.parseInt(remain)

- Integer.parseInt(txt));

labSumMoney.setText(remain);

labResult.setText("FAIL");

labResult.setForeground(Color.red);

labResult.setFont(new Font("宋体", Font.BOLD, ));

}

txtPut.setEnabled(true);

comboBox.setEnabled(true);

// 本次游戏结束后移除集合中所有线程

allObservables.removeAll(allObservables);

}

}

}

2.线程

package com.sxt.dice;

import java.util.List;

import java.util.Observable;

import java.util.Random;

import javax.swing.Icon;

import javax.swing.JLabel;

public class IconThread extends Observable implements Runnable {

/**

* 运用观察者模式,将子线程作为被观察对象,一旦子线程运行完,发生改变,通知观察者

*/

JLabel lab;

Random random = new Random();

List imgs;

public IconThread(JLabel lab, List imgs) {

this.lab = lab;

this.imgs = imgs;

}

@Override

public void run() {

//设置每颗骰子转动次

int count = ;

while (count > ) {

//获取一个随机数[~)

int index = random.nextInt();

//从imgs集合中取相应图片放入lab中

lab.setIcon(imgs.get(index));

count--;

try {

Thread.sleep();

} catch (InterruptedException e) {

// TODO Auto-generated catch block

e.printStackTrace();

}

}

this.setChanged();// 子线程运行完,发生改变

this.notifyObservers();// 通知观察者

}

}

以上所述就是关于Java编写掷骰子游戏的全部内容,希望大家喜欢。

java 骰子游戏_Java编写掷骰子游戏相关推荐

  1. java开发掷骰子游戏_java – 模拟掷骰子游戏,非常初学者

    这里有几个问题,第一个播放器,计算机是非静态变量,你想用静态方法(main)访问它们,所以让它们静态. 第二个在diceRoll()方法之外声明获胜者,这样你就可以在main中使用它来制作那个静态. ...

  2. 用java编写五子棋游戏_java编写一个五子棋游戏,拜托了

    展开全部 保存为appwzq.java import java.awt.*; import java.awt.event.*; import java.applet.Applet; public cl ...

  3. android掷骰子动画,动画制作(掷骰子)

    <动画制作(掷骰子)>由会员分享,可在线阅读,更多相关<动画制作(掷骰子)(3页珍藏版)>请在人人文库网上搜索. 1.攀枝花商贸电子职业技术学校课堂教学设计表学科名称: 动画制 ...

  4. python编写掷骰子游戏改哪里把第0局变成第一局_Python基础案例练习:掷骰子小游戏...

    前言 骰子是我们经常能看到的小玩意儿,今天我们来做一个模拟掷骰子过程的文字版小游戏,送给新接触Python的初学者们~ 本文的文字及图片来源于网络,仅供学习.交流使用,不具有任何商业用途,版权归原作者 ...

  5. html5游戏 dice掷骰子,使用jQuery实现掷骰子游戏

    本文实例为大家共享了jQuery实现掷骰子游戏的详细代码,供大家参考,详细内容如下 直接新版建一个html网页,需要在head中引入jquery,js,一些css代码以及js代码,如下: .wrap{ ...

  6. 编程小游戏:模仿掷骰子,猜大小!

    游戏规则: 玩家进来以后要买筹码: 在每次掷骰子前, 要下注(50-手里剩余的筹码),接着要选择买大小: 程序要模仿掷骰子,产生一个1- 6 的随机数 根据掷骰子的结果,判断玩家的输赢,改变玩家的手里 ...

  7. html5 摇骰子游戏,html5 canvas掷骰子(简单,学习基础canvas)

    下面是编程之家 jb51.cc 通过网络收集整理的代码片段. 编程之家小编现在分享给大家,也给大家做个参考. 置骰子游戏 var cwidth = 400; //保存画布宽度和高度,用于擦除用 var ...

  8. vb用计算机模拟掷骰子游戏,VB随机 掷骰子示例源码

    [实例简介] [实例截图] [核心代码] VERSION 5.00 Begin VB.Form Form1 Caption = "掷骰子" ClientHeight = 3090 ...

  9. html掷骰子小游戏,网页实现掷骰子小游戏

    首先明确需求: 在网页正中间展示骰子,点数为一点,点击骰子,骰子旋转然后停留在随机点位上.再次点击骰子,骰子可以继续旋转并停留在随机点位上. 这里我们使用css3动画.3d旋转配合js实现效果 一,H ...

  10. java 拼图游戏_Java学员作品-拼图游戏

    由于大多数的手机都内置了Java的运行环境,加上Java语言自身的跨平台特性,Java成为了编写手机游戏时最常使用的语言之一. 拼图游戏很多人都玩过,它的游戏规则是将图片进行分割,然后将顺序打乱,要求 ...

最新文章

  1. python回溯算法_什么是回溯法,Python解法交流?
  2. backgroundworker 导致程序无法退出_macOS技巧—六种方法强制退出无响应的程序
  3. 【推荐】JS面象对象编程视频教程
  4. jaxb 命名空间_在JAXB解组期间应用名称空间
  5. linux安装Git依赖的包出错,技术|Linux有问必答:如何在Linux上安装Git
  6. Spring Boot 2.x 把 Guava 干掉了,拥抱本地缓存之王 Caffeine!
  7. 【bozj2287】【[POJ Challenge]消失之物】维护多值递推
  8. MongoDB干货系列1-定期巡检之Mtools
  9. 关于H5调用摄像头麦克风的权限问题
  10. vba批量合并指定的sheet_用VBA实现把多个Excel文件合并到一个Excel文件的多个工作表(Sheet)里...
  11. Hit Refresh读书摘要
  12. 微信支付接口调用问题(android正常,iphone调不起)
  13. 几本经典的投资理财书
  14. 如何两个电脑共享文件实现多人编辑_excel怎么实现多人共同编辑一个文档
  15. 一、与电视有关的视觉特性:
  16. windows记事本自动换行
  17. Onedrive如何同步文件夹
  18. RK3588平台开发系列讲解(USB篇)UAC初识
  19. 英语KOREITE寿山石koreite单词
  20. 微信打开域名网址被拦截 域名网址被微信拦截怎么办

热门文章

  1. UNet++ 论文翻译
  2. “谷姐一下”、“寂寞全消除”
  3. 计算机应用基础的课程讨论,(计算机教学论文:计算机应用基础课程教学方法的讨论.doc...
  4. sas 显示本地服务器,sas连接服务器local
  5. 粒子群算法 java_粒子群算法解决TSP问题
  6. sniffer Pro4.7.5最完整安装教程
  7. 安卓自定义Toast的原理及实现
  8. Hadoop之日志分析
  9. Android小知识- LayoutInflater
  10. C-V2X行业现状、产业化部署与演进路线