aboutsummaryrefslogtreecommitdiff
path: root/engines/sword25/gfx/renderobject.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'engines/sword25/gfx/renderobject.cpp')
-rw-r--r--engines/sword25/gfx/renderobject.cpp56
1 files changed, 47 insertions, 9 deletions
diff --git a/engines/sword25/gfx/renderobject.cpp b/engines/sword25/gfx/renderobject.cpp
index a977eb80ba..807c1eb64b 100644
--- a/engines/sword25/gfx/renderobject.cpp
+++ b/engines/sword25/gfx/renderobject.cpp
@@ -48,6 +48,8 @@
namespace Sword25 {
+int RenderObject::_nextGlobalVersion = 0;
+
RenderObject::RenderObject(RenderObjectPtr<RenderObject> parentPtr, TYPES type, uint handle) :
_managerPtr(0),
_parentPtr(parentPtr),
@@ -65,7 +67,9 @@ RenderObject::RenderObject(RenderObjectPtr<RenderObject> parentPtr, TYPES type,
_type(type),
_initSuccess(false),
_refreshForced(true),
- _handle(0) {
+ _handle(0),
+ _version(++_nextGlobalVersion),
+ _isSolid(false) {
// Renderobject registrieren, abhängig vom Handle-Parameter entweder mit beliebigem oder vorgegebenen Handle.
if (handle == 0)
@@ -106,13 +110,12 @@ RenderObject::~RenderObject() {
RenderObjectRegistry::instance().deregisterObject(this);
}
-bool RenderObject::render() {
+void RenderObject::preRender(RenderObjectQueue *renderQueue) {
// Objektänderungen validieren
validateObject();
- // Falls das Objekt nicht sichtbar ist, muss gar nichts gezeichnet werden
if (!_visible)
- return true;
+ return;
// Falls notwendig, wird die Renderreihenfolge der Kinderobjekte aktualisiert.
if (_childChanged) {
@@ -120,13 +123,36 @@ bool RenderObject::render() {
_childChanged = false;
}
+ renderQueue->add(this);
+
+ RENDEROBJECT_ITER it = _children.begin();
+ for (; it != _children.end(); ++it)
+ (*it)->preRender(renderQueue);
+
+}
+
+bool RenderObject::render(RectangleList *updateRects, const Common::Array<int> &updateRectsMinZ) {
+
+ // Falls das Objekt nicht sichtbar ist, muss gar nichts gezeichnet werden
+ if (!_visible)
+ return true;
+
// Objekt zeichnen.
- doRender();
+ bool needRender = false;
+ int index = 0;
+
+ // Only draw if the bounding box intersects any update rectangle and
+ // the object is in front of the minimum Z value.
+ for (RectangleList::iterator rectIt = updateRects->begin(); !needRender && rectIt != updateRects->end(); ++rectIt, ++index)
+ needRender = (_bbox.contains(*rectIt) || _bbox.intersects(*rectIt)) && getAbsoluteZ() >= updateRectsMinZ[index];
+
+ if (needRender)
+ doRender(updateRects);
// Dann müssen die Kinder gezeichnet werden
RENDEROBJECT_ITER it = _children.begin();
for (; it != _children.end(); ++it)
- if (!(*it)->render())
+ if (!(*it)->render(updateRects, updateRectsMinZ))
return false;
return true;
@@ -157,6 +183,8 @@ bool RenderObject::updateObjectState() {
// Die Bounding-Box neu berechnen und Update-Regions registrieren.
updateBoxes();
+
+ ++_version;
// Änderungen Validieren
validateObject();
@@ -191,9 +219,10 @@ Common::Rect RenderObject::calcBoundingBox() const {
return bbox;
}
-void RenderObject::calcAbsolutePos(int &x, int &y) const {
+void RenderObject::calcAbsolutePos(int &x, int &y, int &z) const {
x = calcAbsoluteX();
y = calcAbsoluteY();
+ z = calcAbsoluteZ();
}
int RenderObject::calcAbsoluteX() const {
@@ -210,6 +239,13 @@ int RenderObject::calcAbsoluteY() const {
return _y;
}
+int RenderObject::calcAbsoluteZ() const {
+ if (_parentPtr.isValid())
+ return _parentPtr->getAbsoluteZ() + _z;
+ else
+ return _z;
+}
+
void RenderObject::deleteAllChildren() {
// Es ist nicht notwendig die Liste zu iterieren, da jedes Kind für sich DetatchChildren an diesem Objekt aufruft und sich somit
// selber entfernt. Daher muss immer nur ein beliebiges Element (hier das letzte) gelöscht werden, bis die Liste leer ist.
@@ -253,7 +289,7 @@ void RenderObject::sortRenderObjects() {
}
void RenderObject::updateAbsolutePos() {
- calcAbsolutePos(_absoluteX, _absoluteY);
+ calcAbsolutePos(_absoluteX, _absoluteY, _absoluteZ);
RENDEROBJECT_ITER it = _children.begin();
for (; it != _children.end(); ++it)
@@ -285,8 +321,10 @@ void RenderObject::setY(int y) {
void RenderObject::setZ(int z) {
if (z < 0)
error("Tried to set a negative Z value (%d).", z);
- else
+ else {
_z = z;
+ updateAbsolutePos();
+ }
}
void RenderObject::setVisible(bool visible) {