首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Swing GUI不响应输入

Swing GUI不响应输入
EN

Stack Overflow用户
提问于 2017-02-14 06:03:09
回答 1查看 71关注 0票数 0

我正在对John Conway的“生活的游戏”进行建模,以便在即将到来的一次会议上展示,我的程序应该已经完成了95%,但是,没有任何用户输入的响应。我的操作侦听器和鼠标侦听器似乎没有正确实现,但我不确定在哪里。程序几乎完全完成了;有几个部分仍然是空的,但它仍然可以正确地编译和创建我的JFrame。

代码语言:javascript
复制
/**
* Created by Brendan Kristiansen on 1/26/2017.
*/
public class GameOfLife
{
    public static void main(String[] args)
    {
        MyFrame frame = new MyFrame();
    }
}

包含全局信息的类:

代码语言:javascript
复制
/**
 * Created by Brendan Kristiansen on 1/26/2017.
 */
public class GLOBAL
{
    /**
     * Build Information for GameOfLife
     */
    public static final double BUILDVERSION = 0.1;
    public static final String BUILDNAME = "Alpha 0.1";

    /**
     * Global Constants for GameOfLife
     */
    public static final int FRAMEHEIGHT = 1000;     //Frame Height
    public static final int FRAMEWIDTH = 1000;      //Frame Width
    public static final int HEIGHT = 100;           //Game Height
    public static final int WIDTH = 100;            //Game Width

    /**
     * Global Variables
     */
    public static int delay = 500;                  //Step Delay (Milliseconds)
    public static byte[][] herd0;                   //Herd Byte Array 0
    public static byte[][] herd1;                   //Herd Byte Array 2
    public static byte[][] startHerd;               //Customized herd before animation is started
    public static byte activeArray;                 //Array currently being displayed
    public static boolean active;                   //States if simulation is repeating
    public static long arraySwitches;               //Tallies times active array is switched

    /**
     * Action Commands
     */
    public static final String CLOSE = "close";         //Closes Application
    public static final String START = "go";            //Starts looping simulation
    public static final String STOP = "stop";           //Stops loop
    public static final String RULES = "rules";         //Pops up window with Rules for GOL
    public static final String ABOUT = "about";         //Displays about dialog
    public static final String RESETGRID = "resetGrid"; //Resets the grid to before the simulation
    public static final String NEWGAME = "new";         //Zeroes the grid and arrays
}

框架:

代码语言:javascript
复制
/**
 * Created by Brendan Kristiansen on 1/26/2017.
 */

import java.awt.*;
import java.awt.event.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.*;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
import javax.swing.event.*;

/**
 * @author Brendan Kristiansen
 */
public class MyFrame extends JFrame implements ActionListener, ChangeListener
{
    private JPanel mPanel;
    private JButton start;
    private JButton stop;
    private JButton setGame;
    private JButton resetGame;
    private JButton newGame;

    private JLabel speedLabel;
    private JSlider speed;

    private HerdPanel mHerdPanel;

    /**
     * Constructor
     */
    public MyFrame()
    {
        GLOBAL.active = false;
        initArrays();
        setSize(GLOBAL.FRAMEWIDTH, GLOBAL.FRAMEHEIGHT);
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        mPanel = new JPanel();
        initForm();
        setVisible(true);
        mPanel.setVisible(true);

        JMenuBar menu = new JMenuBar();

        JMenu game = new JMenu("GameOfLife");
        JMenu help = new JMenu("Help");

        JMenuItem gamePlay = new JMenuItem("Play");
        JMenuItem gameExit = new JMenuItem("Exit");
        JMenuItem helpRules = new JMenuItem("Rules");
        JMenuItem helpAbout = new JMenuItem("About");

        gamePlay.addActionListener(this);
        gameExit.addActionListener(this);
        helpRules.addActionListener(this);
        helpAbout.addActionListener(this);

        gamePlay.setActionCommand(GLOBAL.START);
        gameExit.setActionCommand(GLOBAL.CLOSE);
        helpRules.setActionCommand(GLOBAL.RULES);
        helpAbout.setActionCommand(GLOBAL.ABOUT);

        game.add(gamePlay);
        game.add(gameExit);
        help.add(helpRules);
        help.add(helpAbout);

        menu.add(game);
        menu.add(help);

        this.setJMenuBar(menu);
        this.setVisible(true);
    }

    /**
     * Lays Out Panel
     */
    public void initForm()
    {
        setGame = new JButton("Set Grid");
        resetGame = new JButton("Reset Grid");
        newGame = new JButton("Clear Grid");
        start = new JButton("Start Simulation");
        stop = new JButton("Stop Simulation");
        speedLabel = new JLabel("Simulation Speed (ms): " + GLOBAL.delay);
// N        speed = new JSlider(3000, 50, GLOBAL.delay);

        setGame.addActionListener(this);
        resetGame.addActionListener(this);
        newGame.addActionListener(this);
        start.addActionListener(this);
        stop.addActionListener(this);

//        setGame.setActionCommand(GLOBAL.SETGRID);
        resetGame.setActionCommand(GLOBAL.RESETGRID);
        newGame.setActionCommand(GLOBAL.NEWGAME);
        start.setActionCommand(GLOBAL.START);
        stop.setActionCommand(GLOBAL.STOP);

        mPanel = new JPanel();
        mPanel.setLayout(new BoxLayout(mPanel, BoxLayout.X_AXIS));
        mPanel.setBackground(new Color(100, 100, 100));

        mHerdPanel = new HerdPanel();

        mPanel.add(setGame);
        mPanel.add(resetGame);
        mPanel.add(newGame);
        mPanel.add(start);
        mPanel.add(stop);
//        mPanel.add(speedLabel);
//        mPanel.add(speed);

        getContentPane().add(mPanel, BorderLayout.NORTH);
        getContentPane().add(mHerdPanel, BorderLayout.CENTER);

    }

    /**
     * Directs ActionEvents to the proper functions
     * @param event
     */
    @Override
    public void actionPerformed(ActionEvent event)
    {
        String e = event.toString();
        if(e.equals(GLOBAL.CLOSE))
        {
            System.exit(0);
        }
        else if(e.equals(GLOBAL.START))
        {
            GLOBAL.active = true;
            playGame();
        }
        else if(e.equals(GLOBAL.STOP))
        {
            GLOBAL.active = false;
        }
        else if(e.equals(GLOBAL.NEWGAME))
        {
            initArrays();
            mHerdPanel.paintImage();
        }
        else if(e.equals(GLOBAL.RESETGRID))
        {
            GLOBAL.herd0 = GLOBAL.startHerd;
            GLOBAL.herd1 = GLOBAL.startHerd;
            GLOBAL.activeArray = 0;
            mHerdPanel.paintImage();
        }
        else if (e.equals(GLOBAL.ABOUT))
        {
            JOptionPane.showMessageDialog(null, "Game of Life\n Developed by Brendan Kristiansen with MSU Storytelling.");
        }
        else if (e.equals(GLOBAL.RULES))
        {

        }
    }

    /**
     * Directs ChangeEvents to the proper functions
     * @param e
     */
    @Override
    public void stateChanged(ChangeEvent e)
    {
        GLOBAL.delay = speed.getValue();
    }

    /**
     * initializes byte arrays to be 0
     */
    public void initArrays()
    {
        GLOBAL.herd0 = new byte[GLOBAL.HEIGHT][GLOBAL.WIDTH];
        GLOBAL.herd1 = new byte[GLOBAL.HEIGHT][GLOBAL.WIDTH];
        for(int i = 0; i <= GLOBAL.HEIGHT - 1; i++)
        {
            for(int j = 0; j <= GLOBAL.WIDTH - 1; j++)
            {
                GLOBAL.herd0[i][j] = 0;
            }
        }
        GLOBAL.herd1 = GLOBAL.herd0;
        GLOBAL.activeArray = 0;
        GLOBAL.arraySwitches = 0;
    }

    /**
     *Controls the advancement of the game
     */
    public void playGame()
    {
        GLOBAL.startHerd = GLOBAL.herd0;
        if (GLOBAL.active == true)
        {
            while(GLOBAL.active == true)
            {
                nextFrame();
                try
                {
                    wait(GLOBAL.delay);
                }
                catch(Exception e)
                {
                    System.out.println(e);
                }
            }
        }
        else
        {
            nextFrame();
        }
    }

    /**
     *Advances Game of Life by one frame
     */
    public void nextFrame()
    {
        if (GLOBAL.activeArray == 0)
        {
            for(int i = 0; i <= GLOBAL.HEIGHT; i++)
            {
                for(int j = 0; j <= GLOBAL.WIDTH; j++)
                {
                    int neighbors = countNeighbors(i, j, GLOBAL.herd0);
                    if (neighbors == 3 || neighbors == 4)
                    {
                        GLOBAL.herd1[i][j] = 1;
                    }
                    else
                    {
                        GLOBAL.herd1[i][j] = 0;
                    }
                }
            }
            GLOBAL.activeArray = 1;
            mHerdPanel.paintImage();
        }
        else
        {
            for(int i = 0; i <= GLOBAL.HEIGHT; i++)
            {
                for(int j = 0; j <= GLOBAL.WIDTH; j++)
                {
                    int neighbors = countNeighbors(i, j, GLOBAL.herd1);
                    if (neighbors == 3 || neighbors == 4)
                    {
                        GLOBAL.herd0[i][j] = 1;
                    }
                    else
                    {
                        GLOBAL.herd0[i][j] = 0;
                    }
                }
            }
            GLOBAL.activeArray = 0;
            mHerdPanel.paintImage();
        }
        GLOBAL.arraySwitches++;
    }

    /**
     * Counts the living neighbors of a given cell in a herd
     * @param i
     * @param j
     * @param herd
     * @return
     */
    public int countNeighbors(int i, int j, byte[][] herd)
    {
        int neighbors = 0;
        if(i == 0 && j == 0) //Top left case
        {
            if(herd[i + 1][j] == 1){neighbors++;}       //Bottom Neighbor
            if(herd[i + 1][j + 1] == 1){neighbors++;}   //Bottom right neighbor
            if(herd[i][j + 1] == 1){neighbors++;}       //Right neighbor
        }
        else if(i == 0 && j == GLOBAL.WIDTH) //Top right case
        {
            if(herd[i + 1][j] == 1){neighbors++;}       //Bottom neighbor
            if(herd[i + 1][j - 1] == 1){neighbors++;}   //Bottom left neighbor
            if(herd[i][j - 1] == 1){neighbors++;}       //Left neighbor
        }
        else if(i == GLOBAL.HEIGHT && j == 0) //Bottom left case
        {
            if(herd[i - 1][j] == 1){neighbors++;}       //Top neighbor
            if(herd[i - 1][j + 1] == 1){neighbors++;}   //Top right neighbor
            if(herd[i][j + 1] == 1){neighbors++;}       //Right neighbor
        }
        else if(i == GLOBAL.HEIGHT && j == GLOBAL.WIDTH) //Bottom right case
        {
            if(herd[i - 1][j] == 1){neighbors++;}       //Top neighbor
            if(herd[i - 1][j - 1] == 1){neighbors++;}   //Top left neighbor
            if(herd[i][j - 1] == 1){neighbors++;}       //Left neighbor
        }
        else if(i == 0) //Top Row
        {
            if(herd[i + 1][j] == 1){neighbors++;}       //Bottom neighbor
            if(herd[i + 1][j + 1] == 1){neighbors++;}   //Bottom right neighbor
            if(herd[i][j + 1] == 1){neighbors++;}       //Right neighbor
            if(herd[i + 1][j - 1] == 1){neighbors++;}   //Bottom left neighbor
            if(herd[i][j - 1] == 1){neighbors++;}       //Left neighbor
        }
        else if(j == 0) //Left side
        {
            if(herd[i + 1][j] == 1){neighbors++;}       //Bottom neighbor
            if(herd[i + 1][j + 1] == 1){neighbors++;}   //Bottom right neighbor
            if(herd[i][j + 1] == 1){neighbors++;}       //Right neighbor
            if(herd[i - 1][j] == 1){neighbors++;}       //Top neighbor
            if(herd[i - 1][j + 1] == 1){neighbors++;}   //Top right neighbor
        }
        else if(i == GLOBAL.HEIGHT) //Bottom Row
        {
            if(herd[i - 1][j] == 1){neighbors++;}       //Top neighbor
            if(herd[i - 1][j + 1] == 1){neighbors++;}   //Top right neighbor
            if(herd[i][j + 1] == 1){neighbors++;}       //Right neighbor
            if(herd[i - 1][j - 1] == 1){neighbors++;}   //Top left neighbor
            if(herd[i][j - 1] == 1){neighbors++;}       //Left neighbor
        }
        else if(j == GLOBAL.WIDTH) //Right side
        {
            if(herd[i - 1][j - 1] == 1){neighbors++;}   //Top left neighbor
            if(herd[i][j - 1] == 1){neighbors++;}       //Left neighbor
            if(herd[i - 1][j] == 1){neighbors++;}       //Top neighbor
            if(herd[i + 1][j] == 1){neighbors++;}       //Bottom neighbor
            if(herd[i + 1][j - 1] == 1){neighbors++;}   //Bottom left neighbor
        }
        else //Middle of herd
        {
            if(herd[i + 1][j] == 1){neighbors++;}       //Bottom neighbor
            if(herd[i + 1][j - 1] == 1){neighbors++;}   //Bottom left neighbor
            if(herd[i][j - 1] == 1){neighbors++;}       //Left neighbor
            if(herd[i - 1][j - 1] == 1){neighbors++;}   //Top left neighbor
            if(herd[i - 1][j] == 1){neighbors++;}       //Top neighbor
            if(herd[i - 1][j + 1] == 1){neighbors++;}   //Top right neighbor
            if(herd[i][j + 1] == 1){neighbors++;}       //Right neighbor
            if(herd[i + 1][j + 1] == 1){neighbors++;}   //Bottom right neighbor
        }
        return neighbors;
    }
}

和HerdPanel类。这应该是一个网格,你可以点击它来改变单元格的颜色,然后用你突出显示的单元格玩生活游戏:

代码语言:javascript
复制
/**
 *
 * @author Brendan Kristiansen
 */
import javax.imageio.ImageIO;
import java.io.File;
import java.io.IOException;
import javax.swing.*;
import java.awt.event.*;
import java.awt.*;
import java.awt.image.BufferedImage;

//https://www.shodor.org/stella2java/rgbint.htmlhttps://www.shodor.org/stella2java/rgbint.html

public class HerdPanel extends JPanel implements MouseListener, MouseMotionListener
{
    Graphics2D g;
    Graphics2D g2;
    BufferedImage grid;
    BufferedImage bisonCell;

    /**
     * Constructor
     */
    public HerdPanel()
    {
        setSize(500, 500); //Width, Height
        addMouseListener(this);
        addMouseMotionListener(this);
        try
        {
            bisonCell = ImageIO.read(new File("bison.png"));
        }
        catch (IOException e)
        {
            System.out.println(e);
        }
        grid = new BufferedImage(GLOBAL.WIDTH, GLOBAL.HEIGHT, 1);
        paintImage();
        //g = grid.createGraphics();
    }

    /**
     * Converts byte[][] array to BufferedImage
     */
    public void paintImage()
    {
        if (GLOBAL.activeArray == 0)
        {
            for (int i = 0; i <= GLOBAL.WIDTH - 1; i++)
            {
                for (int j = 0; j <= GLOBAL.HEIGHT - 1; j++)
                {
                    if (GLOBAL.herd0[j][i] == 0)
                    {
                        grid.setRGB(j, i, 16777215);
                    } else
                    {
                        grid.setRGB(j, i, 0);
                    }
                }
            }
        }
        else
        {
            for (int i = 0; i <= GLOBAL.WIDTH; i++)
            {
                for (int j = 0; j <= GLOBAL.HEIGHT; j++)
                {
                    if (GLOBAL.herd1[j][i] == 0)
                    {
                        grid.setRGB(j, i, 16777215);
                    } else
                    {
                        grid.setRGB(j, i, 0);
                    }
                }
            }
        }
        g = grid.createGraphics();
        super.paintComponent(g);
        g.drawImage(grid, null, 0, 0);
        repaint();
    }

    @Override
    public void mouseClicked(MouseEvent e)
    {
        int xClick = (int)(e.getX() / GLOBAL.WIDTH);
        int yClick = (int) (e.getY() / GLOBAL.HEIGHT);
        if(GLOBAL.activeArray == 0)
        {
            GLOBAL.herd0[yClick][xClick] = 1;
        }
        else
        {
            GLOBAL.herd1[yClick][xClick] = 1;
        }
        paintImage();
    }

    @Override
    public void mousePressed(MouseEvent e)
    {
    }

    @Override
    public void mouseReleased(MouseEvent e)
    {
    }

    @Override
    public void mouseEntered(MouseEvent e)
    {
    }

    @Override
    public void mouseExited(MouseEvent e)
    {
    }

    @Override
    public void mouseDragged(MouseEvent e)
    {
    }


    @Override
    public void mouseMoved(MouseEvent e)
    {
    }
}
EN

回答 1

Stack Overflow用户

发布于 2017-02-14 06:04:30

直到游戏结束,您的playGame函数才会返回。Swing UI是单线程的。直到您将控制权交还给swing运行时,它才会刷新。

您需要在后台任务中计算您的游戏寿命,并通过在框架中触发paint事件来重新绘制ui。

你可以在这里找到一个很好的解释:Using threads to paint panel in java

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/42214371

复制
相关文章

相似问题

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