不确定我的贪吃蛇游戏逻辑有什么问题?
Not sure what's wrong with my logic for my snake game?
作为参考,这是link我的作业(课程是C语言课程):Snake
嘴巴应该是“<”、“>”、"v"或“^”,这取决于方向,body段应该是“*” .
所以首先,我的向上和向下箭头键控件被切换,但它打印出正确的字符(即向下移动时打印 "v" 向上移动时打印“^”),我不能找出原因。
此外,当打印头移动时,它只是从 body 上分离并且不会打印新的 body 段(参见 Screencap)。
下面是我的自定义结构,main,scene_render 和 scene_update 函数(我们不允许为此赋值修改 main 函数):
struct Point{
int x;
int y;
};
struct Snake {
struct Point segments[MAX_SEGMENTS];
int num_segments;
int dir; //0=up, 1=down, 2=left, 3=right
};
struct Scene {
// TODO: add fields
struct Snake snake;
struct Point fruit;
};
主要
int main(void) {
// Important: do NOT modify the main function
struct Scene scene;
scene_init(&scene);
int keep_going = 1;
while (keep_going == 1) {
scene_render(&scene);
cons_update();
scene_delay(&scene);
keep_going = scene_update(&scene);
}
return 0;
}
scene_render
void scene_render(const struct Scene *s) {
// TODO: add your code
int num=s->snake.num_segments;
cons_clear_screen();
cons_move_cursor(s->snake.segments[0].y, s->snake.segments[0].x);
if(s->snake.dir==0)
{
cons_printw("v");
}
else if(s->snake.dir==1)
{
cons_printw("^");
}
else if(s->snake.dir==2)
{
cons_printw(">");
}
else
{
cons_printw("<");
}
for(int i=1; i <num; i++)
{
cons_move_cursor(s->snake.segments[i].y, s->snake.segments[i].x);
cons_printw("*");
}
cons_move_cursor(23, 79); //just to get blinking cursor out of the way
}
scene_update
int scene_update(struct Scene *s) {
// This function should return 0 if the player presses 'q',
// 1 otherwise.
struct Scene temp=*s;
int num=temp.snake.num_segments;
int key = cons_get_keypress();
// TODO: add your code
if(key=='q')
{
return 0;
}
if(key==UP_ARROW && temp.snake.dir!=1)
{
temp.snake.dir=0;
temp.snake.segments[0].y=(temp.snake.segments[0].y)+1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
else if(key==DOWN_ARROW && temp.snake.dir!=0)
{
temp.snake.dir=1;
temp.snake.segments[0].y=(temp.snake.segments[0].y)-1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
else if(key==LEFT_ARROW && temp.snake.dir!=3)
{
temp.snake.dir=2;
temp.snake.segments[0].x=(temp.snake.segments[0].x)-1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
else if(key==RIGHT_ARROW && temp.snake.dir!=2)
{
temp.snake.dir=3;
temp.snake.segments[0].x=(temp.snake.segments[0].x)+1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
else if(key==-1)
{
if(temp.snake.dir==0)
{
temp.snake.segments[0].y=(temp.snake.segments[0].y)+1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
else if(temp.snake.dir==1)
{
temp.snake.segments[0].y=(temp.snake.segments[0].y)-1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
else if(temp.snake.dir==2)
{
temp.snake.segments[0].x=(temp.snake.segments[0].x)-1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
else
{
temp.snake.segments[0].x=(temp.snake.segments[0].x)+1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
}
temp.fruit.x=s->fruit.x;
temp.fruit.y=s->fruit.y;
*s=temp;
return 1;
}
之所以body脱离头部是因为你的移动代码:
if(temp.snake.dir==0)
{
temp.snake.segments[0].y=(temp.snake.segments[0].y)+1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
应该是:
if(temp.snake.dir==0)
{
temp.snake.segments[0].y=(temp.snake.segments[0].y)+1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i-1].y;
temp.snake.segments[i].x=s->snake.segments[i-1].x;
}
}
换句话说,第一个 body 部分应该移动到头部原来所在的位置。第二个 body 部分应该移到第一个部分原来所在的位置,依此类推。按照您现在的方式,所有 body 部分始终保持在同一个位置。您需要在许多地方进行此更改,或者更好的是创建一个函数来移动 body,这样您就不会到处都有重复的代码。
至于为什么向上是向下,反之亦然,我只能想象你屏幕的 y 坐标与你认为的相反(增加 y 值会向上移动而不是向下移动)。您应该检查哪种方式,并确保您的代码匹配。
作为参考,这是link我的作业(课程是C语言课程):Snake
嘴巴应该是“<”、“>”、"v"或“^”,这取决于方向,body段应该是“*” .
所以首先,我的向上和向下箭头键控件被切换,但它打印出正确的字符(即向下移动时打印 "v" 向上移动时打印“^”),我不能找出原因。
此外,当打印头移动时,它只是从 body 上分离并且不会打印新的 body 段(参见 Screencap)。
下面是我的自定义结构,main,scene_render 和 scene_update 函数(我们不允许为此赋值修改 main 函数):
struct Point{
int x;
int y;
};
struct Snake {
struct Point segments[MAX_SEGMENTS];
int num_segments;
int dir; //0=up, 1=down, 2=left, 3=right
};
struct Scene {
// TODO: add fields
struct Snake snake;
struct Point fruit;
};
主要
int main(void) {
// Important: do NOT modify the main function
struct Scene scene;
scene_init(&scene);
int keep_going = 1;
while (keep_going == 1) {
scene_render(&scene);
cons_update();
scene_delay(&scene);
keep_going = scene_update(&scene);
}
return 0;
}
scene_render
void scene_render(const struct Scene *s) {
// TODO: add your code
int num=s->snake.num_segments;
cons_clear_screen();
cons_move_cursor(s->snake.segments[0].y, s->snake.segments[0].x);
if(s->snake.dir==0)
{
cons_printw("v");
}
else if(s->snake.dir==1)
{
cons_printw("^");
}
else if(s->snake.dir==2)
{
cons_printw(">");
}
else
{
cons_printw("<");
}
for(int i=1; i <num; i++)
{
cons_move_cursor(s->snake.segments[i].y, s->snake.segments[i].x);
cons_printw("*");
}
cons_move_cursor(23, 79); //just to get blinking cursor out of the way
}
scene_update
int scene_update(struct Scene *s) {
// This function should return 0 if the player presses 'q',
// 1 otherwise.
struct Scene temp=*s;
int num=temp.snake.num_segments;
int key = cons_get_keypress();
// TODO: add your code
if(key=='q')
{
return 0;
}
if(key==UP_ARROW && temp.snake.dir!=1)
{
temp.snake.dir=0;
temp.snake.segments[0].y=(temp.snake.segments[0].y)+1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
else if(key==DOWN_ARROW && temp.snake.dir!=0)
{
temp.snake.dir=1;
temp.snake.segments[0].y=(temp.snake.segments[0].y)-1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
else if(key==LEFT_ARROW && temp.snake.dir!=3)
{
temp.snake.dir=2;
temp.snake.segments[0].x=(temp.snake.segments[0].x)-1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
else if(key==RIGHT_ARROW && temp.snake.dir!=2)
{
temp.snake.dir=3;
temp.snake.segments[0].x=(temp.snake.segments[0].x)+1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
else if(key==-1)
{
if(temp.snake.dir==0)
{
temp.snake.segments[0].y=(temp.snake.segments[0].y)+1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
else if(temp.snake.dir==1)
{
temp.snake.segments[0].y=(temp.snake.segments[0].y)-1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
else if(temp.snake.dir==2)
{
temp.snake.segments[0].x=(temp.snake.segments[0].x)-1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
else
{
temp.snake.segments[0].x=(temp.snake.segments[0].x)+1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
}
temp.fruit.x=s->fruit.x;
temp.fruit.y=s->fruit.y;
*s=temp;
return 1;
}
之所以body脱离头部是因为你的移动代码:
if(temp.snake.dir==0)
{
temp.snake.segments[0].y=(temp.snake.segments[0].y)+1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i].y;
temp.snake.segments[i].x=s->snake.segments[i].x;
}
}
应该是:
if(temp.snake.dir==0)
{
temp.snake.segments[0].y=(temp.snake.segments[0].y)+1;
for(int i=1; i<num; i++)
{
temp.snake.segments[i].y=s->snake.segments[i-1].y;
temp.snake.segments[i].x=s->snake.segments[i-1].x;
}
}
换句话说,第一个 body 部分应该移动到头部原来所在的位置。第二个 body 部分应该移到第一个部分原来所在的位置,依此类推。按照您现在的方式,所有 body 部分始终保持在同一个位置。您需要在许多地方进行此更改,或者更好的是创建一个函数来移动 body,这样您就不会到处都有重复的代码。
至于为什么向上是向下,反之亦然,我只能想象你屏幕的 y 坐标与你认为的相反(增加 y 值会向上移动而不是向下移动)。您应该检查哪种方式,并确保您的代码匹配。