简体   繁体   English

如何在同一屏幕上将OpenGL窗口分为多个窗口?

[英]How to divide an OpenGL window into multiple windows on the same screen?

I have a cube.c program which displays a cube that can be rotated using arrow keys. 我有一个cube.c程序,该程序显示可以使用箭头键旋转的多维数据集。 I want to divide the resulting window containing the cube to be divided into multiple(say 4) windows, so that each window contains a part of that cube (top-right, top-left, bottom-right, bottom-left) and each part responds to the rotation using arrow keys in the way they were supposed to when it was a single window. 我想将包含多维数据集的结果窗口划分为多个(例如4个)窗口,以便每个窗口都包含该多维数据集的一部分(右上,左上,右下,左下),每个零件使用箭头键来响应旋转,就像在单个窗口中那样。 So, if I press right arrow key, the cube should rotate right with corresponding changes visible on every window. 因此,如果我按向右箭头键,则多维数据集应向右旋转,并在每个窗口上可见相应的更改。 Could it be done? 能做到吗? Here's my cube.c : 这是我的cube.c

#include <stdio.h>
#include <stdarg.h>
#include <math.h>
#define GL_GLEXT_PROTOTYPES
#ifdef __APPLE__
#include <GLUT/glut.h>
#else
#include <GL/glut.h>
#endif

// ----------------------------------------------------------
// Function Prototypes
// ----------------------------------------------------------
void display();
void specialKeys();

// ----------------------------------------------------------
// Global Variables
// ----------------------------------------------------------
double rotate_y=0; 
double rotate_x=0;

// ----------------------------------------------------------
// display() Callback function
// ----------------------------------------------------------
void display(){

  //  Clear screen and Z-buffer
  glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT);

  // Reset transformations
  glLoadIdentity();


  // Rotate when user changes rotate_x and rotate_y
  glRotatef( rotate_x, 1.0, 0.0, 0.0 );
  glRotatef( rotate_y, 0.0, 1.0, 0.0 );


  //Multi-colored side - FRONT
  glBegin(GL_POLYGON);

  glColor3f( 1.0, 0.0, 0.0 );     glVertex3f(  0.5, -0.5, -0.5 );      // P1 is red
  glColor3f( 0.0, 1.0, 0.0 );     glVertex3f(  0.5,  0.5, -0.5 );      // P2 is green
  glColor3f( 0.0, 0.0, 1.0 );     glVertex3f( -0.5,  0.5, -0.5 );      // P3 is blue
  glColor3f( 1.0, 0.0, 1.0 );     glVertex3f( -0.5, -0.5, -0.5 );      // P4 is purple

  glEnd();

  // White side - BACK
  glBegin(GL_POLYGON);
  glColor3f(   1.0,  1.0, 1.0 );
  glVertex3f(  0.5, -0.5, 0.5 );
  glVertex3f(  0.5,  0.5, 0.5 );
  glVertex3f( -0.5,  0.5, 0.5 );
  glVertex3f( -0.5, -0.5, 0.5 );
  glEnd();

  // Purple side - RIGHT
  glBegin(GL_POLYGON);
  glColor3f(  1.0,  0.0,  1.0 );
  glVertex3f( 0.5, -0.5, -0.5 );
  glVertex3f( 0.5,  0.5, -0.5 );
  glVertex3f( 0.5,  0.5,  0.5 );
  glVertex3f( 0.5, -0.5,  0.5 );
  glEnd();

  // Green side - LEFT
  glBegin(GL_POLYGON);
  glColor3f(   0.0,  1.0,  0.0 );
  glVertex3f( -0.5, -0.5,  0.5 );
  glVertex3f( -0.5,  0.5,  0.5 );
  glVertex3f( -0.5,  0.5, -0.5 );
  glVertex3f( -0.5, -0.5, -0.5 );
  glEnd();

  // Blue side - TOP
  glBegin(GL_POLYGON);
  glColor3f(   0.0,  0.0,  1.0 );
  glVertex3f(  0.5,  0.5,  0.5 );
  glVertex3f(  0.5,  0.5, -0.5 );
  glVertex3f( -0.5,  0.5, -0.5 );
  glVertex3f( -0.5,  0.5,  0.5 );
  glEnd();

  // Red side - BOTTOM
  glBegin(GL_POLYGON);
  glColor3f(   1.0,  0.0,  0.0 );
  glVertex3f(  0.5, -0.5, -0.5 );
  glVertex3f(  0.5, -0.5,  0.5 );
  glVertex3f( -0.5, -0.5,  0.5 );
  glVertex3f( -0.5, -0.5, -0.5 );
  glEnd();

  glFlush();
  glutSwapBuffers();

}

// ----------------------------------------------------------
// specialKeys() Callback Function
// ----------------------------------------------------------
void specialKeys( int key, int x, int y ) {

  //  Right arrow - increase rotation by 5 degree
  if (key == GLUT_KEY_RIGHT)
    rotate_y += 5;

  //  Left arrow - decrease rotation by 5 degree
  else if (key == GLUT_KEY_LEFT)
    rotate_y -= 5;

  else if (key == GLUT_KEY_UP)
    rotate_x += 5;

  else if (key == GLUT_KEY_DOWN)
    rotate_x -= 5;

  //  Request display update
  glutPostRedisplay();

}

// ----------------------------------------------------------
// main() function
// ----------------------------------------------------------
int main(int argc, char* argv[]){

  //  Initialize GLUT and process user parameters
  glutInit(&argc,argv);

   //  Request double buffered true color window with Z-buffer
  glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH);

  // Create window
  glutCreateWindow("Rotating Cube");

  //  Enable Z-buffer depth test
  glEnable(GL_DEPTH_TEST);

  // Callback functions
  glutDisplayFunc(display);
  glutSpecialFunc(specialKeys);

  //  Pass control to GLUT for events
  glutMainLoop();

  return 0;
}

You can use libtr : 您可以使用libtr

The TR (Tile Rendering) library is an OpenGL utility library for doing tiled rendering. TR(Tile Rendering)库是用于执行平铺渲染的OpenGL实用程序库。 Tiled rendering is a technique for generating large images in pieces (tiles). 平铺渲染是一种用于生成大块图像(平铺)的技术。

TR is memory efficient; TR是高效的内存; arbitrarily large image files may be generated without allocating a full-sized image buffer in main memory. 无需在主存储器中分配完整大小的图像缓冲区即可生成任意大的图像文件。

Thanks for the edit. 感谢您的修改。 But I think you misunderstood the question. 但是我认为您误解了这个问题。 I don't want different faces of the cube on different windows. 我不想在不同的窗口上看到立方体的不同面。 I just want the main window displaying the cube to be split into different parts. 我只希望将显示多维数据集的主窗口拆分为不同的部分。 Something like this, but on same screen: geeks3d.com/public/jegx/200810/equalizer-0.5.5.jpg 像这样的东西,但是在同一屏幕上:geeks3d.com/public/jegx/200810/equalizer-0.5.5.jpg

The effect seen there can be achived by using a additional post-projection transformation composed of a scale and a translation. 可以通过使用由比例尺和平移组成的附加投影后转换来获得在那里看到的效果。 In classic fixed-function GL, such a matrix can simply be pre-multiplied to the projection matrix. 在经典固定功能GL中,此类矩阵可以简单地预乘到投影矩阵。 So you have to make sure that each window renders the same scene with all the same paramaters at the same time, with only this singe transformation beeing different for each window. 因此,您必须确保每个窗口在同一时间使用所有相同的参数渲染相同的场景,并且每个窗口的此唯一转换都不相同。

You will have to set up some kind of "total viewport" which would describe the axis-alingend rectangle the application view is to be extended. 您将必须设置某种“总视口”,该视口将描述要扩展应用程序视图的axis-alingend矩形。 And then, you can describe each window as sum axis-aligned rectangle with respect to that "total viewport". 然后,您可以相对于“总视口”将每个窗口描述为与轴对齐的矩形。 All you have to do is to get a scale factor for x and y, and a translation part. 您要做的就是获取x和y的比例因子以及平移部分。 Both are easie to find. 两者都很容易找到。

On thing you should know is that equalizer where your screenhot is of is a distributed rendering system , meaning the separate displays are (typically) driven by separate machines connected via network. 您应该知道的是,屏幕截图所在的均衡器分布式渲染系统 ,这意味着(通常)单独的显示器由通过网络连接的单独的机器驱动。 The general principle stays the same in this setup, but the "render the same things at the same time" part will become much harder. 在此设置中,一般原理保持不变,但是“同时渲染相同的事物”部分将变得更加困难。 But that stuff is beyond the scope of OpenGL itself. 但是这些东西超出了OpenGL本身的范围。 Software like the aforementioned equalizer actually helps you writing such applications. 像上述均衡器之类的软件实际上可以帮助您编写此类应用程序。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM