Рисование GLBatch несколько раз в разных местах

Я использую GLBatch из библиотеки GLTools, чтобы нарисовать тетраэдр. Я хочу нарисовать тетраэдр несколько раз в разных местах, чтобы нарисовать Серпинского-Тетраэдра. Создание геометрии и рисование конуса прекрасно работает для одного экземпляра тетраэдра, но я хочу нарисовать тетраэдр несколько раз в разных местах. призвание geometry.Draw() несколько раз (с разными матрицами вида модели) не работает. Конус все еще нарисован только один раз.

Как я могу нарисовать GLBatch несколько раз?

Вот мой код:

GLBatch geometry;

// This is called once on initialization.    
void CreateTetrahedron()
{
    geometry.Begin(GL_TRIANGLE_STRIP, 6);

    geometry.Color4f(1, 0, 0, 1);
    geometry.Vertex3f(0, 1, 0);

    geometry.Color4f(1, 0, 0, 1);
    geometry.Vertex3f(-0.5f, 0, 0.5f);

    geometry.Color4f(1, 0, 0, 1);
    geometry.Vertex3f(0.5f, 0, 0.5f);

    if (recursionLevel < 3)
    {
        geometry.Color4f(0, 1, 0, 1);
        geometry.Vertex3f(0, 0, -0.7f);

        geometry.Color4f(0, 0, 1, 1);
        geometry.Vertex3f(0, 1, 0);

        geometry.Color4f(1, 1, 1, 1);
        geometry.Vertex3f(-0.5f, 0, 0.5f);
    }

    geometry.End();
}
// This is where I want to draw it. The function is recursive, and thus the geometry should be drawn multiple times with different matrices.
void DrawSierpinskiTetrahedron(UINT32 level)
{
    if (level == 0)
    {
        geometry.Draw();
    }
    else
    {
        modelViewMatrix.PushMatrix();
        modelViewMatrix.Scale(0.5f, 0.5f, 0.5f);

        modelViewMatrix.PushMatrix();
        modelViewMatrix.Translate(0, 1, 0);
        DrawSierpinskiTetrahedron(level - 1);
        modelViewMatrix.PopMatrix();

        modelViewMatrix.PushMatrix();
        modelViewMatrix.Translate(-0.5f, 0, 0.5f);
        DrawSierpinskiTetrahedron(level - 1);
        modelViewMatrix.PopMatrix();

        modelViewMatrix.PushMatrix();
        modelViewMatrix.Translate(0.5f, 0, 0.5f);
        DrawSierpinskiTetrahedron(level - 1);
        modelViewMatrix.PopMatrix();

        modelViewMatrix.PushMatrix();
        modelViewMatrix.Translate(0, 0, -0.7f);
        DrawSierpinskiTetrahedron(level - 1);
        modelViewMatrix.PopMatrix();

        modelViewMatrix.PopMatrix();
    }
}

void RenderScene(void)
{
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

    modelViewMatrix.PushMatrix();

    // Camera Translation
    modelViewMatrix.Translate(xTrans, yTrans, zTrans);

    // Model Translation, Rotatation und Scale
    glm::mat4 trans = glm::translate(glm::mat4(), translation);
    modelViewMatrix.MultMatrix(glm::value_ptr(trans));
    glm::mat4 rot = glm::mat4_cast(rotation);
    modelViewMatrix.MultMatrix(glm::value_ptr(rot));
    glm::mat4 sc = glm::scale(glm::mat4(), scale);
    modelViewMatrix.MultMatrix(glm::value_ptr(sc));

    // Set the shader for rendering
    shaderManager.UseStockShader(GLT_SHADER_FLAT_ATTRIBUTES, transformPipeline.GetModelViewProjectionMatrix());

    if (recursionLevel < 0)
    {
        recursionLevel = 0;
    }
    if (recursionLevel > 5)
    {
        recursionLevel = 5;
    }

    DrawSierpinskiTetrahedron(recursionLevel);

    gltCheckErrors(0);
    modelViewMatrix.PopMatrix();

    TwDraw();
    glutSwapBuffers();
    glutPostRedisplay();
}

// Initialize rendering context
void SetupRC()
{
    glClearColor(0.0f, 0.0f, 0.0f, 1.0f);

    glFrontFace(GL_CW);
    glEnable(GL_CULL_FACE);
    glEnable(GL_DEPTH_TEST);

    shaderManager.InitializeStockShaders();
    transformPipeline.SetMatrixStacks(modelViewMatrix,projectionMatrix);

    // Create the geometry
    CreateTetrahedron();

    InitGUI();
}

Обновить:

Выполнение следующего не масштабирует тетраэдр.

modelViewMatrix.PushMatrix();
modelViewMatrix.Scale(1000, 1000, 1000);
geometry.Draw();
modelViewMatrix.PopMatrix();

1 ответ

Решение

GLMatrixStack - это класс, который предоставляет матричный стек и операции над верхней матрицей стека.

Класс GLShaderManager может загружать шейдер и обрабатывает установку единообразных переменных шейдера.

Программа шейдера преобразует координаты вершины сетки с помощью матрицы вида модели. Это приводит к тому, что mseh может отображаться в разных местах и ​​с разными ориентациями в сцене. Если матрица вида модели изменяется, она должна быть установлена ​​на соответствующую унифицированную переменную в программе шейдера, чтобы изменения работали. Это можно сделать, позвонив GLShaderManager::UseStockShader перед рисованием сетки.

Адаптируйте ваш код так:

void DrawSierpinskiTetrahedron(UINT32 level)
{
    if (level == 0)
    {
        shaderManager.UseStockShader(GLT_SHADER_FLAT_ATTRIBUTES, transformPipeline.GetModelViewProjectionMatrix());
        geometry.Draw();
    }
    else
    {
        modelViewMatrix.PushMatrix();
        modelViewMatrix.Scale(0.5f, 0.5f, 0.5f);

        modelViewMatrix.PushMatrix();
        modelViewMatrix.Translate(0, 1, 0);
        DrawSierpinskiTetrahedron(level - 1);
        modelViewMatrix.PopMatrix();

        modelViewMatrix.PushMatrix();
        modelViewMatrix.Translate(-0.5f, 0, 0.5f);
        DrawSierpinskiTetrahedron(level - 1);
        modelViewMatrix.PopMatrix();

        modelViewMatrix.PushMatrix();
        modelViewMatrix.Translate(0.5f, 0, 0.5f);
        DrawSierpinskiTetrahedron(level - 1);
        modelViewMatrix.PopMatrix();

        modelViewMatrix.PushMatrix();
        modelViewMatrix.Translate(0, 0, -0.7f);
        DrawSierpinskiTetrahedron(level - 1);
        modelViewMatrix.PopMatrix();

        modelViewMatrix.PopMatrix();
    }
}
Другие вопросы по тегам