Allowed Bubble emitter to recover from context loss 43/28043/5
authorDavid Steele <david.steele@partner.samsung.com>
Wed, 24 Sep 2014 18:17:59 +0000 (19:17 +0100)
committerDavid Steele <david.steele@partner.samsung.com>
Wed, 5 Nov 2014 13:06:12 +0000 (13:06 +0000)
[Problem]  Bubble emitter's background render task is deleted on completion.
Context loss removes frame buffer image, and there is no mechanism to regenerate it.
[Cause]    New requirement
[Solution] Add listener to Stage::ContextRegainedSignal() to re-run the
render task and regenerate the background image.

Change-Id: I08b54b286b04d22b923785b0634497f13380045f
Signed-off-by: David Steele <david.steele@partner.samsung.com>
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-application.cpp
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-application.h
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-platform-abstraction.cpp
optional/dali-toolkit/internal/controls/bubble-effect/bubble-emitter-impl.cpp
optional/dali-toolkit/internal/controls/bubble-effect/bubble-emitter-impl.h

index c2680b2..89138eb 100644 (file)
@@ -24,13 +24,15 @@ namespace Dali
 TestApplication::TestApplication( size_t surfaceWidth,
                                   size_t surfaceHeight,
                                   float  horizontalDpi,
-                                  float  verticalDpi)
+                                  float  verticalDpi,
+                                  ResourcePolicy::DataRetention policy)
 : mCore( NULL ),
   mSurfaceWidth( surfaceWidth ),
   mSurfaceHeight( surfaceHeight ),
   mFrame( 0u ),
   mDpi( horizontalDpi, verticalDpi ),
-  mLastVSyncTime(0u)
+  mLastVSyncTime(0u),
+  mDataRetentionPolicy( policy )
 {
   Initialize();
 }
@@ -39,12 +41,14 @@ TestApplication::TestApplication( bool   initialize,
                                   size_t surfaceWidth,
                                   size_t surfaceHeight,
                                   float  horizontalDpi,
-                                  float  verticalDpi )
+                                  float  verticalDpi,
+                                  ResourcePolicy::DataRetention policy)
 : mCore( NULL ),
   mSurfaceWidth( surfaceWidth ),
   mSurfaceHeight( surfaceHeight ),
   mFrame( 0u ),
-  mDpi( horizontalDpi, verticalDpi )
+  mDpi( horizontalDpi, verticalDpi ),
+  mDataRetentionPolicy( policy )
 {
   if ( initialize )
   {
@@ -59,7 +63,8 @@ void TestApplication::Initialize()
     mPlatformAbstraction,
     mGlAbstraction,
     mGlSyncAbstraction,
-    mGestureManager );
+    mGestureManager,
+    mDataRetentionPolicy);
 
   mCore->ContextCreated();
   mCore->SurfaceResized( mSurfaceWidth, mSurfaceHeight );
@@ -190,7 +195,7 @@ bool TestApplication::RenderOnly( )
 
 void TestApplication::ResetContext()
 {
-  mCore->ContextToBeDestroyed();
+  mCore->ContextDestroyed();
   mCore->ContextCreated();
 }
 
index bcc2dd8..d3bf259 100644 (file)
@@ -50,13 +50,17 @@ public:
   TestApplication( size_t surfaceWidth  = DEFAULT_SURFACE_WIDTH,
                    size_t surfaceHeight = DEFAULT_SURFACE_HEIGHT,
                    float  horizontalDpi = DEFAULT_HORIZONTAL_DPI,
-                   float  verticalDpi   = DEFAULT_VERTICAL_DPI );
+                   float  verticalDpi   = DEFAULT_VERTICAL_DPI,
+                   ResourcePolicy::DataRetention resourcePolicy = ResourcePolicy::DALI_DISCARDS_ALL_DATA );
+
+
 
   TestApplication( bool   initialize,
                    size_t surfaceWidth  = DEFAULT_SURFACE_WIDTH,
                    size_t surfaceHeight = DEFAULT_SURFACE_HEIGHT,
                    float  horizontalDpi = DEFAULT_HORIZONTAL_DPI,
-                   float  verticalDpi   = DEFAULT_VERTICAL_DPI );
+                   float  verticalDpi   = DEFAULT_VERTICAL_DPI,
+                   ResourcePolicy::DataRetention resourcePolicy = ResourcePolicy::DALI_DISCARDS_ALL_DATA );
 
   void Initialize();
   virtual ~TestApplication();
@@ -97,6 +101,7 @@ protected:
 
   Vector2 mDpi;
   unsigned int mLastVSyncTime;
+  ResourcePolicy::DataRetention mDataRetentionPolicy;
 };
 
 } // Dali
index ef3eb77..aa1b5b2 100644 (file)
@@ -227,7 +227,7 @@ Integration::GlyphSet* TestPlatformAbstraction::GetGlyphData ( const Integration
 
       if( getBitmap )
       {
-        bitmapData = Integration::Bitmap::New(Integration::Bitmap::BITMAP_2D_PACKED_PIXELS, true);
+        bitmapData = Integration::Bitmap::New(Integration::Bitmap::BITMAP_2D_PACKED_PIXELS, ResourcePolicy::DISCARD);
         bitmapData->GetPackedPixelsProfile()->ReserveBuffer(Pixel::A8, 64, 64);
         PixelBuffer* pixelBuffer = bitmapData->GetBuffer();
         memset( pixelBuffer, it->character, 64*64 );
@@ -268,7 +268,7 @@ Integration::GlyphSet* TestPlatformAbstraction::GetCachedGlyphData( const Integr
       characters.insert( it->character );
       Integration::GlyphMetrics character = {it->character, Integration::GlyphMetrics::HIGH_QUALITY,  10.0f,  10.0f, 9.0f, 1.0f, 10.0f, it->xPosition, it->yPosition };
 
-      bitmapData = Integration::Bitmap::New(Integration::Bitmap::BITMAP_2D_PACKED_PIXELS, true);
+      bitmapData = Integration::Bitmap::New(Integration::Bitmap::BITMAP_2D_PACKED_PIXELS, ResourcePolicy::DISCARD);
       bitmapData->GetPackedPixelsProfile()->ReserveBuffer(Pixel::A8, 64, 64);
       PixelBuffer* pixelBuffer = bitmapData->GetBuffer();
       memset( pixelBuffer, it->character, 64*64 );
@@ -455,7 +455,7 @@ void TestPlatformAbstraction::GetFileNamesFromDirectory( const std::string& dire
 
 Integration::BitmapPtr TestPlatformAbstraction::GetGlyphImage( const std::string& fontFamily, const std::string& fontStyle, float fontSize, uint32_t character ) const
 {
-  Integration::BitmapPtr image = Integration::Bitmap::New( Integration::Bitmap::BITMAP_2D_PACKED_PIXELS, true );
+  Integration::BitmapPtr image = Integration::Bitmap::New( Integration::Bitmap::BITMAP_2D_PACKED_PIXELS, ResourcePolicy::DISCARD );
   image->GetPackedPixelsProfile()->ReserveBuffer( Pixel::RGBA8888, 1, 1 );
 
   mTrace.PushCall("GetGlyphImage", "");
index 62ef78d..787f842 100644 (file)
@@ -42,6 +42,7 @@ BubbleEmitter::BubbleEmitter( const Vector2& movementArea,
   mMovementArea( movementArea ),
   mShapeImage( shapeImage ),
   mTotalNumOfBubble( maximumNumberOfBubble ),
+  mRenderTaskRunning(false),
   mBubbleSizeRange( bubbleSizeRange ),
   mCurrentUniform( 0 ),
   mDensity( 5 )
@@ -129,7 +130,11 @@ void BubbleEmitter::OnInitialize()
   // Create a cameraActor for the off screen render task.
   mCameraActor = CameraActor::New(mMovementArea);
   mCameraActor.SetParentOrigin(ParentOrigin::CENTER);
-  Stage::GetCurrent().Add(mCameraActor);
+
+  Stage stage = Stage::GetCurrent();
+
+  stage.Add(mCameraActor);
+  stage.ContextRegainedSignal().Connect(this, &BubbleEmitter::OnContextRegained);
 }
 
 Actor BubbleEmitter::GetRootActor()
@@ -139,6 +144,9 @@ Actor BubbleEmitter::GetRootActor()
 
 void BubbleEmitter::SetBackground( Image bgImage, const Vector3& hsvDelta )
 {
+  mBackgroundImage = bgImage;
+  mHSVDelta = hsvDelta;
+
   ImageActor sourceActor = ImageActor::New( bgImage );
   sourceActor.SetSize( mMovementArea );
   sourceActor.SetParentOrigin(ParentOrigin::CENTER);
@@ -156,6 +164,7 @@ void BubbleEmitter::SetBackground( Image bgImage, const Vector3& hsvDelta )
   task.GetCameraActor().SetInvertYAxis(true);
   task.SetTargetFrameBuffer( mEffectImage );
   task.FinishedSignal().Connect(this, &BubbleEmitter::OnRenderFinished);
+  mRenderTaskRunning = true;
 }
 
 void BubbleEmitter::SetShapeImage( Image shapeImage )
@@ -204,6 +213,7 @@ void BubbleEmitter::SetBubbleDensity( unsigned int density )
 // clear the resources created for the off screen rendering
 void BubbleEmitter::OnRenderFinished(RenderTask& source)
 {
+  mRenderTaskRunning = false;
   Actor sourceActor = source.GetSourceActor();
   if( sourceActor )
   {
@@ -213,8 +223,20 @@ void BubbleEmitter::OnRenderFinished(RenderTask& source)
       renderable.RemoveShaderEffect();
     }
   }
-  Stage::GetCurrent().Remove(sourceActor);
-  Stage::GetCurrent().GetRenderTaskList().RemoveTask(source);
+
+  Stage stage = Stage::GetCurrent();
+  stage.Remove(sourceActor);
+  stage.GetRenderTaskList().RemoveTask(source);
+}
+
+void BubbleEmitter::OnContextRegained()
+{
+  // Context was lost, so the framebuffer has been destroyed. Re-create render task
+  // and trigger re-draw if not already running
+  if( ! mRenderTaskRunning )
+  {
+    SetBackground( mBackgroundImage, mHSVDelta );
+  }
 }
 
 void BubbleEmitter::SetBlendMode( bool enable )
index f8952af..30ed0a0 100644 (file)
@@ -135,6 +135,11 @@ private:
   void OnRenderFinished(RenderTask& source);
 
   /**
+   * Callback function from Stage to tell us if the context has been regained.
+   */
+  void OnContextRegained();
+
+  /**
    * Generate the material object which is attached to the meshActor to describe its color, texture, texture mapping mode etc.
    */
   void GenMaterial();
@@ -207,6 +212,8 @@ private:
   unsigned int                mNumBubblePerShader;  ///< How many bubbles for each BubbleEffect shader.
   unsigned int                mNumShader;           ///< How many BubbleEffect shaders are used.
   unsigned int                mTotalNumOfBubble;    ///< mNumBubblePerShader*mNumShader.
+  bool                        mRenderTaskRunning;   ///< If the background render task is currently running
+
   Vector2                     mBubbleSizeRange;     ///< The bubble size range.
 
   std::vector<Mesh>           mMesh;                ///< The mesh vector, each mesh is used to create a meshActor which applies a BubbleEffect.
@@ -219,6 +226,8 @@ private:
 
   unsigned int                mCurrentUniform;      ///< Keep track of the uniform index for the newly emitted bubble
 
+  Vector3                     mHSVDelta;            ///< The HSV difference used to adjust the background image color.
+  Image                       mBackgroundImage;     ///< The original background image
   FrameBufferImage            mEffectImage;         ///< The image stores the adjusted color of the background image.The bubbles pick color from this image.
   CameraActor                 mCameraActor;         ///< The render task views the scene from the perspective of this actor.