0

我正在用 GUI 制作一个简单的猜数字游戏。我需要等待一个循环,等待用户在文本框中输入一个数字,然后按“确定”。如何等待循环内的事件?

注意:我不想要消息框。这是在主窗口中完成的,因此需要等待输入。

编辑:我应该更好地解释自己。我知道 GUI 中有一个循环。我想要的是方法中的另一个循环。也许有更好的方法来做到这一点。现在我想了想,我可以在按钮的事件处理程序中编写代码。虽然我需要全局变量。Whataver,我会考虑一下,但我希望我的问题现在更清楚了。

编辑2:对不起,我的问题不清楚,编辑并没有太大帮助。首先,代码太大,这里就不贴了。我可能不得不发布 GUI 的屏幕截图,所以它不会有太大用处。基本上,我有两个字段,“最大数量”和“允许猜测的数量”。用户输入这两个并点击“播放”。一个新面板变为可用,带有一个文本框和一个“猜测”按钮。用户输入一个猜测,程序检查它是否正确。

第二个无限循环的目的是避免全局变量。看,每次用户点击“玩”,游戏必须生成一个新的随机数作为正确的猜测。如果一切都在一个方法内完成,那没问题。但是如果多次调用“Guess”按钮的事件处理程序,则该数字必须存储为 Form 的实例变量。当然,这没什么大不了的,但我认为数字应该是指导当前游戏的方法的属性,而不是 Form 的属性。

我还必须跟踪方法之外的剩余猜测次数。再说一次,这没什么大不了的。如果可以的话,我只想避免使用全局变量。

再次,我很抱歉我的问题不太清楚。有点累,不想写太多。如果这仍然不清楚,请不要打扰。我会想办法的。

4

5 回答 5

5

C# 自动无限循环等待事件,直到您的表单关闭。您只需要响应按钮单击事件。

于 2009-06-17T03:50:39.560 回答
3

Jason Down 的建议是明智的,创建一个新GuessingGame类并将其添加到您的项目中。我知道您担心“全局变量”(在学校里每个人都被教导永远不要使用它,除非您绝对必须这样做),但请考虑一下您的设计规范。

但是如果多次调用“Guess”按钮的事件处理程序,则该数字必须存储为 Form 的实例变量。当然,这没什么大不了的,但我认为数字应该是指导当前游戏的方法的属性,而不是 Form 的属性。

作为替代方案,将GuessingGame类的实例存储在表单中。这不是全局变量!您自己说过,游戏的重点是跟踪猜测并在每次单击“播放”时生成新的数字进行猜测。如果您在表单中存储游戏实例然后打开另一个表单(例如帮助或关于框),则游戏实例将不可用(因此,不是全局的)。

GuessingGame对象将类似于:

public class GuessingGame
{
    private static Random _RNG = new Random();
    private bool _GameRunning;
    private bool _GameWon;
    private int _Number;
    private int _GuessesRemaining;

    public int GuessesRemaining
    {
        get { return _GuessesRemaining; }
    }

    public bool GameEnded
    {
        get { return !_GameRunning; }
    }

    public bool GameWon
    {
        get { return _GameWon; }
    }

    public GuessingGame()
    {
        _GameRunning = false;
        _GameWon = false;
    }

    public void StartNewGame(int numberOfGuesses, int max)
    {
        if (max <= 0)
            throw new ArgumentOutOfRangeException("max", "Must be > 0");

        if (max == int.MaxValue)
            _Number = _RNG.Next();
        else
            _Number = _RNG.Next(0, max + 1);

        _GuessesRemaining = numberOfGuesses;
        _GameRunning = true;
    }

    public bool MakeGuess(int guess)
    {
        if (_GameRunning)
        {
            _GuessesRemaining--;
            if (_GuessesRemaining <= 0)
            {
                _GameRunning = false;
                _GameWon = false;
                return false;
            }

            if (guess == _Number)
            {
                _GameWon = true;
                return true;
            }
            else
            {
                return false;
            }
        }
        else
        {
            throw new Exception("The game is not running. Call StartNewGame() before making a guess.");
        }
    }
}

这样,所有与游戏相关的数据都封装在类中。在表单的代码隐藏中连接事件很容易:

GuessingGame game = new GuessingGame();

private void btnPlay_Click(object sender, EventArgs e)
{
    int numberOfGuesses = Convert.ToInt32(txtNumberOfGuesses.Text);
    int max = Convert.ToInt32(txtMax.Text);
    game.StartNewGame(numberOfGuesses, max);
}

private void btnGuess_Click(object sender, EventArgs e)
{
    int guess = Convert.ToInt32(txtGuess.Text);
    bool correct = game.MakeGuess(guess);

    if (correct) 
        lblWin.Visible = true;

    if (game.GameEnded)
    {
        // disable guess button, show loss label
    }
}
于 2009-06-17T05:12:01.810 回答
1

您可能应该寻找一本书来实际学习 Windows 编程。

最基本的:

1)Windows代码深处已经存在无限循环。任何 Windows 程序都在不断地循环和扫描输入。

2) 一旦找到输入,这个循环就会触发一个事件。

3)如果您选择接受它,您的任务是编写事件处理程序来处理这些事件。

于 2009-06-17T03:52:18.920 回答
1

正如已经指出的那样,您很可能做错了,但是您可以使用它

应用程序.DoEvents();

在实际循环中处理事件

以正确的方式做到这一点 - 不要使用循环 - 使用编辑框进行输入,然后使用按钮 - 实现按钮 onclick 事件

于 2009-06-17T03:56:15.113 回答
1

是的,如果我正在等待语音事件,它可能会在函数运行时随时发生,我需要在不递归调用函数的情况下处理它

于 2009-11-23T15:17:56.633 回答