Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/160.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/css/35.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 游戏挂起,同时更新砖断路器水平。-开放式总账。_C++_Opengl_Graphics - Fatal编程技术网

C++ 游戏挂起,同时更新砖断路器水平。-开放式总账。

C++ 游戏挂起,同时更新砖断路器水平。-开放式总账。,c++,opengl,graphics,C++,Opengl,Graphics,我已经用OpenGL和OpenGLUT编写了一个简单的破砖游戏。每件事都按照它应该的方式进行,除了当一个关卡结束时,游戏就挂起了。知道为什么吗? 我试图告诉它重置所有参数,但没有任何效果 #include <GL/openglut.h> #include <cmath> #include <string> #include <ctime> #define RADIUS 0.025 #define P_LENGTH 0.3 using nam

我已经用OpenGL和OpenGLUT编写了一个简单的破砖游戏。每件事都按照它应该的方式进行,除了当一个关卡结束时,游戏就挂起了。知道为什么吗? 我试图告诉它重置所有参数,但没有任何效果

#include <GL/openglut.h>
#include <cmath>
#include <string>
#include <ctime>
#define RADIUS    0.025
#define P_LENGTH  0.3
using namespace std;
int WIDTH     = 900,
    HEIGHT    = 650,
    lives     = 3,
    SCORE     = 0,
    LEVEL     = 2,
    BRICK_ROW = 10,
    BRICK_COL = 9;
double x_brick[10][10],
       y_brick[10][10],
       P_XPOS = 0,
       P_YPOS = -0.8,
       x_pos = 0,
       y_pos = -0.75,
       win_aspect,
       SPEED = 0;
bool show[10][10],
     phit_center = false, 
     phit_corner = false,
     game_over   = false,
     RIGHT       = true,
     LEFT        = false,
     UP          = true,
     DOWN        = false,
     started     = false,
     hit         = false;
char life = '0';
void user_input(unsigned char key, int x, int y)
{
     if(key == 13)
            started = true; 
}
void b_draw()
{
      glBegin(GL_QUADS);
      for(int a = 0; a < BRICK_COL; a++)
      {
              for(int b = 0; b < BRICK_ROW; b++)
              {
                      switch(b)
                      {
                      case 0:
                           glColor3f(1.0,0.0,0.0);
                           break;
                      case 1:
                           glColor3f(1.0,0.9,0.1);
                           break;
                      case 2:
                           glColor3f(0.0,1.0,0.0);
                           break;
                      case 3:
                           glColor3f(0.11,0.56,1.0);
                           break;
                      default:
                              glColor3f(1.0,0.0,0.0);
                      }
                      if(show[b][a] == true)
                      {
                                    glVertex2f(x_brick[b][a]*win_aspect,y_brick[b][a]);
                                    glVertex2f(x_brick[b][a]*win_aspect,(y_brick[b][a] - 0.10)); 
                                    glVertex2f((x_brick[b][a]+0.2)*win_aspect,(y_brick[b][a] - 0.10));
                                    glVertex2f((x_brick[b][a]+0.2)*win_aspect,y_brick[b][a]);  
                      }
              }
      }
      glColor3f(0.0,0.0,0.0);
      glEnd();
}

void Set_Level(int level)
{
     int R_Limit = 0;
     switch(level)
     {
       case 1:
          for(int a = 0; a < BRICK_ROW; a++)
          {
            for(int b = 0; b < BRICK_COL; b++)
            {
                    show[a][b] = 1;
            }
          }
          break;
       case 2:
          for(int a = 0; a < BRICK_ROW/2; a++)
          {
                  for(int b = 0; b < BRICK_COL; b++)
                  {
                    if(b >= BRICK_COL/2 - R_Limit && b<=BRICK_COL/2 + R_Limit)
                    show[a][b] = true;
                  }
                  R_Limit++;
          }    
          R_Limit = BRICK_ROW/2;
          for(int a = BRICK_ROW/2; a <= BRICK_ROW; a++)
          {
                  for(int b = 0; b <= BRICK_COL; b++)
                  {
                          if(b >= BRICK_COL/2 - R_Limit && b <= BRICK_COL/2 + R_Limit)
                          show[a][b] = true;                  
                  }
                  R_Limit--;
          }
          break;
       case 3:
            for(int a = 0; a <= BRICK_COL/2; a++)
            {
                    show[a][a] = true;
            }
            for(int a = BRICK_COL; a >= BRICK_COL/2; a--)
            {
                    show[BRICK_COL - a - 1][a] = true;
            }
            break;
     }              
}
bool all_gone()
{
     int local_flag = 0;
     for(int a = 0; a < BRICK_COL; a++)
     {
             for(int b = 0; b < BRICK_ROW; b++)
             {
                     if(show[b][a] == true)
                     {
                                   return false;
                                   local_flag = 1;
                                   break;
                     }
                     if(local_flag)
                                   break;
             }
     }

     return true;
}
void c_draw()
{
     glColor3f(0.0f, 0.0f, 0.0f);
     glBegin(GL_TRIANGLE_FAN);
     glVertex2f(x_pos,y_pos);
     for (float angle = 0; angle < (10); angle+=0.01)
     {
         glVertex2f((x_pos + sin(angle) * RADIUS), (y_pos + (cos(angle)) * RADIUS));
     }
     glEnd();
}
bool crashed()
{
     if(y_pos < P_YPOS - 0.1)
              return true;
     else return false;
}
void c_move()
{
      if(UP && RIGHT)
      {
           x_pos += SPEED;
           y_pos += SPEED;       
      }
      if(UP && LEFT)
      {
            x_pos -= SPEED;
            y_pos += SPEED;
      }
      if(DOWN && RIGHT)
      {
              x_pos += SPEED;
              y_pos -= SPEED;
      }
      if(DOWN && LEFT)
      {
              x_pos -= SPEED;
              y_pos -= SPEED;
      }
}
void p_draw()
{
     glColor3f(0.0,0.0,0.0);
     glBegin(GL_QUADS);
                      glVertex2f(P_XPOS-P_LENGTH, P_YPOS);
                      glVertex2f(P_XPOS+P_LENGTH, P_YPOS);
                      glVertex2f(P_XPOS+P_LENGTH, P_YPOS-0.05);
                      glVertex2f(P_XPOS-P_LENGTH, P_YPOS-0.05);
     glEnd();
}
void SET_BRICKS(int level)
{
     switch(level)
     {
                  case 1:
                       BRICK_ROW = 4;
                       break;
                  case 2:
                       BRICK_ROW = 7;
                       break;
                  case 3:
                       BRICK_ROW = 7;
                       break;
     }
}
void BallLoop()
{
     const int   win_width  = glutGet(GLUT_WINDOW_WIDTH),
                 win_height = glutGet(GLUT_WINDOW_HEIGHT);
     win_aspect = (float)win_width/(float)win_height;
     glClearColor(1.0, 1.0, 1.0, 0);
     glDisable(GL_DEPTH_TEST);
     glClear(GL_COLOR_BUFFER_BIT);
     glViewport(0, 0, win_width, win_height);
     glMatrixMode(GL_PROJECTION);
     glLoadIdentity();
     glOrtho(-win_aspect, win_aspect, -1, 1, -1, 1);
     c_draw();
     b_draw();
     p_draw();
     life = '0' + lives;
     if(started && lives > 0)
                c_move();
     glFlush();
     glutSwapBuffers();
     glutPostRedisplay();
}
void GameLogic()
{  
      if(all_gone())
      {
                         x_pos = 0;
                         y_pos = -0.7;
                         LEVEL++;
                         for(int a = 0; a < BRICK_ROW; a++)
                         {
                                 for(int b = 0; b <BRICK_COL; b++)
                                 {
                                         show[a][b] = true;
                                 }
                         }
                         phit_center = false, 
                         phit_corner = false,
                         game_over   = false,
                         RIGHT       = true,
                         LEFT        = false,
                         UP          = true,
                         DOWN        = false,
                         started     = false,
                         hit         = false;
                         SET_BRICKS(LEVEL);
                         Set_Level(LEVEL);
      }         
      if(x_pos >= win_aspect)
      {
               RIGHT = 0;
               LEFT = 1;
      }
      else if(x_pos <= -win_aspect)
      {
           RIGHT = 1;
           LEFT = 0;
      }
      if(y_pos >= 1-RADIUS || hit )
      {
                  UP = 0;
                  DOWN = 1;
      }
      else if(y_pos <= -1+RADIUS || hit )
      {
           UP = 1;
           DOWN = 0;
      }
      hit = false;
      int flag = 1;
      for(int a = 0; a < BRICK_COL; a++)
      {
             for(int b =0; b < BRICK_ROW; b++)
             {
                     if(x_pos >= x_brick[b][a]*win_aspect && x_pos <= (x_brick[b][a] + 0.2)*win_aspect)
                     {
                              if(y_pos <= y_brick[b][a] && y_pos >= y_brick[b][a] - 0.1)
                              {
                                       if(show[b][a] == 1)
                                       {
                                                     show[b][a] = 0;
                                                     flag = 0;
                                                     hit = true;
                                                     break;
                                       }
                              }
                     }
             }
             if(flag == 0)
                     break;
      }
      phit_corner = false;
      phit_center = false;
      if(x_pos <= (P_XPOS + P_LENGTH - 0.05)&& x_pos >= (P_XPOS - P_LENGTH - 0.05))
      {
              if(y_pos <= P_YPOS)
              {
                       phit_center = true;
              }
      }
      else if((x_pos >=(P_XPOS + P_LENGTH - 0.05) && x_pos <= (P_XPOS + P_LENGTH)) || (x_pos <= (P_XPOS - P_LENGTH + 0.05) && x_pos >= P_XPOS - P_LENGTH))
      {
               if(y_pos <= P_YPOS)
               {
                        phit_corner = true;
               }
      }
      if(phit_center)
      {
                     DOWN = false;
                     UP   = true;
      }
      if(phit_corner)
      {
                     if(LEFT)
                     {
                             LEFT  = false;
                             RIGHT = true;
                     }
                     else
                     {
                         RIGHT = false;
                         LEFT  = true;
                     }
                     UP   = false;
                     DOWN = true;
      }
      if(crashed())
      {           
                 x_pos = 0;
                 y_pos = -0.7;
                 started = false;
                 UP      = true;
                 RIGHT   = true;
                 DOWN    = false;
                 LEFT    = false;    
      }
      BallLoop();     
}
void ArrowKeys(int key, int x, int y)
{
     if(key==GLUT_KEY_LEFT && P_XPOS >= -0.9*win_aspect)
     {
                           for(float a = 0; a < 0.05; a+= 0.001)
                           {
                                      P_XPOS -=0.002;
                                      GameLogic();
                           }
                           if(!started)
                           started = true;
     }
     if(key==GLUT_KEY_RIGHT && P_XPOS <= 0.9*win_aspect)
     {
                            for(float a = 0; a < 0.05; a+= 0.001)
                            {
                                      P_XPOS +=0.002;
                                      GameLogic();
                            }
                            if(!started)
                            started = true;
     }
}
void Init_Game()
{

    int c = 0;
    for(float a = -0.94; c < BRICK_COL; a+=0.21)
    {         

              for(int b = 0; b <= BRICK_ROW; b++)
              {
                      x_brick[b][c] = a;

              }
              c++;
    }
    c = 0;
    for(float a = 0.99; c < BRICK_ROW; a-=0.11)
    {
              for(int  b = 0; b < BRICK_COL; b++)
              {
                       y_brick[c][b] = a;
              }
              c++;
    }
}
void set_speed()
{
    clock_t start = clock();
    for(int a = 1; a < 99999999LLU; a+= 1)
    {
            ;
    }
    clock_t end = clock();
    SPEED = (double)(end - start)/CLOCKS_PER_SEC;
    SPEED /= 800;
 }
int main(int argc, char **argv)
{
    set_speed();
    Init_Game();
    SET_BRICKS(LEVEL);
    Set_Level(LEVEL);
    glutInit(&argc, argv);
    glutInitDisplayMode(GLUT_DEPTH | GLUT_DOUBLE | GLUT_RGBA);
    glutInitWindowPosition(0,0);
    glutInitWindowSize(WIDTH,HEIGHT);                    
    glutCreateWindow("Brick Breaker - By Viraj");
    glutKeyboardFunc(user_input);
    glutSpecialFunc(ArrowKeys);
    glutIdleFunc(GameLogic);
    glutDisplayFunc(BallLoop);
    glutMainLoop(); 
    return 0;
}

请看一看我作为原始问题答案发布的代码的更正版本

为了简单起见,再次在此处重新发布GLFW版本:

#include <GL/glfw.h>

#include <stdlib.h>
#include <math.h>
#include <time.h>

using namespace std;

#define RADIUS 0.025

#define RATIO (4./3.)

bool show[5][10];
float x_brick[4][9];
float y_brick[4][9];

const float SpeedFactor = 1.;

float paddle_x = 0;
float paddle_y = -0.8;
float paddle_speed = 0;
const float PaddleSpeedFactor = 3.;

bool phit_center = false, phit_corner = false;
bool game_over = false;

float speed_x = 0.;
float speed_y = 0.;

float x_pos;
float y_pos;
int lifes = 0;

void draw_bricks()
{
    glColor3f(1.0, 0.0, 0.0);
    glBegin(GL_QUADS);
    for (int a = 0; a < 9; a++) {
        for (int b = 0; b < 4; b++) {
            if (show[b][a] == 1) {
                glVertex2f(x_brick[b][a], y_brick[b][a]);
                glVertex2f(x_brick[b][a], y_brick[b][a] - 0.10);
                glVertex2f(x_brick[b][a] + 0.2,
                       y_brick[b][a] - 0.10);
                glVertex2f(x_brick[b][a] + 0.2, y_brick[b][a]);
            }
        }
    }
    glEnd();
}

void ball_draw()
{
    glColor3f(0.0, 0.0, 0.0);
    glBegin(GL_TRIANGLE_FAN);
    glVertex2f(x_pos, y_pos);
    for (float angle = 0; angle < (10); angle += 0.01) {
        glVertex2f((x_pos + sin(angle) * RADIUS),
               (y_pos + (cos(angle)) * RADIUS));
    }
    glEnd();
}

bool brick_hit()
{
    for (int a = 0; a < 10; a++) {
        for (int b = 0; b < 4; b++) {
            if (x_pos >= x_brick[b][a]
                && x_pos <= x_brick[b][a] + 0.2) {
                if (y_pos <= y_brick[b][a]
                    && y_pos >= y_brick[b][a] - 0.1) {
                    if (show[b][a] == 1) {
                        show[b][a] = 0;
                        return true;
                    }
                }
            }
        }
    }
    return false;
}

bool crashed()
{
    if (y_pos < paddle_y - 0.05)
        return true;

    return false;
}

void paddle_hit()
{
    phit_corner = false;
    phit_center = false;
    if (x_pos <= paddle_x + 0.13 && x_pos >= paddle_x - 0.13) {
        if (y_pos <= paddle_y) {
            phit_center = true;
        }
    } else if ((x_pos >= paddle_x + 0.13 && x_pos <= paddle_x + 0.2) ||
           (x_pos <= paddle_x - 0.13 && x_pos >= paddle_x - 0.2)) {
        if (y_pos <= paddle_y) {
            phit_corner = true;
        }
    }
}

void paddle_move(float dT)
{

    if (paddle_x < RATIO && paddle_x > -RATIO)
        paddle_x += paddle_speed * PaddleSpeedFactor * dT;

    if (paddle_x > 1.) {
        paddle_x = 1.;
        paddle_speed = 0.;
    }

    if (paddle_x < -1.) {
        paddle_x = -1.;
        paddle_speed = 0.;
    }
}

void ball_move(float dT)
{
    x_pos += speed_x * dT;
    y_pos += speed_y * dT;

    if (brick_hit()) {
        speed_y *= -1;
    }

    if (x_pos >= (RATIO - RADIUS) || x_pos <= (-RATIO + RADIUS)) {
        speed_x *= -1;
    }

    if (y_pos >= (1. - RADIUS)) {
        speed_y *= -1;
    }

    paddle_hit();
    if (phit_center) {
        speed_y *= -1;
    speed_x += 0.5 * paddle_speed;
    }
    if (phit_corner) {
        speed_x = -speed_x + 0.2 * paddle_speed;
        speed_y *= -1;
    }

    if( (speed_x * speed_x + speed_y * speed_y) > 0.001 ) {
        float k = 1./sqrt(speed_x * speed_x + speed_y * speed_y);
        speed_x *= k;
        speed_y *= k;
    }
}

void paddle_draw()
{
    glColor3f(0.0, 0.0, 0.0);
    glBegin(GL_QUADS);
    glVertex2f(paddle_x - 0.2, paddle_y);
    glVertex2f(paddle_x + 0.2, paddle_y);
    glVertex2f(paddle_x + 0.2, paddle_y - 0.05);
    glVertex2f(paddle_x - 0.2, paddle_y - 0.05);
    glEnd();
}

void set_xy();

void reset_game()
{
    set_xy();
    lifes = 3;
    speed_x = 0;
    speed_y = 0;
    x_pos = 0;
    y_pos = -0.7;
    paddle_speed = 0;
    paddle_x = 0;
}

void step_game(float dT)
{
    if(!lifes)
        return;

    paddle_move(dT * SpeedFactor);
    ball_move(dT * SpeedFactor);

    if (crashed()) {
        lifes--;
        speed_x = 0;
        speed_y = 0;
        x_pos = 0;
        y_pos = -0.7;
    }
}

static float frandom(float a, float b)
{
    return a + (b - a) * (float)random() / (float)RAND_MAX;
}

void launch_ball()
{
    if(!lifes)
        return;

    speed_y = 1.;
    speed_x = frandom(-1., 1.);

    float k = 1./sqrt(speed_x * speed_x + speed_y + speed_y);
    speed_x *= k;
    speed_y *= k;
}

void keyboard(int key, int action)
{
    switch(key) 
    {
    case GLFW_KEY_ENTER:
        launch_ball();
        break;

    case GLFW_KEY_ESC:
        reset_game();
        break;

    case GLFW_KEY_LEFT:
        switch(action) {
        case GLFW_PRESS:
            paddle_speed = -1.;
            break;

        case GLFW_RELEASE:
            paddle_speed = 0;
            break;
        } break;

    case GLFW_KEY_RIGHT:
        switch(action) {
        case GLFW_PRESS:
            paddle_speed = 1.;
            break;

        case GLFW_RELEASE:
            paddle_speed = 0;
            break;
        } break;
    }
}

void set_xy()
{
    for (int a = 0; a < 5; a++) {
        for (int b = 0; b < 10; b++) {
            show[a][b] = 1;
        }
    }
    int c = 0;
    for (float a = -0.94; c <= 8; a += 0.21, c++) {
        for (int b = 0; b <= 5; b++) {
            x_brick[b][c] = a;

        }
    }
    int d = 0;
    for (float s = 0.99; d <= 3; s -= 0.11, d++) {
        for (int r = 0; r < 9; r++) {
            y_brick[d][r] = s;
        }
    }
}

float display()
{
    int win_width;
    int win_height;
    glfwGetWindowSize(&win_width, &win_height);
    const float win_aspect = (float)win_width / (float)win_height;

    glfwSetTime(0.);

    glViewport(0, 0, win_width, win_height);

    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
    if (win_aspect > RATIO) {
        glOrtho(-win_aspect, win_aspect, -1., 1., -1., 1.);
    } else {
        glOrtho(-RATIO, RATIO, -RATIO / win_aspect, RATIO / win_aspect,
            -1., 1.);
    }

    glMatrixMode(GL_MODELVIEW);

    glClearColor(0., 0., 1., 1.);
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

    glBegin(GL_QUADS);
    glColor3f(1, 1, 1);
    glVertex2f(-RATIO, -1);
    glVertex2f(RATIO, -1);
    glVertex2f(RATIO, 1);
    glVertex2f(-RATIO, 1);
    glEnd();

    draw_bricks();
    paddle_draw();

    ball_draw();

    glfwSwapBuffers();
    return glfwGetTime();
}

int main(int argc, char **argv)
{
    srandom(time(0));

    set_xy();

    if( GL_FALSE == glfwInit() )
        return -1;

    if( GL_FALSE == glfwOpenWindow(800, 600, 8, 8, 8, 8, 0, 0, GLFW_WINDOW) )
        return -2;

    glfwSetWindowTitle("Viraj's Brick Breaker - GLFW version by datenwolf");
    glfwSetKeyCallback(keyboard);

    reset_game();

    while( glfwGetWindowParam(GLFW_OPENED) ) {
        glfwPollEvents();
        float const dT = display();
        step_game(dT);
    }

    glfwTerminate();

    return 0;
}
该内部for循环将使桨叶对关键点做出反应,并在该动画发生时,所有进一步的用户输入将堆积起来,导致奇怪的运动。永远不要这样做。在输入处理程序中,设置一些状态变量,这些变量会影响空闲循环中的游戏逻辑。但永远不要直接从输入处理程序设置动画


请看一下我的代码,编译它,执行它。并尝试理解游戏逻辑、渲染和输入处理之间的分离。

我听说不建议使用。好吧,这是你的问题。如果你使用的工具坏了,无法进行调试,请使用一个没有坏的工具。不要使用Dev-C++,这是一堆废话,不是IDE。@viraj:除了Dev-C++,什么都可以。我发布的链接为您提供了很多其他选择,老实说,如果您可以选择一个因其配色方案而不喜欢的编辑器,还是一个没有调试器的编辑器,请选择第一个。说我选择使用一个坏的工具是因为我最喜欢它的配色方案,这意味着我甚至没有试着调试我的代码,这反过来意味着这里的人不太可能想帮助你。如果您需要帮助设置Eclipse,请在下面询问。不要只是说我会继续使用不起作用的IDEinstead@viraj:除了Dev废话以外的任何东西。C::B和Eclipse都是不错的选择。Visual Studio也是。或者是任何像样的文本编辑器,真的。你怎么猜到的?我还在学校,所以我先学习QBASIC,然后再看VisualBasic,然后再转到C++。关于编码风格,我想你是指我存储行空间和使用{}的方式吧?此外,您在聊天时也停止了回复。我尝试在DeV C++上使用GLFW,并在DeVCPP上安装DEV包,但每次编译代码时,它都会成功编译,但不会出现窗口。大约两分钟后,防病毒程序将其标记为病毒。回到程序,我试图做与你的重置游戏功能相同的事情,但是在内部。它似乎不起作用。我所说的编码风格是指如何使用变量、函数等。您的代码的结构类似于基本程序。许多C代码编写者会认为这是一种侮辱;直到现在,我才对聊天做出反应,因为我是离线的。@viraj:最能说明问题的迹象是,sonebody在思想上陷入了一个基本世界,那就是使用全局变量。虽然将全局状态放在全局变量中没有错,但函数之间传递的数据应该通过参数传递。
void ArrowKeys(int key, int x, int y)
{
     if(key==GLUT_KEY_LEFT && P_XPOS >= -0.9*win_aspect)
     {
                       for(float a = 0; a < 0.05; a+= 0.001)
                       {
                                  P_XPOS -=0.002;
                                  GameLogic();
                       }