Also habe ich mir auf youtube einen kleinen Intro-Kurs angeschaut, um die Grundlagen von OpenGL zu erlernen und lernte Dinge wie ein Dreieck und eine einfache Kamera-Klasse, etc. Ich wollte versuchen, eine Voxel-Engine zu entwickeln so offensichtlich war das erste, was ich mir vorstellen konnte, ein einfacher Würfel, den ich irgendwann replizieren konnte. Mein Problem ist jedoch, dass wenn ich gehe, um die Vertices und Dreiecke zu rendern, scheinen sie in einem Durcheinander zu sein, das nicht dem ähnelt, was ich hart in der Cube-Klasse codiert habe. Ich weiß, dass 0,0 die Mitte des Bildschirms ist; 1 in der x-Achse ist das Recht; -1 ist die linke; 1 in der y-Achse ist die Spitze und -1 ist die Unterseite. Wenn ich jedoch durch meine Ecken und Dreiecke zum Eckenpuffer sende, scheint es etwas völlig anderes zu machen. Es ist wahrscheinlich ein wirklich dummer Fehler von meiner Seite.Inverted X Axis OpenGL
Cube::Cube()
{
m_vertices[0] = Vertex(glm::vec3(-0.5, -0.5, 0));
m_vertices[1] = Vertex(glm::vec3(-0.5, 0.5, 0));
m_vertices[2] = Vertex(glm::vec3(0.5, 0.5, 0));
m_vertices[3] = Vertex(glm::vec3(0.5, -0.5, 0));
m_vertices[4] = Vertex(glm::vec3(-0.5, -0.5, 1));
m_vertices[5] = Vertex(glm::vec3(-0.5, 0.5, 1));
m_vertices[6] = Vertex(glm::vec3(0.5, 0.5, 1));
m_vertices[7] = Vertex(glm::vec3(0.5, -0.5, 1));
m_triangles[0] = Triangle(0, 1, 2); //Front
//m_triangles[1] = Triangle(0, 2, 3); //Front
//m_triangles[2] = Triangle(1, 5, 6); //Top
//m_triangles[3] = Triangle(1, 6, 2); //Top
//m_triangles[4] = Triangle(3, 5, 4); //Left
//m_triangles[5] = Triangle(3, 5, 4); //Left
//m_triangles[6] = Triangle(3, 2, 7); //Right
//m_triangles[7] = Triangle(3, 3, 7); //Right
//m_triangles[8] = Triangle(7, 6, 4); //Back
//m_triangles[9] = Triangle(5, 6, 7); //Back
//m_triangles[10] = Triangle(0, 4, 7); //Bottom
//m_triangles[11] = Triangle(0, 3, 7); //Bottom
}
void Cube::Render()
{
Draw(m_vertices, sizeof(m_vertices)/sizeof(m_vertices[0]), m_triangles, (sizeof(m_triangles)/sizeof(m_triangles[0])));
}
Die Funktion draw von meiner Mesh-Klasse geerbt
void Mesh::Draw(Vertex* vertices, unsigned int numVertices, Triangle* triangles, unsigned int numTriangles)
{
//Array of indices
std::vector<unsigned int> indices;
for (int i = 0; i < numTriangles; i++)
{
indices.push_back(triangles[i].GetTriangle()[0]);
indices.push_back(triangles[i].GetTriangle()[1]);
indices.push_back(triangles[i].GetTriangle()[2]);
}
//How many vertices to draw
m_drawCount = indices.size();
//Generate and bind vertex array
glGenVertexArrays(1, &m_vertexArrayObject);
glBindVertexArray(m_vertexArrayObject);
//Generate and bind buffers
glGenBuffers(NUM_BUFFERS, m_vertexArrayBuffers);
glBindBuffer(GL_ARRAY_BUFFER, m_vertexArrayBuffers[POSITION_VB]);
//Write vertex data to the buffer
glBufferData(GL_ARRAY_BUFFER, numVertices * sizeof(vertices[0]), &vertices[0], GL_STATIC_DRAW);
//Only one attribute for the vertex data
glEnableVertexAttribArray(0);
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 0, 0);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_vertexArrayBuffers[INDEX_VB]);
//Write vertex data to the buffer
glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indices[0]) * indices.size(), &indices[0], GL_STATIC_DRAW);
//Unbind vertex array
glBindVertexArray(0);
glBindVertexArray(m_vertexArrayObject);
glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
glDrawElements(GL_TRIANGLES, m_drawCount, GL_UNSIGNED_INT, 0);
glBindVertexArray(0);
}
Vertex und Dreieck structs in mesh.h
struct Vertex
{
public:
//Constructor
Vertex()
{
}
//Constructor
Vertex(const glm::vec3& pos)
{
//Set vertex position
this->m_pos = pos;
}
protected:
private:
//Vertex position
glm::vec3 m_pos;
};
struct Triangle
{
public:
//Constructor
Triangle()
{
}
//Constructor
Triangle(int point1, int point2, int point3)
{
SetTriangle(point1, point2, point3);
}
int* GetTriangle()
{
return m_points;
}
void SetTriangle(int point1, int point2, int point3)
{
m_points[0] = point1;
m_points[1] = point2;
m_points[2] = point3;
}
protected:
private:
int m_points[3];
};
Kamerafunktionen
Camera::Camera(const glm::vec3 pos, float fov, float aspect, float zNear, float zFar)
{
m_perspectiveMatrix = glm::perspective(fov, aspect, zNear, zFar);
m_pos = pos;
m_forward = glm::vec3(0, 0, 1);
m_up = glm::vec3(0, 1, 0);
}
glm::mat4 Camera::GetViewProjection() const
{
return m_perspectiveMatrix * glm::lookAt(m_pos, m_pos + m_forward, m_up);
}
Hinweis in der das Cube-Konstruktor bin ich nur ein Dreieck zu schaffen, die unten links, oben links sein sollten, oben rechts noch ist dies das Ergebnis:
Ein weiterer Hinweis ist, dass meine Kamera Drehung ab und zu sein scheint. Wenn Sie die Y-Drehung ändern, wird sie tatsächlich auf der X-Achse gedreht und die X-Drehung ändert sich auf der Y-Achse.
Auch wenn jemand einen besseren Weg zum Erstellen und Rendern des Cubes hätte, wäre ich dankbar. Sobald ich das tun kann, werde ich wahrscheinlich in letsmakeavoxelengine Tutorials schauen.
Edit: Es fühlt sich an wie die x- und y-Achse invertiert sind. Ich könnte einfach alle meine Funktionen invertieren, um dem entgegenzuwirken, aber das ist irgendwie ein hacky Weg um es herum und es repariert immer noch nicht das zugrunde liegende Problem, das später mehr Ärger verursachen könnte.
Edit2: Transform.h
#pragma once
#include <glm\glm.hpp>
#include <glm\gtx\transform.hpp>
#include "Camera.h"
struct Transform
{
public:
//Constructor
Transform(const glm::vec3& pos = glm::vec3(), const glm::vec3& rot = glm::vec3(), const glm::vec3& scale = glm::vec3(1.0f, 1.0f, 1.0f))
{
this->m_pos = pos;
this->m_rot = rot;
this->m_scale = scale;
}
//Get the model matrix
inline glm::mat4 GetModelMatrix() const
{
//Create all the transform matrices
//Position matrix
glm::mat4 posMatrix = glm::translate(m_pos);
//Scale matrix
glm::mat4 scaleMatrix = glm::scale(m_scale);
//Rotation matrix X
glm::mat4 rotXMatrix = glm::rotate(m_rot.x, glm::vec3(1.0f, 0.0f, 0.0f));
//Rotation matrix Y
glm::mat4 rotYMatrix = glm::rotate(m_rot.y, glm::vec3(0.0f, 1.0f, 0.0f));
//Rotation matrix Z
glm::mat4 rotZMatrix = glm::rotate(m_rot.z, glm::vec3(0.0f, 0.0f, 1.0f));
//Combined rotation matrix
glm::mat4 rotMatrix = rotXMatrix * rotYMatrix * rotZMatrix;
return posMatrix * rotMatrix * scaleMatrix;
}
inline glm::mat4 GetMVP(const Camera& camera) const
{
glm::mat4 ViewProjection = camera.GetViewProjection();
glm::mat4 ModelMatrix = GetModelMatrix();
return ViewProjection * ModelMatrix;//camera.GetViewProjection() * GetModel();
}
//Get position
inline glm::vec3* GetPosition() { return &m_pos; }
//Get rotation
inline glm::vec3* GetRotation() { return &m_rot; }
//Get scale
inline glm::vec3* GetScale() { return &m_scale; }
//Set Position
inline void SetPosition(const glm::vec3& pos) { this->m_pos = pos; }
//Set Rotation
inline void SetRotation(const glm::vec3& rot) { this->m_rot = rot; }
//Set Scale
inline void SetScale(const glm::vec3& scale) { this->m_scale = scale; }
private:
//Transform position
glm::vec3 m_pos;
//Transform rotation
glm::vec3 m_rot;
//Transform scale
glm::vec3 m_scale;
};
Cube, Transformieren und Kamera-Anrufe in main.cpp:
Cube cube;
Transform transform;
Camera camera(glm::vec3(0.0f, 0.0f, -3.0f), 70.0f, (float)display.GetWidth()/(float)display.GetHeight(), 0.01f, 100.0f);
Edit3: 100% invertiert auf X-Achse. Neuer cube.cpp code:
m_vertices[0] = Vertex(glm::vec3(-0.5, -0.5, 0)); //BottomLeftFront
m_vertices[1] = Vertex(glm::vec3(-0.5, 0.5, 0)); //TopLeftFront
m_vertices[2] = Vertex(glm::vec3(0.5, 0.5, 0)); //TopRightFront
m_vertices[3] = Vertex(glm::vec3(0.5, -0.5, 0)); //BottomRightFront
m_vertices[4] = Vertex(glm::vec3(-0.5, -0.5, 1)); //BottomLeftBack
m_vertices[5] = Vertex(glm::vec3(-0.5, 0.5, 1)); //TopLeftBack
m_vertices[6] = Vertex(glm::vec3(0.5, 0.5, 1)); //TopRightBack
m_vertices[7] = Vertex(glm::vec3(0.5, -0.5, 1)); //BottomRightBack
m_triangles[0] = Triangle(0, 1, 2); //Front
m_triangles[1] = Triangle(0, 2, 3); //Front
//m_triangles[2] = Triangle(1, 5, 6); //Top
//m_triangles[3] = Triangle(1, 6, 2); //Top
m_triangles[4] = Triangle(3, 5, 4); //Left //BottomLeftFront, TopRightBack, BottomRightBack
//m_triangles[5] = Triangle(3, 5, 4); //Left
//m_triangles[6] = Triangle(3, 2, 7); //Right
//m_triangles[7] = Triangle(3, 3, 7); //Right
//m_triangles[8] = Triangle(7, 6, 4); //Back
//m_triangles[9] = Triangle(5, 6, 7); //Back
//m_triangles[10] = Triangle(0, 4, 7); //Bottom
//m_triangles[11] = Triangle(0, 3, 7); //Bottom
Ich habe einen Kommentar neben das neue Dreieck geschrieben, das Ihnen sagt, was die tatsächlichen resultierenden Dreieckspunkte waren. Das Dreieck, das ich eingestellt habe, sollte BottomRightFront, TopLeftBack, BottomLeftBack entsprechend dem Code sein. Ich werde auch einen Screenshot hinzufügen, wie es aussieht.
Können Sie ein vollständiges Beispiel bereitstellen, das kompiliert wird? Herkömmlich verwenden wir ein Rechtssystem, wenn also die X-Achse nach rechts zeigt und die Y-Achse nach oben zeigt, dann zeigt die Z-Achse nach hinten (zur Kamera hin); aber Ihr zNear und zFar sind positiv, und Ihr m_forwards ist (0 0 1) und nicht (0 0 -1); Ist das eine gute Sache? – Buster
Ich denke, es muss eine gute Sache sein, denn wenn ich mir die Quelle aus den Videos ansehe, die ich gesehen habe, scheint es dasselbe zu sein. Und wie kann ich Ihnen das Projekt am besten zusenden? Google Drive? Quelle für die Kamera-Klasse aus den Videos hier btw: https://github.com/BennyQBD/ModernOpenGLTutorial/blob/master/camera.h – therealkf
Hat Ihre "pos" eine negative z-Koordinate? Wenn nicht, dann ist das vielleicht das Problem. Aber vielleicht auch nicht, denn wenn das Problem genau das ist, dann würde ich erwarten, dass das Bild horizontal und vertikal gedreht wird. – Buster