You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在旧版OpenGL 2.4中程序化绘制(超/n维)立方体并单循环绘面

嘿,我懂你赶课赶得焦头烂额的感觉——OpenGL 2.4的固定管线本来就有点复古,还要用单个for循环搞定(超)立方体绘制,确实得抓准核心逻辑。刚好你已经摸到了二进制映射顶点的门道,咱们顺着这个思路往下走就行!

用单个for循环在OpenGL 2.4中绘制(超)立方体

核心逻辑拆解

你发现的二进制顶点映射是关键:n维立方体的每个顶点都对应一个n位二进制数——每一位代表一个维度的坐标,比如第k位为0时坐标取-1,为1时取1(你也可以换成0/1,只要统一规则就行)。

而n维立方体的所有面,本质是固定某一个维度的坐标为极值(+1或-1),然后遍历剩下n-1维的所有顶点组合,按顺序连接成闭合面。比如3维立方体的6个面,就是固定x/y/z分别为±1,每个面对应4个顶点(2^(3-1))。

要实现单个for循环,我们可以把「维度」和「极值方向」合并到循环变量里:n维立方体共有2n个面,循环变量从0到2n-1,前n个循环对应每个维度取+1,后n个对应取-1。

OpenGL 2.4代码实现(3维示例,可扩展到n维)

因为OpenGL 2.4是固定管线,我们用经典的立即模式glBegin()/glEnd()来绘制。下面的代码用单个外层for循环遍历所有面,完全贴合你的需求:

#include <GL/glut.h>
#include <math.h>

const int DIMENSIONS = 3; // 改成4就是4维超立方体,需额外做投影
const float SCALE = 1.0f; // 立方体半边长,顶点坐标范围±SCALE

// 根据二进制数生成对应顶点坐标
void getVertex(int binary, float* vertex) {
    for (int i = 0; i < DIMENSIONS; i++) {
        vertex[i] = (binary & (1 << i)) ? SCALE : -SCALE;
    }
}

void display() {
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    glLoadIdentity();
    glRotatef(45.0f, 1.0f, 1.0f, 0.0f); // 旋转视角方便观察

    // 单个for循环覆盖所有2*DIMENSIONS个面
    for (int face = 0; face < 2 * DIMENSIONS; face++) {
        int fixed_dim = face % DIMENSIONS; // 当前要固定的维度
        float fixed_val = (face < DIMENSIONS) ? SCALE : -SCALE; // 固定的坐标值(+/-SCALE)

        glBegin(GL_QUADS); // 3维用四边形,n维需换成GL_POLYGON
        // 遍历剩余DIMENSIONS-1维的所有顶点组合(共2^(DIMENSIONS-1)个)
        for (int i = 0; i < (1 << (DIMENSIONS - 1)); i++) {
            float vertex[DIMENSIONS];
            int bit_pos = 0;
            // 构造顶点:固定维度设为fixed_val,其余维度用i的二进制位填充
            for (int dim = 0; dim < DIMENSIONS; dim++) {
                if (dim == fixed_dim) {
                    vertex[dim] = fixed_val;
                } else {
                    vertex[dim] = (i & (1 << bit_pos)) ? SCALE : -SCALE;
                    bit_pos++;
                }
            }
            // 给不同维度的面设置不同颜色(可选,方便区分)
            glColor3f((fixed_dim == 0) ? 1.0f : 0.0f, 
                      (fixed_dim == 1) ? 1.0f : 0.0f, 
                      (fixed_dim == 2) ? 1.0f : 0.0f);
            glVertex3fv(vertex); // 3维用glVertex3fv,n维需对应调整
        }
        glEnd();
    }

    glutSwapBuffers();
}

int main(int argc, char** argv) {
    glutInit(&argc, argv);
    glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH);
    glutInitWindowSize(800, 600);
    glutCreateWindow("Procedural Cube (OpenGL 2.4)");
    glEnable(GL_DEPTH_TEST);
    glutDisplayFunc(display);
    glutMainLoop();
    return 0;
}

扩展到n维超立方体的注意事项

  1. 投影处理:n>3时,超立方体无法直接在3D屏幕显示,需要做投影变换——比如丢弃某几个维度,或者用线性组合将n维坐标映射到3维空间。
  2. 绘制模式调整:n维立方体的面是n-1维超平面,需要把GL_QUADS换成GL_POLYGON,同时确保顶点按顺序连接(避免面被OpenGL判定为背面而不渲染)。
  3. 循环逻辑通用:不管n是多少,外层for循环始终遍历2n个面,内层遍历2^(n-1)个顶点,逻辑完全复用。

为什么这个循环能覆盖所有面?

循环变量face从0到2n-1,每个值对应一个「维度+方向」的组合:

  • 前n个face(0到n-1):对应第face个维度取+SCALE;
  • 后n个face(n到2n-1):对应第face%n个维度取-SCALE;
    每个面内的顶点遍历覆盖了剩余n-1维的所有二进制组合,确保没有遗漏任何顶点。

内容的提问来源于stack exchange,提问作者galex-713

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.22 08:19:11