xoreos  0.0.5
animationthread.cpp
Go to the documentation of this file.
1 /* xoreos - A reimplementation of BioWare's Aurora engine
2  *
3  * xoreos is the legal property of its developers, whose names
4  * can be found in the AUTHORS file distributed with this source
5  * distribution.
6  *
7  * xoreos is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU General Public License
9  * as published by the Free Software Foundation; either version 3
10  * of the License, or (at your option) any later version.
11  *
12  * xoreos is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with xoreos. If not, see <http://www.gnu.org/licenses/>.
19  */
20 
25 #include "glm/gtc/type_ptr.hpp"
26 
27 #include "src/common/threads.h"
28 
29 #include "src/events/events.h"
30 
31 #include "src/graphics/camera.h"
32 
35 
36 namespace Graphics {
37 
38 namespace Aurora {
39 
41  : model(m),
42  lastChanged(0),
43  skippedCount(0) {
44 }
45 
47  : _paused(true),
48  _flushing(false),
49  _modelsSem(1),
50  _registerSem(1) {
51 }
52 
54  _paused.store(true);
55  _modelsSem.lock();
57 }
58 
60  _paused.store(false);
61 }
62 
64  if (_paused.load())
65  registerModelInternal(model);
66  else {
68  _registerQueue.push(model);
70  }
71 }
72 
74  if (_paused.load())
76  else {
77  _modelsSem.lock();
80  }
81 }
82 
84  _flushing.store(true);
85  _modelsSem.lock();
86 
87  for (ModelList::iterator m = _models.begin();
88  m != _models.end();
89  ++m) {
90  m->model->flushNodeBuffers();
91  }
92 
94  _flushing.store(false);
95 }
96 
98  while (!_killThread.load(boost::memory_order_relaxed)) {
99  if (EventMan.quitRequested())
100  break;
101 
102  if (_paused.load()) {
103  EventMan.delay(100);
104  continue;
105  }
106 
107  _modelsSem.lock();
108 
109  // Register queued models
110  if (_registerSem.lockTry()) {
111  while (!_registerQueue.empty()) {
113  _registerQueue.pop();
114  }
116  }
117 
118  if (_models.empty()) {
119  _modelsSem.unlock();
120  EventMan.delay(100);
121  continue;
122  }
123 
124  for (ModelList::iterator m = _models.begin();
125  m != _models.end();
126  ++m) {
127  if (EventMan.quitRequested() || _paused.load())
128  break;
129 
130  if (m->skippedCount < getNumIterationsToSkip(m->model)) {
131  ++m->skippedCount;
132  continue;
133  } else
134  m->skippedCount = 0;
135 
136  if (_flushing.load()) {
137  _modelsSem.unlock();
138  while (_flushing.load()) // Spin until flushing is complete
139  ;
140  _modelsSem.lock();
141  }
142 
143  uint32 now = EventMan.getTimestamp();
144  float dt = 0;
145  if (m->lastChanged > 0)
146  dt = (now - m->lastChanged) / 1000.f;
147  m->lastChanged = now;
148 
149  m->model->manageAnimations(dt);
150  }
151 
152  _modelsSem.unlock();
153 
154  EventMan.delay(10);
155  }
156 }
157 
159  for (ModelList::iterator m = _models.begin(); m != _models.end(); ++m) {
160  if (m->model == model)
161  return;
162  }
163  _models.push_back(PoolModel(model));
164 }
165 
167  ModelList::iterator m;
168  for (m = _models.begin(); m != _models.end(); ++m) {
169  if (m->model == model)
170  break;
171  }
172  if (m != _models.end())
173  _models.erase(m);
174 }
175 
177  const float *campos = CameraMan.getPosition();
178 
179  float x, y, z;
180  model->getPosition(x, y, z);
181 
182  float dist = glm::distance(glm::make_vec3(campos), glm::vec3(x, y, z));
183  return roundf(dist) / 8;
184 }
185 
186 } // End of namespace Aurora
187 
188 } // End of namespace Engines
void getPosition(float &x, float &y, float &z) const
Get the current position of the model.
Definition: model.cpp:207
bool lockTry()
Definition: mutex.cpp:71
uint8_t uint8
Definition: types.h:200
void unregisterModelInternal(Model *model)
boost::atomic< bool > _killThread
Definition: thread.h:53
Camera management.
bool lock(uint32 timeout=0)
Definition: mutex.cpp:60
boost::atomic< bool > _flushing
void unregisterModel(Model *model)
Remove a model from the processing pool.
Threading system helpers.
The global events manager.
A 3D model of an object.
void registerModel(Model *model)
Add a model to the processing pool.
void flush()
Apply changes to position and geometry of all models in the processing pool.
#define EventMan
Shortcut for accessing the events manager.
Definition: events.h:210
uint8 getNumIterationsToSkip(Model *model) const
uint32_t uint32
Definition: types.h:204
void unlock()
Definition: mutex.cpp:75
#define CameraMan
Shortcut for accessing the camera manager.
Definition: camera.h:83
Common::Semaphore _modelsSem
Semaphore protecting access to the model list.
Dedicated animation thread.
Common::Semaphore _registerSem
Semaphore protecting access to the registration queue.