From 2d283f04b794847ef5543c2b7b42938c8420ae20 Mon Sep 17 00:00:00 2001 From: "Seungho, Baek" Date: Mon, 25 May 2020 11:41:52 +0900 Subject: [PATCH 01/16] Remove Assert when NativeImageSource is reset Change-Id: Icd5f4dd5e215a3d1fd3c3eaf8d980baaeb46822d Signed-off-by: Seungho, Baek --- dali/internal/system/common/capture-impl.cpp | 4 ---- 1 file changed, 4 deletions(-) diff --git a/dali/internal/system/common/capture-impl.cpp b/dali/internal/system/common/capture-impl.cpp index 253a3fd..2836fb3 100644 --- a/dali/internal/system/common/capture-impl.cpp +++ b/dali/internal/system/common/capture-impl.cpp @@ -109,8 +109,6 @@ void Capture::Start( Dali::Actor source, const Dali::Vector2& size, const std::s Dali::NativeImageSourcePtr Capture::GetNativeImageSource() const { - DALI_ASSERT_ALWAYS( mNativeImageSourcePtr && "mNativeImageSourcePtr is NULL."); - return mNativeImageSourcePtr; } @@ -133,8 +131,6 @@ void Capture::CreateNativeImageSource( const Vector2& size ) void Capture::DeleteNativeImageSource() { - DALI_ASSERT_ALWAYS(mNativeImageSourcePtr && "mNativeImageSource is NULL."); - mNativeImageSourcePtr.Reset(); } -- 2.7.4 From 1a114a6a20202ef475db4f0b410c39c97d7f3515 Mon Sep 17 00:00:00 2001 From: Daekwang Ryu Date: Wed, 27 May 2020 15:18:13 +0900 Subject: [PATCH 02/16] Free an unnecessary variable anymore The parameter of app_get_id() has to be freed when it is not necessary anymore. Change-Id: Ic8a85286fa40031b405443876f794adabe2da81e --- dali/internal/adaptor/tizen-wayland/adaptor-impl-tizen.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/dali/internal/adaptor/tizen-wayland/adaptor-impl-tizen.cpp b/dali/internal/adaptor/tizen-wayland/adaptor-impl-tizen.cpp index fb0cddd..dda9e96 100755 --- a/dali/internal/adaptor/tizen-wayland/adaptor-impl-tizen.cpp +++ b/dali/internal/adaptor/tizen-wayland/adaptor-impl-tizen.cpp @@ -91,6 +91,7 @@ void Adaptor::GetAppId( std::string& appId ) if ( id ) { appId = id; + free( id ); } else { -- 2.7.4 From 7d019dfdc3cc881e188ae122600f41acb46de154 Mon Sep 17 00:00:00 2001 From: Heeyong Song Date: Fri, 22 May 2020 16:23:43 +0900 Subject: [PATCH 03/16] Delete multiple surfaces when the updated thread is destroyed Change-Id: I1d2f1431f1b4bb827691e28bfffba96c542eb227 --- .../adaptor/common/combined-update-render-controller.cpp | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/dali/internal/adaptor/common/combined-update-render-controller.cpp b/dali/internal/adaptor/common/combined-update-render-controller.cpp index 5c5840a..75d469c 100644 --- a/dali/internal/adaptor/common/combined-update-render-controller.cpp +++ b/dali/internal/adaptor/common/combined-update-render-controller.cpp @@ -796,11 +796,15 @@ void CombinedUpdateRenderController::UpdateRenderThread() // Inform core of context destruction mCore.ContextDestroyed(); - currentSurface = mAdaptorInterfaces.GetRenderSurfaceInterface(); - if( currentSurface ) + + WindowContainer windows; + mAdaptorInterfaces.GetWindowContainerInterface( windows ); + + // Destroy surfaces + for( auto&& window : windows ) { - currentSurface->DestroySurface(); - currentSurface = nullptr; + Dali::RenderSurfaceInterface* surface = window->GetSurface(); + surface->DestroySurface(); } // Shutdown EGL -- 2.7.4 From b2ebaf613fe04fce45fa18b4d1bec27277d7e7f5 Mon Sep 17 00:00:00 2001 From: Heeyong Song Date: Tue, 28 Apr 2020 14:34:50 +0900 Subject: [PATCH 04/16] Add a thread mode In case of ThreadMode::RUN_IF_REQUESTED, the update thread runs when the application requests rendering. Change-Id: I8aac3fcd7fb802b0b8d5259fe40ecf14f7b905c3 --- dali/internal/adaptor/common/adaptor-impl.cpp | 19 ++++++++- dali/internal/adaptor/common/adaptor-impl.h | 2 + .../common/combined-update-render-controller.cpp | 49 +++++++++++++++++++--- .../common/combined-update-render-controller.h | 4 +- .../adaptor/common/thread-controller-interface.h | 9 +++- dali/internal/system/common/thread-controller.cpp | 4 +- dali/internal/system/common/thread-controller.h | 3 +- 7 files changed, 78 insertions(+), 12 deletions(-) diff --git a/dali/internal/adaptor/common/adaptor-impl.cpp b/dali/internal/adaptor/common/adaptor-impl.cpp index 737845d..a48eb5f 100755 --- a/dali/internal/adaptor/common/adaptor-impl.cpp +++ b/dali/internal/adaptor/common/adaptor-impl.cpp @@ -199,7 +199,7 @@ void Adaptor::Initialize( GraphicsFactory& graphicsFactory, Dali::Configuration: mDisplayConnection = Dali::DisplayConnection::New( *mGraphics, defaultWindow->GetSurface()->GetSurfaceType() ); - mThreadController = new ThreadController( *this, *mEnvironmentOptions ); + mThreadController = new ThreadController( *this, *mEnvironmentOptions, mThreadMode ); // Should be called after Core creation if( mEnvironmentOptions->GetPanGestureLoggingLevel() ) @@ -1030,7 +1030,21 @@ void Adaptor::NotifyLanguageChanged() void Adaptor::RenderOnce() { - RequestUpdateOnce(); + if( mThreadController ) + { + UpdateMode updateMode; + if( mThreadMode == ThreadMode::NORMAL ) + { + updateMode = UpdateMode::NORMAL; + } + else + { + updateMode = UpdateMode::FORCE_RENDER; + + ProcessCoreEvents(); + } + mThreadController->RequestUpdateOnce( updateMode ); + } } const LogFactoryInterface& Adaptor::GetLogFactory() @@ -1141,6 +1155,7 @@ Adaptor::Adaptor(Dali::Integration::SceneHolder window, Dali::Adaptor& adaptor, mSystemTracer(), mObjectProfiler( nullptr ), mSocketFactory(), + mThreadMode( ThreadMode::NORMAL ), mEnvironmentOptionsOwned( environmentOptions ? false : true /* If not provided then we own the object */ ), mUseRemoteSurface( false ) { diff --git a/dali/internal/adaptor/common/adaptor-impl.h b/dali/internal/adaptor/common/adaptor-impl.h index 9e4c079..31fd83a 100755 --- a/dali/internal/adaptor/common/adaptor-impl.h +++ b/dali/internal/adaptor/common/adaptor-impl.h @@ -76,6 +76,7 @@ class LifeCycleObserver; class ObjectProfiler; class SceneHolder; class ConfigurationManager; +enum class ThreadMode; /** * Implementation of the Adaptor class. @@ -685,6 +686,7 @@ private: // Data SystemTrace mSystemTracer; ///< System tracer ObjectProfiler* mObjectProfiler; ///< Tracks object lifetime for profiling SocketFactory mSocketFactory; ///< Socket factory + ThreadMode mThreadMode; ///< The thread mode const bool mEnvironmentOptionsOwned:1; ///< Whether we own the EnvironmentOptions (and thus, need to delete it) bool mUseRemoteSurface:1; ///< whether the remoteSurface is used or not diff --git a/dali/internal/adaptor/common/combined-update-render-controller.cpp b/dali/internal/adaptor/common/combined-update-render-controller.cpp index 75d469c..0e20903 100644 --- a/dali/internal/adaptor/common/combined-update-render-controller.cpp +++ b/dali/internal/adaptor/common/combined-update-render-controller.cpp @@ -89,7 +89,7 @@ const unsigned int MAXIMUM_UPDATE_REQUESTS = 2; // EVENT THREAD /////////////////////////////////////////////////////////////////////////////////////////////////// -CombinedUpdateRenderController::CombinedUpdateRenderController( AdaptorInternalServices& adaptorInterfaces, const EnvironmentOptions& environmentOptions ) +CombinedUpdateRenderController::CombinedUpdateRenderController( AdaptorInternalServices& adaptorInterfaces, const EnvironmentOptions& environmentOptions, ThreadMode threadMode ) : mFpsTracker( environmentOptions ), mUpdateStatusLogger( environmentOptions ), mEventThreadSemaphore(), @@ -109,6 +109,7 @@ CombinedUpdateRenderController::CombinedUpdateRenderController( AdaptorInternalS mDefaultHalfFrameNanoseconds( 0u ), mUpdateRequestCount( 0u ), mRunning( FALSE ), + mThreadMode( threadMode ), mUpdateRenderRunCount( 0 ), mDestroyUpdateRenderThread( FALSE ), mUpdateRenderThreadCanSleep( FALSE ), @@ -289,7 +290,7 @@ void CombinedUpdateRenderController::RequestUpdateOnce( UpdateMode updateMode ) ++mUpdateRequestCount; } - if( IsUpdateRenderThreadPaused() ) + if( IsUpdateRenderThreadPaused() || updateMode == UpdateMode::FORCE_RENDER ) { LOG_EVENT_TRACE; @@ -418,9 +419,31 @@ void CombinedUpdateRenderController::AddSurface( Dali::RenderSurfaceInterface* s void CombinedUpdateRenderController::RunUpdateRenderThread( int numberOfCycles, AnimationProgression animationProgression, UpdateMode updateMode ) { ConditionalWait::ScopedLock lock( mUpdateRenderThreadWaitCondition ); - mUpdateRenderRunCount = numberOfCycles; + + switch( mThreadMode ) + { + case ThreadMode::NORMAL: + { + mUpdateRenderRunCount = numberOfCycles; + mUseElapsedTimeAfterWait = ( animationProgression == AnimationProgression::USE_ELAPSED_TIME ); + break; + } + case ThreadMode::RUN_IF_REQUESTED: + { + if( updateMode != UpdateMode::FORCE_RENDER ) + { + // Render only if the update mode is FORCE_RENDER which means the application requests it. + // We don't want to awake the update thread. + return; + } + + mUpdateRenderRunCount++; // Increase the update request count + mUseElapsedTimeAfterWait = TRUE; // The elapsed time should be used. We want animations to proceed. + break; + } + } + mUpdateRenderThreadCanSleep = FALSE; - mUseElapsedTimeAfterWait = ( animationProgression == AnimationProgression::USE_ELAPSED_TIME ); mUploadWithoutRendering = ( updateMode == UpdateMode::SKIP_RENDER ); LOG_COUNTER_EVENT( "mUpdateRenderRunCount: %d, mUseElapsedTimeAfterWait: %d", mUpdateRenderRunCount, mUseElapsedTimeAfterWait ); mUpdateRenderThreadWaitCondition.Notify( lock ); @@ -442,6 +465,12 @@ void CombinedUpdateRenderController::StopUpdateRenderThread() bool CombinedUpdateRenderController::IsUpdateRenderThreadPaused() { ConditionalWait::ScopedLock lock( mUpdateRenderThreadWaitCondition ); + + if( mThreadMode == ThreadMode::RUN_IF_REQUESTED ) + { + return !mRunning || mUpdateRenderThreadCanSleep; + } + return ( mUpdateRenderRunCount != CONTINUOUS ) || // Report paused if NOT continuously running mUpdateRenderThreadCanSleep; // Report paused if sleeping } @@ -562,7 +591,7 @@ void CombinedUpdateRenderController::UpdateRenderThread() uint64_t currentFrameStartTime = 0; TimeService::GetNanoseconds( currentFrameStartTime ); - const uint64_t timeSinceLastFrame = currentFrameStartTime - lastFrameTime; + uint64_t timeSinceLastFrame = currentFrameStartTime - lastFrameTime; // Optional FPS Tracking when continuously rendering if( useElapsedTime && mFpsTracker.Enabled() ) @@ -609,6 +638,16 @@ void CombinedUpdateRenderController::UpdateRenderThread() float frameDelta = 0.0f; if( useElapsedTime ) { + if( mThreadMode == ThreadMode::RUN_IF_REQUESTED ) + { + extraFramesDropped = 0; + while( timeSinceLastFrame >= mDefaultFrameDurationNanoseconds ) + { + timeSinceLastFrame -= mDefaultFrameDurationNanoseconds; + extraFramesDropped++; + } + } + // If using the elapsed time, then calculate frameDelta as a multiple of mDefaultFrameDelta noOfFramesSinceLastUpdate += extraFramesDropped; diff --git a/dali/internal/adaptor/common/combined-update-render-controller.h b/dali/internal/adaptor/common/combined-update-render-controller.h index 54cc67d..965479e 100644 --- a/dali/internal/adaptor/common/combined-update-render-controller.h +++ b/dali/internal/adaptor/common/combined-update-render-controller.h @@ -80,7 +80,7 @@ public: /** * Constructor */ - CombinedUpdateRenderController( AdaptorInternalServices& adaptorInterfaces, const EnvironmentOptions& environmentOptions ); + CombinedUpdateRenderController( AdaptorInternalServices& adaptorInterfaces, const EnvironmentOptions& environmentOptions, ThreadMode threadMode ); /** * Non virtual destructor. Not intended as base class. @@ -367,6 +367,8 @@ private: unsigned int mUpdateRequestCount; ///< Count of update-requests we have received to ensure we do not go to sleep too early. unsigned int mRunning; ///< Read and set on the event-thread only to state whether we are running. + ThreadMode mThreadMode; ///< Whether the thread runs continuously or runs when it is requested. + // // NOTE: cannot use booleans as these are used from multiple threads, must use variable with machine word size for atomic read/write // diff --git a/dali/internal/adaptor/common/thread-controller-interface.h b/dali/internal/adaptor/common/thread-controller-interface.h index 6b9055b..efeb819 100644 --- a/dali/internal/adaptor/common/thread-controller-interface.h +++ b/dali/internal/adaptor/common/thread-controller-interface.h @@ -34,7 +34,14 @@ namespace Adaptor enum class UpdateMode { NORMAL, ///< Update and render - SKIP_RENDER ///< Update and resource upload but no rendering + SKIP_RENDER, ///< Update and resource upload but no rendering + FORCE_RENDER ///< Force update and render +}; + +enum class ThreadMode +{ + NORMAL, ///< The thread runs continuously + RUN_IF_REQUESTED ///< The threads runs when it is requested }; /** diff --git a/dali/internal/system/common/thread-controller.cpp b/dali/internal/system/common/thread-controller.cpp index a9054ec..31a5a24 100644 --- a/dali/internal/system/common/thread-controller.cpp +++ b/dali/internal/system/common/thread-controller.cpp @@ -32,14 +32,14 @@ namespace Internal namespace Adaptor { -ThreadController::ThreadController( AdaptorInternalServices& adaptorInterfaces, const EnvironmentOptions& environmentOptions ) +ThreadController::ThreadController( AdaptorInternalServices& adaptorInterfaces, const EnvironmentOptions& environmentOptions, ThreadMode threadMode ) : mThreadControllerInterface( NULL ) { switch( environmentOptions.GetThreadingMode() ) { case ThreadingMode::COMBINED_UPDATE_RENDER: { - mThreadControllerInterface = new CombinedUpdateRenderController( adaptorInterfaces, environmentOptions ); + mThreadControllerInterface = new CombinedUpdateRenderController( adaptorInterfaces, environmentOptions, threadMode ); break; } } diff --git a/dali/internal/system/common/thread-controller.h b/dali/internal/system/common/thread-controller.h index c4f3961..d51e57d 100644 --- a/dali/internal/system/common/thread-controller.h +++ b/dali/internal/system/common/thread-controller.h @@ -34,6 +34,7 @@ namespace Adaptor { enum class UpdateMode; +enum class ThreadMode; class AdaptorInternalServices; class EnvironmentOptions; @@ -49,7 +50,7 @@ public: /** * Constructor */ - ThreadController( AdaptorInternalServices& adaptorInterfaces, const EnvironmentOptions& environmentOptions ); + ThreadController( AdaptorInternalServices& adaptorInterfaces, const EnvironmentOptions& environmentOptions, ThreadMode threadMode ); /** * Non virtual destructor. Not intended as base class. -- 2.7.4 From c398715c18cdaf20493e6aded77b30e22ed6b0d3 Mon Sep 17 00:00:00 2001 From: Wonsik Jung Date: Tue, 2 Jun 2020 11:09:23 +0900 Subject: [PATCH 05/16] Update window's geometry to ecore_wl2. When the ecore wl2 window is resized or changed position then the window is hidden, the window's position and size is not updated by the Tizen Display Server. Because wayland protocol is destroyed by window's hidden. To fix that, window's geometry is updated again before window is shown. Change-Id: Iafa6a7ae5509c54f2e11bd6bd3ca8e0d23a1439b --- .../tizen-wayland/ecore-wl2/window-base-ecore-wl2.cpp | 15 +++++++++++++++ .../tizen-wayland/ecore-wl2/window-base-ecore-wl2.h | 3 +++ 2 files changed, 18 insertions(+) diff --git a/dali/internal/window-system/tizen-wayland/ecore-wl2/window-base-ecore-wl2.cpp b/dali/internal/window-system/tizen-wayland/ecore-wl2/window-base-ecore-wl2.cpp index 89fae58..dbd8aa6 100755 --- a/dali/internal/window-system/tizen-wayland/ecore-wl2/window-base-ecore-wl2.cpp +++ b/dali/internal/window-system/tizen-wayland/ecore-wl2/window-base-ecore-wl2.cpp @@ -688,6 +688,8 @@ WindowBaseEcoreWl2::WindowBaseEcoreWl2( Dali::PositionSize positionSize, Any sur mBrightness( 0 ), mBrightnessChangeState( 0 ), mBrightnessChangeDone( true ), + mVisible( true ), + mWindowPositionSize( positionSize ), mOwnSurface( false ), mMoveResizeSerial( 0 ), mLastSubmittedMoveResizeSerial( 0 ) @@ -949,6 +951,9 @@ void WindowBaseEcoreWl2::OnRotation( void* data, int type, void* event ) rotationEvent.height = ev->w; } + mWindowPositionSize.width = rotationEvent.width; + mWindowPositionSize.height = rotationEvent.height; + mRotationSignal.Emit( rotationEvent ); } } @@ -1521,16 +1526,19 @@ bool WindowBaseEcoreWl2::IsEglWindowRotationSupported() void WindowBaseEcoreWl2::Move( PositionSize positionSize ) { + mWindowPositionSize = positionSize; ecore_wl2_window_position_set( mEcoreWindow, positionSize.x, positionSize.y ); } void WindowBaseEcoreWl2::Resize( PositionSize positionSize ) { + mWindowPositionSize = positionSize; ecore_wl2_window_geometry_set( mEcoreWindow, positionSize.x, positionSize.y, positionSize.width, positionSize.height ); } void WindowBaseEcoreWl2::MoveResize( PositionSize positionSize ) { + mWindowPositionSize = positionSize; ecore_wl2_window_sync_geometry_set( mEcoreWindow, ++mMoveResizeSerial, positionSize.x, positionSize.y, positionSize.width, positionSize.height ); } @@ -1580,11 +1588,18 @@ void WindowBaseEcoreWl2::SetAcceptFocus( bool accept ) void WindowBaseEcoreWl2::Show() { + if( !mVisible ) + { + ecore_wl2_window_geometry_set( mEcoreWindow, mWindowPositionSize.x, mWindowPositionSize.y, mWindowPositionSize.width, mWindowPositionSize.height ); + } + mVisible = true; + ecore_wl2_window_show( mEcoreWindow ); } void WindowBaseEcoreWl2::Hide() { + mVisible = false; ecore_wl2_window_hide( mEcoreWindow ); } diff --git a/dali/internal/window-system/tizen-wayland/ecore-wl2/window-base-ecore-wl2.h b/dali/internal/window-system/tizen-wayland/ecore-wl2/window-base-ecore-wl2.h index c7a7240..f429435 100644 --- a/dali/internal/window-system/tizen-wayland/ecore-wl2/window-base-ecore-wl2.h +++ b/dali/internal/window-system/tizen-wayland/ecore-wl2/window-base-ecore-wl2.h @@ -496,6 +496,9 @@ private: uint32_t mBrightnessChangeState; bool mBrightnessChangeDone; + bool mVisible:1; + Dali::PositionSize mWindowPositionSize; + bool mOwnSurface; volatile uint32_t mMoveResizeSerial; -- 2.7.4 From 5167c1e4978ea61ffc8c3f74c15595b97662d347 Mon Sep 17 00:00:00 2001 From: Wonsik Jung Date: Tue, 2 Jun 2020 15:21:21 +0900 Subject: [PATCH 06/16] DALi Version 1.5.14 Change-Id: I2a694e23d32a43a58eba993458e54670a3373302 --- dali/public-api/dali-adaptor-version.cpp | 2 +- packaging/dali-adaptor.spec | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/dali/public-api/dali-adaptor-version.cpp b/dali/public-api/dali-adaptor-version.cpp index 5a65498..28b3ebd 100644 --- a/dali/public-api/dali-adaptor-version.cpp +++ b/dali/public-api/dali-adaptor-version.cpp @@ -28,7 +28,7 @@ namespace Dali const unsigned int ADAPTOR_MAJOR_VERSION = 1; const unsigned int ADAPTOR_MINOR_VERSION = 5; -const unsigned int ADAPTOR_MICRO_VERSION = 13; +const unsigned int ADAPTOR_MICRO_VERSION = 14; const char * const ADAPTOR_BUILD_DATE = __DATE__ " " __TIME__; #ifdef DEBUG_ENABLED diff --git a/packaging/dali-adaptor.spec b/packaging/dali-adaptor.spec index c5a2b63..acc28db 100644 --- a/packaging/dali-adaptor.spec +++ b/packaging/dali-adaptor.spec @@ -17,7 +17,7 @@ Name: dali-adaptor Summary: The DALi Tizen Adaptor -Version: 1.5.13 +Version: 1.5.14 Release: 1 Group: System/Libraries License: Apache-2.0 and BSD-3-Clause and MIT -- 2.7.4 From d95e058075b693420f96b803425a14f994929d43 Mon Sep 17 00:00:00 2001 From: Heeyong Song Date: Tue, 19 May 2020 17:32:25 +0900 Subject: [PATCH 07/16] Call PostRender method of the surface if needed Change-Id: Ic5651f52dfa42b08a4bc514af765188310f8f863 --- .../dali-test-suite-utils/test-application.cpp | 17 +++++++++++++---- .../dali-test-suite-utils/test-application.h | 1 + .../common/combined-update-render-controller.cpp | 11 ++++++++--- 3 files changed, 22 insertions(+), 7 deletions(-) diff --git a/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.cpp b/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.cpp index f85f14d..e8c0d12 100644 --- a/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.cpp +++ b/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.cpp @@ -188,9 +188,13 @@ bool TestApplication::Render( uint32_t intervalMilliseconds, const char* locatio { DoUpdate( intervalMilliseconds, location ); + // Reset the status + mRenderStatus.SetNeedsUpdate( false ); + mRenderStatus.SetNeedsPostRender( false ); + mCore->PreRender( mRenderStatus, false /*do not force clear*/, false /*do not skip rendering*/ ); - mCore->RenderScene( mScene, true /*render the off-screen buffers*/); - mCore->RenderScene( mScene, false /*render the surface*/); + mCore->RenderScene( mRenderStatus, mScene, true /*render the off-screen buffers*/); + mCore->RenderScene( mRenderStatus, mScene, false /*render the surface*/); mCore->PostRender( false /*do not skip rendering*/ ); mFrame++; @@ -214,12 +218,17 @@ bool TestApplication::GetRenderNeedsUpdate() return mRenderStatus.NeedsUpdate(); } +bool TestApplication::GetRenderNeedsPostRender() +{ + return mRenderStatus.NeedsPostRender(); +} + bool TestApplication::RenderOnly( ) { // Update Time values mCore->PreRender( mRenderStatus, false /*do not force clear*/, false /*do not skip rendering*/ ); - mCore->RenderScene( mScene, true /*render the off-screen buffers*/); - mCore->RenderScene( mScene, false /*render the surface*/); + mCore->RenderScene( mRenderStatus, mScene, true /*render the off-screen buffers*/); + mCore->RenderScene( mRenderStatus, mScene, false /*render the surface*/); mCore->PostRender( false /*do not skip rendering*/ ); mFrame++; diff --git a/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.h b/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.h index a922e23..e96f759 100644 --- a/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.h +++ b/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.h @@ -74,6 +74,7 @@ public: bool RenderOnly( ); void ResetContext(); bool GetRenderNeedsUpdate(); + bool GetRenderNeedsPostRender(); uint32_t Wait( uint32_t durationToWait ); static void EnableLogging( bool enabled ) { diff --git a/dali/internal/adaptor/common/combined-update-render-controller.cpp b/dali/internal/adaptor/common/combined-update-render-controller.cpp index 0e20903..b310671 100644 --- a/dali/internal/adaptor/common/combined-update-render-controller.cpp +++ b/dali/internal/adaptor/common/combined-update-render-controller.cpp @@ -741,18 +741,23 @@ void CombinedUpdateRenderController::UpdateRenderThread() if ( scene && windowSurface ) { + Integration::RenderStatus windowRenderStatus; + windowSurface->InitializeGraphics(); // Render off-screen frame buffers first if any - mCore.RenderScene( scene, true ); + mCore.RenderScene( windowRenderStatus, scene, true ); // Switch to the EGL context of the surface windowSurface->PreRender( surfaceResized ); // Switch GL context // Render the surface - mCore.RenderScene( scene, false ); + mCore.RenderScene( windowRenderStatus, scene, false ); - windowSurface->PostRender( false, false, surfaceResized ); // Swap Buffer + if( windowRenderStatus.NeedsPostRender() ) + { + windowSurface->PostRender( false, false, surfaceResized ); // Swap Buffer + } } } } -- 2.7.4 From 7e12b804069b4baedfbd6588cd238b4d5406e680 Mon Sep 17 00:00:00 2001 From: Joogab Yun Date: Mon, 8 Jun 2020 19:10:06 +0900 Subject: [PATCH 08/16] DALi Version 1.5.15 Change-Id: I3b8b0f9bb1d4d3ff852a88d552e9f030f7f845ab --- dali/public-api/dali-adaptor-version.cpp | 2 +- packaging/dali-adaptor.spec | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/dali/public-api/dali-adaptor-version.cpp b/dali/public-api/dali-adaptor-version.cpp index 28b3ebd..d89bb3f 100644 --- a/dali/public-api/dali-adaptor-version.cpp +++ b/dali/public-api/dali-adaptor-version.cpp @@ -28,7 +28,7 @@ namespace Dali const unsigned int ADAPTOR_MAJOR_VERSION = 1; const unsigned int ADAPTOR_MINOR_VERSION = 5; -const unsigned int ADAPTOR_MICRO_VERSION = 14; +const unsigned int ADAPTOR_MICRO_VERSION = 15; const char * const ADAPTOR_BUILD_DATE = __DATE__ " " __TIME__; #ifdef DEBUG_ENABLED diff --git a/packaging/dali-adaptor.spec b/packaging/dali-adaptor.spec index acc28db..7a83814 100644 --- a/packaging/dali-adaptor.spec +++ b/packaging/dali-adaptor.spec @@ -17,7 +17,7 @@ Name: dali-adaptor Summary: The DALi Tizen Adaptor -Version: 1.5.14 +Version: 1.5.15 Release: 1 Group: System/Libraries License: Apache-2.0 and BSD-3-Clause and MIT -- 2.7.4 From 62b1236eb4b8dea02d1c6e6d952a904de83ddd5f Mon Sep 17 00:00:00 2001 From: Heeyong Song Date: Mon, 8 Jun 2020 18:41:09 +0900 Subject: [PATCH 09/16] Throw an exception if the Adaptor is not instantiated Change-Id: I707c2d351d4c28cfb05954cdd6d59c08269d8024 --- dali/internal/adaptor/common/adaptor.cpp | 4 ++++ dali/internal/system/linux/timer-impl-ecore.cpp | 8 ++++---- 2 files changed, 8 insertions(+), 4 deletions(-) diff --git a/dali/internal/adaptor/common/adaptor.cpp b/dali/internal/adaptor/common/adaptor.cpp index e77dea8..9551d82 100755 --- a/dali/internal/adaptor/common/adaptor.cpp +++ b/dali/internal/adaptor/common/adaptor.cpp @@ -107,21 +107,25 @@ void Adaptor::Stop() bool Adaptor::AddIdle( CallbackBase* callback, bool hasReturnValue ) { + DALI_ASSERT_ALWAYS( IsAvailable() && "Adaptor not instantiated" ); return mImpl->AddIdle( callback, hasReturnValue, false ); } bool Adaptor::AddWindow( Dali::Integration::SceneHolder childWindow, const std::string& childWindowName, const std::string& childWindowClassName, bool childWindowMode ) { + DALI_ASSERT_ALWAYS( IsAvailable() && "Adaptor not instantiated" ); return mImpl->AddWindow( childWindow, childWindowName, childWindowClassName, childWindowMode ); } void Adaptor::RemoveIdle( CallbackBase* callback ) { + DALI_ASSERT_ALWAYS( IsAvailable() && "Adaptor not instantiated" ); mImpl->RemoveIdle( callback ); } void Adaptor::ProcessIdle() { + DALI_ASSERT_ALWAYS( IsAvailable() && "Adaptor not instantiated" ); mImpl->ProcessIdle(); } diff --git a/dali/internal/system/linux/timer-impl-ecore.cpp b/dali/internal/system/linux/timer-impl-ecore.cpp index fde050d..7ebea28 100644 --- a/dali/internal/system/linux/timer-impl-ecore.cpp +++ b/dali/internal/system/linux/timer-impl-ecore.cpp @@ -81,7 +81,7 @@ Timer::~Timer() void Timer::Start() { // Timer should be used in the event thread - DALI_ASSERT_DEBUG( Adaptor::IsAvailable() ); + DALI_ASSERT_ALWAYS( Adaptor::IsAvailable() ); if(mImpl->mId != NULL) { @@ -94,7 +94,7 @@ void Timer::Start() void Timer::Stop() { // Timer should be used in the event thread - DALI_ASSERT_DEBUG( Adaptor::IsAvailable() ); + DALI_ASSERT_ALWAYS( Adaptor::IsAvailable() ); ResetTimerData(); } @@ -102,7 +102,7 @@ void Timer::Stop() void Timer::Pause() { // Timer should be used in the event thread - DALI_ASSERT_DEBUG( Adaptor::IsAvailable() ); + DALI_ASSERT_ALWAYS( Adaptor::IsAvailable() ); if( mImpl->mId != NULL ) { @@ -113,7 +113,7 @@ void Timer::Pause() void Timer::Resume() { // Timer should be used in the event thread - DALI_ASSERT_DEBUG( Adaptor::IsAvailable() ); + DALI_ASSERT_ALWAYS( Adaptor::IsAvailable() ); if( mImpl->mId != NULL ) { -- 2.7.4 From 0e9c6d5b7970bf6f385efa3c9b2173cce83c3da0 Mon Sep 17 00:00:00 2001 From: neostom432 Date: Tue, 16 Jun 2020 02:15:02 +0900 Subject: [PATCH 10/16] DALi Version 1.5.16 Change-Id: I7380bcff70ae49949edf1fc1283e88533206fd16 --- dali/public-api/dali-adaptor-version.cpp | 2 +- packaging/dali-adaptor.spec | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/dali/public-api/dali-adaptor-version.cpp b/dali/public-api/dali-adaptor-version.cpp index d89bb3f..e5ef10f 100644 --- a/dali/public-api/dali-adaptor-version.cpp +++ b/dali/public-api/dali-adaptor-version.cpp @@ -28,7 +28,7 @@ namespace Dali const unsigned int ADAPTOR_MAJOR_VERSION = 1; const unsigned int ADAPTOR_MINOR_VERSION = 5; -const unsigned int ADAPTOR_MICRO_VERSION = 15; +const unsigned int ADAPTOR_MICRO_VERSION = 16; const char * const ADAPTOR_BUILD_DATE = __DATE__ " " __TIME__; #ifdef DEBUG_ENABLED diff --git a/packaging/dali-adaptor.spec b/packaging/dali-adaptor.spec index 7a83814..706b1fd 100644 --- a/packaging/dali-adaptor.spec +++ b/packaging/dali-adaptor.spec @@ -17,7 +17,7 @@ Name: dali-adaptor Summary: The DALi Tizen Adaptor -Version: 1.5.15 +Version: 1.5.16 Release: 1 Group: System/Libraries License: Apache-2.0 and BSD-3-Clause and MIT -- 2.7.4 From 31b3e92ff29394d14bcf9ff95b8a1e33173fd784 Mon Sep 17 00:00:00 2001 From: "huiyu.eun" Date: Tue, 16 Jun 2020 15:44:24 +0900 Subject: [PATCH 11/16] Change unsetenv to setenv unsetenv("AUL_LOADER_INIT") -> setenv("AUL_LOADER_INIT", "0", "1") Change-Id: If5420fc0a3baed766f03486ae14571bdd3d87212 Signed-off-by: huiyu.eun --- dali/internal/adaptor/tizen-wayland/framework-tizen.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/dali/internal/adaptor/tizen-wayland/framework-tizen.cpp b/dali/internal/adaptor/tizen-wayland/framework-tizen.cpp index c440eeb..1a05da1 100644 --- a/dali/internal/adaptor/tizen-wayland/framework-tizen.cpp +++ b/dali/internal/adaptor/tizen-wayland/framework-tizen.cpp @@ -401,7 +401,7 @@ struct Framework::Impl if(getenv("AUL_LOADER_INIT")) { - unsetenv("AUL_LOADER_INIT"); + setenv("AUL_LOADER_INIT", "0", 1); ecore_shutdown(); } } -- 2.7.4 From 6fca3747046705fdbebd72f6fe7f86aada43d707 Mon Sep 17 00:00:00 2001 From: Heeyong Song Date: Thu, 18 Jun 2020 15:42:22 +0900 Subject: [PATCH 12/16] Fix feedback sound API mm_sound_play_keysound() should be use with mm_sound_stop_keysound(). Change-Id: I4197a848508e12f880b30bded19d8c918b1af7bb --- plugins/dali-feedback.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/plugins/dali-feedback.cpp b/plugins/dali-feedback.cpp index c53935f..68dcc04 100644 --- a/plugins/dali-feedback.cpp +++ b/plugins/dali-feedback.cpp @@ -82,7 +82,7 @@ int DaliFeedback::PlaySound( const std::string& fileName ) void DaliFeedback::StopSound( int handle ) { - int errorCode = mm_sound_stop_sound( handle ); + int errorCode = mm_sound_stop_keysound( NULL ); if( errorCode < 0 ) { DEBUG_PRINTF( "StopSound() handle = %d failed with error code = %d\n", handle, errorCode); -- 2.7.4 From af634906664f835cd54f971dfe4bdf07216acb91 Mon Sep 17 00:00:00 2001 From: Joogab Yun Date: Wed, 17 Jun 2020 16:13:03 +0900 Subject: [PATCH 13/16] The advance of the letters is too narrow. So, remove the floor. Change-Id: Iae4c426819d7002ad1e4c7aab74818a3ef82aa30 --- dali/internal/text/text-abstraction/shaping-impl.cpp | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/dali/internal/text/text-abstraction/shaping-impl.cpp b/dali/internal/text/text-abstraction/shaping-impl.cpp index b785c02..da78f59 100755 --- a/dali/internal/text/text-abstraction/shaping-impl.cpp +++ b/dali/internal/text/text-abstraction/shaping-impl.cpp @@ -249,10 +249,10 @@ struct Shaping::Plugin const GlyphIndex index = rtlIndex + j; mIndices.PushBack( glyphInfo[index].codepoint ); - mAdvance.PushBack( floor( glyphPositions[index].x_advance * FROM_266 ) ); + mAdvance.PushBack( glyphPositions[index].x_advance * FROM_266 ); mCharacterMap.PushBack( glyphInfo[index].cluster ); - mOffset.PushBack( floor( glyphPositions[index].x_offset * FROM_266 ) ); - mOffset.PushBack( floor( glyphPositions[index].y_offset * FROM_266 ) ); + mOffset.PushBack( glyphPositions[index].x_offset * FROM_266 ); + mOffset.PushBack( glyphPositions[index].y_offset * FROM_266 ); } i += numberOfGlyphsInCluster; @@ -260,10 +260,10 @@ struct Shaping::Plugin else { mIndices.PushBack( glyphInfo[i].codepoint ); - mAdvance.PushBack( floor( glyphPositions[i].x_advance * FROM_266 ) ); + mAdvance.PushBack( glyphPositions[i].x_advance * FROM_266 ); mCharacterMap.PushBack( glyphInfo[i].cluster ); - mOffset.PushBack( floor( glyphPositions[i].x_offset * FROM_266 ) ); - mOffset.PushBack( floor( glyphPositions[i].y_offset * FROM_266 ) ); + mOffset.PushBack( glyphPositions[i].x_offset * FROM_266 ); + mOffset.PushBack( glyphPositions[i].y_offset * FROM_266 ); ++i; } -- 2.7.4 From aa35ce5329eb4bc15b19d919f6ce7d0ceb64be7a Mon Sep 17 00:00:00 2001 From: Anton Obzhirov Date: Tue, 14 Apr 2020 16:00:16 +0100 Subject: [PATCH 14/16] Partial update implementation, first phase. Change-Id: I222a1972d5727f6e01bb941b08339c38aad1546a --- .../dali-test-suite-utils/test-application.cpp | 38 ++- .../dali-test-suite-utils/test-application.h | 6 +- .../src/dali-adaptor/utc-Dali-Window.cpp | 18 ++ dali/devel-api/adaptor-framework/window-devel.cpp | 5 + dali/devel-api/adaptor-framework/window-devel.h | 15 +- .../adaptor-framework/render-surface-interface.h | 7 +- .../adaptor-framework/scene-holder-impl.cpp | 15 ++ dali/internal/adaptor/common/adaptor-impl.cpp | 3 +- .../common/combined-update-render-controller.cpp | 25 +- .../common/combined-update-render-controller.h | 2 + dali/internal/graphics/common/graphics-interface.h | 14 +- dali/internal/graphics/gles/egl-graphics.cpp | 13 +- dali/internal/graphics/gles/egl-graphics.h | 10 + dali/internal/graphics/gles/egl-implementation.cpp | 293 ++++++++++++++++++++- dali/internal/graphics/gles/egl-implementation.h | 48 +++- .../internal/system/common/environment-options.cpp | 18 +- dali/internal/system/common/environment-options.h | 6 + .../internal/system/common/environment-variables.h | 2 + dali/internal/window-system/common/window-impl.cpp | 106 ++++++++ dali/internal/window-system/common/window-impl.h | 5 + .../window-system/common/window-render-surface.cpp | 21 +- .../window-system/common/window-render-surface.h | 4 +- .../native-render-surface-ecore-wl.cpp | 22 +- .../tizen-wayland/native-render-surface-ecore-wl.h | 4 +- .../ubuntu-x11/pixmap-render-surface-ecore-x.cpp | 4 +- .../ubuntu-x11/pixmap-render-surface-ecore-x.h | 4 +- 26 files changed, 664 insertions(+), 44 deletions(-) diff --git a/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.cpp b/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.cpp index e8c0d12..b2a3fb9 100644 --- a/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.cpp +++ b/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.cpp @@ -26,13 +26,15 @@ TestApplication::TestApplication( uint32_t surfaceWidth, uint32_t surfaceHeight, uint32_t horizontalDpi, uint32_t verticalDpi, - bool initialize ) + bool initialize, + bool enablePartialUpdate ) : mCore( NULL ), mSurfaceWidth( surfaceWidth ), mSurfaceHeight( surfaceHeight ), mFrame( 0u ), mDpi{ horizontalDpi, verticalDpi }, - mLastVSyncTime(0u) + mLastVSyncTime(0u), + mPartialUpdateEnabled(enablePartialUpdate) { if( initialize ) { @@ -59,7 +61,8 @@ void TestApplication::CreateCore() mGlContextHelperAbstraction, Integration::RenderToFrameBuffer::FALSE, Integration::DepthBufferAvailable::TRUE, - Integration::StencilBufferAvailable::TRUE ); + Integration::StencilBufferAvailable::TRUE, + mPartialUpdateEnabled ? Integration::PartialUpdateAvailable::TRUE : Integration::PartialUpdateAvailable::FALSE ); mCore->ContextCreated(); @@ -193,8 +196,8 @@ bool TestApplication::Render( uint32_t intervalMilliseconds, const char* locatio mRenderStatus.SetNeedsPostRender( false ); mCore->PreRender( mRenderStatus, false /*do not force clear*/, false /*do not skip rendering*/ ); - mCore->RenderScene( mRenderStatus, mScene, true /*render the off-screen buffers*/); - mCore->RenderScene( mRenderStatus, mScene, false /*render the surface*/); + mCore->RenderScene( mRenderStatus, mScene, true /*render the off-screen buffers*/ ); + mCore->RenderScene( mRenderStatus, mScene, false /*render the surface*/ ); mCore->PostRender( false /*do not skip rendering*/ ); mFrame++; @@ -202,6 +205,27 @@ bool TestApplication::Render( uint32_t intervalMilliseconds, const char* locatio return mStatus.KeepUpdating() || mRenderStatus.NeedsUpdate(); } +bool TestApplication::PreRenderWithPartialUpdate(uint32_t intervalMilliseconds, const char* location, std::vector>& damagedRects) +{ + DoUpdate(intervalMilliseconds, location); + + mCore->PreRender(mRenderStatus, false /*do not force clear*/, false /*do not skip rendering*/ ); + mCore->PreRender(mScene, damagedRects); + + return mStatus.KeepUpdating() || mRenderStatus.NeedsUpdate(); +} + +bool TestApplication::RenderWithPartialUpdate(std::vector>& damagedRects, Rect& clippingRect) +{ + mCore->RenderScene(mRenderStatus, mScene, true /*render the off-screen buffers*/, clippingRect); + mCore->RenderScene(mRenderStatus, mScene, false /*render the surface*/, clippingRect); + mCore->PostRender(false /*do not skip rendering*/); + + mFrame++; + + return mStatus.KeepUpdating() || mRenderStatus.NeedsUpdate(); +} + uint32_t TestApplication::GetUpdateStatus() { return mStatus.KeepUpdating(); @@ -227,8 +251,8 @@ bool TestApplication::RenderOnly( ) { // Update Time values mCore->PreRender( mRenderStatus, false /*do not force clear*/, false /*do not skip rendering*/ ); - mCore->RenderScene( mRenderStatus, mScene, true /*render the off-screen buffers*/); - mCore->RenderScene( mRenderStatus, mScene, false /*render the surface*/); + mCore->RenderScene( mRenderStatus, mScene, true /*render the off-screen buffers*/ ); + mCore->RenderScene( mRenderStatus, mScene, false /*render the surface*/ ); mCore->PostRender( false /*do not skip rendering*/ ); mFrame++; diff --git a/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.h b/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.h index e96f759..1df0743 100644 --- a/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.h +++ b/automated-tests/src/dali-adaptor/dali-test-suite-utils/test-application.h @@ -51,7 +51,8 @@ public: uint32_t surfaceHeight = DEFAULT_SURFACE_HEIGHT, uint32_t horizontalDpi = DEFAULT_HORIZONTAL_DPI, uint32_t verticalDpi = DEFAULT_VERTICAL_DPI, - bool initialize = true ); + bool initialize = true, + bool enablePartialUpdate = false ); void Initialize(); void CreateCore(); @@ -69,6 +70,8 @@ public: void ProcessEvent(const Integration::Event& event); void SendNotification(); bool Render( uint32_t intervalMilliseconds = DEFAULT_RENDER_INTERVAL, const char* location=NULL ); + bool PreRenderWithPartialUpdate(uint32_t intervalMilliseconds, const char* location, std::vector>& damagedRects); + bool RenderWithPartialUpdate(std::vector>& damagedRects, Rect& clippingRect); uint32_t GetUpdateStatus(); bool UpdateOnly( uint32_t intervalMilliseconds = DEFAULT_RENDER_INTERVAL ); bool RenderOnly( ); @@ -108,6 +111,7 @@ protected: struct { uint32_t x; uint32_t y; } mDpi; uint32_t mLastVSyncTime; + bool mPartialUpdateEnabled; static bool mLoggingEnabled; }; diff --git a/automated-tests/src/dali-adaptor/utc-Dali-Window.cpp b/automated-tests/src/dali-adaptor/utc-Dali-Window.cpp index 4b14df2..cb7de36 100644 --- a/automated-tests/src/dali-adaptor/utc-Dali-Window.cpp +++ b/automated-tests/src/dali-adaptor/utc-Dali-Window.cpp @@ -16,6 +16,7 @@ */ #include +#include #include #include @@ -412,3 +413,20 @@ int UtcDaliWindowFocusChangedSignalN(void) END_TEST; } + +int UtcDaliWindowPartialUpdate(void) +{ + Dali::Window window; + try + { + std::vector> damagedAreas; + DevelWindow::SetDamagedAreas(window, damagedAreas); + DALI_TEST_CHECK( false ); // Should not reach here! + } + catch( ... ) + { + DALI_TEST_CHECK( true ); + } + + END_TEST; +} diff --git a/dali/devel-api/adaptor-framework/window-devel.cpp b/dali/devel-api/adaptor-framework/window-devel.cpp index b9fadbb..44e9801 100755 --- a/dali/devel-api/adaptor-framework/window-devel.cpp +++ b/dali/devel-api/adaptor-framework/window-devel.cpp @@ -148,6 +148,11 @@ int32_t GetNativeId( Window window ) return GetImplementation( window ).GetNativeId(); } +void SetDamagedAreas(Window window, std::vector>& areas) +{ + GetImplementation(window).SetDamagedAreas(areas); +} + } // namespace DevelWindow } // namespace Dali diff --git a/dali/devel-api/adaptor-framework/window-devel.h b/dali/devel-api/adaptor-framework/window-devel.h index 958b940..1eb3501 100755 --- a/dali/devel-api/adaptor-framework/window-devel.h +++ b/dali/devel-api/adaptor-framework/window-devel.h @@ -2,7 +2,7 @@ #define DALI_WINDOW_DEVEL_H /* - * Copyright (c) 2019 Samsung Electronics Co., Ltd. + * Copyright (c) 2020 Samsung Electronics Co., Ltd. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -18,7 +18,10 @@ * */ +// EXTERNAL INCLUDES + // INTERNAL INCLUDES +#include #include namespace Dali @@ -250,6 +253,16 @@ DALI_ADAPTOR_API void SetAvailableOrientations( Window window, const Dali::Vecto */ DALI_ADAPTOR_API int32_t GetNativeId( Window window ); +/** + * @brief Sets damaged areas of the window. + * + * This API is for setting static damaged areas of the window for partial update. + * + * @param[in] window The window instance + * @param[in] areas The damaged areas list to set + */ +DALI_ADAPTOR_API void SetDamagedAreas(Window window, std::vector>& areas); + } // namespace DevelWindow } // namespace Dali diff --git a/dali/integration-api/adaptor-framework/render-surface-interface.h b/dali/integration-api/adaptor-framework/render-surface-interface.h index 25ad128..e148662 100644 --- a/dali/integration-api/adaptor-framework/render-surface-interface.h +++ b/dali/integration-api/adaptor-framework/render-surface-interface.h @@ -20,6 +20,7 @@ // EXTERNAL INCLUDES #include +#include #include #include #include @@ -136,9 +137,10 @@ public: * If the operation fails, then Core::Render should not be called until there is * a surface to render onto. * @param[in] resizingSurface True if the surface is being resized + * @param[in] damagedRects List of damaged rects this render pass * @return True if the operation is successful, False if the operation failed */ - virtual bool PreRender( bool resizingSurface ) = 0; + virtual bool PreRender( bool resizingSurface, const std::vector>& damagedRects, Rect& clippingRect ) = 0; /** * @brief Invoked by render thread after Core::Render @@ -146,7 +148,8 @@ public: * @param[in] replacingSurface True if the surface is being replaced. * @param[in] resizingSurface True if the surface is being resized. */ - virtual void PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface ) = 0; + virtual void PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface, const std::vector>& damagedRects ) = 0; + /** * @brief Invoked by render thread when the thread should be stop */ diff --git a/dali/integration-api/adaptor-framework/scene-holder-impl.cpp b/dali/integration-api/adaptor-framework/scene-holder-impl.cpp index 7162a1c..5bbe94b 100644 --- a/dali/integration-api/adaptor-framework/scene-holder-impl.cpp +++ b/dali/integration-api/adaptor-framework/scene-holder-impl.cpp @@ -31,6 +31,7 @@ // INTERNAL INCLUDES #include #include +#include #include #include @@ -208,6 +209,13 @@ void SceneHolder::SurfaceResized() { PositionSize surfacePositionSize = mSurface->GetPositionSize(); mScene.SurfaceResized( static_cast( surfacePositionSize.width ), static_cast( surfacePositionSize.height ) ); + + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetFullSwapNextFrame(); + } } Dali::RenderSurfaceInterface* SceneHolder::GetSurface() const @@ -220,6 +228,13 @@ void SceneHolder::SetBackgroundColor( const Vector4& color ) if( mScene ) { mScene.SetBackgroundColor( color ); + + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetFullSwapNextFrame(); + } } } diff --git a/dali/internal/adaptor/common/adaptor-impl.cpp b/dali/internal/adaptor/common/adaptor-impl.cpp index a48eb5f..58f9c85 100755 --- a/dali/internal/adaptor/common/adaptor-impl.cpp +++ b/dali/internal/adaptor/common/adaptor-impl.cpp @@ -181,7 +181,8 @@ void Adaptor::Initialize( GraphicsFactory& graphicsFactory, Dali::Configuration: eglContextHelperImpl, ( 0u != mEnvironmentOptions->GetRenderToFboInterval() ) ? Integration::RenderToFrameBuffer::TRUE : Integration::RenderToFrameBuffer::FALSE, mGraphics->GetDepthBufferRequired(), - mGraphics->GetStencilBufferRequired() ); + mGraphics->GetStencilBufferRequired(), + mGraphics->GetPartialUpdateRequired() ); defaultWindow->SetAdaptor( Get() ); diff --git a/dali/internal/adaptor/common/combined-update-render-controller.cpp b/dali/internal/adaptor/common/combined-update-render-controller.cpp index b310671..b514cb6 100644 --- a/dali/internal/adaptor/common/combined-update-render-controller.cpp +++ b/dali/internal/adaptor/common/combined-update-render-controller.cpp @@ -745,18 +745,35 @@ void CombinedUpdateRenderController::UpdateRenderThread() windowSurface->InitializeGraphics(); + // clear previous frame damaged render items rects, buffer history is tracked on surface level + mDamagedRects.clear(); + + // If user damaged areas are not set + if (!eglImpl.DamageAreasSet()) + { + // Collect damage rects + mCore.PreRender( scene, mDamagedRects ); + } + // Render off-screen frame buffers first if any mCore.RenderScene( windowRenderStatus, scene, true ); - // Switch to the EGL context of the surface - windowSurface->PreRender( surfaceResized ); // Switch GL context + Rect clippingRect; // Empty for fbo rendering + + // Switch to the EGL context of the surface, merge damaged areas for previous frames + windowSurface->PreRender( surfaceResized, mDamagedRects, clippingRect ); // Switch GL context + + if (clippingRect.IsEmpty()) + { + mDamagedRects.clear(); + } // Render the surface - mCore.RenderScene( windowRenderStatus, scene, false ); + mCore.RenderScene( windowRenderStatus, scene, false, clippingRect ); if( windowRenderStatus.NeedsPostRender() ) { - windowSurface->PostRender( false, false, surfaceResized ); // Swap Buffer + windowSurface->PostRender( false, false, surfaceResized, mDamagedRects ); // Swap Buffer with damage } } } diff --git a/dali/internal/adaptor/common/combined-update-render-controller.h b/dali/internal/adaptor/common/combined-update-render-controller.h index 965479e..8dfd4eb 100644 --- a/dali/internal/adaptor/common/combined-update-render-controller.h +++ b/dali/internal/adaptor/common/combined-update-render-controller.h @@ -391,6 +391,8 @@ private: volatile unsigned int mUploadWithoutRendering; ///< Will be set to upload the resource only (with no rendering) volatile unsigned int mFirstFrameAfterResume; ///< Will be set to check the first frame after resume (for log) + + std::vector> mDamagedRects; ///< Keeps collected damaged render items rects for one render pass }; } // namespace Adaptor diff --git a/dali/internal/graphics/common/graphics-interface.h b/dali/internal/graphics/common/graphics-interface.h index 93c1b2f..4404fab 100644 --- a/dali/internal/graphics/common/graphics-interface.h +++ b/dali/internal/graphics/common/graphics-interface.h @@ -42,8 +42,9 @@ public: * Constructor */ GraphicsInterface() -: mDepthBufferRequired( Integration::DepthBufferAvailable::FALSE ), - mStencilBufferRequired( Integration::StencilBufferAvailable::FALSE ) + : mDepthBufferRequired( Integration::DepthBufferAvailable::FALSE ), + mStencilBufferRequired( Integration::StencilBufferAvailable::FALSE ), + mPartialUpdateRequired( Integration::PartialUpdateAvailable::FALSE ) { }; @@ -81,11 +82,20 @@ public: return mStencilBufferRequired; }; + /** + * Get whether the stencil buffer is required + * @return TRUE if the stencil buffer is required + */ + Integration::PartialUpdateAvailable GetPartialUpdateRequired() + { + return mPartialUpdateRequired; + }; protected: Integration::DepthBufferAvailable mDepthBufferRequired; ///< Whether the depth buffer is required Integration::StencilBufferAvailable mStencilBufferRequired; ///< Whether the stencil buffer is required + Integration::PartialUpdateAvailable mPartialUpdateRequired; ///< Whether the partial update is required }; } // Adaptor diff --git a/dali/internal/graphics/gles/egl-graphics.cpp b/dali/internal/graphics/gles/egl-graphics.cpp index 406e69c..e13ce0b 100644 --- a/dali/internal/graphics/gles/egl-graphics.cpp +++ b/dali/internal/graphics/gles/egl-graphics.cpp @@ -62,6 +62,7 @@ void EglGraphics::Initialize( EnvironmentOptions* environmentOptions ) mDepthBufferRequired = static_cast< Integration::DepthBufferAvailable >( environmentOptions->DepthBufferRequired() ); mStencilBufferRequired = static_cast< Integration::StencilBufferAvailable >( environmentOptions->StencilBufferRequired() ); + mPartialUpdateRequired = static_cast< Integration::PartialUpdateAvailable >( environmentOptions->PartialUpdateRequired() ); mMultiSamplingLevel = environmentOptions->GetMultiSamplingLevel(); @@ -72,7 +73,7 @@ void EglGraphics::Initialize( EnvironmentOptions* environmentOptions ) EglInterface* EglGraphics::Create() { - mEglImplementation = Utils::MakeUnique< EglImplementation >( mMultiSamplingLevel, mDepthBufferRequired, mStencilBufferRequired ); + mEglImplementation = Utils::MakeUnique< EglImplementation >( mMultiSamplingLevel, mDepthBufferRequired, mStencilBufferRequired, mPartialUpdateRequired ); mEglImageExtensions = Utils::MakeUnique< EglImageExtensions >( mEglImplementation.get() ); mEglSync->Initialize( mEglImplementation.get() ); // The sync impl needs the EglDisplay @@ -128,6 +129,16 @@ EglImageExtensions* EglGraphics::GetImageExtensions() return mEglImageExtensions.get(); } +void EglGraphics::SetDamagedAreas(std::vector>& areas) +{ + mEglImplementation->SetDamageAreas(areas); +} + +void EglGraphics::SetFullSwapNextFrame() +{ + mEglImplementation->SetFullSwapNextFrame(); +} + } // Adaptor } // Internal } // Dali diff --git a/dali/internal/graphics/gles/egl-graphics.h b/dali/internal/graphics/gles/egl-graphics.h index 8ee45bc..410395c 100644 --- a/dali/internal/graphics/gles/egl-graphics.h +++ b/dali/internal/graphics/gles/egl-graphics.h @@ -126,6 +126,16 @@ public: EglImageExtensions* GetImageExtensions(); /** + * Sets fixed damaged areas for partial rendering. This overrides automatic partial rendering. + */ + void SetDamagedAreas( std::vector>& areas ); + + /** + * Instructs egl implementation to do full swap regardless of stored data, resets the data. + */ + void SetFullSwapNextFrame(); + + /** * @copydoc Dali::Internal::Adaptor::GraphicsInterface::Destroy() */ void Destroy() override; diff --git a/dali/internal/graphics/gles/egl-implementation.cpp b/dali/internal/graphics/gles/egl-implementation.cpp index 38851f9..3710dd1 100755 --- a/dali/internal/graphics/gles/egl-implementation.cpp +++ b/dali/internal/graphics/gles/egl-implementation.cpp @@ -63,7 +63,8 @@ namespace Adaptor EglImplementation::EglImplementation( int multiSamplingLevel, Integration::DepthBufferAvailable depthBufferRequired, - Integration::StencilBufferAvailable stencilBufferRequired ) + Integration::StencilBufferAvailable stencilBufferRequired , + Integration::PartialUpdateAvailable partialUpdateRequired ) : mContextAttribs(), mEglNativeDisplay( 0 ), mEglNativeWindow( 0 ), @@ -81,9 +82,14 @@ EglImplementation::EglImplementation( int multiSamplingLevel, mIsWindow( true ), mDepthBufferRequired( depthBufferRequired == Integration::DepthBufferAvailable::TRUE ), mStencilBufferRequired( stencilBufferRequired == Integration::StencilBufferAvailable::TRUE ), + mPartialUpdateRequired( partialUpdateRequired == Integration::PartialUpdateAvailable::TRUE ), mIsSurfacelessContextSupported( false ), mIsKhrCreateContextSupported( false ), - mSwapBufferCountAfterResume( 0 ) + mSwapBufferCountAfterResume( 0 ), + mEglSetDamageRegionKHR( 0 ), + mEglSwapBuffersWithDamageKHR( 0 ), + mBufferAge( 0 ), + mFullSwapNextFrame( true ) { } @@ -169,6 +175,18 @@ bool EglImplementation::CreateContext() DALI_LOG_INFO(Debug::Filter::gShader, Debug::General, "*** GL_SHADING_LANGUAGE_VERSION : %s***\n", glGetString(GL_SHADING_LANGUAGE_VERSION)); DALI_LOG_INFO(Debug::Filter::gShader, Debug::General, "*** Supported Extensions ***\n%s\n\n", glGetString(GL_EXTENSIONS)); + mEglSetDamageRegionKHR = reinterpret_cast(eglGetProcAddress("eglSetDamageRegionKHR")); + if (!mEglSetDamageRegionKHR) + { + DALI_LOG_ERROR("Coudn't find eglSetDamageRegionKHR!\n"); + mPartialUpdateRequired = false; + } + mEglSwapBuffersWithDamageKHR = reinterpret_cast(eglGetProcAddress("eglSwapBuffersWithDamageKHR")); + if (!mEglSwapBuffersWithDamageKHR) + { + DALI_LOG_ERROR("Coudn't find eglSwapBuffersWithDamageKHR!\n"); + mPartialUpdateRequired = false; + } return true; } @@ -190,6 +208,18 @@ bool EglImplementation::CreateWindowContext( EGLContext& eglContext ) mEglWindowContexts.push_back( eglContext ); + mEglSetDamageRegionKHR = reinterpret_cast(eglGetProcAddress("eglSetDamageRegionKHR")); + if (!mEglSetDamageRegionKHR) + { + DALI_LOG_ERROR("Coudn't find eglSetDamageRegionKHR!\n"); + mPartialUpdateRequired = false; + } + mEglSwapBuffersWithDamageKHR = reinterpret_cast(eglGetProcAddress("eglSwapBuffersWithDamageKHR")); + if (!mEglSwapBuffersWithDamageKHR) + { + DALI_LOG_ERROR("Coudn't find eglSwapBuffersWithDamageKHR!\n"); + mPartialUpdateRequired = false; + } return true; } @@ -321,7 +351,266 @@ void EglImplementation::SwapBuffers( EGLSurface& eglSurface ) } #endif //DALI_PROFILE_UBUNTU + // DALI_LOG_ERROR("EglImplementation::SwapBuffers()\n"); eglSwapBuffers( mEglDisplay, eglSurface ); + mFullSwapNextFrame = false; + +#ifndef DALI_PROFILE_UBUNTU + if( mSwapBufferCountAfterResume < THRESHOLD_SWAPBUFFER_COUNT ) + { + DALI_LOG_RELEASE_INFO( "EglImplementation::SwapBuffers finished.\n" ); + mSwapBufferCountAfterResume++; + } +#endif //DALI_PROFILE_UBUNTU + } +} + +EGLint EglImplementation::GetBufferAge(EGLSurface& eglSurface) const +{ + EGLint age = 0; + eglQuerySurface(mEglDisplay, eglSurface, EGL_BUFFER_AGE_EXT, &age); + if (age < 0) + { + DALI_LOG_ERROR("eglQuerySurface(%d)\n", eglGetError()); + age = 0; + } + + // 0 - invalid buffer + // 1, 2, 3 + if (age > 3) + { + DALI_LOG_ERROR("EglImplementation::GetBufferAge() buffer age %d > 3\n", age); + age = 0; // shoudn't be more than 3 back buffers, if there is just reset, I don't want to add extra history level + } + + return age; +} + +bool EglImplementation::DamageAreasSet() const +{ + return (mDamagedAreas.size() ? true : false); +} + +void EglImplementation::SetDamageAreas( std::vector>& damagedAreas ) +{ + mFullSwapNextFrame = true; + mDamagedAreas = damagedAreas; +} + +void EglImplementation::SetFullSwapNextFrame() +{ + mFullSwapNextFrame = true; +} + +void mergeRects(Rect& mergingRect, const std::vector>& rects) +{ + uint32_t i = 0; + if (mergingRect.IsEmpty()) + { + for (;i < rects.size(); i++) + { + if (!rects[i].IsEmpty()) + { + mergingRect = rects[i]; + break; + } + } + } + + for (;i < rects.size(); i++) + { + mergingRect.Merge(rects[i]); + } +} + +void insertRects(std::list>>& damagedRectsList, const std::vector>& damagedRects) +{ + damagedRectsList.push_front(damagedRects); + if (damagedRectsList.size() > 4) // past triple buffers + current + { + damagedRectsList.pop_back(); + } +} + +void EglImplementation::SetDamage( EGLSurface& eglSurface, const std::vector>& damagedRects, Rect& clippingRect ) +{ + if (!mPartialUpdateRequired) + { + return; + } + + if (eglSurface != EGL_NO_SURFACE) // skip if using surfaceless context + { + EGLint width = 0; + EGLint height = 0; + eglQuerySurface(mEglDisplay, eglSurface, EGL_WIDTH, &width); + eglQuerySurface(mEglDisplay, eglSurface, EGL_HEIGHT, &height); + Rect surfaceRect(0, 0, width, height); + + mSurfaceRect = surfaceRect; + + if (mFullSwapNextFrame) + { + mBufferAge = 0; + insertRects(mBufferDamagedRects, std::vector>(1, surfaceRect)); + clippingRect = Rect(); + return; + } + + EGLint bufferAge = GetBufferAge(eglSurface); + if (mDamagedAreas.size()) + { + mBufferAge = bufferAge; + if (bufferAge == 0) + { + // Buffer age is reset + clippingRect = Rect(); + return; + } + + mergeRects(clippingRect, mDamagedAreas); + } + else + { + // Buffer age 0 means the back buffer in invalid and requires full swap + if (!damagedRects.size() || bufferAge != mBufferAge || bufferAge == 0) + { + // No damage or buffer is out of order or buffer age is reset + mBufferAge = bufferAge; + insertRects(mBufferDamagedRects, std::vector>(1, surfaceRect)); + clippingRect = Rect(); + return; + } + + // We push current frame damaged rects here, zero index for current frame + mBufferAge = bufferAge; + insertRects(mBufferDamagedRects, damagedRects); + + // Merge damaged rects into clipping rect + auto bufferDamagedRects = mBufferDamagedRects.begin(); + while (bufferAge-- >= 0 && bufferDamagedRects != mBufferDamagedRects.end()) + { + const std::vector>& rects = *bufferDamagedRects++; + mergeRects(clippingRect, rects); + } + } + + if (!clippingRect.Intersect(surfaceRect) || clippingRect.Area() > surfaceRect.Area() * 0.8) + { + // clipping area too big or doesn't intersect surface rect + clippingRect = Rect(); + return; + } + + // DALI_LOG_ERROR("eglSetDamageRegionKHR(%d, %d, %d, %d)\n", clippingRect.x, clippingRect.y, clippingRect.width, clippingRect.height); + EGLBoolean result = mEglSetDamageRegionKHR(mEglDisplay, eglSurface, reinterpret_cast(&clippingRect), 1); + if (result == EGL_FALSE) + { + DALI_LOG_ERROR("eglSetDamageRegionKHR(%d)\n", eglGetError()); + } + } +} + +void EglImplementation::SwapBuffers(EGLSurface& eglSurface, const std::vector>& damagedRects) +{ + if (eglSurface != EGL_NO_SURFACE ) // skip if using surfaceless context + { + if (!mPartialUpdateRequired || mFullSwapNextFrame || mBufferAge == 0 || !damagedRects.size()) + { + SwapBuffers(eglSurface); + return; + } + +#ifndef DALI_PROFILE_UBUNTU + if( mSwapBufferCountAfterResume < THRESHOLD_SWAPBUFFER_COUNT ) + { + DALI_LOG_RELEASE_INFO( "EglImplementation::SwapBuffers started.\n" ); + } +#endif //DALI_PROFILE_UBUNTU + + if (mDamagedAreas.size()) + { + // DALI_LOG_ERROR("EglImplementation::SwapBuffers(%d)\n", mDamagedAreas.size()); + EGLBoolean result = mEglSwapBuffersWithDamageKHR(mEglDisplay, eglSurface, reinterpret_cast(mDamagedAreas.data()), mDamagedAreas.size()); + if (result == EGL_FALSE) + { + DALI_LOG_ERROR("eglSwapBuffersWithDamageKHR(%d)\n", eglGetError()); + } + +#ifndef DALI_PROFILE_UBUNTU + if( mSwapBufferCountAfterResume < THRESHOLD_SWAPBUFFER_COUNT ) + { + DALI_LOG_RELEASE_INFO( "EglImplementation::SwapBuffers finished.\n" ); + mSwapBufferCountAfterResume++; + } +#endif //DALI_PROFILE_UBUNTU + return; + } + + // current frame damaged rects were pushed by EglImplementation::SetDamage() to 0 index. + EGLint bufferAge = mBufferAge; + mCombinedDamagedRects.clear(); + + // Combine damaged rects from previous frames (beginning from bufferAge index) with the current frame (0 index) + auto bufferDamagedRects = mBufferDamagedRects.begin(); + while (bufferAge-- >= 0 && bufferDamagedRects != mBufferDamagedRects.end()) + { + const std::vector>& rects = *bufferDamagedRects++; + mCombinedDamagedRects.insert(mCombinedDamagedRects.end(), rects.begin(), rects.end()); + } + + // Merge intersecting rects, form an array of non intersecting rects to help driver a bit + // Could be optional and can be removed, needs to be checked with and without on platform + const int n = mCombinedDamagedRects.size(); + for (int i = 0; i < n-1; i++) + { + if (mCombinedDamagedRects[i].IsEmpty()) + { + continue; + } + + for (int j = i+1; j < n; j++) + { + if (mCombinedDamagedRects[j].IsEmpty()) + { + continue; + } + + if (mCombinedDamagedRects[i].Intersects(mCombinedDamagedRects[j])) + { + mCombinedDamagedRects[i].Merge(mCombinedDamagedRects[j]); + mCombinedDamagedRects[j].width = 0; + mCombinedDamagedRects[j].height = 0; + } + } + } + + int j = 0; + for (int i = 0; i < n; i++) + { + if (!mCombinedDamagedRects[i].IsEmpty()) + { + mCombinedDamagedRects[j++] = mCombinedDamagedRects[i]; + } + } + + if (j != 0) + { + mCombinedDamagedRects.resize(j); + } + + if (!mCombinedDamagedRects.size() || (mCombinedDamagedRects[0].Area() > mSurfaceRect.Area() * 0.8)) + { + SwapBuffers(eglSurface); + return; + } + + // DALI_LOG_ERROR("EglImplementation::SwapBuffers(%d)\n", mCombinedDamagedRects.size()); + EGLBoolean result = mEglSwapBuffersWithDamageKHR(mEglDisplay, eglSurface, reinterpret_cast(mCombinedDamagedRects.data()), mCombinedDamagedRects.size()); + if (result == EGL_FALSE) + { + DALI_LOG_ERROR("eglSwapBuffersWithDamageKHR(%d)\n", eglGetError()); + } #ifndef DALI_PROFILE_UBUNTU if( mSwapBufferCountAfterResume < THRESHOLD_SWAPBUFFER_COUNT ) diff --git a/dali/internal/graphics/gles/egl-implementation.h b/dali/internal/graphics/gles/egl-implementation.h index efb9754..b505352 100644 --- a/dali/internal/graphics/gles/egl-implementation.h +++ b/dali/internal/graphics/gles/egl-implementation.h @@ -19,9 +19,13 @@ */ // EXTERNAL INCLUDES +#include +#include + #include #include #include +#include #include // INTERNAL INCLUDES @@ -46,10 +50,12 @@ public: * @param[in] multiSamplingLevel The Multi-sampling level required * @param[in] depthBufferRequired Whether the depth buffer is required * @param[in] stencilBufferRequired Whether the stencil buffer is required + * @param[in] partialUpdatedRequired Whether the partial update is required */ EglImplementation( int multiSamplingLevel, Integration::DepthBufferAvailable depthBufferRequired, - Integration::StencilBufferAvailable stencilBufferRequired ); + Integration::StencilBufferAvailable stencilBufferRequired, + Integration::PartialUpdateAvailable partialUpdateRequired ); /** * Destructor @@ -124,6 +130,36 @@ public: virtual void SwapBuffers( EGLSurface& eglSurface ); /** + * Gets current back buffer age + */ + EGLint GetBufferAge( EGLSurface& eglSurface ) const; + + /** + * Gets if user set damaged areas + */ + bool DamageAreasSet() const; + + /** + * Sets damaged areas, overrides auto calculated ones + */ + void SetDamageAreas( std::vector>& damagedArea ); + + /** + * Forces full surface swap next frame, resets current partial update state. + */ + void SetFullSwapNextFrame(); + + /** + * Performs an OpenGL set damage command with damaged rects + */ + virtual void SetDamage( EGLSurface& eglSurface, const std::vector>& damagedRects, Rect& clippingRect ); + + /** + * Performs an OpenGL swap buffers command with damaged rects + */ + virtual void SwapBuffers( EGLSurface& eglSurface, const std::vector>& damagedRects ); + + /** * Performs an OpenGL copy buffers command */ virtual void CopyBuffers( EGLSurface& eglSurface ); @@ -246,10 +282,20 @@ private: bool mIsWindow; bool mDepthBufferRequired; bool mStencilBufferRequired; + bool mPartialUpdateRequired; bool mIsSurfacelessContextSupported; bool mIsKhrCreateContextSupported; uint32_t mSwapBufferCountAfterResume; + PFNEGLSETDAMAGEREGIONKHRPROC mEglSetDamageRegionKHR; + PFNEGLSWAPBUFFERSWITHDAMAGEEXTPROC mEglSwapBuffersWithDamageKHR; + + EGLint mBufferAge; + std::list>> mBufferDamagedRects; + std::vector> mCombinedDamagedRects; + std::vector> mDamagedAreas; + Rect mSurfaceRect; + bool mFullSwapNextFrame; }; } // namespace Adaptor diff --git a/dali/internal/system/common/environment-options.cpp b/dali/internal/system/common/environment-options.cpp index 7fea428..1d00be7 100644 --- a/dali/internal/system/common/environment-options.cpp +++ b/dali/internal/system/common/environment-options.cpp @@ -42,6 +42,7 @@ const unsigned int DEFAULT_STATISTICS_LOG_FREQUENCY = 2; const int DEFAULT_MULTI_SAMPLING_LEVEL = -1; const bool DEFAULT_DEPTH_BUFFER_REQUIRED_SETTING = true; const bool DEFAULT_STENCIL_BUFFER_REQUIRED_SETTING = true; +const bool DEFAULT_PARTIAL_UPDATE_REQUIRED_SETTING = false; unsigned int GetIntegerEnvironmentVariable( const char* variable, unsigned int defaultValue ) { @@ -130,7 +131,8 @@ EnvironmentOptions::EnvironmentOptions() mThreadingMode( ThreadingMode::COMBINED_UPDATE_RENDER ), mGlesCallAccumulate( false ), mDepthBufferRequired( DEFAULT_DEPTH_BUFFER_REQUIRED_SETTING ), - mStencilBufferRequired( DEFAULT_STENCIL_BUFFER_REQUIRED_SETTING ) + mStencilBufferRequired( DEFAULT_STENCIL_BUFFER_REQUIRED_SETTING ), + mPartialUpdateRequired( DEFAULT_PARTIAL_UPDATE_REQUIRED_SETTING ) { ParseEnvironmentOptions(); } @@ -391,6 +393,11 @@ bool EnvironmentOptions::StencilBufferRequired() const return mStencilBufferRequired; } +bool EnvironmentOptions::PartialUpdateRequired() const +{ + return mPartialUpdateRequired; +} + void EnvironmentOptions::ParseEnvironmentOptions() { // get logging options @@ -660,6 +667,15 @@ void EnvironmentOptions::ParseEnvironmentOptions() mStencilBufferRequired = false; } } + + int partialUpdateRequired( -1 ); + if( GetIntegerEnvironmentVariable( DALI_ENV_ENABLE_PARTIAL_UPDATE, partialUpdateRequired ) ) + { + if( partialUpdateRequired > 0 ) + { + mPartialUpdateRequired = true; + } + } } } // Adaptor diff --git a/dali/internal/system/common/environment-options.h b/dali/internal/system/common/environment-options.h index f72ebdd..4d4b458 100644 --- a/dali/internal/system/common/environment-options.h +++ b/dali/internal/system/common/environment-options.h @@ -316,6 +316,11 @@ public: */ bool StencilBufferRequired() const; + /** + * @return Whether the partial update is required. + */ + bool PartialUpdateRequired() const; + /// Deleted copy constructor. EnvironmentOptions( const EnvironmentOptions& ) = delete; @@ -383,6 +388,7 @@ private: // Data bool mGlesCallAccumulate; ///< Whether or not to accumulate gles call statistics bool mDepthBufferRequired; ///< Whether the depth buffer is required bool mStencilBufferRequired; ///< Whether the stencil buffer is required + bool mPartialUpdateRequired; ///< Whether the partial update is required std::unique_ptr mTraceManager; ///< TraceManager }; diff --git a/dali/internal/system/common/environment-variables.h b/dali/internal/system/common/environment-variables.h index ca1a9c8..1be9185 100644 --- a/dali/internal/system/common/environment-variables.h +++ b/dali/internal/system/common/environment-variables.h @@ -128,6 +128,8 @@ namespace Adaptor #define DALI_ENV_DISABLE_STENCIL_BUFFER "DALI_DISABLE_STENCIL_BUFFER" +#define DALI_ENV_ENABLE_PARTIAL_UPDATE "DALI_ENABLE_PARTIAL_UPDATE" + #define DALI_ENV_WEB_ENGINE_NAME "DALI_WEB_ENGINE_NAME" #define DALI_ENV_DPI_HORIZONTAL "DALI_DPI_HORIZONTAL" diff --git a/dali/internal/window-system/common/window-impl.cpp b/dali/internal/window-system/common/window-impl.cpp index b21ca77..15be716 100755 --- a/dali/internal/window-system/common/window-impl.cpp +++ b/dali/internal/window-system/common/window-impl.cpp @@ -32,6 +32,7 @@ // INTERNAL HEADERS #include +#include #include #include #include @@ -188,18 +189,42 @@ std::string Window::GetClassName() const void Window::Raise() { mWindowBase->Raise(); + + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetFullSwapNextFrame(); + } + DALI_LOG_RELEASE_INFO( "Window (%p), WinId (%d), Raise() \n", this, mNativeWindowId ); } void Window::Lower() { mWindowBase->Lower(); + + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetFullSwapNextFrame(); + } + DALI_LOG_RELEASE_INFO( "Window (%p), WinId (%d), Lower() \n", this, mNativeWindowId ); } void Window::Activate() { mWindowBase->Activate(); + + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetFullSwapNextFrame(); + } + DALI_LOG_RELEASE_INFO( "Window (%p), WinId (%d), Activate() \n", this, mNativeWindowId ); } @@ -412,6 +437,13 @@ void Window::Show() mVisibilityChangedSignal.Emit( handle, true ); } + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetFullSwapNextFrame(); + } + DALI_LOG_RELEASE_INFO( "Window (%p), WinId (%d), Show(): iconified = %d, visible = %d\n", this, mNativeWindowId, mIconified, mVisible ); } @@ -430,6 +462,14 @@ void Window::Hide() mVisibilityChangedSignal.Emit( handle, false ); } + + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetFullSwapNextFrame(); + } + DALI_LOG_RELEASE_INFO( "Window (%p), WinId (%d), Hide(): iconified = %d, visible = %d\n", this, mNativeWindowId, mIconified, mVisible ); } @@ -478,6 +518,13 @@ void Window::SetInputRegion( const Rect< int >& inputRegion ) { mWindowBase->SetInputRegion( inputRegion ); + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetFullSwapNextFrame(); + } + DALI_LOG_INFO( gWindowLogFilter, Debug::Verbose, "Window::SetInputRegion: x = %d, y = %d, w = %d, h = %d\n", inputRegion.x, inputRegion.y, inputRegion.width, inputRegion.height ); } @@ -589,6 +636,13 @@ void Window::SetSize( Dali::Window::WindowSize size ) mAdaptor->SurfaceResizeComplete( mSurface.get(), newSize ); } + + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetFullSwapNextFrame(); + } } Dali::Window::WindowSize Window::GetSize() const @@ -609,6 +663,13 @@ void Window::SetPosition( Dali::Window::WindowPosition position ) PositionSize oldRect = mSurface->GetPositionSize(); mWindowSurface->MoveResize( PositionSize( position.GetX(), position.GetY(), oldRect.width, oldRect.height ) ); + + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetFullSwapNextFrame(); + } } Dali::Window::WindowPosition Window::GetPosition() const @@ -647,6 +708,13 @@ void Window::SetPositionSize( PositionSize positionSize ) mResizeSignal.Emit( handle, newSize ); mAdaptor->SurfaceResizeComplete( mSurface.get(), newSize ); } + + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetFullSwapNextFrame(); + } } Dali::Layer Window::GetRootLayer() const @@ -711,6 +779,13 @@ void Window::OnIconifyChanged( bool iconified ) DALI_LOG_RELEASE_INFO( "Window (%p), WinId (%d), Deiconified: visible = %d\n", this, mNativeWindowId, mVisible ); } + + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetFullSwapNextFrame(); + } } void Window::OnFocusChanged( bool focusIn ) @@ -718,6 +793,13 @@ void Window::OnFocusChanged( bool focusIn ) Dali::Window handle( this ); mFocusChangedSignal.Emit( focusIn ); mFocusChangeSignal.Emit( handle, focusIn ); + + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetFullSwapNextFrame(); + } } void Window::OnOutputTransformed() @@ -784,6 +866,13 @@ void Window::OnPause() { mEventHandler->Pause(); } + + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetFullSwapNextFrame(); + } } void Window::OnResume() @@ -792,6 +881,13 @@ void Window::OnResume() { mEventHandler->Resume(); } + + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetFullSwapNextFrame(); + } } void Window::RecalculateTouchPosition( Integration::Point& point ) @@ -915,6 +1011,16 @@ int32_t Window::GetNativeId() const return mWindowBase->GetNativeWindowId(); } +void Window::SetDamagedAreas(std::vector>& areas) +{ + GraphicsInterface& graphics = mAdaptor->GetGraphicsInterface(); + EglGraphics* eglGraphics = static_cast(&graphics); + if (eglGraphics) + { + eglGraphics->SetDamagedAreas(areas); + } +} + } // Adaptor } // Internal diff --git a/dali/internal/window-system/common/window-impl.h b/dali/internal/window-system/common/window-impl.h index ca1d3bf..3a877ae 100755 --- a/dali/internal/window-system/common/window-impl.h +++ b/dali/internal/window-system/common/window-impl.h @@ -359,6 +359,11 @@ public: */ void SetAvailableOrientations( const Dali::Vector& orientations ); + /** + * @copydoc Dali::DevelWindow::SetDamagedAreas() + */ + void SetDamagedAreas(std::vector>& areas); + public: // Dali::Internal::Adaptor::SceneHolder /** diff --git a/dali/internal/window-system/common/window-render-surface.cpp b/dali/internal/window-system/common/window-render-surface.cpp index c95d508..dfaefa4 100644 --- a/dali/internal/window-system/common/window-render-surface.cpp +++ b/dali/internal/window-system/common/window-render-surface.cpp @@ -352,10 +352,12 @@ void WindowRenderSurface::StartRender() { } -bool WindowRenderSurface::PreRender( bool resizingSurface ) +bool WindowRenderSurface::PreRender( bool resizingSurface, const std::vector>& damagedRects, Rect& clippingRect ) { MakeContextCurrent(); + auto eglGraphics = static_cast(mGraphics); + if( resizingSurface ) { // Window rotate or screen rotate @@ -386,19 +388,24 @@ bool WindowRenderSurface::PreRender( bool resizingSurface ) DALI_LOG_INFO( gWindowRenderSurfaceLogFilter, Debug::Verbose, "WindowRenderSurface::PreRender: Set resize\n" ); } + + if (eglGraphics) + { + Internal::Adaptor::EglImplementation& eglImpl = eglGraphics->GetEglImplementation(); + eglImpl.SetFullSwapNextFrame(); + } } - auto eglGraphics = static_cast(mGraphics); - if ( eglGraphics ) + if (eglGraphics) { - GlImplementation& mGLES = eglGraphics->GetGlesInterface(); - mGLES.PreRender(); + Internal::Adaptor::EglImplementation& eglImpl = eglGraphics->GetEglImplementation(); + eglImpl.SetDamage( mEGLSurface, damagedRects, clippingRect ); } return true; } -void WindowRenderSurface::PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface ) +void WindowRenderSurface::PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface, const std::vector>& damagedRects ) { // Inform the gl implementation that rendering has finished before informing the surface auto eglGraphics = static_cast(mGraphics); @@ -438,7 +445,7 @@ void WindowRenderSurface::PostRender( bool renderToFbo, bool replacingSurface, b } Internal::Adaptor::EglImplementation& eglImpl = eglGraphics->GetEglImplementation(); - eglImpl.SwapBuffers( mEGLSurface ); + eglImpl.SwapBuffers( mEGLSurface, damagedRects ); if( mRenderNotification ) { diff --git a/dali/internal/window-system/common/window-render-surface.h b/dali/internal/window-system/common/window-render-surface.h index f8160b8..bc03611 100644 --- a/dali/internal/window-system/common/window-render-surface.h +++ b/dali/internal/window-system/common/window-render-surface.h @@ -156,12 +156,12 @@ public: // from Dali::RenderSurfaceInterface /** * @copydoc Dali::RenderSurfaceInterface::PreRender() */ - virtual bool PreRender( bool resizingSurface ) override; + virtual bool PreRender( bool resizingSurface, const std::vector>& damagedRects, Rect& clippingRect ) override; /** * @copydoc Dali::RenderSurfaceInterface::PostRender() */ - virtual void PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface ); + virtual void PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface, const std::vector>& damagedRects ) override; /** * @copydoc Dali::RenderSurfaceInterface::StopRender() diff --git a/dali/internal/window-system/tizen-wayland/native-render-surface-ecore-wl.cpp b/dali/internal/window-system/tizen-wayland/native-render-surface-ecore-wl.cpp index 3ef4f68..48069c7 100644 --- a/dali/internal/window-system/tizen-wayland/native-render-surface-ecore-wl.cpp +++ b/dali/internal/window-system/tizen-wayland/native-render-surface-ecore-wl.cpp @@ -216,20 +216,30 @@ void NativeRenderSurfaceEcoreWl::StartRender() { } -bool NativeRenderSurfaceEcoreWl::PreRender( bool ) +bool NativeRenderSurfaceEcoreWl::PreRender( bool resizingSurface, const std::vector>& damagedRects, Rect& clippingRect ) { - // nothing to do for pixmaps + auto eglGraphics = static_cast(mGraphics); + if (eglGraphics) + { + Internal::Adaptor::EglImplementation& eglImpl = eglGraphics->GetEglImplementation(); + if (resizingSurface) + { + eglImpl.SetFullSwapNextFrame(); + } + + eglImpl.SetDamage(mEGLSurface, damagedRects, clippingRect); + } + return true; } -void NativeRenderSurfaceEcoreWl::PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface ) +void NativeRenderSurfaceEcoreWl::PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface, const std::vector>& damagedRects ) { auto eglGraphics = static_cast(mGraphics); - if ( eglGraphics ) + if (eglGraphics) { Internal::Adaptor::EglImplementation& eglImpl = eglGraphics->GetEglImplementation(); - - eglImpl.SwapBuffers( mEGLSurface ); + eglImpl.SwapBuffers( mEGLSurface, damagedRects ); } if( mThreadSynchronization ) diff --git a/dali/internal/window-system/tizen-wayland/native-render-surface-ecore-wl.h b/dali/internal/window-system/tizen-wayland/native-render-surface-ecore-wl.h index e3a33ba..bfca63c 100644 --- a/dali/internal/window-system/tizen-wayland/native-render-surface-ecore-wl.h +++ b/dali/internal/window-system/tizen-wayland/native-render-surface-ecore-wl.h @@ -116,12 +116,12 @@ public: // from Dali::RenderSurfaceInterface /** * @copydoc Dali::RenderSurfaceInterface::PreRender() */ - virtual bool PreRender( bool resizingSurface ) override; + virtual bool PreRender( bool resizingSurface, const std::vector>& damagedRects, Rect& clippingRect ) override; /** * @copydoc Dali::RenderSurfaceInterface::PostRender() */ - virtual void PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface ); + virtual void PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface, const std::vector>& damagedRects ) override; /** * @copydoc Dali::RenderSurfaceInterface::StopRender() diff --git a/dali/internal/window-system/ubuntu-x11/pixmap-render-surface-ecore-x.cpp b/dali/internal/window-system/ubuntu-x11/pixmap-render-surface-ecore-x.cpp index 2e93140..527f5cc 100644 --- a/dali/internal/window-system/ubuntu-x11/pixmap-render-surface-ecore-x.cpp +++ b/dali/internal/window-system/ubuntu-x11/pixmap-render-surface-ecore-x.cpp @@ -220,13 +220,13 @@ void PixmapRenderSurfaceEcoreX::StartRender() { } -bool PixmapRenderSurfaceEcoreX::PreRender( bool ) +bool PixmapRenderSurfaceEcoreX::PreRender( bool, const std::vector>&, Rect& ) { // Nothing to do for pixmaps return true; } -void PixmapRenderSurfaceEcoreX::PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface ) +void PixmapRenderSurfaceEcoreX::PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface, const std::vector>& damagedRects ) { auto eglGraphics = static_cast(mGraphics); diff --git a/dali/internal/window-system/ubuntu-x11/pixmap-render-surface-ecore-x.h b/dali/internal/window-system/ubuntu-x11/pixmap-render-surface-ecore-x.h index 034fee6..ebedfef 100644 --- a/dali/internal/window-system/ubuntu-x11/pixmap-render-surface-ecore-x.h +++ b/dali/internal/window-system/ubuntu-x11/pixmap-render-surface-ecore-x.h @@ -114,12 +114,12 @@ public: // from Dali::RenderSurfaceInterface /** * @copydoc Dali::RenderSurfaceInterface::PreRender() */ - virtual bool PreRender( bool resizingSurface ) override; + virtual bool PreRender( bool resizingSurface, const std::vector>& damagedRects, Rect& clippingRect ) override; /** * @copydoc Dali::RenderSurfaceInterface::PostRender() */ - virtual void PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface ) override; + virtual void PostRender( bool renderToFbo, bool replacingSurface, bool resizingSurface, const std::vector>& damagedRects ) override; /** * @copydoc Dali::RenderSurfaceInterface::StopRender() -- 2.7.4 From 4461208a8cf11f6c1765cc0fd81a8c46c0cd9b8d Mon Sep 17 00:00:00 2001 From: Sunghyun Kim Date: Mon, 22 Jun 2020 17:33:09 +0900 Subject: [PATCH 15/16] DALi Version 1.5.17 Change-Id: Ided273236003f8c233c282275d26259bfce35d8c --- dali/public-api/dali-adaptor-version.cpp | 2 +- packaging/dali-adaptor.spec | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/dali/public-api/dali-adaptor-version.cpp b/dali/public-api/dali-adaptor-version.cpp index e5ef10f..0fce620 100644 --- a/dali/public-api/dali-adaptor-version.cpp +++ b/dali/public-api/dali-adaptor-version.cpp @@ -28,7 +28,7 @@ namespace Dali const unsigned int ADAPTOR_MAJOR_VERSION = 1; const unsigned int ADAPTOR_MINOR_VERSION = 5; -const unsigned int ADAPTOR_MICRO_VERSION = 16; +const unsigned int ADAPTOR_MICRO_VERSION = 17; const char * const ADAPTOR_BUILD_DATE = __DATE__ " " __TIME__; #ifdef DEBUG_ENABLED diff --git a/packaging/dali-adaptor.spec b/packaging/dali-adaptor.spec index 706b1fd..6523580 100644 --- a/packaging/dali-adaptor.spec +++ b/packaging/dali-adaptor.spec @@ -17,7 +17,7 @@ Name: dali-adaptor Summary: The DALi Tizen Adaptor -Version: 1.5.16 +Version: 1.5.17 Release: 1 Group: System/Libraries License: Apache-2.0 and BSD-3-Clause and MIT -- 2.7.4 From 589ec1d7fa9d28ddd347b86bef3a730cecebc047 Mon Sep 17 00:00:00 2001 From: "huiyu.eun" Date: Mon, 25 Nov 2019 17:58:43 +0900 Subject: [PATCH 16/16] Add Component Application Structure Add Component Application Structure Change-Id: I6d37796b495db417f81d0cd14dd66818c0d69ba4 Signed-off-by: huiyu.eun --- build/tizen/deps-check.cmake | 7 ++ build/tizen/profiles/common-profile.cmake | 7 ++ build/tizen/profiles/ivi-profile.cmake | 7 ++ build/tizen/profiles/mobile-profile.cmake | 6 + build/tizen/profiles/tv-profile.cmake | 7 ++ build/tizen/profiles/wearable-profile.cmake | 7 ++ .../adaptor-framework/component-application.h | 127 +++++++++++++++++++++ dali/devel-api/file.list | 2 +- dali/internal/adaptor/common/framework.h | 13 ++- dali/internal/adaptor/file.list | 5 +- .../tizen-wayland/component-application-impl.cpp | 53 +++++++++ .../tizen-wayland/component-application-impl.h | 111 ++++++++++++++++++ .../tizen-wayland/component-application.cpp | 53 +++++++++ .../adaptor/tizen-wayland/framework-tizen.cpp | 121 ++++++++++++++++---- dali/public-api/file.list | 2 +- packaging/dali-adaptor.spec | 6 +- 16 files changed, 505 insertions(+), 29 deletions(-) create mode 100644 dali/devel-api/adaptor-framework/component-application.h create mode 100644 dali/internal/adaptor/tizen-wayland/component-application-impl.cpp create mode 100644 dali/internal/adaptor/tizen-wayland/component-application-impl.h create mode 100644 dali/internal/adaptor/tizen-wayland/component-application.cpp diff --git a/build/tizen/deps-check.cmake b/build/tizen/deps-check.cmake index b496dd9..ac5382a 100644 --- a/build/tizen/deps-check.cmake +++ b/build/tizen/deps-check.cmake @@ -89,6 +89,7 @@ CHECK_MODULE_AND_SET( CAPI_SYSTEM_INFO capi-system-info [] ) CHECK_MODULE_AND_SET( CAPI_SYSTEM_SENSOR capi-system-sensor capi_system_sensor_support ) CHECK_MODULE_AND_SET( CAPI_SYSTEM_SYSTEM_SETTINGS capi-system-system-settings [] ) CHECK_MODULE_AND_SET( CAPI_APPFW_APPLICATION capi-appfw-application [] ) +CHECK_MODULE_AND_SET( COMPONENT_BASED_CORE_BASE component-based-core-base [] ) CHECK_MODULE_AND_SET( ELEMENTARY elementary [] ) CHECK_MODULE_AND_SET( BUNDLE bundle [] ) @@ -211,6 +212,10 @@ ELSE() SET( cachePath /home/owner ) ENDIF() +IF( enable_appfw ) + ADD_DEFINITIONS( -DUSE_APPFW -DCOMPONENT_APPLICATION_SUPPORT) +ENDIF() + ####################################################### ADD_DEFINITIONS( -DDALI_PROFILE_${enable_profile}) @@ -330,6 +335,7 @@ IF( enable_appfw ) ${CAPI_APPFW_WIDGET_BASE_CFLAGS} ${ECORE_IMF_CFLAGS} ${FRIBIDI_CFLAGS} + ${COMPONENT_BASED_CORE_BASE_CFLAGS} ) SET( DALI_LDFLAGS ${DALI_LDFLAGS} @@ -344,6 +350,7 @@ IF( enable_appfw ) ${CAPI_APPFW_WIDGET_BASE_LDFLAGS} ${ECORE_IMF_LDFLAGS} ${FRIBIDI_LDFLAGS} + ${COMPONENT_BASED_CORE_BASE_LDFLAGS} ) ELSE() SET( DALI_CFLAGS ${DALI_CFLAGS} diff --git a/build/tizen/profiles/common-profile.cmake b/build/tizen/profiles/common-profile.cmake index 2c18ce0..bdc26ff 100644 --- a/build/tizen/profiles/common-profile.cmake +++ b/build/tizen/profiles/common-profile.cmake @@ -65,3 +65,10 @@ IF( ENABLE_TRACE ) ${adaptor_trace_tizen_src_files} ) ENDIF() + +IF( COMPONENT_APPLICATION_SUPPORT ) + SET( SOURCES ${SOURCES} + ${adaptor_adaptor_component_application_src_files} + ) +ENDIF() + diff --git a/build/tizen/profiles/ivi-profile.cmake b/build/tizen/profiles/ivi-profile.cmake index 765a1ea..77d540c 100644 --- a/build/tizen/profiles/ivi-profile.cmake +++ b/build/tizen/profiles/ivi-profile.cmake @@ -66,3 +66,10 @@ IF( ENABLE_TRACE ) ${adaptor_trace_tizen_src_files} ) ENDIF() + +IF( COMPONENT_APPLICATION_SUPPORT ) + SET( SOURCES ${SOURCES} + ${adaptor_adaptor_component_application_src_files} + ) +ENDIF() + diff --git a/build/tizen/profiles/mobile-profile.cmake b/build/tizen/profiles/mobile-profile.cmake index 38cc849..0ba3e35 100644 --- a/build/tizen/profiles/mobile-profile.cmake +++ b/build/tizen/profiles/mobile-profile.cmake @@ -66,3 +66,9 @@ IF( ENABLE_TRACE ) ) ENDIF() +IF( COMPONENT_APPLICATION_SUPPORT ) + SET( SOURCES ${SOURCES} + ${adaptor_adaptor_component_application_src_files} + ) +ENDIF() + diff --git a/build/tizen/profiles/tv-profile.cmake b/build/tizen/profiles/tv-profile.cmake index fbaa533..ff4b008 100644 --- a/build/tizen/profiles/tv-profile.cmake +++ b/build/tizen/profiles/tv-profile.cmake @@ -65,3 +65,10 @@ IF( ENABLE_TRACE ) ${adaptor_trace_tizen_src_files} ) ENDIF() + +IF( COMPONENT_APPLICATION_SUPPORT ) + SET( SOURCES ${SOURCES} + ${adaptor_adaptor_component_application_src_files} + ) +ENDIF() + diff --git a/build/tizen/profiles/wearable-profile.cmake b/build/tizen/profiles/wearable-profile.cmake index 3682664..7d5b1b4 100644 --- a/build/tizen/profiles/wearable-profile.cmake +++ b/build/tizen/profiles/wearable-profile.cmake @@ -67,3 +67,10 @@ IF( ENABLE_TRACE ) ${adaptor_trace_tizen_src_files} ) ENDIF() + +IF( COMPONENT_APPLICATION_SUPPORT ) + SET( SOURCES ${SOURCES} + ${adaptor_adaptor_component_application_src_files} + ) +ENDIF() + diff --git a/dali/devel-api/adaptor-framework/component-application.h b/dali/devel-api/adaptor-framework/component-application.h new file mode 100644 index 0000000..1f23b2f --- /dev/null +++ b/dali/devel-api/adaptor-framework/component-application.h @@ -0,0 +1,127 @@ +#ifndef DALI_COMPONENT_APPLICATION_H +#define DALI_COMPONENT_APPLICATION_H + +/* + * Copyright (c) 2020 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +// INTERNAL INCLUDES +#include + +namespace Dali +{ +namespace Internal DALI_INTERNAL +{ + +namespace Adaptor +{ +class ComponentApplication; +} + +} + +/** + * @brief An ComponentApplication class object should be created by every component-based application + * that wishes to use Dali. + * + * Component application draw multiple UI applications based on frame components. + * component application can draw multiple UIs in one process. + * + * It provides a means for initializing the + * resources required by the Dali::Core. + * + * The ComponentApplication class emits several signals which the user can + * connect to. The user should not create any Dali objects in the main + * function and instead should connect to the Init signal of the + * ComponentApplication and create the Dali Widget object in the connected callback. + * + */ +class DALI_ADAPTOR_API ComponentApplication : public Application +{ +public: + typedef Signal< Any () > CreateSignalType; + +public: + /** + * @brief This is the constructor for component applications without an argument list. + * @return A handle to the ComponentApplication + */ + static ComponentApplication New( ); + + /** + * @brief This is the constructor for component applications. + * + * @param[in,out] argc A pointer to the number of arguments + * @param[in,out] argv A pointer to the argument list + * @return A handle to the ComponentApplication + */ + static ComponentApplication New( int* argc, char **argv[] ); + + /** + * @brief This is the constructor for component applications with a stylesheet + * + * @param[in,out] argc A pointer to the number of arguments + * @param[in,out] argv A pointer to the argument list + * @param[in] stylesheet The path to user defined theme file + * @return A handle to the ComponentApplication + */ + static ComponentApplication New( int* argc, char **argv[], const std::string& stylesheet ); + + /** + * @brief The default constructor. + */ + ComponentApplication() = default; + + /** + * @brief Copy Constructor. + * + * @param[in] componentApplication Handle to an object + */ + ComponentApplication( const ComponentApplication& componentApplication ) = default; + + /** + * @brief Assignment operator. + * + * @param[in] componentApplication Handle to an object + * @return A reference to this + */ + ComponentApplication& operator=( const ComponentApplication& componentApplication ) = default; + + /** + * @brief Destructor + */ + ~ComponentApplication() = default; + + /** + * @brief The user should connect to this signal to determine when they should initialize + * their application. + * The callback function is called before the main loop of the application starts. + * @return The signal to connect to + */ + CreateSignalType& CreateSignal(); + +public: + /// @cond internal + /** + * @brief Internal constructor. + */ + explicit DALI_INTERNAL ComponentApplication(Internal::Adaptor::ComponentApplication* componentApplication); + /// @endcond +}; +} // namespace Dali + +#endif // DALI_COMPONENT_APPLICATION_H + diff --git a/dali/devel-api/file.list b/dali/devel-api/file.list index 33c3ab3..b7e8f1f 100755 --- a/dali/devel-api/file.list +++ b/dali/devel-api/file.list @@ -84,6 +84,7 @@ SET( devel_api_adaptor_framework_header_files ${adaptor_devel_api_dir}/adaptor-framework/key-devel.h ${adaptor_devel_api_dir}/adaptor-framework/thread-settings.h ${adaptor_devel_api_dir}/adaptor-framework/window-devel.h + ${adaptor_devel_api_dir}/adaptor-framework/component-application.h ) @@ -117,4 +118,3 @@ SET( text_abstraction_header_files ${adaptor_devel_api_dir}/text-abstraction/text-renderer.h ${adaptor_devel_api_dir}/text-abstraction/text-renderer-layout-helper.h ) - diff --git a/dali/internal/adaptor/common/framework.h b/dali/internal/adaptor/common/framework.h index d95388c..e4b172b 100644 --- a/dali/internal/adaptor/common/framework.h +++ b/dali/internal/adaptor/common/framework.h @@ -28,6 +28,9 @@ // INTERNAL INCLUDES #include #include +#ifdef COMPONENT_APPLICATION_SUPPORT +#include +#endif namespace Dali { @@ -54,7 +57,8 @@ public: { NORMAL, ///< normal appFramework WATCH, ///< watch appFramework - WIDGET ///< widget appFramework + WIDGET, ///< widget appFramework + COMPONENT ///< component appFramework }; /** @@ -141,6 +145,13 @@ public: * Invoked when the platform surface is destroyed. */ virtual void OnSurfaceDestroyed( Any newSurface ) {} + +#ifdef COMPONENT_APPLICATION_SUPPORT + /** + * Invoked when the component application is created. + */ + virtual Any OnCreate() { return nullptr; } +#endif }; public: diff --git a/dali/internal/adaptor/file.list b/dali/internal/adaptor/file.list index defd518..cf5b02c 100644 --- a/dali/internal/adaptor/file.list +++ b/dali/internal/adaptor/file.list @@ -48,4 +48,7 @@ SET( adaptor_adaptor_windows_src_files ${adaptor_adaptor_dir}/windows/framework-win.cpp ) - +SET( adaptor_adaptor_component_application_src_files + ${adaptor_adaptor_dir}/tizen-wayland/component-application.cpp + ${adaptor_adaptor_dir}/tizen-wayland/component-application-impl.cpp +) diff --git a/dali/internal/adaptor/tizen-wayland/component-application-impl.cpp b/dali/internal/adaptor/tizen-wayland/component-application-impl.cpp new file mode 100644 index 0000000..bf3855c --- /dev/null +++ b/dali/internal/adaptor/tizen-wayland/component-application-impl.cpp @@ -0,0 +1,53 @@ +/* + * Copyright (c) 2020 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +// CLASS HEADER +#include + +namespace Dali +{ + +namespace Internal +{ + +namespace Adaptor +{ +ComponentApplicationPtr ComponentApplication::New( + int* argc, + char **argv[], + const std::string& stylesheet, + Dali::Application::WINDOW_MODE windowMode) +{ + ComponentApplicationPtr application ( new ComponentApplication (argc, argv, stylesheet, windowMode ) ); + return application; +} + +ComponentApplication::ComponentApplication( int* argc, char** argv[], const std::string& stylesheet, Dali::Application::WINDOW_MODE windowMode ) +: Application(argc, argv, stylesheet, windowMode, PositionSize(), Framework::COMPONENT) +{ +} + +Any ComponentApplication::OnCreate() +{ + return mCreateSignal.Emit(); +} + +} // namespace Adaptor + +} // namespace Internal + +} // namespace Dali diff --git a/dali/internal/adaptor/tizen-wayland/component-application-impl.h b/dali/internal/adaptor/tizen-wayland/component-application-impl.h new file mode 100644 index 0000000..cd7e6c2 --- /dev/null +++ b/dali/internal/adaptor/tizen-wayland/component-application-impl.h @@ -0,0 +1,111 @@ +#ifndef DALI_INTERNAL_COMPONENT_APPLICATION_H +#define DALI_INTERNAL_COMPONENT_APPLICATION_H + +/* + * Copyright (c) 2020 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +// INTERNAL INCLUDES +#include +#include + +namespace Dali +{ +class Adaptor; + +namespace Internal +{ + +namespace Adaptor +{ + +class ComponentApplication; +typedef IntrusivePtr ComponentApplicationPtr; + +/** + * Implementation of the ComponentApplication class. + */ +class ComponentApplication : public Application +{ +public: + typedef Dali::ComponentApplication::CreateSignalType CreateSignal; + +public: + /** + * Create a new component application + * @param[in] argc A pointer to the number of arguments + * @param[in] argv A pointer to the argument list + * @param[in] stylesheet The path to user defined theme file + * @param[in] windowMode A member of WINDOW_MODE + * @return A handle to the ComponentApplication + */ + static ComponentApplicationPtr New( int* argc, char **argv[], const std::string& stylesheet, WINDOW_MODE windowMode ); + + /** + * @brief The default constructor. + */ + ComponentApplication( int* argc, char **argv[], const std::string& stylesheet, WINDOW_MODE windowMode ); + + /** + * @brief Undefined copy constructor. + */ + ComponentApplication( const ComponentApplication& ) = default; + + /** + * @brief Destructor + */ + virtual ~ComponentApplication() = default; + + /** + *@brief Undefined assignment operator. + */ + ComponentApplication& operator=( const ComponentApplication& ) = delete; + +public: // From Framework::Observer + /** + * Called when the framework is Component Application Created. + */ + virtual Any OnCreate(); + +public: + CreateSignal mCreateSignal; +}; + +inline ComponentApplication& GetImplementation(Dali::ComponentApplication& application) +{ + DALI_ASSERT_ALWAYS(application && "application handle is empty"); + + BaseObject& handle = application.GetBaseObject(); + + return static_cast(handle); +} + +inline const ComponentApplication& GetImplementation(const Dali::ComponentApplication& application) +{ + DALI_ASSERT_ALWAYS(application && "application handle is empty"); + + const BaseObject& handle = application.GetBaseObject(); + + return static_cast(handle); +} + + +} // namespace Adaptor + +} // namespace Internal + +} // namespace Dali +#endif diff --git a/dali/internal/adaptor/tizen-wayland/component-application.cpp b/dali/internal/adaptor/tizen-wayland/component-application.cpp new file mode 100644 index 0000000..c1e0761 --- /dev/null +++ b/dali/internal/adaptor/tizen-wayland/component-application.cpp @@ -0,0 +1,53 @@ +/* + * Copyright (c) 2020 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +// CLASS HEADER +#include + +// INTERNAL INCLUDES +#include + +namespace Dali +{ + +ComponentApplication ComponentApplication::New() +{ + return New( NULL, NULL ); +} + +ComponentApplication ComponentApplication::New( int* argc, char **argv[] ) +{ + return New( argc, argv, "" ); +} + +ComponentApplication ComponentApplication::New( int* argc, char **argv[], const std::string& stylesheet ) +{ + Internal::Adaptor::ComponentApplicationPtr internal = Internal::Adaptor::ComponentApplication::New( argc, argv, stylesheet, TRANSPARENT ); + return ComponentApplication(internal.Get()); +} + +ComponentApplication::CreateSignalType& ComponentApplication::CreateSignal() +{ + return Internal::Adaptor::GetImplementation(*this).mCreateSignal; +} + +ComponentApplication::ComponentApplication(Internal::Adaptor::ComponentApplication* implementation) +: Application(implementation) +{ +} + +} // namespace Dali diff --git a/dali/internal/adaptor/tizen-wayland/framework-tizen.cpp b/dali/internal/adaptor/tizen-wayland/framework-tizen.cpp index 1a05da1..d4236cf 100644 --- a/dali/internal/adaptor/tizen-wayland/framework-tizen.cpp +++ b/dali/internal/adaptor/tizen-wayland/framework-tizen.cpp @@ -41,6 +41,10 @@ #include #endif // TIZEN_PLATFORM_CONFIG_SUPPORTED +#ifdef COMPONENT_APPLICATION_SUPPORT +#include +#endif + #include // INTERNAL INCLUDES @@ -222,35 +226,60 @@ struct Framework::Impl int AppMain() { int ret; - - if (mApplicationType == NORMAL) - { - ret = AppNormalMain(); - } - else if(mApplicationType == WIDGET) + switch ( mApplicationType ) { - ret = AppWidgetMain(); - } - else - { - ret = AppWatchMain(); + case NORMAL: + { + ret = AppNormalMain(); + break; + } + case WIDGET: + { + ret = AppWidgetMain(); + break; + } + case WATCH: + { + ret = AppWatchMain(); + break; + } +#ifdef COMPONENT_APPLICATION_SUPPORT + case COMPONENT: + { + ret = AppComponentMain(); + break; + } +#endif } return ret; } void AppExit() { - if (mApplicationType == NORMAL) - { - AppNormalExit(); - } - else if(mApplicationType == WIDGET) + switch ( mApplicationType ) { - AppWidgetExit(); - } - else - { - AppWatchExit(); + case NORMAL: + { + AppNormalExit(); + break; + } + case WIDGET: + { + AppWidgetExit(); + break; + } + case WATCH: + { + AppWatchExit(); + break; + } +#ifdef COMPONENT_APPLICATION_SUPPORT + case COMPONENT: + { + AppComponentExit(); + break; + } +#endif } } @@ -697,6 +726,56 @@ struct Framework::Impl #endif } +#ifdef COMPONENT_APPLICATION_SUPPORT + int AppComponentMain() + { + int ret; + + /*Crate component_based_app_base_lifecycle_callback*/ + component_based_app_base_lifecycle_callback_s callback; + callback.init = AppInit; + callback.run = AppRun; + callback.exit = AppExit; + callback.create = ComponentAppCreate; + callback.terminate = ComponentAppTerminate; + callback.fini = ComponentAppFinish; + + return component_based_app_base_main(*mFramework->mArgc, *mFramework->mArgv, &callback, mFramework);; + } + + static void* ComponentAppCreate( void *data ) + { + Framework* framework = static_cast(data); + Observer *observer = &framework->mObserver; + observer->OnInit(); + + return Dali::AnyCast( observer->OnCreate() ); + } + + static void ComponentAppTerminate( void *data ) + { + Observer *observer = &static_cast(data)->mObserver; + observer->OnTerminate(); + } + + static void ComponentAppFinish( void *data ) + { + ecore_shutdown(); + + if(getenv("AUL_LOADER_INIT")) + { + setenv("AUL_LOADER_INIT", "0", 1); + ecore_shutdown(); + } + } + + void AppComponentExit() + { + component_based_app_base_exit(); + } + +#endif + private: // Undefined Impl( const Impl& impl ); diff --git a/dali/public-api/file.list b/dali/public-api/file.list index 71866f1..e4d3ac3 100644 --- a/dali/public-api/file.list +++ b/dali/public-api/file.list @@ -54,4 +54,4 @@ SET( adaptor_dali_wearable_header_file SET( public_dali_watch_header_files ${adaptor_public_api_dir}/watch/watch-application.h ${adaptor_public_api_dir}/watch/watch-time.h -) \ No newline at end of file +) diff --git a/packaging/dali-adaptor.spec b/packaging/dali-adaptor.spec index 6523580..0e7a469 100644 --- a/packaging/dali-adaptor.spec +++ b/packaging/dali-adaptor.spec @@ -103,6 +103,7 @@ BuildRequires: pkgconfig(capi-system-system-settings) # for feedback plugin BuildRequires: pkgconfig(mm-sound) BuildRequires: pkgconfig(feedback) +BuildRequires: pkgconfig(component-based-core-base) # for multiprofile Requires: %{name}-compat = %{version}-%{release} @@ -277,10 +278,6 @@ cmake_flags+=" -DCMAKE_BUILD_TYPE=Debug" cmake_flags+=" -DENABLE_TRACE=ON" %endif -%if 0%{?enable_appfw} -cmake_flags+=" -DUSE_APPFW" -%endif - libtoolize --force cd %{_builddir}/%{name}-%{version}/build/tizen @@ -300,6 +297,7 @@ cmake_flags+=" -DCMAKE_INSTALL_INCLUDEDIR=%{_includedir}" cmake_flags+=" -DENABLE_TIZEN_MAJOR_VERSION=%{tizen_version_major}" cmake_flags+=" -DENABLE_FEEDBACK=YES" cmake_flags+=" -DENABLE_APPFW=YES" +cmake_flags+=" -DCOMPONENT_APPLICATION_SUPPORT=YES" # Set up the build via Cmake ####################################################################### -- 2.7.4