首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >为Maze Solver java程序添加功能

为Maze Solver java程序添加功能
EN

Stack Overflow用户
提问于 2015-09-17 22:53:37
回答 1查看 254关注 0票数 0

我正在用java编写一个迷宫解决程序,我很难弄清楚如何添加某些特性。现在,我让它为我硬编码的2D字符数组工作。

我需要可以:

  1. 从文本文件中加载一个迷宫(用户可以选择),并将其放入2D字符数组中。
  2. 启动迷宫(基本上是一个在MazeApp.java中启动MazeApp.java()方法的按钮)

可以控制Thread.sleep()中solveMaze方法中的值的滚动条。

以及一个文本字段,该字段可以显示(或不显示)迷宫中正在进行的内容(即“没有加载迷宫”、“迷宫加载”、“正在进行的解决方案”、“在此时找到finish:")。

处理GUI的MazeApp:

代码语言:javascript
运行
复制
import java.awt.*;
import javax.swing.*;

public class MazeApp extends JPanel implements Runnable {
    final private int cellSize = 20; // how big the cells/squares are
    final private int rows = 25; // how many rows are in the array (need to be able to get this info from txt file)
    final private int cols = 25; // how many columns are in the array (need to be able to get this info from txt file)
    private boolean mazeSolved = false; // boolean to check if maze is solved
    private boolean solutionExists = true;
    private int startLocX, startLocY; // ints used for '@' start location
    int cellLocX, cellLocY; // cell location that moves through the maze

//    private char[][] easyMaze = {
//            {'#','#', '#', '#', '#'},
//            {'#','@', '.', '.', '#'},
//            {'#','#', '#', '.', '#'},
//            {'#','.', '.', '.', '#'},
//            {'#','#', '#', '#', '#'},
//            {'-','-', '-', '-', '-'},
//            {'#','#', '#', '#', '#'},
//            {'#','=', '.', '.', '#'},
//            {'#','#', '#', '.', '#'},
//            {'#','*', '.', '.', '#'},
//            {'#','#', '#', '#', '#'},
//    };

    //hard coded example 1 level maze with multiple finishes;
    private char[][] easyMaze = {
            {'#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#'},
            {'#','.','#','.','.','.','#','.','.','.','.','.','.','.','#','.','.','.','.','.','.','.','.','.','#'},
            {'#','.','#','.','#','.','#','.','#','#','.','#','.','#','#','.','#','#','.','#','#','#','#','.','#'},
            {'#','.','#','.','#','.','#','.','#','#','.','#','.','#','#','.','#','.','.','.','.','#','#','.','#'},
            {'#','.','.','.','#','.','#','.','#','#','.','#','.','#','#','.','#','.','#','.','.','#','#','.','#'},
            {'#','.','#','.','#','.','#','.','.','.','.','#','.','#','#','.','#','.','#','.','.','#','#','.','#'},
            {'#','.','#','.','#','.','#','.','#','#','.','#','.','#','#','.','.','.','.','.','.','.','.','.','#'},
            {'#','.','#','.','#','.','#','.','#','#','.','#','.','.','.','.','#','.','#','#','#','#','.','.','#'},
            {'#','.','.','.','#','.','.','.','#','#','.','#','.','#','#','.','#','.','#','.','#','.','.','.','#'},
            {'#','.','#','#','#','#','#','#','#','#','.','#','.','#','#','.','#','.','#','.','#','.','#','.','#'},
            {'#','.','#','.','.','.','#','.','.','.','.','#','.','#','#','.','#','.','#','.','#','.','#','.','#'},
            {'#','.','#','.','#','.','#','.','#','#','#','#','.','#','#','.','#','.','#','.','#','.','#','.','#'},
            {'#','.','#','.','#','.','#','.','#','#','#','#','.','#','#','.','#','.','#','.','#','.','#','.','#'},
            {'#','.','.','.','#','.','.','.','#','.','.','.','.','#','#','.','.','.','.','.','.','.','.','.','#'},
            {'#','#','#','#','#','#','.','#','#','#','#','#','#','#','#','.','#','.','#','#','#','.','#','.','#'},
            {'#','.','.','.','.','.','.','.','.','.','#','#','#','#','#','.','#','.','.','.','#','.','#','.','#'},
            {'#','.','#','.','#','#','#','#','#','#','#','#','#','#','#','.','#','.','#','.','#','.','#','.','#'},
            {'#','.','#','.','.','.','.','.','.','.','.','.','.','.','#','.','#','.','#','.','#','.','#','.','#'},
            {'#','.','#','.','#','#','#','#','#','#','#','#','#','.','#','.','#','.','#','.','#','.','#','.','#'},
            {'#','.','#','.','#','.','.','.','.','.','.','.','.','.','#','.','#','.','#','.','#','.','#','.','#'},
            {'#','.','#','.','#','.','#','#','#','#','#','#','#','#','#','.','#','.','#','.','#','.','#','.','#'},
            {'#','.','#','.','#','.','.','.','.','.','.','.','.','.','#','.','#','.','#','.','#','.','#','#','#'},
            {'#','@','#','.','#','#','.','#','#','#','#','.','.','.','#','.','#','.','#','.','#','.','#','#','#'},
            {'#','.','.','.','#','#','.','#','#','#','#','.','.','#','#','.','.','.','.','.','.','.','.','*','#'},
            {'#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#','#'}
    };

    // goes through array and paints cells
    public void paintComponent(Graphics myGrfx) {

        super.paintComponent(myGrfx);

        //for loop to paint the rows
        for(int i = 0;  i < rows; i++){

            //for loop to paint the cols
            for(int j = 0; j < cols; j++) {
                if (i == cellLocX && j == cellLocY) {
                    myGrfx.setColor(Color.GREEN);
                    myGrfx.fillRect(j * cellSize, i * cellSize, cellSize, cellSize);
                } else if (easyMaze[i][j] == '#') {
                    myGrfx.setColor(Color.BLACK);
                    myGrfx.fillRect(j * cellSize, i * cellSize, cellSize, cellSize);
                } else if (easyMaze[i][j] == '*') {
                    myGrfx.setColor(Color.RED);
                    myGrfx.fillRect(j * cellSize, i * cellSize, cellSize, cellSize);
                } else if (easyMaze[i][j] == '.') {
                    myGrfx.setColor(Color.WHITE);
                    myGrfx.fillRect(j * cellSize, i * cellSize, cellSize, cellSize);
                } else if (easyMaze[i][j] == 'x') {
                    myGrfx.setColor(Color.LIGHT_GRAY);
                    myGrfx.fillRect(j * cellSize, i * cellSize, cellSize, cellSize);
                } else if (easyMaze[i][j] == '=') {
                    myGrfx.setColor(Color.BLUE);
                    myGrfx.fillRect(j * cellSize, i * cellSize, cellSize, cellSize);
                }
            }
        }
    }

    // goes through the array to find '@', starts start locations points at i and j
    public void getStartPosition() {
        for(int i = 0;  i < rows; i++){
            for(int j = 0; j < cols; j++) {
                if (easyMaze[i][j] == '@') {
                    startLocX = i;
                    startLocY = j;
                }
            }
        }
    }

    public void getStairsPosition() {
        for(int i = 0;  i < rows; i++){
            for(int j = 0; j < cols; j++) {
                if (easyMaze[i][j] == '=') {
                    startLocX = i;
                    startLocY = j;
                }
            }
        }
    }

    // marks visited paths with an 'x', shaded light gray
    public void markPath(int locX, int locY){
        easyMaze[locX][locY] = 'x';
        cellLocX = locX;
        cellLocY = locY;
    }

    // method you have to use for threads, need to replace with timer stuff
    public void run() {
        getStartPosition();
        solveMaze(startLocX, startLocY);
    }

    // checks to see if the maze has found an exit
    public boolean isFinished(int locX, int locY) {
        if (easyMaze[locX][locY] == '*') {
            return true;
        } else {
            return false;
        }
    }

    // boolean that checks for walls
    public boolean outOfBounds(int locX, int locY) {
        if (easyMaze[locX][locY] == '#') {
            return true;
        } else {
            return false;
        }
    }

    // boolean to check if a cell has been visited
    public boolean haveVisited(int locX, int locY) {
        if (easyMaze[locX][locY] == 'x') {

            return true;
        } else {
            return false;
        }
    }

    public void noSolution() {
        for(int i = 0;  i < rows; i++){
            for(int j = 0; j < cols; j++) {
                if (easyMaze[i][j] == '#' || easyMaze[i][j] == 'x') {
                    solutionExists = false;
                }
            }
        }
    }

    // method that calls itself and checks for finish, walls, or already visited paths
    private void solveMaze(int locX, int locY) {
        if (isFinished(locX, locY)) {
            mazeSolved = true;
            JOptionPane.showMessageDialog(this, "Yay, we found the finish!");
            System.exit(0);
        }

        if (outOfBounds(locX, locY)) {
            return;
        }

        if (haveVisited(locX, locY)) {
            return;
        }

        if (!mazeSolved) {
            markPath(locX, locY);
            repaint();
            try {Thread.sleep(50); } catch (Exception e) { }

            solveMaze(locX, locY+1); // move right
            solveMaze(locX + 1,locY); // move down
            solveMaze(locX - 1, locY); // move up
            solveMaze(locX, locY - 1); // move left
        }
    } // end solveMaze
} // end class

这是测试类:

代码语言:javascript
运行
复制
import javax.swing.*;

public class MazeTest {
    public static void main (String[] args) {
        JFrame maze = new JFrame();
        maze.setSize(750, 520);
        maze.setLocationRelativeTo(null);
        maze.setTitle("Maze Solver 1.0");
        MazeApp myMazeApp = new MazeApp();
        maze.setContentPane(myMazeApp);
        maze.setVisible(true);
        Thread myThread = new Thread(myMazeApp);
        myThread.start();
    }
}
EN

回答 1

Stack Overflow用户

发布于 2015-09-17 23:34:19

将以下代码添加到MazeApp中应该可以做到这一点:

代码语言:javascript
运行
复制
private static final int initialSpeed = 50;
private static final int paddingTop = 30;
private static final int paddingLeft = 30;
private JButton loadMazeBtn = new JButton("Load Maze");
private JButton runMazeBtn = new JButton("Run Maze");
private JScrollBar speedBar = new JScrollBar(JScrollBar.HORIZONTAL);
private JLabel statusLabel = new JLabel("Starting up...");

private void add(JComponent component, int x, int y) {
    add(component);
    component.setLocation(x, y);
    component.setSize(component.getPreferredSize());
}

public MazeApp() {
    setLayout(null);

    int x = cols * cellSize + paddingLeft;
    int y = paddingTop;

    add(loadMazeBtn, x, y);
    add(runMazeBtn, x, y + 40);
    add(speedBar, x, y + 80);
    add(statusLabel, x, y + 120);

    loadMazeBtn.addActionListener(new ActionListener() {
        @Override
        public void actionPerformed(ActionEvent e) {
            // Fill in your code to load the maze
        }
    });

    runMazeBtn.addActionListener(new ActionListener() {
        @Override
        public void actionPerformed(ActionEvent e) {
            // Fill in your code to run the maze
        }
    });

    speedBar.setValue(initialSpeed);
}

// Call this method when you want to change the status text
// (i.e. "no maze loaded", "maze loaded", "solution in progress", "found finish at this point: ")
public void setStatusText(String text) {
    statusLabel.setText(text);
}

// Call this function to feed the Thread.sleep
public int getSpeed() {
    return speedBar.getValue();
}

您只需填写“加载迷宫”和“运行代码”的代码,并在状态更改时添加对setStatusText的调用。

对于“速度条”,将solveMaze中的solveMaze代码更改为

代码语言:javascript
运行
复制
Thread.sleep(getSpeed());
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/32641213

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档