私は古いプロジェクトから新しいものへのコードをプロットしています。古いものはGLFWに基づいており、新しいものはGLFW3に基づいています。データを保存するために使用されるオブジェクトにはいくつかの変更が加えられました。一見すると最終結果は変更されるべきではありませんが、実際には歪んだイメージが生成されます。私はそれがMVP行列と関係があると考えています。この種のモデル歪みの原因は何ですか
the glitchのスクリーンショットそれは2つのボックスになるはず^ _^
drawメソッドが指定した基本色と(一瞬ハードコードされた)光源を用いて物体を描画:
glm::mat4 view, model, mvp, projection;
Mesh* mesh = (Mesh*)rm.Get(renderable->model);
Position* frame = (Position*)positions->Get(renderable->owner);
int program_id = ((Shader*)rm.Get(renderable->program))->program_id;
//vertex buffer
glEnableVertexAttribArray(0);
glBindBuffer(GL_ARRAY_BUFFER, mesh->vertex.buffer_id);
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 0, (void*)0);
//normal buffer
glEnableVertexAttribArray(1);
glBindBuffer(GL_ARRAY_BUFFER, mesh->normal.buffer_id);
glVertexAttribPointer(1, 3, GL_FLOAT, GL_TRUE, 0, (void*)0);
//texture uv buffer
glEnableVertexAttribArray(2);
glBindBuffer(GL_ARRAY_BUFFER, mesh->uv.buffer_id);
glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, 0, (void*)0);
glUseProgram(program_id);
view = camera->view;
projection = camera->projection;
mvp = projection * view * frame->mat4;
//set color
GLint base_color = glGetUniformLocation(program_id, "base_color");
if(base_color != -1)
glUniform3f(base_color, renderable->diffuse_color.r,
renderable->diffuse_color.g,
renderable->diffuse_color.b);
glm::vec4 light_pos = glm::vec4(0.0f, 5.0f, 0.0f, 1.0f);
glm::vec4 light = glm::normalize(glm::inverse(frame->mat4) * light_pos);
GLint light_position = glGetUniformLocation(program_id, "light_position");
if(light_position != -1) glUniform3f(light_position, light.x, light.y, light.z);
GLint light_ambient = glGetUniformLocation(program_id, "light_ambient");
if(light_ambient != -1) glUniform3f(light_ambient, 0.4f, 0.4f, 0.4f);
GLint light_diffuse = glGetUniformLocation(program_id, "light_diffuse");
if(light_diffuse != -1) glUniform3f(light_diffuse, 0.7f, 0.7f, 0.7f);
GLint mvp44 = glGetUniformLocation(program_id, "MVP");
glUniformMatrix4fv(mvp44, 1, GL_FALSE, &mvp[0][0]);
// Starting from vertex 0; 3 vertices total -> 1 triangle
glDrawArrays(GL_TRIANGLES, 0, mesh->vertex.size/3);
glDisableVertexAttribArray(0);
glDisableVertexAttribArray(1);
glDisableVertexAttribArray(2);
ビューおよび射影行列計算方法:
camera->target = glm::vec3(position->x_axis) - glm::vec3{1.0f, 0.0f, 0.0f};
camera->view = glm::lookAt(glm::vec3(position->position), camera->target, glm::vec3(position->y_axis));
camera->projection = glm::perspective(camera->fovy, camera->aspect, camera->near_r, camera->far_r);
カメラ構造体:
struct Camera: public Component {
glm::mat4 projection;
glm::mat4 view;
glm::vec3 target;
glm::vec3 up;
float fovy;
float aspect;
float near_r;
float far_r;
bool directed;
}。
位置の構造体:
struct Position: public Component {
union {
struct {
glm::mat4 mat4;
};
struct {
glm::vec4 x_axis;
glm::vec4 y_axis;
glm::vec4 z_axis;
glm::vec4 position;
};
struct {
glm::vec4 fwd;
glm::vec4 up;
glm::vec4 right;
glm::vec4 position;
};
};
};
メッシュ構造体は、対応するバッファのIDの、そのサイズが含まれています。
カメラ初期化データ:
camera->up = glm::vec3(0.0f, 1.0f, 0.0f);
camera->fovy = 65.0f;
camera->aspect = 4.0f/3.0f;
camera->near_r = 0.1f;
camera->far_r = 100.0f;
camera->directed = true;
位置initilizationデータ:
position->position = glm::vec4{ 5.0f, 0.0f, 0.0f, 1.0f };
position->fwd = glm::vec4{ 1.0f, 0.0f, 0.0f, 1.0f };
position->up = glm::vec4{ 0.0f, 1.0f, 0.0f, 1.0f };
position->right = glm::vec4{ 0.0f, 0.0f, 1.0f, 1.0f };
シェーダとモデルデータとそれらのロード/結合機能は、以前のプロジェクトから変更されず、トラブルが発生することはありません。
MVP行列の内容:位置については
r=0.000000000 g=0.000000000 b=7.81581593 a=8.00000000
r=0.000000000 g=1.56968546 b=6.81381416 a=7.00000000
r=1.17726409 g=0.000000000 b=6.81381416 a=7.00000000
r=0.000000000 g=0.000000000 b=5.01000977 a=5.00000000
:
r=1.000000000 g=0.000000000 b=0.000000000 a=1.00000000
r=0.000000000 g=1.000000000 b=0.000000000 a=1.00000000
r=0.000000000 g=0.000000000 b=1.000000000 a=1.00000000
r=5.000000000 g=0.000000000 b=0.000000000 a=1.00000000
(おそらく)無関係ですが、なぜキャストが最初の行にフェストするのですか? – Quentin
部分的に私はどのようにデータを保存しているのか、デバッグ目的のためにハードにコード化されているためです。テンプレートを使用して落としたので、前回のプログラム反復でコードを混乱させてインタフェースを利用しました。しかし、結果として、すべてのストレージが必須の型にキャストする必要のある抽象コンポーネント型を返すことになります。同じことがリソースストレージにも適用されます。 – Ben
よろしくお願いします。 Cスタイルのキャストの代わりに 'static_cast'を使い、チェックされたダウンキャストをいくつかのCPUサイクルの代わりにしたいときは' dynamic_cast'を使いたいかもしれません。誤って間違った型にキャストしてしまったときに、おそらく数時間であなたの頭を抜くことができます:) – Quentin