CuteLogger
Fast and simple logging solution for Qt based applications
glwidget.h
1 /*
2  * Copyright (c) 2011-2017 Meltytech, LLC
3  * Author: Dan Dennedy <dan@dennedy.org>
4  *
5  * This program is free software: you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License as published by
7  * the Free Software Foundation, either version 3 of the License, or
8  * (at your option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program. If not, see <http://www.gnu.org/licenses/>.
17  */
18 
19 #ifndef GLWIDGET_H
20 #define GLWIDGET_H
21 
22 #include <QSemaphore>
23 #include <QQuickWidget>
24 #include <QOpenGLFunctions>
25 #include <QOpenGLShaderProgram>
26 #include <QOpenGLFramebufferObject>
27 #include <QOpenGLContext>
28 #include <QOffscreenSurface>
29 #include <QMutex>
30 #include <QThread>
31 #include <QRect>
32 #include "mltcontroller.h"
33 #include "sharedframe.h"
34 
35 class QOpenGLFunctions_3_2_Core;
36 class QOpenGLTexture;
37 class QmlFilter;
38 class QmlMetadata;
39 
40 namespace Mlt {
41 
42 class Filter;
43 class RenderThread;
44 class FrameRenderer;
45 
46 typedef void* ( *thread_function_t )( void* );
47 
48 class GLWidget : public QQuickWidget, public Controller, protected QOpenGLFunctions
49 {
50  Q_OBJECT
51  Q_PROPERTY(QRect rect READ rect NOTIFY rectChanged)
52  Q_PROPERTY(float zoom READ zoom NOTIFY zoomChanged)
53  Q_PROPERTY(QPoint offset READ offset NOTIFY offsetChanged)
54 
55 public:
56  GLWidget(QObject *parent = 0);
57  ~GLWidget();
58 
59  void createThread(RenderThread** thread, thread_function_t function, void* data);
60  void startGlsl();
61  void stopGlsl();
62  int setProducer(Mlt::Producer*, bool isMulti = false);
63  int reconfigure(bool isMulti);
64 
65  void play(double speed = 1.0) {
66  Controller::play(speed);
67  if (speed == 0) emit paused();
68  else emit playing();
69  }
70  void seek(int position) {
71  Controller::seek(position);
72  emit paused();
73  }
74  void pause() {
75  Controller::pause();
76  emit paused();
77  }
78  int displayWidth() const { return m_rect.width(); }
79  int displayHeight() const { return m_rect.height(); }
80 
81  QObject* videoWidget() { return this; }
82  Filter* glslManager() const { return m_glslManager; }
83  QRect rect() const { return m_rect; }
84  float zoom() const { return m_zoom * MLT.profile().width() / m_rect.width(); }
85  QPoint offset() const;
86  QImage image() const;
87  void requestImage() const;
88 
89 public slots:
90  void onFrameDisplayed(const SharedFrame& frame);
91  void setZoom(float zoom);
92  void setOffsetX(int x);
93  void setOffsetY(int y);
94  void setBlankScene();
95  void setCurrentFilter(QmlFilter* filter, QmlMetadata* meta);
96 
97 signals:
98  void frameDisplayed(const SharedFrame& frame);
99  void dragStarted();
100  void seekTo(int x);
101  void gpuNotSupported();
102  void started();
103  void paused();
104  void playing();
105  void rectChanged();
106  void zoomChanged();
107  void offsetChanged();
108  void imageReady();
109 
110 private:
111  QRect m_rect;
112  GLuint m_texture[3];
113  QOpenGLShaderProgram* m_shader;
114  QPoint m_dragStart;
115  Filter* m_glslManager;
116  QSemaphore m_initSem;
117  bool m_isInitialized;
118  Event* m_threadStartEvent;
119  Event* m_threadStopEvent;
120  Event* m_threadCreateEvent;
121  Event* m_threadJoinEvent;
122  FrameRenderer* m_frameRenderer;
123  int m_projectionLocation;
124  int m_modelViewLocation;
125  int m_vertexLocation;
126  int m_texCoordLocation;
127  int m_colorspaceLocation;
128  int m_textureLocation[3];
129  float m_zoom;
130  QPoint m_offset;
131  QOffscreenSurface m_offscreenSurface;
132  QOpenGLContext* m_shareContext;
133  SharedFrame m_sharedFrame;
134  QMutex m_mutex;
135 
136  static void on_frame_show(mlt_consumer, void* self, mlt_frame frame);
137 
138 private slots:
139  void initializeGL();
140  void resizeGL(int width, int height);
141  void updateTexture(GLuint yName, GLuint uName, GLuint vName);
142  void paintGL();
143 
144 protected:
145  void resizeEvent(QResizeEvent* event);
146  void mousePressEvent(QMouseEvent *);
147  void mouseMoveEvent(QMouseEvent *);
148  void keyPressEvent(QKeyEvent* event);
149  void createShader();
150 };
151 
152 class RenderThread : public QThread
153 {
154  Q_OBJECT
155 public:
156  RenderThread(thread_function_t function, void* data, QOpenGLContext *context, QSurface* surface);
157 
158 protected:
159  void run();
160 
161 private:
162  thread_function_t m_function;
163  void* m_data;
164  QOpenGLContext* m_context;
165  QSurface* m_surface;
166 };
167 
168 class FrameRenderer : public QThread
169 {
170  Q_OBJECT
171 public:
172  FrameRenderer(QOpenGLContext* shareContext, QSurface* surface);
173  ~FrameRenderer();
174  QSemaphore* semaphore() { return &m_semaphore; }
175  QOpenGLContext* context() const { return m_context; }
176  SharedFrame getDisplayFrame();
177  Q_INVOKABLE void showFrame(Mlt::Frame frame);
178  void requestImage();
179  QImage image() const { return m_image; }
180 
181 public slots:
182  void cleanup();
183 
184 signals:
185  void textureReady(GLuint yName, GLuint uName = 0, GLuint vName = 0);
186  void frameDisplayed(const SharedFrame& frame);
187  void imageReady();
188 
189 private:
190  QSemaphore m_semaphore;
191  SharedFrame m_displayFrame;
192  QOpenGLContext* m_context;
193  QSurface* m_surface;
194  qint64 m_previousMSecs;
195  bool m_imageRequested;
196  QImage m_image;
197 
198 public:
199  GLuint m_renderTexture[3];
200  GLuint m_displayTexture[3];
201  QOpenGLFunctions_3_2_Core* m_gl32;
202 };
203 
204 } // namespace
205 
206 #endif
Definition: encodedock.h:35
The SharedFrame provides thread safe access to Mlt::Frame data.
Definition: sharedframe.h:48