Interactive Mandelbrot viewer with Qt and OpenGL.
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

103 lines
2.2 KiB

3 years ago
#include <iostream>
#include <QResource>
#include "../headers/OutputWidget.h"
3 years ago
3 years ago
using std::cout, std::endl;
3 years ago
void OutputWidget::initializeGL() {
3 years ago
cout << "Initialize OpenGL" << endl;
3 years ago
initializeOpenGLFunctions();
3 years ago
getMandelbrot()->init();
initShader();
3 years ago
3 years ago
auto format = this->format();
3 years ago
cout << "OpenGL version: " << format.majorVersion() << "." << format.minorVersion() << endl;
3 years ago
vao = createVAO();
3 years ago
glClearColor(0.5f, 0.5f, 0.5f, 1.0f);
3 years ago
}
void OutputWidget::paintGL() {
getMandelbrot()->draw(vao, shader);
3 years ago
}
void OutputWidget::resizeGL(int w, int h) {
3 years ago
}
GLuint OutputWidget::createVAO() {
GLuint vboId;
glGenBuffers(1, &vboId);
glBindBuffer(GL_ARRAY_BUFFER, vboId);
auto vertices = genVertices();
size_t size = vertices.size() * sizeof(QVector2D);
glBufferData(GL_ARRAY_BUFFER, (GLsizeiptr)size, &vertices[0], GL_STATIC_DRAW);
GLuint vaoId;
glGenVertexArrays(1, &vaoId);
glBindVertexArray(vaoId);
glBindBuffer(GL_ARRAY_BUFFER, vboId);
3 years ago
glVertexAttribPointer(0, 2, GL_FLOAT, GL_FALSE, sizeof(QVector2D), (void*) nullptr);
glEnableVertexAttribArray(0);
glBindVertexArray(0);
return vaoId;
}
std::vector<QVector2D> OutputWidget::genVertices() {
return {
{-1, -1},
{1, -1},
{1, 1},
{-1, 1}
};
}
3 years ago
void OutputWidget::initShader() {
if (!shader.addShaderFromSourceFile(QOpenGLShader::Vertex, "Vertex.glsl")) close();
if (!shader.addShaderFromSourceFile(QOpenGLShader::Fragment, "Fragment.glsl")) close();
if (!shader.link()) close();
if (!shader.bind()) close();
3 years ago
}
QVector2D relative(QPoint p, QSize s){
return {
float(p.x()) / float(s.width()),
float(p.y()) / float(s.height())
};
}
3 years ago
void OutputWidget::wheelEvent(QWheelEvent *e) {
double modifier = 1;
if (e->angleDelta().y() > 0)
modifier *= 1.1;
else
modifier /= 1.1;
getMandelbrot()->zoomRelative(modifier, relative(mousePos, size()));
update();
3 years ago
}
void OutputWidget::mouseMoveEvent(QMouseEvent *e) {
QPoint newMousePos = e->pos();
QPoint diff = newMousePos - mousePos;
mousePos = newMousePos;
getMandelbrot()->translateRelative(relative(diff, size()));
update();
3 years ago
}
void OutputWidget::mousePressEvent(QMouseEvent *e) {
mousePos = e->pos();
3 years ago
}
void OutputWidget::mouseReleaseEvent(QMouseEvent *e) {
}
void OutputWidget::keyPressEvent(QKeyEvent *e) {
}