用于游戏的 C# WPF 键盘移动

C# WPF keyboard movement for game

我正在尝试使用 wpf 在 c# 中制作一个小游戏。我的矩形四处移动,我要解决的问题是,如果您在按住原始键的同时按下另一个键,然后松开其中一个键,它将朝按住的方向移动。我的代码有效,但是如果 运行 一旦释放一个键就会有延迟,那么矩形将继续移动。

    enum Direction { left, right, up, down, none};
    Direction _direction = Direction.none;
    bool _directionIsPressed = false;
    bool _directionIsReleased = false;
    double x = 0;
    double y = 0;

    public MainWindow()
    {
        InitializeComponent();



        DispatcherTimer timer = new DispatcherTimer();
        timer.Tick += new EventHandler(MovePlayer);
        timer.Start();

        this.KeyDown += new KeyEventHandler(OnButtonKeyDown);
        this.KeyUp += new KeyEventHandler(OnButtonKeyRelease);

    }

    private void MovePlayer(object sender, EventArgs e)
    {
        switch (_direction)
        {
            case Direction.down:
                y += .05;
                Canvas.SetTop(Player, y);
                break;
            case Direction.up:
                y -= .05;
                Canvas.SetTop(Player, y);
                break;
            case Direction.left:
                x -= .05;
                Canvas.SetLeft(Player, x);
                break;
            case Direction.right:
                x += .05;
                Canvas.SetLeft(Player, x);
                break;
        }
    }

    private void OnButtonKeyDown(object sender, KeyEventArgs e)
    {
        switch (e.Key)
        {
            case Key.Down:
                _direction = Direction.down;
                _directionIsPressed = true;
                break;
            case Key.Up:
                _direction = Direction.up;
                _directionIsPressed = true;
                break;
            case Key.Left:
                _direction = Direction.left;
                _directionIsPressed = true;
                break;
            case Key.Right:
                _direction = Direction.right;
                _directionIsPressed = true;
                break;
            default:
                _direction = Direction.none;
                break;
        }
    }

    //When a key is released it will set the direction to none then 
    //reset the direction but there is about a half second delay in 
    //setting the direction again
    private void OnButtonKeyRelease(Object sender, KeyEventArgs e) 
    {
        _direction = Direction.none;
        this.KeyDown += new KeyEventHandler(OnButtonKeyDown);
    }

编辑: 如果有人想在 C# 中使用 wpf 进行平滑的键盘移动,我就是这样修复它的。谢谢 Stefan 的帮助。

        public MainWindow()
    {
        InitializeComponent();
        DispatcherTimer timer = new DispatcherTimer();
        timer.Tick += new EventHandler(MovePlayer);
        timer.Start();
    }

    private void MovePlayer(object sender, EventArgs e)
    {
        if(Keyboard.IsKeyDown(Key.Left))
        {
            x -= .05;
            Canvas.SetLeft(Player, x);
        }
        if(Keyboard.IsKeyDown(Key.Up))
        {
            y -= .05;
            Canvas.SetTop(Player, y);
        }
        if(Keyboard.IsKeyDown(Key.Down))
        {
            y += .05;
            Canvas.SetTop(Player, y);
        }
        if(Keyboard.IsKeyDown(Key.Right))
        {
            x += .05;
            Canvas.SetLeft(Player, x);
        }
    }

与其在不同的函数中使用两个 switch 语句,不如尝试将它们合并为一个。延迟的原因可能是从一个功能跳转到另一个功能所需的开销。

您可以尝试在按下按键时移动播放器,而不是单独调用 MovePlayer()。

private void OnButtonKeyDown(object sender, KeyEventArgs e)
{
    switch (e.Key)
    {
        case Key.Down:
            y += .05;
            Canvas.SetTop(Player, y);
            break;
        case Key.Up:
            y -= .05;
            Canvas.SetTop(Player, y);
            break;
        case Key.Left:
            x -= .05;
            Canvas.SetLeft(Player, x);
            break;
        case Key.Right:
            x += .05;
            Canvas.SetLeft(Player, x);
            break;
        default:
            _direction = Direction.none;
            break;
    }
}

如果你想允许组合运动,例如向上+向左一起那么我只能用计时器和Keyboard.IsKeyDown(键)验证

private void MovePlayer(object sender, EventArgs e)
{
    if (Keyboard.IsKeyDown(Key.Down))
    {
        y += .05;
        Canvas.SetTop(Player, y);
    }
    if(Keyboard.IsKeyDown(Key.Up))
    {
        y -= .05;
        Canvas.SetTop(Player, y);
    }
    if (Keyboard.IsKeyDown(Key.Left))
    {
        x -= .05;
        Canvas.SetLeft(Player, x);
    }
    if (Keyboard.IsKeyDown(Key.Right))
    {
        x += .05;
        Canvas.SetLeft(Player, x);
    }
}

其他情况,如果当时只能在一个简单的方向上进行移动,你可以检查你的KeyReleased例程中的语句。

private void OnButtonKeyRelease(Object sender, KeyEventArgs e) 
{
    if (Keyboard.IsKeyDown(Key.Down))
        _direction = Direction.down;
    else if(Keyboard.IsKeyDown(Key.Up))
        _direction = Direction.up;
    else if (Keyboard.IsKeyDown(Key.Left))
        _direction = Direction.left;
    else if (Keyboard.IsKeyDown(Key.Right))
        _direction = Direction.right;
    else
        _direction = Direction.none;
}

但是如果你想同时按下 2 个以上的移动按钮,你需要将它保存在某个数组中并检查 稍后被按下,并根据此按钮设置移动。