src/platform/qt/DisplayGL.h (view raw)
1/* Copyright (c) 2013-2015 Jeffrey Pfau
2 *
3 * This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6#pragma once
7
8#if defined(BUILD_GL) || defined(BUILD_GLES2)
9
10#include "Display.h"
11
12#ifdef USE_EPOXY
13#include <epoxy/gl.h>
14#ifndef GLdouble
15#define GLdouble GLdouble
16#endif
17#endif
18
19#include <QAtomicInt>
20#include <QElapsedTimer>
21#include <QHash>
22#include <QList>
23#include <QMouseEvent>
24#include <QOpenGLContext>
25#include <QPainter>
26#include <QQueue>
27#include <QThread>
28#include <QTimer>
29
30#include <array>
31
32#include "CoreController.h"
33#include "VideoProxy.h"
34
35#include "platform/video-backend.h"
36
37class QOpenGLPaintDevice;
38
39uint qHash(const QSurfaceFormat&, uint seed = 0);
40
41namespace QGBA {
42
43class PainterGL;
44class DisplayGL : public Display {
45Q_OBJECT
46
47public:
48 DisplayGL(const QSurfaceFormat& format, QWidget* parent = nullptr);
49 ~DisplayGL();
50
51 void startDrawing(std::shared_ptr<CoreController>) override;
52 bool isDrawing() const override { return m_isDrawing; }
53 bool supportsShaders() const override;
54 VideoShader* shaders() override;
55 void setVideoProxy(std::shared_ptr<VideoProxy>) override;
56 int framebufferHandle() override;
57
58 static bool supportsFormat(const QSurfaceFormat&);
59
60public slots:
61 void stopDrawing() override;
62 void pauseDrawing() override;
63 void unpauseDrawing() override;
64 void forceDraw() override;
65 void lockAspectRatio(bool lock) override;
66 void lockIntegerScaling(bool lock) override;
67 void interframeBlending(bool enable) override;
68 void showOSDMessages(bool enable) override;
69 void filter(bool filter) override;
70 void framePosted() override;
71 void setShaders(struct VDir*) override;
72 void clearShaders() override;
73 void resizeContext() override;
74 void setVideoScale(int scale) override;
75
76protected:
77 virtual void paintEvent(QPaintEvent*) override { forceDraw(); }
78 virtual void resizeEvent(QResizeEvent*) override;
79
80private:
81 void resizePainter();
82
83 static QHash<QSurfaceFormat, bool> s_supports;
84
85 bool m_isDrawing = false;
86 bool m_hasStarted = false;
87 std::unique_ptr<PainterGL> m_painter;
88 QThread m_drawThread;
89 std::shared_ptr<CoreController> m_context;
90};
91
92class PainterGL : public QObject {
93Q_OBJECT
94
95public:
96 PainterGL(QWindow* surface, const QSurfaceFormat& format);
97 ~PainterGL();
98
99 void setContext(std::shared_ptr<CoreController>);
100 void setMessagePainter(MessagePainter*);
101 void enqueue(const uint32_t* backing);
102
103 bool supportsShaders() const { return m_supportsShaders; }
104
105 void setVideoProxy(std::shared_ptr<VideoProxy>);
106 void interrupt();
107
108public slots:
109 void create();
110 void destroy();
111
112 void forceDraw();
113 void draw();
114 void start();
115 void stop();
116 void pause();
117 void unpause();
118 void resize(const QSize& size);
119 void lockAspectRatio(bool lock);
120 void lockIntegerScaling(bool lock);
121 void interframeBlending(bool enable);
122 void showOSD(bool enable);
123 void filter(bool filter);
124 void resizeContext();
125
126 void setShaders(struct VDir*);
127 void clearShaders();
128 VideoShader* shaders();
129
130 int glTex();
131
132signals:
133 void started();
134
135private:
136 void makeCurrent();
137 void performDraw();
138 void dequeue();
139 void dequeueAll();
140
141 std::array<std::array<uint32_t, 0x100000>, 3> m_buffers;
142 QList<uint32_t*> m_free;
143 QQueue<uint32_t*> m_queue;
144 QAtomicInt m_lagging = 0;
145 uint32_t* m_buffer;
146 QPainter m_painter;
147 QMutex m_mutex;
148 QWindow* m_surface;
149 QSurfaceFormat m_format;
150 std::unique_ptr<QOpenGLPaintDevice> m_window;
151 std::unique_ptr<QOpenGLContext> m_gl;
152 bool m_active = false;
153 bool m_started = false;
154 std::shared_ptr<CoreController> m_context;
155 CoreController::Interrupter m_interrupter;
156 bool m_supportsShaders;
157 bool m_showOSD;
158 VideoShader m_shader{};
159 VideoBackend* m_backend = nullptr;
160 QSize m_size;
161 MessagePainter* m_messagePainter = nullptr;
162 QElapsedTimer m_delayTimer;
163 std::shared_ptr<VideoProxy> m_videoProxy;
164};
165
166}
167
168#endif