-
-
Notifications
You must be signed in to change notification settings - Fork 2
/
asyncrenderinternal.h
109 lines (88 loc) · 2.84 KB
/
asyncrenderinternal.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
#ifndef ASYNCRENDERINTERNAL_H
#define ASYNCRENDERINTERNAL_H
#include <QThread>
#include <QMutex>
#include <QWaitCondition>
// glew.h must come before qgl.h
#include "glew.h"
#include <qgl.h>
#include <deque>
#include <vector>
#include "asyncrenderwidget.h"
using std::deque;
using std::vector;
using std::make_pair;
#include <tr1/unordered_map>
using std::tr1::unordered_map;
class Geometry;
class QImage;
namespace AsyncRenderInternal {
//------------------------------------------
// Jobs are passed between threads to get stuff rendered.
class Job
{
public:
Job(uint32_t _requesterId, Camera const &_camera, RenderData *_data, Geometry *_geometry = NULL)
: requesterId(_requesterId), camera(_camera), data(_data), geometry(_geometry), result(NULL) {
}
//deletes data,geometry,result and sets 'em to NULL:
void deleteData();
uint32_t requesterId;
Camera camera;
RenderData *data;
Geometry *geometry;
QImage *result;
};
//------------------------------------------
// The Controller is in charge of coordinating individual
// widgets and the backend threads, using queues of jobs.
class Controller : public QObject
{
Q_OBJECT
friend class RenderThread;
friend class ComputeThread;
//there's a singleton, global render controller you get with this static member function:
public:
static Controller &controller();
private:
Controller();
virtual ~Controller();
std::vector< QThread * > threads; //kept around so we can wait() on 'em later.
bool quitThreads; //how we tell threads to suicide later.
//These functions are called by AsyncRenderWidget constructor/destructor to assign ids to active widgets:
public:
void registerWidget(AsyncRenderWidget *widget);
void unregisterWidget(AsyncRenderWidget *widget);
private:
unordered_map< uint32_t, AsyncRenderWidget * > idToWidget;
uint32_t freshId;
//These functions are called to actually kick off async rendering:
public:
void queue(AsyncRenderWidget *widget, Camera const &camera, RenderData *data);
void queue(AsyncRenderWidget *widget, Camera const &camera, Geometry *geometry);
private:
std::deque< Job * > computeQueue;
std::deque< Job * > renderQueue;
QMutex computeQueueLock;
QWaitCondition computeQueueHasData;
QMutex renderQueueLock;
QWaitCondition renderQueueHasData;
//Slot used by render threads to return jobs:
public slots:
void jobFinished(Job *job);
};
//------------------------------------------
//The ComputeThread takes jobs from the computeQueue, runs their RenderData
// to produce Geometry, and places them onto the renderQueue.
class ComputeThread : public QThread
{
public:
ComputeThread(Controller *controller);
virtual ~ComputeThread();
virtual void run();
Controller *controller;
};
//------------------------------------------
//RenderThread defined in its own header.
} //namespace AsyncRenderInternal
#endif //ASYNCRENDERINTERNAL_H