END_TEST;
}
-int utcDaliActorPartialAddRemoveRenderer(void)
+int utcDaliActorPartialUpdateAddRemoveRenderer(void)
{
TestApplication application(
TestApplication::DEFAULT_SURFACE_WIDTH,
END_TEST;
}
+int utcDaliActorPartialUpdate3DTransform(void)
+{
+ TestApplication application(
+ TestApplication::DEFAULT_SURFACE_WIDTH,
+ TestApplication::DEFAULT_SURFACE_HEIGHT,
+ TestApplication::DEFAULT_HORIZONTAL_DPI,
+ TestApplication::DEFAULT_VERTICAL_DPI,
+ true,
+ true);
+
+ tet_infoline("Check the damaged rect with 3D transformed actors");
+
+ const TestGlAbstraction::ScissorParams& glScissorParams(application.GetGlAbstraction().GetScissorParams());
+
+ Actor actor1 = CreateRenderableActor();
+ actor1[Actor::Property::ANCHOR_POINT] = AnchorPoint::TOP_LEFT;
+ actor1[Actor::Property::POSITION] = Vector3(16.0f, 16.0f, 0.0f);
+ actor1[Actor::Property::SIZE] = Vector3(16.0f, 16.0f, 0.0f);
+ actor1.SetResizePolicy(ResizePolicy::FIXED, Dimension::ALL_DIMENSIONS);
+ application.GetScene().Add(actor1);
+
+ // Add a new actor
+ Actor actor2 = CreateRenderableActor();
+ actor2[Actor::Property::ANCHOR_POINT] = AnchorPoint::TOP_LEFT;
+ actor2[Actor::Property::POSITION] = Vector3(160.0f, 160.0f, 0.0f);
+ actor2[Actor::Property::SIZE] = Vector3(16.0f, 16.0f, 0.0f);
+ actor2.SetResizePolicy(ResizePolicy::FIXED, Dimension::ALL_DIMENSIONS);
+ application.GetScene().Add(actor2);
+
+ application.SendNotification();
+
+ std::vector<Rect<int>> damagedRects;
+
+ // Actor added, damaged rect is added size of actor
+ application.PreRenderWithPartialUpdate(TestApplication::RENDER_FRAME_INTERVAL, nullptr, damagedRects);
+ DALI_TEST_EQUALS(damagedRects.size(), 2, TEST_LOCATION);
+
+ // Aligned by 16
+ Rect<int> clippingRect1 = Rect<int>(16, 768, 32, 32); // in screen coordinates
+ Rect<int> clippingRect2 = Rect<int>(160, 624, 32, 32);
+ DALI_TEST_EQUALS<Rect<int>>(clippingRect1, damagedRects[0], TEST_LOCATION);
+ DALI_TEST_EQUALS<Rect<int>>(clippingRect2, damagedRects[1], TEST_LOCATION);
+
+ Rect<int> surfaceRect = Rect<int>(0, 0, TestApplication::DEFAULT_SURFACE_WIDTH, TestApplication::DEFAULT_SURFACE_HEIGHT);
+ application.RenderWithPartialUpdate(damagedRects, surfaceRect);
+
+ damagedRects.clear();
+ surfaceRect = Rect<int>(0, 0, TestApplication::DEFAULT_SURFACE_WIDTH, TestApplication::DEFAULT_SURFACE_HEIGHT);
+ application.PreRenderWithPartialUpdate(TestApplication::RENDER_FRAME_INTERVAL, nullptr, damagedRects);
+ application.RenderWithPartialUpdate(damagedRects, surfaceRect);
+
+ damagedRects.clear();
+ surfaceRect = Rect<int>(0, 0, TestApplication::DEFAULT_SURFACE_WIDTH, TestApplication::DEFAULT_SURFACE_HEIGHT);
+ application.PreRenderWithPartialUpdate(TestApplication::RENDER_FRAME_INTERVAL, nullptr, damagedRects);
+ application.RenderWithPartialUpdate(damagedRects, surfaceRect);
+
+ // Rotate actor1 on y axis
+ actor1[Actor::Property::ORIENTATION] = Quaternion(Radian(Degree(90.0)), Vector3::YAXIS);
+
+ // Remove actor2
+ actor2.Unparent();
+
+ application.SendNotification();
+
+ damagedRects.clear();
+ application.PreRenderWithPartialUpdate(TestApplication::RENDER_FRAME_INTERVAL, nullptr, damagedRects);
+
+ // Should update full area
+ surfaceRect = Rect<int>(0, 0, TestApplication::DEFAULT_SURFACE_WIDTH, TestApplication::DEFAULT_SURFACE_HEIGHT);
+ DALI_TEST_EQUALS(damagedRects.size(), 1, TEST_LOCATION);
+ DALI_TEST_EQUALS<Rect<int>>(surfaceRect, damagedRects[0], TEST_LOCATION);
+ application.RenderWithPartialUpdate(damagedRects, surfaceRect);
+
+ // Add actor2 again
+ application.GetScene().Add(actor2);
+
+ application.SendNotification();
+
+ damagedRects.clear();
+ application.PreRenderWithPartialUpdate(TestApplication::RENDER_FRAME_INTERVAL, nullptr, damagedRects);
+
+ // Should update full area
+ surfaceRect = Rect<int>(0, 0, TestApplication::DEFAULT_SURFACE_WIDTH, TestApplication::DEFAULT_SURFACE_HEIGHT);
+ DALI_TEST_EQUALS(damagedRects.size(), 1, TEST_LOCATION);
+ DALI_TEST_EQUALS<Rect<int>>(surfaceRect, damagedRects[0], TEST_LOCATION);
+ application.RenderWithPartialUpdate(damagedRects, surfaceRect);
+
+ // Reset the orientation of actor1
+ actor1[Actor::Property::ORIENTATION] = Quaternion::IDENTITY;
+
+ application.SendNotification();
+
+ damagedRects.clear();
+ application.PreRenderWithPartialUpdate(TestApplication::RENDER_FRAME_INTERVAL, nullptr, damagedRects);
+
+ // Should update full area
+ surfaceRect = Rect<int>(0, 0, TestApplication::DEFAULT_SURFACE_WIDTH, TestApplication::DEFAULT_SURFACE_HEIGHT);
+ DALI_TEST_EQUALS(damagedRects.size(), 1, TEST_LOCATION);
+ DALI_TEST_EQUALS<Rect<int>>(surfaceRect, damagedRects[0], TEST_LOCATION);
+ application.RenderWithPartialUpdate(damagedRects, surfaceRect);
+
+ // Make actor2 dirty
+ actor2[Actor::Property::SIZE] = Vector3(32.0f, 32.0f, 0.0f);
+
+ application.SendNotification();
+
+ damagedRects.clear();
+ application.PreRenderWithPartialUpdate(TestApplication::RENDER_FRAME_INTERVAL, nullptr, damagedRects);
+
+ clippingRect2 = Rect<int>(160, 608, 48, 48);
+ DALI_TEST_EQUALS(damagedRects.size(), 1, TEST_LOCATION);
+ DALI_TEST_EQUALS<Rect<int>>(clippingRect2, damagedRects[0], TEST_LOCATION);
+
+ application.RenderWithPartialUpdate(damagedRects, clippingRect2);
+ DALI_TEST_EQUALS(clippingRect2.x, glScissorParams.x, TEST_LOCATION);
+ DALI_TEST_EQUALS(clippingRect2.y, glScissorParams.y, TEST_LOCATION);
+ DALI_TEST_EQUALS(clippingRect2.width, glScissorParams.width, TEST_LOCATION);
+ DALI_TEST_EQUALS(clippingRect2.height, glScissorParams.height, TEST_LOCATION);
+
+ // Remove actor1
+ actor1.Unparent();
+
+ application.SendNotification();
+
+ damagedRects.clear();
+ surfaceRect = Rect<int>(0, 0, TestApplication::DEFAULT_SURFACE_WIDTH, TestApplication::DEFAULT_SURFACE_HEIGHT);
+ application.PreRenderWithPartialUpdate(TestApplication::RENDER_FRAME_INTERVAL, nullptr, damagedRects);
+ application.RenderWithPartialUpdate(damagedRects, surfaceRect);
+
+ // Rotate actor1 on y axis
+ actor1[Actor::Property::ORIENTATION] = Quaternion(Radian(Degree(90.0)), Vector3::YAXIS);
+
+ // Add actor1 again
+ application.GetScene().Add(actor1);
+
+ application.SendNotification();
+
+ damagedRects.clear();
+ application.PreRenderWithPartialUpdate(TestApplication::RENDER_FRAME_INTERVAL, nullptr, damagedRects);
+
+ // Should update full area
+ surfaceRect = Rect<int>(0, 0, TestApplication::DEFAULT_SURFACE_WIDTH, TestApplication::DEFAULT_SURFACE_HEIGHT);
+ DALI_TEST_EQUALS(damagedRects.size(), 1, TEST_LOCATION);
+ DALI_TEST_EQUALS<Rect<int>>(surfaceRect, damagedRects[0], TEST_LOCATION);
+ application.RenderWithPartialUpdate(damagedRects, surfaceRect);
+
+ END_TEST;
+}
+
int UtcDaliActorCaptureAllTouchAfterStartPropertyP(void)
{
TestApplication application;
// Clean collected dirty/damaged rects on exit if 3d layer or 3d node or other conditions.
DamagedRectsCleaner damagedRectCleaner(damagedRects, surfaceRect);
+ bool cleanDamagedRect = false;
// Mark previous dirty rects in the sorted array. The array is already sorted by node and renderer, frame number.
// so you don't need to sort: std::stable_sort(itemsDirtyRects.begin(), itemsDirtyRects.end());
for(uint32_t listIndex = 0u; listIndex < listCount; ++listIndex)
{
RenderItem& item = renderList->GetItem(listIndex);
- // If the item does 3D transformation, do early exit and clean the damaged rect array
+ // If the item does 3D transformation, make full update
if(item.mUpdateArea == Vector4::ZERO)
{
- return;
+ cleanDamagedRect = true;
+
+ // Save the full rect in the damaged list. We need it when this item is removed
+ DirtyRect dirtyRect(item.mNode, item.mRenderer, surfaceRect);
+ auto dirtyRectPos = std::lower_bound(itemsDirtyRects.begin(), itemsDirtyRects.end(), dirtyRect);
+ if(dirtyRectPos != itemsDirtyRects.end() && dirtyRectPos->node == item.mNode && dirtyRectPos->renderer == item.mRenderer)
+ {
+ // Replace the rect
+ dirtyRectPos->visited = true;
+ dirtyRectPos->rect = dirtyRect.rect;
+ }
+ else
+ {
+ // Else, just insert the new dirtyrect in the correct position
+ itemsDirtyRects.insert(dirtyRectPos, dirtyRect);
+ }
+ continue;
}
Rect<int> rect;
{
dirtyRectPos->visited = true;
}
+ else
+ {
+ // The item is not in the list for some reason. Add it!
+ itemsDirtyRects.insert(dirtyRectPos, dirtyRect);
+ }
}
}
}
}
itemsDirtyRects.resize(j - itemsDirtyRects.begin());
- damagedRectCleaner.SetCleanOnReturn(false);
+
+ if(!cleanDamagedRect)
+ {
+ damagedRectCleaner.SetCleanOnReturn(false);
+ }
// Reset updated flag from the root
Layer* root = sceneObject->GetRoot();