m2b-ar-tp2/fish_painter.cpp

66 lines
1.6 KiB
C++

#include "fish_painter.h"
#include <QtMath>
const GLfloat vertices[] = {
1, 0, 0,
-1, .5, 0,
-1, -.5, 0,
};
void FishPainter::create(QOpenGLExtraFunctions *glf) {
(void) glf;
if (!program.addShaderFromSourceFile(QOpenGLShader::Vertex,
":/shaders/fish.vert")) {
qCritical() << program.log();
}
if (!program.addShaderFromSourceFile(QOpenGLShader::Fragment,
":/shaders/fish.frag")) {
qCritical() << program.log();
}
if (!program.link()) {
qCritical() << program.log();
}
vao.create();
{QOpenGLVertexArrayObject::Binder bind(&vao);
vbo.create();
vbo.bind();
vbo.allocate(vertices, 9 * sizeof (GLfloat));
program.bind();
program.setAttributeBuffer("position", GL_FLOAT, 0, 3);
program.enableAttributeArray("position");
}
}
void FishPainter::paint(QOpenGLExtraFunctions *glf,
const QMatrix4x4 &projection,
const QMatrix4x4 &view,
const std::vector<Fish> fishes) {
const QVector3D X(1, 0, 0);
{QOpenGLVertexArrayObject::Binder bind(&vao);
program.setUniformValue("projection", projection);
program.setUniformValue("view", view);
QMatrix4x4 model;
for (const Fish &fish : fishes) {
model.setToIdentity();
model.translate(fish.position);
if (!fish.velocity.isNull()) {
double dot = QVector3D::dotProduct(X, fish.velocity);
double angle = qAcos(dot / fish.velocity.length());
if (angle != 0) {
model.rotate(qRadiansToDegrees(angle),
QVector3D::crossProduct(X, fish.velocity));
}
}
program.setUniformValue("model", model);
glf->glDrawArrays(GL_TRIANGLES, 0, 3);
}
}
}