目錄
運行出的游戲界面如下:
?User類
?CodeUtil類
游戲設置
登陸代碼
?注冊代碼
游戲代碼
運行出的游戲界面如下:
?
?
?按住A不松開,顯示完整圖片;松開A顯示隨機打亂的圖片
?User類
package domain;/*** @ClassName: User* @Author: Kox* @Data: 2023/2/2* @Sketch:*/
public class User {private String username;private String password;public User() {}public User(String username, String password) {this.username = username;this.password = password;}/*** 獲取* @return username*/public String getUsername() {return username;}/*** 設置* @param username*/public void setUsername(String username) {this.username = username;}/*** 獲取* @return password*/public String getPassword() {return password;}/*** 設置* @param password*/public void setPassword(String password) {this.password = password;}}
?CodeUtil類
package util;import java.util.ArrayList;
import java.util.Random;public class CodeUtil {public static String getCode(){//1.創建一個集合ArrayList<Character> list = new ArrayList<>();//52 索引的范圍:0 ~ 51//2.添加字母 a - z A - Zfor (int i = 0; i < 26; i++) {list.add((char)('a' + i));//a - zlist.add((char)('A' + i));//A - Z}//3.打印集合//System.out.println(list);//4.生成4個隨機字母String result = "";Random r = new Random();for (int i = 0; i < 4; i++) {//獲取隨機索引int randomIndex = r.nextInt(list.size());char c = list.get(randomIndex);result = result + c;}//System.out.println(result);//長度為4的隨機字符串//5.在后面拼接數字 0~9int number = r.nextInt(10);//6.把隨機數字拼接到result的后面result = result + number;//System.out.println(result);//ABCD5//7.把字符串變成字符數組char[] chars = result.toCharArray();//[A,B,C,D,5]//8.在字符數組中生成一個隨機索引int index = r.nextInt(chars.length);//9.拿著4索引上的數字,跟隨機索引上的數字進行交換char temp = chars[4];chars[4] = chars[index];chars[index] = temp;//10.把字符數組再變回字符串String code = new String(chars);//System.out.println(code);return code;}
}
游戲設置
package ui;import javax.swing.*;
import javax.swing.border.BevelBorder;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.util.Random;/*** @ClassName: GameJFrame* @Author: Kox* @Data: 2023/1/30* @Sketch:*/
public class GameJFrame extends JFrame implements KeyListener, ActionListener {// 管理數據int[][] data = new int[4][4];// 記錄空白方塊在二維數組的位置int x = 0;int y = 0;// 展示當前圖片的路徑String path = "拼圖小游戲_image\\image\\girl\\girl7\\";// 存儲正確的數據int[][] win = {{1, 2, 3, 4},{5, 6, 7, 8},{9, 10, 11, 12},{13, 14, 15, 0}};// 定義變量用來統計步數int step = 0;// 選項下面的條目對象JMenuItem replayItem = new JMenuItem("重新游戲");JMenuItem reLoginItem = new JMenuItem("重新登錄");JMenuItem closeItem = new JMenuItem("關閉游戲");JMenuItem accountItem = new JMenuItem("公眾號");JMenuItem beautiful = new JMenuItem("美女");JMenuItem animal = new JMenuItem("動物");JMenuItem exercise = new JMenuItem("運動");// 游戲界面public GameJFrame() {// 初始化界面initJFrame();// 初始化菜單initJMenuBar();// 初始化數據initDate();// 初始化圖片initImage();// 顯示this.setVisible(true);}// 數據private void initDate() {int[] tempArr = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15};Random r = new Random();for (int i = 0; i < tempArr.length; i++) {int index = r.nextInt(tempArr.length);int temp = tempArr[i];tempArr[i] = tempArr[index];tempArr[index] = temp;}for (int i = 0; i < tempArr.length; i++) {if (tempArr[i] == 0) {x = i / 4;y = i % 4;}data[i / 4][i % 4] = tempArr[i];}}// 圖片private void initImage() {// 清空原本已經出現的所有圖片this.getContentPane().removeAll();if (victory()) {JLabel winJLabel = new JLabel(new ImageIcon("拼圖小游戲_image\\image\\win.png"));winJLabel.setBounds(203, 283, 197, 73);this.getContentPane().add(winJLabel);}JLabel stepCount = new JLabel("步數:" + step);stepCount.setBounds(50, 30, 100, 20);this.getContentPane().add(stepCount);for (int i = 0; i < 4; i++) {for (int j = 0; j < 4; j++) {int num = data[i][j];// 創建一個圖片ImageIcon對象ImageIcon icon = new ImageIcon(path + num + ".jpg");// 創建一個JLabel的對象JLabel jLabel1 = new JLabel(icon);// 指定圖片位置jLabel1.setBounds(105 * j + 83, 105 * i + 134, 105, 105);// 給圖片添加邊框jLabel1.setBorder(new BevelBorder(BevelBorder.LOWERED));// 管理容器添加到界面中this.getContentPane().add(jLabel1);}}// 添加背景圖片JLabel background = new JLabel(new ImageIcon("拼圖小游戲_image\\image\\background.png"));background.setBounds(40, 40, 508, 560);this.getContentPane().add(background);// 刷新一下界面this.getContentPane().repaint();}// 菜單private void initJMenuBar() {// 菜單對象JMenuBar jMenuBar = new JMenuBar();// 選項-功能JMenu functionJMenu = new JMenu("功能");// 選項-關于我們JMenu aboutJMenu = new JMenu("關于我們");// 選項-換圖JMenu changePicture = new JMenu("更換圖片");// 選項下面的條目添加到選項中functionJMenu.add(changePicture);functionJMenu.add(replayItem);functionJMenu.add(reLoginItem);functionJMenu.add(closeItem);changePicture.add(beautiful);changePicture.add(animal);changePicture.add(exercise);aboutJMenu.add(accountItem);// 給條目綁定事件replayItem.addActionListener(this);reLoginItem.addActionListener(this);closeItem.addActionListener(this);accountItem.addActionListener(this);beautiful.addActionListener(this);animal.addActionListener(this);exercise.addActionListener(this);// 將菜單里面的兩個選項添加到菜單當中jMenuBar.add(functionJMenu);jMenuBar.add(aboutJMenu);// 給整個界面設置菜單this.setJMenuBar(jMenuBar);}// 界面private void initJFrame() {// 設置界面的寬高this.setSize(603, 680);// 設置界面的標題this.setTitle("拼圖單機版 v1.0");// 設置界面置頂this.setAlwaysOnTop(true);// 設置界面居中this.setLocationRelativeTo(null);// 設置關閉模式this.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE);// 取消默認的居中放置this.setLayout(null);// 添加鍵盤監聽事件this.addKeyListener(this);}@Overridepublic void keyTyped(KeyEvent e) {}// 按下@Overridepublic void keyPressed(KeyEvent e) {int code = e.getKeyCode();if (code == 65) {// 刪除界面中的素有圖片this.getContentPane().removeAll();// 加載第一張完整的圖片JLabel all = new JLabel(new ImageIcon(path + "all.jpg"));all.setBounds(83, 134, 420, 420);this.getContentPane().add(all);// 添加背景圖片JLabel background = new JLabel(new ImageIcon("拼圖小游戲_image\\image\\background.png"));background.setBounds(40, 40, 508, 560);this.getContentPane().add(background);// 刷新界面this.getContentPane().repaint();}}// 松下@Overridepublic void keyReleased(KeyEvent e) {// 判斷游戲是否勝利if (victory()) {return;}int code = e.getKeyCode();if (code == 37) {System.out.println("向左移動");if (y == 3) {return;}data[x][y] = data[x][y + 1];data[x][y + 1] = 0;y++;// 計算器step++;initImage();} else if(code == 38) {System.out.println("向上移動");if (x == 3) {return;}data[x][y] = data[x + 1][y];data[x + 1][y] = 0;x++;// 計算器step++;initImage();} else if(code == 39) {System.out.println("向右移動");if (y == 0) {return;}data[x][y] = data[x][y - 1];data[x][y - 1] = 0;y--;// 計算器step++;initImage();} else if(code == 40) {System.out.println("向下移動");if (x == 0) {return;}data[x][y] = data[x - 1][y];data[x - 1][y] = 0;x--;// 計算器step++;initImage();} else if (code == 65) {initImage();} else if (code == 87) {initImage();data = new int[][] {{1, 2, 3, 4},{5, 6, 7, 8},{9, 10, 11, 12},{13, 14, 15, 0}};initImage();}}// 勝利public boolean victory() {for (int i = 0; i < data.length; i++) {for (int j = 0; j < data[i].length; j++) {if (data[i][j] != win[i][j]) {return false;}}}return true;}@Overridepublic void actionPerformed(ActionEvent e) {// 獲取當前被點擊的條目對象Object obj = e.getSource();Random r = new Random();// 判斷if (obj == beautiful) {System.out.println("換美女");int index = r.nextInt(11) + 1;path = "拼圖小游戲_image\\image\\girl\\girl" + index +"\\";step = 0;initDate();initImage();} else if (obj == animal) {System.out.println("換動物");int index = r.nextInt(8) + 1;path = "拼圖小游戲_image\\image\\animal\\animal" + index +"\\";step = 0;initDate();initImage();} else if (obj == exercise) {System.out.println("換運動");int index = r.nextInt(10) + 1;path = "拼圖小游戲_image\\image\\sport\\sport" + index +"\\";step = 0;initDate();initImage();}if (obj == replayItem) {System.out.println("重新游戲");step = 0;initDate();initImage();} else if(obj == reLoginItem) {System.out.println("重新登錄");this.setVisible(false);new LoginJFrame();} else if(obj == closeItem) {System.out.println("關閉游戲");System.exit(0);} else if(obj == accountItem) {System.out.println("公眾號");JDialog jDialog = new JDialog();JLabel jLabel = new JLabel(new ImageIcon("拼圖小游戲_image\\image\\about.png"));jLabel.setBounds(0, 0, 150, 150);jDialog.getContentPane().add(jLabel);jDialog.setSize(344, 344);jDialog.setAlwaysOnTop(true);jDialog.setLocationRelativeTo(null);jDialog.setModal(true);jDialog.setVisible(true);}}
}
登陸代碼
package ui;import domain.User;
import util.CodeUtil;import javax.swing.*;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.io.BufferedReader;
import java.io.File;
import java.io.FileReader;
import java.util.ArrayList;public class LoginJFrame extends JFrame implements MouseListener {static ArrayList<User> allUsers = new ArrayList<>();static {allUsers.add(new User("zhangsan","123"));allUsers.add(new User("lisi","1234"));}JButton login = new JButton();JButton register = new JButton();JTextField username = new JTextField();//JTextField password = new JTextField();JPasswordField password = new JPasswordField();JTextField code = new JTextField();//正確的驗證碼JLabel rightCode = new JLabel();public LoginJFrame() {//初始化界面initJFrame();//在這個界面中添加內容initView();//讓當前界面顯示出來this.setVisible(true);}public void initView() {//1. 添加用戶名文字JLabel usernameText = new JLabel(new ImageIcon("拼圖小游戲_image\\image\\login\\用戶名.png"));usernameText.setBounds(116, 135, 47, 17);this.getContentPane().add(usernameText);//2.添加用戶名輸入框username.setBounds(195, 134, 200, 30);this.getContentPane().add(username);//3.添加密碼文字JLabel passwordText = new JLabel(new ImageIcon("拼圖小游戲_image\\image\\login\\密碼.png"));passwordText.setBounds(130, 195, 32, 16);this.getContentPane().add(passwordText);//4.密碼輸入框password.setBounds(195, 195, 200, 30);this.getContentPane().add(password);//驗證碼提示JLabel codeText = new JLabel(new ImageIcon("拼圖小游戲_image\\image\\login\\驗證碼.png"));codeText.setBounds(133, 256, 50, 30);this.getContentPane().add(codeText);//驗證碼的輸入框code.setBounds(195, 256, 100, 30);this.getContentPane().add(code);String codeStr = CodeUtil.getCode();//設置內容rightCode.setText(codeStr);//綁定鼠標事件rightCode.addMouseListener(this);//位置和寬高rightCode.setBounds(300, 256, 50, 30);//添加到界面this.getContentPane().add(rightCode);//5.添加登錄按鈕login.setBounds(123, 310, 128, 47);login.setIcon(new ImageIcon("拼圖小游戲_image\\image\\login\\登錄按鈕.png"));//去除按鈕的邊框login.setBorderPainted(false);//去除按鈕的背景login.setContentAreaFilled(false);//給登錄按鈕綁定鼠標事件login.addMouseListener(this);this.getContentPane().add(login);//6.添加注冊按鈕register.setBounds(256, 310, 128, 47);register.setIcon(new ImageIcon("拼圖小游戲_image\\image\\login\\注冊按鈕.png"));//去除按鈕的邊框register.setBorderPainted(false);//去除按鈕的背景register.setContentAreaFilled(false);//給注冊按鈕綁定鼠標事件register.addMouseListener(this);this.getContentPane().add(register);//7.添加背景圖片JLabel background = new JLabel(new ImageIcon("拼圖小游戲_image\\image\\login\\background.png"));background.setBounds(0, 0, 470, 390);this.getContentPane().add(background);}public void initJFrame() {this.setSize(488, 430);//設置寬高this.setTitle("拼圖游戲 V1.0登錄");//設置標題this.setDefaultCloseOperation(3);//設置關閉模式this.setLocationRelativeTo(null);//居中this.setAlwaysOnTop(true);//置頂this.setLayout(null);//取消內部默認布局}//點擊@Overridepublic void mouseClicked(MouseEvent e) {if (e.getSource() == login) {System.out.println("點擊了登錄按鈕");//獲取兩個文本輸入框中的內容String usernameInput = username.getText();String passwordInput = password.getText();//獲取用戶輸入的驗證碼String codeInput = code.getText();//創建一個User對象User userInfo = new User(usernameInput, passwordInput);System.out.println("用戶輸入的用戶名為" + usernameInput);System.out.println("用戶輸入的密碼為" + passwordInput);if (codeInput.length() == 0) {showJDialog("驗證碼不能為空");} else if (usernameInput.length() == 0 || passwordInput.length() == 0) {//校驗用戶名和密碼是否為空System.out.println("用戶名或者密碼為空");//調用showJDialog方法并展示彈框showJDialog("用戶名或者密碼為空");} else if (!codeInput.equalsIgnoreCase(rightCode.getText())) {showJDialog("驗證碼輸入錯誤");} else if (contains(userInfo)) {System.out.println("用戶名和密碼正確可以開始玩游戲了");//關閉當前登錄界面this.setVisible(false);//打開游戲的主界面//需要把當前登錄的用戶名傳遞給游戲界面new GameJFrame();} else {System.out.println("用戶名或密碼錯誤");showJDialog("用戶名或密碼錯誤");}} else if (e.getSource() == register) {System.out.println("點擊了注冊按鈕");} else if (e.getSource() == rightCode) {System.out.println("更換驗證碼");//獲取一個新的驗證碼String code = CodeUtil.getCode();rightCode.setText(code);}}public void showJDialog(String content) {//創建一個彈框對象JDialog jDialog = new JDialog();//給彈框設置大小jDialog.setSize(200, 150);//讓彈框置頂jDialog.setAlwaysOnTop(true);//讓彈框居中jDialog.setLocationRelativeTo(null);//彈框不關閉永遠無法操作下面的界面jDialog.setModal(true);//創建Jlabel對象管理文字并添加到彈框當中JLabel warning = new JLabel(content);warning.setBounds(0, 0, 200, 150);jDialog.getContentPane().add(warning);//讓彈框展示出來jDialog.setVisible(true);}//按下不松@Overridepublic void mousePressed(MouseEvent e) {if (e.getSource() == login) {login.setIcon(new ImageIcon("拼圖小游戲_image\\image\\login\\登錄按下.png"));} else if (e.getSource() == register) {register.setIcon(new ImageIcon("拼圖小游戲_image\\image\\login\\注冊按下.png"));}}//松開按鈕@Overridepublic void mouseReleased(MouseEvent e) {if (e.getSource() == login) {login.setIcon(new ImageIcon("jigsawgame\\image\\login\\登錄按鈕.png"));} else if (e.getSource() == register) {register.setIcon(new ImageIcon("jigsawgame\\image\\login\\注冊按鈕.png"));}}//鼠標劃入@Overridepublic void mouseEntered(MouseEvent e) {}//鼠標劃出@Overridepublic void mouseExited(MouseEvent e) {}//判斷用戶在集合中是否存在public boolean contains(User userInput){for (int i = 0; i < allUsers.size(); i++) {User rightUser = allUsers.get(i);if(userInput.getUsername().equals(rightUser.getUsername()) && userInput.getPassword().equals(rightUser.getPassword())){//有相同的代表存在,返回true,后面的不需要再比了return true;}}//循環結束之后還沒有找到就表示不存在return false;}}
?注冊代碼
package ui;import domain.User;
import util.CodeUtil;import javax.swing.*;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.io.*;
import java.util.ArrayList;
import java.util.List;public class RegisterJFrame extends JFrame implements MouseListener {ArrayList<User> list = new ArrayList<>();//提升三個輸入框的變量的作用范圍,讓這三個變量可以在本類中所有方法里面可以使用。JTextField username = new JTextField();JTextField password = new JTextField();JTextField rePassword = new JTextField();//提升兩個按鈕變量的作用范圍,讓這兩個變量可以在本類中所有方法里面可以使用。JButton submit = new JButton();JButton reset = new JButton();public RegisterJFrame() throws IOException {user();initFrame();initView();setVisible(true);}public void user() throws IOException {File file = new File("user.txt");file.createNewFile();BufferedReader br = new BufferedReader(new FileReader("user.txt"));String str;while ((str = br.readLine()) != null) {String[] user = str.split("&");//nameString name = user[0].split("=")[1];//passwordString password = user[1].split("=")[1];list.add(new User(name, password));}}@Overridepublic void mouseClicked(MouseEvent e) {//獲取輸入框中的內容String userNameStr = username.getText();String passWordStr = password.getText();String rePasswordText = rePassword.getText();if (e.getSource() == submit){//注冊System.out.println("注冊");//判斷輸入框是否有空if ((userNameStr.length() == 0) || (passWordStr.length() == 0) || (rePasswordText.length() == 0)){showDialog("賬號或密碼不能為空");//清空密碼password.setText("");rePassword.setText("");} else if (!passWordStr.equals(rePasswordText)) {showDialog("密碼不一致");//清空密碼rePassword.setText("");} else if (!tfUsername(userNameStr)) { //賬戶已存在showDialog("賬號已存在");} else {try {//將數據存入本地文件中User(userNameStr,passWordStr);showDialog("注冊成功");this.setVisible(false);new LoginJFrame();} catch (IOException ex) {throw new RuntimeException(ex);}}//}else if(e.getSource() == reset){//重置System.out.println("重置");password.setText("");rePassword.setText("");username.setText("");}}/** 將數據賬號數據存入本地文件中* 參數1:賬號 參數2:密碼* */private void User(String name , String password) throws IOException {String user = "name="+name+"&password="+password;BufferedWriter bw = new BufferedWriter(new FileWriter("user.txt",true));bw.write(user);bw.newLine();bw.close();}/** 檢測賬號是否存在* 返回值 boolean* 傳入 username* */private boolean tfUsername(String userName){for (User user : list) {if(user.getUsername().equals(userName))return false;}return true;}@Overridepublic void mousePressed(MouseEvent e) {if (e.getSource() == submit) {submit.setIcon(new ImageIcon("拼圖小游戲_image\\image\\register\\注冊按下.png"));} else if (e.getSource() == reset) {reset.setIcon(new ImageIcon("拼圖小游戲_image\\image\\register\\重置按下.png"));}}@Overridepublic void mouseReleased(MouseEvent e) {if (e.getSource() == submit) {submit.setIcon(new ImageIcon("拼圖小游戲_image\\image\\register\\注冊按鈕.png"));} else if (e.getSource() == reset) {reset.setIcon(new ImageIcon("拼圖小游戲_image\\image\\register\\重置按鈕.png"));}}@Overridepublic void mouseEntered(MouseEvent e) {}@Overridepublic void mouseExited(MouseEvent e) {}private void initView() {//添加注冊用戶名的文本JLabel usernameText = new JLabel(new ImageIcon("拼圖小游戲_image\\image\\login\\用戶名.png"));usernameText.setBounds(85, 135, 80, 20);//添加注冊用戶名的輸入框username.setBounds(195, 134, 200, 30);//添加注冊密碼的文本JLabel passwordText = new JLabel(new ImageIcon("拼圖小游戲_image\\image\\register\\注冊密碼.png"));passwordText.setBounds(97, 193, 70, 20);//添加密碼輸入框password.setBounds(195, 195, 200, 30);//添加再次輸入密碼的文本JLabel rePasswordText = new JLabel(new ImageIcon("拼圖小游戲_image\\image\\register\\再次輸入密碼.png"));rePasswordText.setBounds(64, 255, 95, 20);//添加再次輸入密碼的輸入框rePassword.setBounds(195, 255, 200, 30);//注冊的按鈕submit.setIcon(new ImageIcon("拼圖小游戲_image\\image\\register\\注冊按鈕.png"));submit.setBounds(123, 310, 128, 47);submit.setBorderPainted(false);submit.setContentAreaFilled(false);submit.addMouseListener(this);//重置的按鈕reset.setIcon(new ImageIcon("拼圖小游戲_image\\image\\register\\重置按鈕.png"));reset.setBounds(256, 310, 128, 47);reset.setBorderPainted(false);reset.setContentAreaFilled(false);reset.addMouseListener(this);//背景圖片JLabel background = new JLabel(new ImageIcon("拼圖小游戲_image\\image\\background.png"));background.setBounds(0, 0, 470, 390);this.getContentPane().add(usernameText);this.getContentPane().add(passwordText);this.getContentPane().add(rePasswordText);this.getContentPane().add(username);this.getContentPane().add(password);this.getContentPane().add(rePassword);this.getContentPane().add(submit);this.getContentPane().add(reset);this.getContentPane().add(background);}private void initFrame() {//對自己的界面做一些設置。//設置寬高setSize(488, 430);//設置標題setTitle("拼圖游戲 V1.0注冊");//取消內部默認布局setLayout(null);//設置關閉模式setDefaultCloseOperation(3);//設置居中setLocationRelativeTo(null);//設置置頂setAlwaysOnTop(true);}//只創建一個彈框對象JDialog jDialog = new JDialog();//因為展示彈框的代碼,會被運行多次//所以,我們把展示彈框的代碼,抽取到一個方法中。以后用到的時候,就不需要寫了//直接調用就可以了。public void showDialog(String content){if(!jDialog.isVisible()){//把彈框中原來的文字給清空掉。jDialog.getContentPane().removeAll();JLabel jLabel = new JLabel(content);jLabel.setBounds(0,0,200,150);jDialog.add(jLabel);//給彈框設置大小jDialog.setSize(200, 150);//要把彈框在設置為頂層 -- 置頂效果jDialog.setAlwaysOnTop(true);//要讓jDialog居中jDialog.setLocationRelativeTo(null);//讓彈框jDialog.setModal(true);//讓jDialog顯示出來jDialog.setVisible(true);}}
}
游戲代碼
import java.io.IOException;import ui.GameJFrame;
import ui.LoginJFrame;
import ui.RegisterJFrame;/*** @ClassName: App* @Author: Kox* @Data: 2023/1/30* @Sketch:*/
public class App {public static void main(String[] args) throws IOException {// 登錄界面new LoginJFrame();// 注冊界面new RegisterJFrame();// 游戲界面new GameJFrame();}
}