2012-09-24 20 views
1

我使用Ncurses库在C++中制作Pacman。我可以用我的代码移动Pacman,但我想移动它,以便即使在我不按任何键时pacman仍在移动,并且当我按另一个方向键时,它会改变方向。现在,当我按下按键时,pacman只需要一步。在pacman向那个方向移动之前,我还必须按两次或三次按键。即使没有按下按键,我如何在屏幕上发生什么?

if (ch==KEY_LEFT) 
{ 
    int b,row,column; 
    getyx(stdscr,row,column); 
    int h; 
    do // do-whileloop to move the pacman left until it hits the wall 
    { 
     column-=1; 
     mvprintw(row,column,">"); //print the ">" symbol 
     refresh(); 
     waitf(0.1);  //this pauses the game for 0.1sec 
     attron(COLOR_PAIR(1));  
     mvprintw(row,column,">"); 
     attroff(COLOR_PAIR(1)); 
     refresh(); 
     waitf(0.1); 
     mvprintw(row,(b),"O"); //showing the open mouth of pacman 
     refresh(); 
     waitf(0.1); 
     attron(COLOR_PAIR(1));a 
     mvprintw(row,column,"O"); 
     attroff(COLOR_PAIR(1)); 
     h = getch(); 
    } 
    while(h == KEY_LEFT); 
} 

right = getch(); 

循环向右移动在if条件

up = getch(); 

循环,在if条件

down = getch(); 

接力拉升在一个if条件下移动。

+0

放置这样一个条件,当用户移动pacman时,它会进入一个循环并停下来,只有当它到达墙壁时才等待下一条指令。 –

+0

但我希望只要按下另一个键,pacman就会改变它的方向。 – User14229754

回答

0

我建议你看一看的model-view-controller模型,它会帮助你这个问题,所有如果你继续你的程序是这样,你将有其他问题。

编辑:快捷

要将你吃豆子不断,您将需要一个单独的线程来控制它,让它移动。看看pthreads吧。

如果您只保留用户输入到程序的主运行循环中,那么您必须按几次按键的问题也会消失(这里的问题是处理器必须在getch ()行,否则不会被检测到

+2

这个答案太宽泛了,它并没有真正回答这个问题。 – Dialecticus

+0

我是初学者,我缺乏时间。请问你能告诉我一些其他的解决方案吗? – User14229754

+0

用快捷方式编辑 – Minion91

5

标准解决方案是finite-state machine。该字符有六种可能的状态:站立,向上移动,向右移动,向下移动,移动离开了,死了。而不是一个按键直接移动的字符,该按键应该改变人物的状态。

在这样一个小的应用程序,而不是实现一个非常灵活鳍ITE状态机,你可以用一个非常简单的实现为这样:

enum PlayerState { 
    Standing, 
    MovingUp, 
    MovingRight, 
    MovingDown, 
    MovingLeft, 
    Dead 
}; 

然后,你的游戏循环中,您可以添加一个非常简单的状态检查,然后花费的框架适当的行动。

switch(state) { 
case Standing: 
    break; 
case MovingUp: 
    player.PositionY += 1; 
    break; 
// ... 
} 

最后一步是勾选输入,这取决于您检索输入的方法。使用回调,一个例子是:

void KeyDown(Key k) { 
    switch(k) { 
    case UpArrow: 
     if(state != Dead) 
      state = MovingUp; 
     break; 
    case RightArrow: 
     if(state != Dead) 
      state = MovingRight; 
    // ... 
    } 
} 

你可以看到为什么在一个较大的项目,以实施更灵活的有限状态机也将是重要的,但我希望这个例子给你一个易于理解的想法。直到一些键被按下

1

功能getch被阻止。如果您不希望被阻止,请在getch之前致电_kbhit,以确保输入缓冲区中有东西。

编辑:看看ncurses的功能nodelaycbreak。他们启用异步输入。

+0

我不能在ncurses中使用kbhit()。 – User14229754

+0

你在使用什么操作系统,以及使用什么编译器? – Dialecticus

+0

g ++编译器。我使用putty软件连接我的大学服务器。 – User14229754

3

您需要一个等效的kbhit,即。一个非阻塞的getch。这真的给了解决方案,在输入上设置O_NONBLOCK。看一个例子here。一旦你有了这个,只需连续循环,只需检查键击,不用等待实际的按键。

+0

对于O_NONBLOCK来说是+1,因为我已经触及了这些C API。 –

0

这是很容易
每个方向做4功能 和作用,把其中获得通过的kbhit激活其他3个方向函数内。

并放置一个else语句,如果你没有按下按钮(例如(!kbhit()); 然后把所有这些放在一个循环中。


如果你对所有的方向功能都这样做,你应该能够得到理想的结果。

+0

这个巨大的,丑陋的代码转储不是一个有用的“答案”。 – Blastfurnace

+0

其他答案至少试图解决这个问题并提供具体的解决方案。另一方面,你从你自己的(封闭的)问题中粘贴相同的格式不正确的代码,而没有解释或指导。请看看其他的问题和答案,以了解网站的工作原理。不要拿这个人,我知道你可以做得更好。干杯。 – Blastfurnace

+0

我不知道为什么every1一直说它严重格式化我怎么能让它更好? –

相关问题