简体   繁体   English

添加while循环后程序/GUI冻结

[英]Program/GUI freezes after adding while loop

I'm trying to add a while loop to count the number of attempts made and add it to the message in my GUI.我正在尝试添加一个 while 循环来计算尝试次数并将其添加到我的 GUI 中的消息中。 After adding the while loop the program freezes, but no errors output to the console.添加 while 循环后,程序冻结,但没有错误输出到控制台。

I've tested it without a GUI and got it to print using System.out.print fine, but I can't get this to even allow a second input.我已经在没有 GUI 的情况下对其进行了测试,并使用 System.out.print 将其打印得很好,但是我什至无法获得第二个输入。 I have to stop the code from running to quit out.我必须停止运行代码才能退出。

Any advice would be appreciated!任何意见,将不胜感激!

import javax.swing.JFrame;
import javax.swing.JLabel;
import java.awt.BorderLayout;
import java.awt.Dimension;
import java.util.*;
import javax.swing.SwingConstants;
import java.awt.Font;
import javax.swing.JTextField;
import javax.swing.JButton;
import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;

public class GuessingGame extends JFrame {
private JTextField txtGuess;
private JLabel lblOutput;
private int theNumber;
private int attempt;
public void checkGuess() {
    String guessText = txtGuess.getText();
    String message = "";
    try {

        int guess = Integer.parseInt(guessText);
        while(guess!=theNumber) {
            if (guess < 0 || guess >100) {
                message = "Please enter a number between 0 and 100";
                attempt++;
            }
            else if (guess < theNumber) {
                message = guess + " is too low. Try again.";
                attempt++;
            }
            else if (guess > theNumber) {
                message = guess + " is too high. Try again.";
                attempt++;
            }
            else {
                message = guess + " is correct! It took " + attempt+ " attempts. Starting new game.";
                attempt++;
                newGame();
            }
        }
    } 
        catch(Exception e) {
        message= "Enter a whole number between 0 and 100";
    } 
        finally {
            lblOutput.setText(message);
            txtGuess.requestFocus();
            txtGuess.selectAll();
        }
}
public void newGame() {
    theNumber = (int)(Math.random() * 100 + 1);
    }

public GuessingGame() {
    setTitle("Hi-Lo Guessing Game");
    setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    getContentPane().setLayout(null);

    JLabel lblHiloGuessingGame = new JLabel("Hi-Lo Guessing Game");
    lblHiloGuessingGame.setFont(new Font("Tahoma", Font.BOLD, 15));
    lblHiloGuessingGame.setHorizontalAlignment(SwingConstants.CENTER);
    lblHiloGuessingGame.setBounds(12, 35, 408, 16);
    getContentPane().add(lblHiloGuessingGame);

    JLabel lblGuessANumber = new JLabel("Guess a number between 1 and 100");
    lblGuessANumber.setHorizontalAlignment(SwingConstants.CENTER);
    lblGuessANumber.setBounds(58, 86, 245, 16);
    getContentPane().add(lblGuessANumber);

    txtGuess = new JTextField();
    txtGuess.addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent e) {
            checkGuess();
        }
    });
    txtGuess.setBounds(310, 85, 32, 19);
    getContentPane().add(txtGuess);
    txtGuess.setColumns(10);

    JButton btnGuess = new JButton("Guess!");
    btnGuess.addActionListener(new ActionListener() {
        public void actionPerformed(ActionEvent e) {
        checkGuess();
        }
        });
    btnGuess.setBounds(163, 137, 97, 25);
    getContentPane().add(btnGuess);

    lblOutput = new JLabel("Enter a number and click guess");
    lblOutput.setHorizontalAlignment(SwingConstants.CENTER);
    lblOutput.setFont(new Font("Tahoma", Font.ITALIC, 13));
    lblOutput.setBounds(84, 197, 265, 19);
    getContentPane().add(lblOutput);
}

public static void main(String[] args) {
    GuessingGame theGame = new GuessingGame();
    theGame.newGame();
    theGame.setSize(new Dimension(450,300));
    theGame.setVisible(true);
    }

} }

I don't think you need an action performed handler for the text field, because doing anything to the text field shouldn't count as an attempt, right?我认为您不需要为文本字段执行操作处理程序,因为对文本字段执行任何操作都不应算作尝试,对吗? Only pressing the Guess button counts as an attempt.只有按下 Guess 按钮才算作一次尝试。

So you can delete this:所以你可以删除它:

txtGuess.addActionListener(new ActionListener() {
    public void actionPerformed(ActionEvent e) {
        checkGuess();
    }
});

Now checkGuess will be called whenever the user presses the button.现在,只要用户按下按钮,就会调用checkGuess Right now, it will parse the number from the text field, and enter a while loop to check that number.现在,它将解析文本字段中的数字,并输入一个 while 循环来检查该数字。 However, since guess is never modified in the while loop, the while loop never breaks.然而,由于在 while 循环中从来没有修改过guess ,所以while 循环永远不会中断。

Even if you read the guess inside the while loop, guess still wouldn't change, because while the while loop is running, the user cannot interact with the UI.即使您在 while 循环中读取了guessguess仍然不会改变,因为在 while 循环运行时,用户无法与 UI 进行交互

A better way to do this, is to simply remove the while loop:一个更好的方法是简单地删除 while 循环:

public void checkGuess() {
    String guessText = txtGuess.getText();
    String message = "";
    try {

        int guess = Integer.parseInt(guessText);
        if (guess < 0 || guess >100) {
            message = "Please enter a number between 0 and 100";
            attempt++;
        }
        else if (guess < theNumber) {
            message = guess + " is too low. Try again.";
            attempt++;
        }
        else if (guess > theNumber) {
            message = guess + " is too high. Try again.";
            attempt++;
        }
        else {
            message = guess + " is correct! It took " + attempt+ " attempts. Starting new game.";
            attempt++;
            newGame();
        }
    } 
        catch(Exception e) {
        message= "Enter a whole number between 0 and 100";
    } 
        finally {
            lblOutput.setText(message);
            txtGuess.requestFocus();
            txtGuess.selectAll();
        }
}

Although it seems like you need a while loop here, you actually don't.虽然看起来您在这里需要一个 while 循环,但实际上不需要。 This is because checkGuess will be called every time you press the Guess button.这是因为每次按下 Guess 按钮时都会调用checkGuess

Unlike in a command line, you don't ask for input in a GUI program, you wait for it.不像在命令行,你不要在GUI程序要求输入,你等着吧。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM