[dali_1.1.5] Merge branch 'devel/master' 79/48979/1
authorChu Hoang <c.hoang@samsung.com>
Fri, 2 Oct 2015 09:39:14 +0000 (10:39 +0100)
committerChu Hoang <c.hoang@samsung.com>
Fri, 2 Oct 2015 09:39:14 +0000 (10:39 +0100)
Change-Id: I2e16bbff8532a10e8b997abc1e536343c12bd737

46 files changed:
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-platform-abstraction.cpp
automated-tests/src/dali-toolkit/dali-toolkit-test-utils/test-platform-abstraction.h
automated-tests/src/dali-toolkit/utc-Dali-Control.cpp
automated-tests/src/dali-toolkit/utc-Dali-ControlRenderer.cpp
automated-tests/src/dali-toolkit/utc-Dali-RendererFactory.cpp
automated-tests/src/dali-toolkit/utc-Dali-ShaderEffects.cpp
dali-toolkit/devel-api/controls/renderer-factory/control-renderer.cpp
dali-toolkit/devel-api/controls/renderer-factory/control-renderer.h
dali-toolkit/devel-api/controls/renderer-factory/renderer-factory.cpp
dali-toolkit/devel-api/controls/renderer-factory/renderer-factory.h
dali-toolkit/devel-api/shader-effects/dissolve-effect.h
dali-toolkit/internal/controls/image-view/image-view-impl.cpp
dali-toolkit/internal/controls/renderers/border/border-renderer.cpp
dali-toolkit/internal/controls/renderers/border/border-renderer.h
dali-toolkit/internal/controls/renderers/color/color-renderer.cpp
dali-toolkit/internal/controls/renderers/color/color-renderer.h
dali-toolkit/internal/controls/renderers/control-renderer-data-impl.cpp [new file with mode: 0644]
dali-toolkit/internal/controls/renderers/control-renderer-data-impl.h
dali-toolkit/internal/controls/renderers/control-renderer-impl.cpp
dali-toolkit/internal/controls/renderers/control-renderer-impl.h
dali-toolkit/internal/controls/renderers/gradient/gradient-renderer.cpp
dali-toolkit/internal/controls/renderers/gradient/gradient-renderer.h
dali-toolkit/internal/controls/renderers/gradient/gradient.cpp
dali-toolkit/internal/controls/renderers/gradient/gradient.h
dali-toolkit/internal/controls/renderers/image/image-renderer.cpp
dali-toolkit/internal/controls/renderers/image/image-renderer.h
dali-toolkit/internal/controls/renderers/npatch/npatch-renderer.cpp
dali-toolkit/internal/controls/renderers/npatch/npatch-renderer.h
dali-toolkit/internal/controls/renderers/renderer-factory-impl.cpp
dali-toolkit/internal/controls/renderers/renderer-factory-impl.h
dali-toolkit/internal/controls/text-controls/text-field-impl.cpp
dali-toolkit/internal/controls/text-controls/text-label-impl.cpp
dali-toolkit/internal/file.list
dali-toolkit/internal/text/decorator/text-decorator.cpp
dali-toolkit/internal/text/rendering/atlas/text-atlas-renderer.cpp
dali-toolkit/internal/text/text-controller.cpp
dali-toolkit/internal/text/text-controller.h
dali-toolkit/public-api/controls/buttons/button.h
dali-toolkit/public-api/controls/buttons/push-button.h
dali-toolkit/public-api/controls/control-impl.cpp
dali-toolkit/public-api/controls/control-impl.h
dali-toolkit/public-api/controls/control.h
dali-toolkit/public-api/controls/image-view/image-view.h
dali-toolkit/public-api/controls/page-turn-view/page-turn-view.h
dali-toolkit/public-api/dali-toolkit-version.cpp
packaging/dali-toolkit.spec

index a0a3589..d9ea25e 100644 (file)
@@ -150,14 +150,6 @@ bool TestPlatformAbstraction::IsLoading()
 }
 
 /**
- * @copydoc PlatformAbstraction::GetDefaultFontDescription()
- */
-void TestPlatformAbstraction::GetDefaultFontDescription( std::string& family, std::string& style ) const
-{
-  // TODO
-}
-
-/**
  * @copydoc PlatformAbstraction::GetDefaultFontSize()
  */
 int TestPlatformAbstraction::GetDefaultFontSize() const
index 673e1af..3502e70 100644 (file)
@@ -139,11 +139,6 @@ public:
   virtual bool IsLoading();
 
   /**
-   * @copydoc PlatformAbstraction::GetDefaultFontDescription()
-   */
-  virtual void GetDefaultFontDescription( std::string& family, std::string& style ) const;
-
-  /**
    * @copydoc PlatformAbstraction::GetDefaultFontSize()
    */
   virtual int GetDefaultFontSize() const;
index f77f903..4bfc808 100644 (file)
@@ -382,7 +382,20 @@ int UtcDaliControlBackgroundColor(void)
   DALI_TEST_EQUALS( control.GetBackgroundColor(), Color::TRANSPARENT, TEST_LOCATION );
 
   control.SetBackgroundColor( Color::RED );
-  DALI_TEST_EQUALS( control.GetBackgroundColor(), Color::RED, TEST_LOCATION );
+
+  Property::Value propValue = control.GetProperty( Control::Property::BACKGROUND );
+  Property::Map* resultMap = propValue.GetMap();
+  DALI_TEST_CHECK( resultMap->Find( "renderer-type" ) );
+  DALI_TEST_CHECK( resultMap->Find( "renderer-type" )->Get<std::string>() == "color-renderer" );
+  DALI_TEST_CHECK( resultMap->Find( "blend-color" ) );
+  DALI_TEST_CHECK( resultMap->Find( "blend-color" )->Get<Vector4>() == Color::RED );
+
+  control.SetBackgroundColor( Color::YELLOW );
+
+  propValue = control.GetProperty( Control::Property::BACKGROUND );
+  resultMap = propValue.GetMap();
+  DALI_TEST_CHECK( resultMap->Find( "blend-color" ) );
+  DALI_TEST_CHECK( resultMap->Find( "blend-color" )->Get<Vector4>() == Color::YELLOW );
 
   END_TEST;
 }
@@ -396,21 +409,21 @@ int UtcDaliControlBackgroundImage(void)
 
   Image image = ResourceImage::New("TestImage");
   control.SetBackgroundImage( image );
-  DALI_TEST_EQUALS( control.GetBackgroundColor(), Color::TRANSPARENT, TEST_LOCATION );
-
-  control.SetBackgroundColor( Color::GREEN );
-  DALI_TEST_EQUALS( control.GetBackgroundColor(), Color::GREEN, TEST_LOCATION );
-
-  control.SetBackgroundColor( Color::RED );
-  DALI_TEST_EQUALS( control.GetBackgroundColor(), Color::RED, TEST_LOCATION );
 
-  control.ClearBackground();
-  DALI_TEST_EQUALS( control.GetBackgroundColor(), Color::TRANSPARENT, TEST_LOCATION );
+  Property::Value propValue = control.GetProperty( Control::Property::BACKGROUND );
+  Property::Map* resultMap = propValue.GetMap();
+  DALI_TEST_CHECK( resultMap->Find( "renderer-type" ) );
+  DALI_TEST_CHECK( resultMap->Find( "renderer-type" )->Get<std::string>() == "image-renderer" );
+  DALI_TEST_CHECK( resultMap->Find( "image-url" ) );
+  DALI_TEST_CHECK( resultMap->Find( "image-url" )->Get<std::string>() == "TestImage" );
 
-  control.SetBackgroundColor( Color::YELLOW );
+  image = ResourceImage::New("TestImage2");
   control.SetBackgroundImage( image );
-  // The background can be either an image or a color, not both
-  DALI_TEST_EQUALS( control.GetBackgroundColor(), Color::TRANSPARENT, TEST_LOCATION );
+
+  propValue = control.GetProperty( Control::Property::BACKGROUND );
+  resultMap = propValue.GetMap();
+  DALI_TEST_CHECK( resultMap->Find( "image-url" ) );
+  DALI_TEST_CHECK( resultMap->Find( "image-url" )->Get<std::string>() == "TestImage2" );
 
   END_TEST;
 }
@@ -420,34 +433,42 @@ int UtcDaliControlBackgroundProperties(void)
   ToolkitTestApplication application;
   Control control = Control::New();
 
-  DALI_TEST_CHECK( control.GetChildCount() == 0 );
   DALI_TEST_EQUALS( control.GetBackgroundColor(), Color::TRANSPARENT, TEST_LOCATION );
   DALI_TEST_CHECK( control.GetProperty( Control::Property::BACKGROUND ).Get< Property::Map >().Empty() );
 
   Property::Map colorMap;
   colorMap["color"] = Color::RED;
   control.SetProperty( Control::Property::BACKGROUND, colorMap );
-  DALI_TEST_EQUALS( control.GetBackgroundColor(), Color::RED, TEST_LOCATION );
-  DALI_TEST_CHECK( control.GetChildCount() > 0 );
   Property::Value propValue = control.GetProperty( Control::Property::BACKGROUND );
   Property::Map* resultMap = propValue.GetMap();
-  DALI_TEST_CHECK( resultMap->Find( "color" ) );
-  DALI_TEST_CHECK( resultMap->Find( "color" )->Get<Vector4>() == Color::RED );
+  DALI_TEST_CHECK( resultMap->Find( "renderer-type" ) );
+  DALI_TEST_CHECK( resultMap->Find( "renderer-type" )->Get<std::string>() == "color-renderer" );
+  DALI_TEST_CHECK( resultMap->Find( "blend-color" ) );
+  DALI_TEST_CHECK( resultMap->Find( "blend-color" )->Get<Vector4>() == Color::RED );
 
   Property::Map imageMap;
   imageMap[ "filename" ] = "TestImage";
   control.SetProperty( Control::Property::BACKGROUND, imageMap );
-  DALI_TEST_CHECK( control.GetChildCount() > 0 );
-  DALI_TEST_EQUALS( control.GetBackgroundColor(), Color::TRANSPARENT, TEST_LOCATION );
   propValue = control.GetProperty( Control::Property::BACKGROUND );
   resultMap = propValue.GetMap();
-  DALI_TEST_CHECK( resultMap->Find( "filename" ) );
-  DALI_TEST_CHECK( resultMap->Find( "filename" )->Get< std::string>() == "TestImage" );
+  DALI_TEST_CHECK( resultMap->Find( "renderer-type" ) );
+  DALI_TEST_CHECK( resultMap->Find( "renderer-type" )->Get<std::string>() == "image-renderer" );
+  DALI_TEST_CHECK( resultMap->Find( "image-url" ) );
+  DALI_TEST_CHECK( resultMap->Find( "image-url" )->Get<std::string>() == "TestImage" );
+
+  Property::Map rendererMap;
+  rendererMap["renderer-type"] = "color-renderer";
+  rendererMap["blend-color"] = Color::CYAN;
+  control.SetProperty( Control::Property::BACKGROUND, rendererMap );
+  propValue = control.GetProperty( Control::Property::BACKGROUND );
+  resultMap = propValue.GetMap();
+  DALI_TEST_CHECK( resultMap->Find( "renderer-type" ) );
+  DALI_TEST_CHECK( resultMap->Find( "renderer-type" )->Get<std::string>() == "color-renderer" );
+  DALI_TEST_CHECK( resultMap->Find( "blend-color" ) );
+  DALI_TEST_CHECK( resultMap->Find( "blend-color" )->Get<Vector4>() == Color::CYAN );
 
   Property::Map emptyMap;
   control.SetProperty( Control::Property::BACKGROUND, emptyMap );
-  DALI_TEST_CHECK( control.GetChildCount() == 0 );
-  DALI_TEST_EQUALS( control.GetBackgroundColor(), Color::TRANSPARENT, TEST_LOCATION );
   DALI_TEST_CHECK( control.GetProperty( Control::Property::BACKGROUND ).Get< Property::Map >().Empty() );
 
   END_TEST;
index be623c2..e0b50d1 100644 (file)
 using namespace Dali;
 using namespace Dali::Toolkit;
 
+namespace
+{
+const char* TEST_IMAGE_FILE_NAME =  "gallery_image_01.jpg";
+const char* TEST_NPATCH_FILE_NAME =  "gallery_image_01.9.jpg";
+}
+
 void dali_control_renderer_startup(void)
 {
   test_return_value = TET_UNDEF;
@@ -68,7 +74,7 @@ int UtcDaliControlRendererCopyAndAssignment(void)
   END_TEST;
 }
 
-int UtcDaliControlRendererSetDepthIndex(void)
+int UtcDaliControlRendererSetGetDepthIndex(void)
 {
   ToolkitTestApplication application;
   tet_infoline( "UtcDaliControlRendererSetDepthIndex" );
@@ -87,14 +93,80 @@ int UtcDaliControlRendererSetDepthIndex(void)
   controlRenderer.SetOnStage( actor );
 
   DALI_TEST_EQUALS( actor.GetRendererAt(0u).GetDepthIndex(), 1.f, TEST_LOCATION );
+  DALI_TEST_EQUALS( controlRenderer.GetDepthIndex(), 1.f, TEST_LOCATION );
 
   controlRenderer.SetDepthIndex( -1.f );
   DALI_TEST_EQUALS( actor.GetRendererAt(0u).GetDepthIndex(), -1.f, TEST_LOCATION );
+  DALI_TEST_EQUALS( controlRenderer.GetDepthIndex(), -1.f, TEST_LOCATION );
+
+  END_TEST;
+}
+
+int UtcDaliControlRendererSize(void)
+{
+  ToolkitTestApplication application;
+  tet_infoline( "UtcDaliControlRendererGetNaturalSize" );
+
+  RendererFactory factory = RendererFactory::Get();
+  Vector2 rendererSize( 20.f, 30.f );
+  Vector2 naturalSize;
+
+  // color renderer
+  ControlRenderer colorRenderer = factory.GetControlRenderer( Color::MAGENTA );
+  colorRenderer.SetSize( rendererSize );
+  DALI_TEST_EQUALS( colorRenderer.GetSize(), rendererSize, TEST_LOCATION );
+  colorRenderer.GetNaturalSize(naturalSize);
+  DALI_TEST_EQUALS( naturalSize, Vector2::ZERO, TEST_LOCATION );
+
+  // image renderer
+  Image image = ResourceImage::New(TEST_IMAGE_FILE_NAME, ImageDimensions(100, 200));
+  ControlRenderer imageRenderer = factory.GetControlRenderer( image );
+  imageRenderer.SetSize( rendererSize );
+  DALI_TEST_EQUALS( imageRenderer.GetSize(), rendererSize, TEST_LOCATION );
+  imageRenderer.GetNaturalSize(naturalSize);
+  DALI_TEST_EQUALS( naturalSize, Vector2(100.f, 200.f), TEST_LOCATION );
+
+  // n patch renderer
+  TestPlatformAbstraction& platform = application.GetPlatform();
+  Vector2 testSize(80.f, 160.f);
+  platform.SetClosestImageSize(testSize);
+  image = ResourceImage::New(TEST_NPATCH_FILE_NAME);
+  ControlRenderer nPatchRenderer = factory.GetControlRenderer( image );
+  nPatchRenderer.SetSize( rendererSize );
+  DALI_TEST_EQUALS( nPatchRenderer.GetSize(), rendererSize, TEST_LOCATION );
+  nPatchRenderer.GetNaturalSize(naturalSize);
+  DALI_TEST_EQUALS( naturalSize, testSize, TEST_LOCATION );
+
+  // border renderer
+  float borderSize = 5.f;
+  ControlRenderer borderRenderer = factory.GetControlRenderer( borderSize, Color::RED );
+  borderRenderer.SetSize( rendererSize );
+  DALI_TEST_EQUALS( borderRenderer.GetSize(), rendererSize, TEST_LOCATION );
+  borderRenderer.GetNaturalSize(naturalSize);
+  DALI_TEST_EQUALS( naturalSize, Vector2::ZERO, TEST_LOCATION );
+
+  // gradient renderer
+  Property::Map propertyMap;
+  propertyMap.Insert("renderer-type", "gradient-renderer");
+  Vector2 start(-1.f, -1.f);
+  Vector2 end(1.f, 1.f);
+  propertyMap.Insert("gradient-start-position", start);
+  propertyMap.Insert("gradient-end-position", end);
+  propertyMap.Insert("gradient-stop-offset", Vector2(0.f, 1.f));
+  Property::Array stopColors;
+  stopColors.PushBack( Color::RED );
+  stopColors.PushBack( Color::GREEN );
+  propertyMap.Insert("gradient-stop-color", stopColors);
+  ControlRenderer gradientRenderer = factory.GetControlRenderer(propertyMap);
+  gradientRenderer.SetSize( rendererSize );
+  DALI_TEST_EQUALS( gradientRenderer.GetSize(), rendererSize, TEST_LOCATION );
+  gradientRenderer.GetNaturalSize(naturalSize);
+  DALI_TEST_EQUALS( naturalSize, Vector2::ZERO,TEST_LOCATION );
 
   END_TEST;
 }
 
-int UtcDaliControlRendererSetOnStage(void)
+int UtcDaliControlRendererSetOnOffStage(void)
 {
   ToolkitTestApplication application;
   tet_infoline( "UtcDaliControlRendererSetDepthIndex" );
@@ -114,10 +186,380 @@ int UtcDaliControlRendererSetOnStage(void)
   DALI_TEST_CHECK( actor.GetRendererCount() == 0u );
 
   controlRenderer.SetOnStage( actor );
+  application.SendNotification();
+  application.Render(0);
+  DALI_TEST_CHECK( actor.GetRendererCount() == 1u );
 
+  controlRenderer.SetOffStage( actor );
+  application.SendNotification();
+  application.Render(0);
+  DALI_TEST_CHECK( actor.GetRendererCount() == 0u );
+
+  END_TEST;
+}
+
+int UtcDaliControlRendererRemoveAndReset(void)
+{
+  ToolkitTestApplication application;
+  tet_infoline( "intUtcDaliControlRendererRemoveAndReset" );
+
+  RendererFactory factory = RendererFactory::Get();
+
+  Actor actor = Actor::New();
+  actor.SetSize(200.f, 200.f);
+  Stage::GetCurrent().Add( actor );
+
+  ControlRenderer imageRenderer;
+  // test calling RemoveAndReset with an empty handle
+  try
+  {
+    imageRenderer.RemoveAndReset( actor );
+    tet_result(TET_PASS);
+  }
+  catch (DaliException& exception)
+  {
+    tet_result(TET_FAIL);
+  }
+
+  Image image = ResourceImage::New(TEST_IMAGE_FILE_NAME, ImageDimensions(100, 200));
+  imageRenderer = factory.GetControlRenderer(image);
+  DALI_TEST_CHECK( imageRenderer );
+
+  imageRenderer.SetOnStage( actor );
   application.SendNotification();
   application.Render(0);
   DALI_TEST_CHECK( actor.GetRendererCount() == 1u );
 
+  imageRenderer.RemoveAndReset( actor );
+  application.SendNotification();
+  application.Render(0);
+  DALI_TEST_CHECK( actor.GetRendererCount() == 0u ); // renderer is removed from actor
+  DALI_TEST_CHECK( !imageRenderer ); // control renderer is reset
+
+  END_TEST;
+}
+
+int UtcDaliControlRendererGetPropertyMap1(void)
+{
+  ToolkitTestApplication application;
+  tet_infoline( "UtcDaliControlRendererGetPropertyMap1: ColorRenderer" );
+
+  RendererFactory factory = RendererFactory::Get();
+  Property::Map propertyMap;
+  propertyMap.Insert("renderer-type", "color-renderer");
+  propertyMap.Insert("blend-color", Color::BLUE);
+  ControlRenderer colorRenderer = factory.GetControlRenderer( propertyMap );
+
+  Property::Map resultMap;
+  colorRenderer.CreatePropertyMap( resultMap );
+
+  Property::Value* typeValue = resultMap.Find( "renderer-type", Property::STRING );
+  DALI_TEST_CHECK( typeValue );
+  DALI_TEST_CHECK( typeValue->Get<std::string>() == "color-renderer" );
+
+  Property::Value* colorValue = resultMap.Find( "blend-color", Property::VECTOR4 );
+  DALI_TEST_CHECK( colorValue );
+  DALI_TEST_CHECK( colorValue->Get<Vector4>() == Color::BLUE );
+
+  // change the blend color
+  factory.ResetRenderer( colorRenderer, Color::CYAN );
+  colorRenderer.CreatePropertyMap( resultMap );
+
+  colorValue = resultMap.Find( "blend-color", Property::VECTOR4 );
+  DALI_TEST_CHECK( colorValue );
+  DALI_TEST_CHECK( colorValue->Get<Vector4>() == Color::CYAN );
+
+  END_TEST;
+}
+
+int UtcDaliControlRendererGetPropertyMap2(void)
+{
+  ToolkitTestApplication application;
+  tet_infoline( "UtcDaliControlRendererGetPropertyMap2: BorderRenderer" );
+
+  RendererFactory factory = RendererFactory::Get();
+  Property::Map propertyMap;
+  propertyMap.Insert("renderer-type", "border-renderer");
+  propertyMap.Insert("border-color", Color::BLUE);
+  propertyMap.Insert("border-size", 5.f);
+  ControlRenderer borderRenderer = factory.GetControlRenderer( propertyMap );
+
+  Property::Map resultMap;
+  borderRenderer.CreatePropertyMap( resultMap );
+
+  // check the property values from the returned map from control renderer
+  Property::Value* typeValue = resultMap.Find( "renderer-type", Property::STRING );
+  DALI_TEST_CHECK( typeValue );
+  DALI_TEST_CHECK( typeValue->Get<std::string>() == "border-renderer" );
+
+  Property::Value* colorValue = resultMap.Find( "border-color", Property::VECTOR4 );
+  DALI_TEST_CHECK( colorValue );
+  DALI_TEST_CHECK( colorValue->Get<Vector4>() == Color::BLUE );
+
+  Property::Value* sizeValue = resultMap.Find( "border-size", Property::FLOAT );
+  DALI_TEST_CHECK( sizeValue );
+  DALI_TEST_CHECK( sizeValue->Get<float>() == 5.f );
+
+  borderRenderer = factory.GetControlRenderer( 10.f, Color::CYAN );
+  borderRenderer.CreatePropertyMap( resultMap );
+
+  typeValue = resultMap.Find( "renderer-type", Property::STRING );
+  DALI_TEST_CHECK( typeValue );
+  DALI_TEST_CHECK( typeValue->Get<std::string>() == "border-renderer" );
+
+   colorValue = resultMap.Find( "border-color", Property::VECTOR4 );
+  DALI_TEST_CHECK( colorValue );
+  DALI_TEST_CHECK( colorValue->Get<Vector4>() == Color::CYAN );
+
+  colorValue = resultMap.Find( "border-size", Property::FLOAT );
+  DALI_TEST_CHECK( colorValue );
+  DALI_TEST_CHECK( colorValue->Get<float>() == 10.f );
+
+  END_TEST;
+}
+
+int UtcDaliControlRendererGetPropertyMap3(void)
+{
+  ToolkitTestApplication application;
+  tet_infoline( "UtcDaliControlRendererGetPropertyMap3: linear GradientRenderer" );
+
+  RendererFactory factory = RendererFactory::Get();
+  DALI_TEST_CHECK( factory );
+
+  Property::Map propertyMap;
+  propertyMap.Insert("renderer-type", "gradient-renderer");
+
+  Vector2 start(-1.f, -1.f);
+  Vector2 end(1.f, 1.f);
+  propertyMap.Insert("gradient-start-position", start);
+  propertyMap.Insert("gradient-end-position", end);
+  propertyMap.Insert("gradient-spread-method", "repeat");
+
+  propertyMap.Insert("gradient-stop-offset", Vector2(0.2f, 0.8f));
+
+  Property::Array stopColors;
+  stopColors.PushBack( Color::RED );
+  stopColors.PushBack( Color::GREEN );
+  propertyMap.Insert("gradient-stop-color", stopColors);
+
+  ControlRenderer gradientRenderer = factory.GetControlRenderer(propertyMap);
+
+  Property::Map resultMap;
+  gradientRenderer.CreatePropertyMap( resultMap );
+
+  // check the property values from the returned map from control renderer
+  Property::Value* value = resultMap.Find( "renderer-type", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == "gradient-renderer" );
+
+  value = resultMap.Find( "gradient-units", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == "object-bounding-box" );
+
+  value = resultMap.Find( "gradient-spread-method", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == "repeat" );
+
+  value = resultMap.Find( "gradient-start-position", Property::VECTOR2 );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_EQUALS( value->Get<Vector2>(), start , Math::MACHINE_EPSILON_100, TEST_LOCATION );
+
+  value = resultMap.Find( "gradient-end-position", Property::VECTOR2 );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_EQUALS( value->Get<Vector2>(), end , Math::MACHINE_EPSILON_100, TEST_LOCATION );
+
+  value = resultMap.Find( "gradient-stop-offset", Property::ARRAY );
+  DALI_TEST_CHECK( value );
+  Property::Array* offsetArray = value->GetArray();
+  DALI_TEST_CHECK( offsetArray->Count() == 2 );
+  DALI_TEST_EQUALS( offsetArray->GetElementAt(0).Get<float>(), 0.2f , Math::MACHINE_EPSILON_100, TEST_LOCATION );
+  DALI_TEST_EQUALS( offsetArray->GetElementAt(1).Get<float>(), 0.8f , Math::MACHINE_EPSILON_100, TEST_LOCATION );
+
+  value = resultMap.Find( "gradient-stop-color", Property::ARRAY );
+  DALI_TEST_CHECK( value );
+  Property::Array* colorArray = value->GetArray();
+  DALI_TEST_CHECK( colorArray->Count() == 2 );
+  DALI_TEST_EQUALS( colorArray->GetElementAt(0).Get<Vector4>(), Color::RED , Math::MACHINE_EPSILON_100, TEST_LOCATION );
+  DALI_TEST_EQUALS( colorArray->GetElementAt(1).Get<Vector4>(), Color::GREEN , Math::MACHINE_EPSILON_100, TEST_LOCATION );
+
+  END_TEST;
+}
+
+int UtcDaliControlRendererGetPropertyMap4(void)
+{
+  ToolkitTestApplication application;
+  tet_infoline( "UtcDaliControlRendererGetPropertyMap4: radial GradientRenderer" );
+
+  RendererFactory factory = RendererFactory::Get();
+  DALI_TEST_CHECK( factory );
+
+  Property::Map propertyMap;
+  propertyMap.Insert("renderer-type", "gradient-renderer");
+
+  Vector2 center(100.f, 100.f);
+  float radius = 100.f;
+  propertyMap.Insert("gradient-units", "user-space");
+  propertyMap.Insert("gradient-center", center);
+  propertyMap.Insert("gradient-radius", radius);
+  propertyMap.Insert("gradient-stop-offset", Vector3(0.1f, 0.3f, 1.1f));
+
+  Property::Array stopColors;
+  stopColors.PushBack( Color::RED );
+  stopColors.PushBack( Color::BLACK );
+  stopColors.PushBack( Color::GREEN );
+  propertyMap.Insert("gradient-stop-color", stopColors);
+
+  ControlRenderer gradientRenderer = factory.GetControlRenderer(propertyMap);
+  DALI_TEST_CHECK( gradientRenderer );
+
+  Property::Map resultMap;
+  gradientRenderer.CreatePropertyMap( resultMap );
+
+  // check the property values from the returned map from control renderer
+  Property::Value* value = resultMap.Find( "renderer-type", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == "gradient-renderer" );
+
+  value = resultMap.Find( "gradient-units", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == "user-space" );
+
+  value = resultMap.Find( "gradient-spread-method", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == "pad" );
+
+  value = resultMap.Find( "gradient-center", Property::VECTOR2 );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_EQUALS( value->Get<Vector2>(), center , Math::MACHINE_EPSILON_100, TEST_LOCATION );
+
+  value = resultMap.Find( "gradient-radius", Property::FLOAT );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_EQUALS( value->Get<float>(), radius , Math::MACHINE_EPSILON_100, TEST_LOCATION );
+
+  value = resultMap.Find( "gradient-stop-offset", Property::ARRAY );
+  DALI_TEST_CHECK( value );
+  Property::Array* offsetArray = value->GetArray();
+  DALI_TEST_CHECK( offsetArray->Count() == 3 );
+  DALI_TEST_EQUALS( offsetArray->GetElementAt(0).Get<float>(), 0.1f , Math::MACHINE_EPSILON_100, TEST_LOCATION );
+  DALI_TEST_EQUALS( offsetArray->GetElementAt(1).Get<float>(), 0.3f , Math::MACHINE_EPSILON_100, TEST_LOCATION );
+  // any stop value will be clamped to [0.0, 1.0];
+  DALI_TEST_EQUALS( offsetArray->GetElementAt(2).Get<float>(), 1.0f , Math::MACHINE_EPSILON_100, TEST_LOCATION );
+
+  value = resultMap.Find( "gradient-stop-color", Property::ARRAY );
+  DALI_TEST_CHECK( value );
+  Property::Array* colorArray = value->GetArray();
+  DALI_TEST_CHECK( colorArray->Count() == 3 );
+  DALI_TEST_EQUALS( colorArray->GetElementAt(0).Get<Vector4>(), Color::RED , Math::MACHINE_EPSILON_100, TEST_LOCATION );
+  DALI_TEST_EQUALS( colorArray->GetElementAt(1).Get<Vector4>(), Color::BLACK , Math::MACHINE_EPSILON_100, TEST_LOCATION );
+  DALI_TEST_EQUALS( colorArray->GetElementAt(2).Get<Vector4>(), Color::GREEN , Math::MACHINE_EPSILON_100, TEST_LOCATION );
+
+  END_TEST;
+}
+
+int UtcDaliControlRendererGetPropertyMap5(void)
+{
+  ToolkitTestApplication application;
+  tet_infoline( "UtcDaliControlRendererGetPropertyMap5: ImageRenderer" );
+
+  RendererFactory factory = RendererFactory::Get();
+  Property::Map propertyMap;
+  propertyMap.Insert( "renderer-type", "image-renderer" );
+  propertyMap.Insert( "image-url", TEST_IMAGE_FILE_NAME );
+  propertyMap.Insert( "image-desired-width", 20 );
+  propertyMap.Insert( "image-desired-height", 30 );
+  propertyMap.Insert( "image-fitting-mode", "fit-height" );
+  propertyMap.Insert( "image-sampling-mode", "box-then-nearest" );
+
+  ControlRenderer imageRenderer = factory.GetControlRenderer(propertyMap);
+  DALI_TEST_CHECK( imageRenderer );
+
+  Property::Map resultMap;
+  imageRenderer.CreatePropertyMap( resultMap );
+
+  // check the property values from the returned map from control renderer
+  Property::Value* value = resultMap.Find( "renderer-type", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == "image-renderer" );
+
+  value = resultMap.Find( "image-url", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == TEST_IMAGE_FILE_NAME );
+
+  value = resultMap.Find( "image-fitting-mode", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == "fit-height" );
+
+  value = resultMap.Find( "image-sampling-mode", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == "box-then-nearest" );
+
+  value = resultMap.Find( "image-desired-width", Property::INTEGER );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<int>() == 20 );
+
+  value = resultMap.Find( "image-desired-height", Property::INTEGER );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<int>() == 30 );
+
+  // Get an image renderer with an image handle, and test the default property values
+  Image image = ResourceImage::New(TEST_IMAGE_FILE_NAME, ImageDimensions(100, 200));
+  imageRenderer = factory.GetControlRenderer(image);
+  imageRenderer.CreatePropertyMap( resultMap );
+
+  value = resultMap.Find( "renderer-type", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == "image-renderer" );
+
+  value = resultMap.Find( "image-url", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == TEST_IMAGE_FILE_NAME );
+
+  value = resultMap.Find( "image-fitting-mode", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == "shrink-to-fit" );
+
+  value = resultMap.Find( "image-sampling-mode", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == "box" );
+
+  value = resultMap.Find( "image-desired-width", Property::INTEGER );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<int>() == 100 );
+
+  value = resultMap.Find( "image-desired-height", Property::INTEGER );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<int>() == 200 );
+
+  END_TEST;
+}
+
+int UtcDaliControlRendererGetPropertyMap6(void)
+{
+  ToolkitTestApplication application;
+  tet_infoline( "UtcDaliControlRendererGetPropertyMap6: NPatchRenderer" );
+
+  RendererFactory factory = RendererFactory::Get();
+  Property::Map propertyMap;
+  propertyMap.Insert( "renderer-type", "n-patch-renderer" );
+  propertyMap.Insert( "image-url", TEST_NPATCH_FILE_NAME );
+  propertyMap.Insert( "border-only", true );
+  ControlRenderer nPatchRenderer = factory.GetControlRenderer( propertyMap );
+
+  Property::Map resultMap;
+  nPatchRenderer.CreatePropertyMap( resultMap );
+
+  // check the property values from the returned map from control renderer
+  Property::Value* value = resultMap.Find( "renderer-type", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == "n-patch-renderer" );
+
+  value = resultMap.Find( "image-url", Property::STRING );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<std::string>() == TEST_NPATCH_FILE_NAME );
+
+  value = resultMap.Find( "border-only", Property::BOOLEAN );
+  DALI_TEST_CHECK( value );
+  DALI_TEST_CHECK( value->Get<bool>() );
+
   END_TEST;
 }
index c132161..a570b72 100644 (file)
@@ -282,6 +282,9 @@ int UtcDaliRendererFactoryGetColorRenderer2(void)
   DALI_TEST_CHECK( gl.GetUniformValue<Vector4>( "uBlendColor", actualValue ) );
   DALI_TEST_EQUALS( actualValue, testColor, TEST_LOCATION );
 
+  controlRenderer.SetOffStage( actor );
+  DALI_TEST_CHECK( actor.GetRendererCount() == 0u );
+
   END_TEST;
 }
 
@@ -324,6 +327,9 @@ int UtcDaliRendererFactoryGetBorderRenderer1(void)
   DALI_TEST_CHECK( gl.GetUniformValue<float>( "uBorderSize", actualSize ) );
   DALI_TEST_EQUALS( actualSize, testSize, TEST_LOCATION );
 
+  controlRenderer.SetOffStage( actor );
+  DALI_TEST_CHECK( actor.GetRendererCount() == 0u );
+
   END_TEST;
 }
 
@@ -411,6 +417,9 @@ int UtcDaliRendererFactoryGetLinearGradientRenderer(void)
   application.SendNotification();
   application.Render(0);
 
+  controlRenderer.SetOffStage( actor );
+  DALI_TEST_CHECK( actor.GetRendererCount() == 0u );
+
   END_TEST;
 }
 
@@ -515,6 +524,9 @@ int UtcDaliRendererFactoryGetImageRenderer1(void)
   DALI_TEST_CHECK( gl.GetUniformValue< int >( "sTexture", textureUnit ) );
   DALI_TEST_EQUALS( textureUnit, 0, TEST_LOCATION );
 
+  controlRenderer.SetOffStage( actor );
+  DALI_TEST_CHECK( actor.GetRendererCount() == 0u );
+
   END_TEST;
 }
 
@@ -610,6 +622,9 @@ int UtcDaliRendererFactoryGetNPatchRenderer1(void)
   DALI_TEST_CHECK( gl.GetUniformValue< int >( "sTexture", textureUnit ) );
   DALI_TEST_EQUALS( textureUnit, 0, TEST_LOCATION );
 
+  controlRenderer.SetOffStage( actor );
+  DALI_TEST_CHECK( actor.GetRendererCount() == 0u );
+
   END_TEST;
 }
 
index cc5195d..33dfee4 100644 (file)
@@ -123,24 +123,69 @@ int UtcDaliCreateDisplacementEffectFixed(void)
   END_TEST;
 }
 
-int UtcDaliCreateDissolveEffect(void)
+int UtcDaliCreateDissolveEffect( bool highPrecision )
 {
   ToolkitTestApplication application;
 
-  ShaderEffect effect = Toolkit::CreateDissolveEffect();
-  DALI_TEST_CHECK( effect );
+  Property::Map effect = Toolkit::CreateDissolveEffect( highPrecision );
+  DALI_TEST_CHECK( !effect.Empty() );
+
+  Property::Value* customShaderValue = effect.Find( "shader" );
+  DALI_TEST_CHECK( customShaderValue );
+
+  Property::Map customShader;
+  DALI_TEST_CHECK( customShaderValue->Get( customShader ) );
+
+  Property::Value* vertexShaderValue = customShader.Find( "vertex-shader" );
+  DALI_TEST_CHECK( vertexShaderValue );
+
+  std::string vertexShader;
+  DALI_TEST_CHECK( vertexShaderValue->Get( vertexShader ) );
+  DALI_TEST_CHECK( !vertexShader.empty() );
+
+  Property::Value* fragmentShaderValue = customShader.Find( "fragment-shader" );
+  DALI_TEST_CHECK( fragmentShaderValue );
+
+  std::string fragmentShader;
+  DALI_TEST_CHECK( fragmentShaderValue->Get( fragmentShader ) );
+  DALI_TEST_CHECK( !fragmentShader.empty() );
+
+  Property::Value* gridXValue = customShader.Find( "subdivide-grid-x" );
+  DALI_TEST_CHECK( gridXValue );
+
+  int gridX = 0;
+  DALI_TEST_CHECK( gridXValue->Get( gridX ) );
+  DALI_TEST_CHECK( gridX > 1 );
+
+  Property::Value* gridYValue = customShader.Find( "subdivide-grid-y" );
+  DALI_TEST_CHECK( gridYValue );
+
+  int gridY = 0;
+  DALI_TEST_CHECK( gridYValue->Get( gridY ) );
+  DALI_TEST_CHECK( gridY > 1 );
+
+  Property::Value* hintsValue = customShader.Find( "hints" );
+  DALI_TEST_CHECK( hintsValue );
+
+  std::string hints;
+  DALI_TEST_CHECK( hintsValue->Get( hints ) );
+  DALI_TEST_CHECK( hints == "output-is-transparent" );
+
+  Actor actor = Actor::New();
+  Toolkit::DissolveEffectSetCentralLine( actor, Vector2::ONE, Vector2::ONE, 0.0f );
+  DALI_TEST_CHECK( actor.GetPropertyIndex( "uPercentage" ) != Property::INVALID_INDEX );
 
   END_TEST;
 }
 
-int UtcDaliCreateDissolveEffectMediumPrecision(void)
+int UtcDaliCreateDissolveEffectHighPrecision(void)
 {
-  ToolkitTestApplication application;
-
-  ShaderEffect effect = Toolkit::CreateDissolveEffect(false);
-  DALI_TEST_CHECK( effect );
+  return UtcDaliCreateDissolveEffect(true);
+}
 
-  END_TEST;
+int UtcDaliCreateDissolveEffectMediumPrecision(void)
+{
+  return UtcDaliCreateDissolveEffect(false);
 }
 
 int UtcDaliCreateDissolveLocalEffect(void)
index e460b77..c036334 100644 (file)
@@ -56,16 +56,50 @@ void ControlRenderer::SetSize( const Vector2& size )
   GetImplementation( *this ).SetSize(size);
 }
 
+const Vector2& ControlRenderer::GetSize() const
+{
+  return GetImplementation( *this ).GetSize();
+}
+
+void ControlRenderer::GetNaturalSize(Vector2& naturalSize ) const
+{
+  GetImplementation( *this ).GetNaturalSize( naturalSize );
+}
+
 void ControlRenderer::SetDepthIndex( float index )
 {
   GetImplementation( *this ).SetDepthIndex(index);
 }
 
+float ControlRenderer::GetDepthIndex() const
+{
+  return GetImplementation( *this ).GetDepthIndex();
+}
+
 void ControlRenderer::SetOnStage( Actor& actor )
 {
   GetImplementation( *this ).SetOnStage(actor);
 }
 
+void ControlRenderer::SetOffStage( Actor& actor )
+{
+  GetImplementation( *this ).SetOffStage(actor);
+}
+
+void ControlRenderer::RemoveAndReset( Actor& actor )
+{
+  if( actor && *this )
+  {
+    SetOffStage( actor );
+  }
+  Reset();
+}
+
+void ControlRenderer::CreatePropertyMap( Property::Map& map ) const
+{
+  GetImplementation( *this ).CreatePropertyMap( map );
+}
+
 } // namespace Toolkit
 
 } // namespace Dali
index d5f0df4..fe26fab 100644 (file)
@@ -33,7 +33,8 @@ class ControlRenderer;
 }
 
 /**
- * ControlRenderer provides renderer for rendering the controls. A control may have multiple ControlRenders.
+ * @brief ControlRenderer provides renderer for rendering the controls. A control may have multiple ControlRenders.
+ *
  * ControlRenderers reuses geometry, shader etc. across controls and manages the renderer and material to exist only when control is on-stage.
  * It also responds to actor size and color change, and provides the clipping at the renderer level.
  * Note: The control renderer responds to the the Actor::COLOR by blending it with the 'Multiply' operator.
@@ -70,14 +71,31 @@ public:
   ControlRenderer& operator=( const ControlRenderer& handle );
 
   /**
-   * Set the size of the painting area.
+   * @brief Set the size of the painting area.
    *
    * @param[in] size The size of the painting area.
    */
   void SetSize( const Vector2& size );
 
   /**
-   * Set the depth index of this renderer.
+   * @brief Get the size of the painting area.
+   *
+   * @return The size of the renderer's painting area.
+   */
+  const Vector2& GetSize() const;
+
+  /**
+   * @brief Return the natural size of the renderer.
+   *
+   * Deriving classes stipulate the natural size and by default a renderer has a ZERO natural size.
+   *
+   * @param[out] naturalSize The renderer's natural size
+   */
+  void GetNaturalSize( Vector2& naturalSize ) const;
+
+  /**
+   * @brief Set the depth index of this renderer.
+   *
    * Depth-index controls draw-order for overlapping renderers.
    * Renderer with higher depth indices are rendered in front of other renderer with smaller values
    *
@@ -86,13 +104,46 @@ public:
   void SetDepthIndex( float index );
 
   /**
-   * Renderer only exists when control is on stage.
+   * @brief Get the depth index of this renderer
+   *
+   * @return The depth index of this renderer.
+   */
+  float GetDepthIndex() const;
+
+  /**
+   * @brief Renderer only exists when control is on stage.
+   *
    * This function should be called when the control put on stage.
    *
    * @param[in] actor The actor applying this renderer.
    */
   void SetOnStage( Actor& actor );
 
+  /**
+   * @brief Renderer is destroyed when control is off stage.
+   *
+   * This function should be called when the control removes from stage
+   *
+   * @param[in] actor The actor applying this renderer.
+   */
+  void SetOffStage( Actor& actor );
+
+  /**
+   * @brief Remove the renderer from actor and reset the control renderer self.
+   *
+   * This function can be called with an empty handle. If the control renderer is empty, do nothing.
+   *
+   * @param[in] actor The actor to be set off stage.
+   */
+  void RemoveAndReset( Actor& actor );
+
+  /**
+   * @brief Create the property map representing this renderer.
+   *
+   * @param[out] map The renderer property map.
+   */
+  void CreatePropertyMap( Property::Map& map ) const;
+
 public: // Not intended for application developers
 
   explicit DALI_INTERNAL ControlRenderer(Internal::ControlRenderer *impl);
index ce70893..3f7ef6c 100644 (file)
@@ -122,6 +122,11 @@ bool RendererFactory::ResetRenderer( ControlRenderer& renderer, const std::strin
   return GetImplementation( *this ).ResetRenderer( renderer, url );
 }
 
+bool RendererFactory::ResetRenderer( ControlRenderer& renderer, const Property::Map& propertyMap )
+{
+  return GetImplementation( *this ).ResetRenderer( renderer, propertyMap );
+}
+
 } // namespace Toolkit
 
 } // namespace Dali
index da948db..13242f4 100644 (file)
@@ -37,7 +37,7 @@ class RendererFactory;
 }
 
 /**
- * RendererFactory is a singleton object that provides and shares renderers for controls
+ * @brief RendererFactory is a singleton object that provides and shares renderers for controls
  *
  * The renderer type is required in the property map for requesting a control renderer.
  *
@@ -163,6 +163,19 @@ public:
    */
   bool ResetRenderer( ControlRenderer& renderer, const std::string& url );
 
+
+  /**
+   * @brief Request the current control renderer from the property map, merging the property map with the renderer
+   *
+   * if the current renderer is capable of merging with the property map the reset the renderer with the merged properties
+   * else the renderer would be a handle to a newly created internal renderer.
+   *
+   * @param[in] propertyMap The map contains the properties required by the control renderer
+   *            Depends on the content of the map, different kind of renderer would be returned.
+   * @return Whether a new internal control renderer is created.
+   */
+  bool ResetRenderer( ControlRenderer& renderer, const Property::Map& propertyMap );
+
 private:
 
   explicit DALI_INTERNAL RendererFactory(Internal::RendererFactory *impl);
index 4aee8cc..95cccc8 100644 (file)
  */
 
 // EXTERNAL INCLUDES
-#include <dali/public-api/shader-effects/shader-effect.h>
+#include <string.h>
+#include <dali/devel-api/rendering/shader.h>
+
+namespace
+{
+  template < typename T>
+  void SafeSetCustomProperty( Dali::Actor& actor, const std::string& name, const T& value )
+  {
+    Dali::Property::Index index = actor.GetPropertyIndex( name );
+    if ( Dali::Property::INVALID_INDEX == index )
+    {
+      index = actor.RegisterProperty( name, value );
+    }
+    else
+    {
+      actor.SetProperty( index, value );
+    }
+  }
+
+  template < typename T>
+  void SafeSetCustomProperty( Dali::Actor& actor, const std::string& name, const T& value, Dali::Property::AccessMode accessMode )
+  {
+    Dali::Property::Index index = actor.GetPropertyIndex( name );
+    if ( Dali::Property::INVALID_INDEX == index )
+    {
+      index = actor.RegisterProperty( name, value, accessMode );
+    }
+    else
+    {
+      actor.SetProperty( index, value );
+    }
+  }
+
+};
 
 namespace Dali
 {
@@ -34,11 +67,11 @@ namespace Toolkit
  * As we use the texture coordinate as pixel position to calculate random offset,
  * the line should passing through rectangle {(0,0),(0,1),(1,0),(1,1)},
  * so make the position parameter with two component values between 0.0 to 1.0
- * @param[in] dissolveEffect The shader effect
  * @param[in] position The point ( locates within rectangle {(0,0),(0,1),(1,0),(1,1)} ) passed through by the central line
  * @param[in] displacement The direction of the central line
+ * @param[in] initialProgress, the normalised initial progress of the shader
  */
-inline void DissolveEffectSetCentralLine( ShaderEffect& dissolveEffect, const Vector2& position, const Vector2& displacement )
+inline void DissolveEffectSetCentralLine( Actor& actor, const Vector2& position, const Vector2& displacement, float initialProgress )
 {
   // the line passes through 'position' and has the direction of 'displacement'
     float coefA, coefB, coefC; //line equation: Ax+By+C=0;
@@ -102,10 +135,11 @@ inline void DissolveEffectSetCentralLine( ShaderEffect& dissolveEffect, const Ve
     rotation = Vector2(-displacement.x, displacement.y);
     rotation.Normalize();
 
-    dissolveEffect.SetUniform( "uSaddleParam", saddleParam );
-    dissolveEffect.SetUniform( "uTranslation", translation );
-    dissolveEffect.SetUniform( "uRotation", rotation );
-    dissolveEffect.SetUniform( "uToNext", toNext );
+    SafeSetCustomProperty( actor, "uSaddleParam", saddleParam );
+    SafeSetCustomProperty( actor, "uTranslation", translation );
+    SafeSetCustomProperty( actor, "uRotation", rotation );
+    SafeSetCustomProperty( actor, "uToNext", toNext );
+    SafeSetCustomProperty( actor, "uPercentage", initialProgress, Dali::Property::ANIMATABLE );
 }
 /**
  * @brief Create a new Dissolve effect
@@ -119,69 +153,108 @@ inline void DissolveEffectSetCentralLine( ShaderEffect& dissolveEffect, const Ve
  *  @return A handle to a newly allocated ShaderEffect
  */
 
-inline ShaderEffect CreateDissolveEffect(bool useHighPrecision = true)
+inline Property::Map CreateDissolveEffect( bool useHighPrecision = true )
 {
-  std::string prefixHighPrecision( "precision highp float;\n");
-    std::string prefixMediumPrecision( "precision mediump float;\n" );
-    std::string vertexShader(
-      "uniform float uPercentage;\n"
-      "uniform vec3 uSaddleParam;\n"
-      "uniform vec2 uTranslation;\n"
-      "uniform vec2 uRotation; \n"
-      "uniform float uToNext;\n"
-      "varying float vPercentage;\n"
-      "void main()\n"
-      "{\n"
-        "gl_Position = uProjection * uModelView * vec4(aPosition, 1.0);\n"
-        "vTexCoord = aTexCoord;\n"
-        //Calculate the distortion value given the dissolve central line
-        "vec2 texCoor = vec2( (aTexCoord.s - sTextureRect.s ) / (sTextureRect.p - sTextureRect.s), (aTexCoord.t- sTextureRect.t)/(sTextureRect.q - sTextureRect.t) ); \n"
-        "vec2 value = texCoor + uTranslation; \n"
-        "mat2 rotateMatrix = mat2( uRotation.s, uRotation.t, -uRotation.t, uRotation.s ); \n"
-        "value = rotateMatrix * value; \n"
-        "if(uToNext == 1.0)  \n"
-        "  value.s = uSaddleParam[2] + value.s; \n"
-        "float delay = value.t*value.t / uSaddleParam[0] - value.s*value.s/uSaddleParam[1];\n"
-        "vPercentage = clamp( uPercentage*2.0 - 0.5*sin(delay*1.571) - 0.5, 0.0, 1.0 ); \n"
-      "}\n");
-    std::string fragmentShader(
-      "varying float vPercentage;\n"
-      "float rand(vec2 co) \n"
-      "{\n"
-      "  return fract(sin(dot(co.xy ,vec2(12.9898,78.233))) * 43758.5453); \n"
-      "}\n"
-      "void main()\n"
-      "{\n"
-        //Calculate the randomness
-        "float offsetS = rand( vTexCoord * vPercentage ) * (sTextureRect.p - sTextureRect.s) - vTexCoord.s  + sTextureRect.s; \n"
-        "float offsetT = rand( vec2(vTexCoord.t*vPercentage, vTexCoord.s * vPercentage) ) * (sTextureRect.q - sTextureRect.t) - vTexCoord.t + sTextureRect.t; \n"
-        "vec2 lookupCoord = vTexCoord + vec2(offsetS, offsetT) * vPercentage; \n"
-        "gl_FragColor = texture2D( sTexture, lookupCoord ) * uColor; \n"
-        "gl_FragColor.a *= 1.0 - vPercentage; \n"
-      "}" );
-
-    // Create the implementation, temporarily owned on stack,
-    Dali::ShaderEffect shaderEffect;
-    if( useHighPrecision )
-    {
-      shaderEffect =  Dali::ShaderEffect::New(
-          prefixHighPrecision+vertexShader, prefixHighPrecision + fragmentShader,
-          ShaderEffect::GeometryHints( ShaderEffect::HINT_GRID | ShaderEffect::HINT_BLENDING ) );
-    }
-    else
-    {
-      shaderEffect =  Dali::ShaderEffect::New(
-          prefixMediumPrecision+vertexShader, prefixMediumPrecision + fragmentShader,
-          ShaderEffect::GeometryHints( ShaderEffect::HINT_GRID | ShaderEffect::HINT_BLENDING ) );
-    }
+  const char* prefixHighPrecision( "precision highp float;\n");
+  const char* prefixMediumPrecision( "precision mediump float;\n" );
+
+  const char* vertexShader( DALI_COMPOSE_SHADER(
+    attribute mediump vec2 aPosition;\n
+    \n
+    uniform mediump mat4 uMvpMatrix;\n
+    uniform vec3 uSize;\n
+    uniform vec4 uTextureRect;
+    \n
+    uniform float uPercentage;\n
+    uniform vec3 uSaddleParam;\n
+    uniform vec2 uTranslation;\n
+    uniform vec2 uRotation; \n
+    uniform float uToNext;\n
+    \n
+    varying float vPercentage;\n
+    varying vec2 vTexCoord;\n
+
+    void main()\n
+    {\n
+      mediump vec4 vertexPosition = vec4(aPosition, 0.0, 1.0);\n
+      vertexPosition.xyz *= uSize;\n
+      vertexPosition = uMvpMatrix * vertexPosition;\n
+      gl_Position = vertexPosition;\n
+
+      vec2 texCoord = aPosition + vec2(0.5);
+      vTexCoord = texCoord;\n
+      //Calculate the distortion value given the dissolve central line
+      vec2 value = texCoord + uTranslation; \n
+      mat2 rotateMatrix = mat2( uRotation.s, uRotation.t, -uRotation.t, uRotation.s ); \n
+      value = rotateMatrix * value; \n
+      if(uToNext == 1.0)  \n
+        value.s = uSaddleParam[2] + value.s; \n
+      float delay = value.t*value.t / uSaddleParam[0] - value.s*value.s/uSaddleParam[1];\n
+      vPercentage = clamp( uPercentage*2.0 - 0.5*sin(delay*1.571) - 0.5, 0.0, 1.0 ); \n
+    })
+  );
+
+  const char* fragmentShader( DALI_COMPOSE_SHADER(
+    varying float vPercentage;\n
+    varying mediump vec2 vTexCoord;\n
+    \n
+    uniform sampler2D sTexture;\n
+    uniform lowp vec4 uColor;\n
+    uniform vec4 uTextureRect;
+    \n
+    float rand(vec2 co) \n
+    {\n
+      return fract(sin(dot(co.xy ,vec2(12.9898,78.233))) * 43758.5453); \n
+    }\n
+    \n
+    void main()\n
+    {\n
+
+      //Calculate the randomness
+      float offsetS = rand( vTexCoord * vPercentage ) - vTexCoord.s; \n
+      float offsetT = rand( vec2(vTexCoord.t*vPercentage, vTexCoord.s * vPercentage) ) - vTexCoord.t; \n
+      vec2 lookupCoord = vTexCoord + vec2(offsetS, offsetT) * vPercentage; \n
+      gl_FragColor = texture2D( sTexture, lookupCoord ) * uColor; \n
+      gl_FragColor.a *= 1.0 - vPercentage; \n
+    } )
+  );
+
+  Property::Map map;
+
+  Property::Map customShader;
+
+  std::string vertexShaderString;
+  std::string fragmentShaderString;
+  if( useHighPrecision )
+  {
+    vertexShaderString.reserve(strlen( prefixHighPrecision ) + strlen( vertexShader ));
+    vertexShaderString.append( prefixHighPrecision );
+
+    fragmentShaderString.reserve(strlen( prefixHighPrecision ) + strlen( fragmentShader ));
+    fragmentShaderString.append( prefixHighPrecision );
+  }
+  else
+  {
+    vertexShaderString.reserve(strlen( prefixMediumPrecision ) + strlen( vertexShader ));
+    vertexShaderString.append( prefixMediumPrecision );
+
+    fragmentShaderString.reserve(strlen( prefixMediumPrecision ) + strlen( fragmentShader ));
+    fragmentShaderString.append( prefixMediumPrecision );
+  }
+
+  vertexShaderString.append( vertexShader );
+  fragmentShaderString.append( fragmentShader );
 
-    shaderEffect.SetUniform( "uPercentage", 0.0f );
-    shaderEffect.SetProperty( ShaderEffect::Property::GRID_DENSITY, Dali::Property::Value(50.0f) );
+  customShader[ "vertex-shader" ] = vertexShaderString;
+  customShader[ "fragment-shader" ] = fragmentShaderString;
 
-    DissolveEffectSetCentralLine( shaderEffect, Vector2(1.0f,0.5f), Vector2(-1.0f, 0.0f) );
+  customShader[ "subdivide-grid-x" ] = 20;
+  customShader[ "subdivide-grid-y" ] = 20;
 
-    return shaderEffect;
+  customShader[ "hints" ] = "output-is-transparent";
 
+  map[ "shader" ] = customShader;
+  return map;
 }
 
 } // namespace Toolkit
index 76493a6..554469b 100644 (file)
@@ -97,16 +97,23 @@ void ImageView::SetImage( Image image )
 
 void ImageView::SetImage( Property::Map map )
 {
-  mImage.Reset();
-  mUrl.clear();
   mPropertyMap = map;
 
-  mRenderer = Toolkit::RendererFactory::Get().GetControlRenderer( mPropertyMap );
+  bool newRendererCreated = false;
+  if( mRenderer )
+  {
+    newRendererCreated = Toolkit::RendererFactory::Get().ResetRenderer( mRenderer, mPropertyMap );
+  }
+  else
+  {
+    mRenderer = Toolkit::RendererFactory::Get().GetControlRenderer( mPropertyMap );
+    newRendererCreated = true;
+  }
 
   //we need to inform any newly created renderers if it is on stage
-  if( Self().OnStage() )
+  CustomActor self = Self();
+  if( newRendererCreated && self.OnStage() )
   {
-    CustomActor self = Self();
     mRenderer.SetOnStage( self );
   }
 
index 1450460..6542a2c 100644 (file)
@@ -37,6 +37,9 @@ namespace Internal
 
 namespace
 {
+const char * const RENDERER_TYPE("renderer-type");
+const char * const RENDERER_TYPE_VALUE("border-renderer");
+
 const char * const COLOR_NAME("border-color");
 const char * const COLOR_UNIFORM_NAME("uBorderColor");
 const char * const SIZE_NAME("border-size");
@@ -85,7 +88,7 @@ BorderRenderer::~BorderRenderer()
 {
 }
 
-void BorderRenderer::Initialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap )
+void BorderRenderer::DoInitialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap )
 {
   Initialize( factoryCache );
 
@@ -119,6 +122,14 @@ void BorderRenderer::DoSetOnStage( Actor& actor )
   mBorderSizeIndex = (mImpl->mRenderer).RegisterProperty( SIZE_UNIFORM_NAME, mBorderSize );
 }
 
+void BorderRenderer::DoCreatePropertyMap( Property::Map& map ) const
+{
+  map.Clear();
+  map.Insert( RENDERER_TYPE, RENDERER_TYPE_VALUE );
+  map.Insert( COLOR_NAME, mBorderColor );
+  map.Insert( SIZE_NAME, mBorderSize );
+}
+
 void BorderRenderer::Initialize( RendererFactoryCache& factoryCache)
 {
   mImpl->mGeometry = factoryCache.GetGeometry( RendererFactoryCache::BORDER_GEOMETRY );
index 5a1f575..9c53935 100644 (file)
@@ -60,9 +60,9 @@ public:
 public:  // from ControlRenderer
 
   /**
-   * @copydoc ControlRenderer::Initialize
+   * @copydoc ControlRenderer::DoInitialize
    */
-  virtual void Initialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap );
+  virtual void DoInitialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap );
 
   /**
    * @copydoc ControlRenderer::SetClipRect
@@ -75,6 +75,11 @@ protected:
    */
   virtual void DoSetOnStage( Actor& actor );
 
+  /**
+   * @copydoc ControlRenderer::CreatePropertyMap
+   */
+  virtual void DoCreatePropertyMap( Property::Map& map ) const;
+
 public:
 
   /**
index 7b3ae1c..68164ea 100644 (file)
@@ -37,6 +37,8 @@ namespace Internal
 
 namespace
 {
+const char * const RENDERER_TYPE("renderer-type");
+const char * const RENDERER_TYPE_VALUE("color-renderer");
 const char * const COLOR_NAME("blend-color");
 const char * const COLOR_UNIFORM_NAME("uBlendColor");
 
@@ -75,7 +77,7 @@ ColorRenderer::~ColorRenderer()
 {
 }
 
-void ColorRenderer::Initialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap )
+void ColorRenderer::DoInitialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap )
 {
   Initialize( factoryCache );
 
@@ -105,6 +107,13 @@ void ColorRenderer::SetOffset( const Vector2& offset )
   //ToDo: renderer applies the offset
 }
 
+void ColorRenderer::DoCreatePropertyMap( Property::Map& map ) const
+{
+  map.Clear();
+  map.Insert( RENDERER_TYPE, RENDERER_TYPE_VALUE );
+  map.Insert( COLOR_NAME, mBlendColor );
+}
+
 void ColorRenderer::DoSetOnStage( Actor& actor )
 {
   mBlendColorIndex = (mImpl->mRenderer).RegisterProperty( COLOR_UNIFORM_NAME, mBlendColor );
index 5f5dd27..ae5ccca 100644 (file)
@@ -56,9 +56,9 @@ public:
 public:  // from ControlRenderer
 
   /**
-   * @copydoc ControlRenderer::Initialize
+   * @copydoc ControlRenderer::DoInitialize
    */
-  virtual void Initialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap );
+  virtual void DoInitialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap );
 
   /**
    * @copydoc ControlRenderer::SetSize
@@ -75,6 +75,11 @@ public:  // from ControlRenderer
    */
   virtual void SetOffset( const Vector2& offset );
 
+  /**
+   * @copydoc ControlRenderer::CreatePropertyMap
+   */
+  virtual void DoCreatePropertyMap( Property::Map& map ) const;
+
 protected:
   /**
    * @copydoc ControlRenderer::DoSetOnStage
diff --git a/dali-toolkit/internal/controls/renderers/control-renderer-data-impl.cpp b/dali-toolkit/internal/controls/renderers/control-renderer-data-impl.cpp
new file mode 100644 (file)
index 0000000..6a58cfb
--- /dev/null
@@ -0,0 +1,247 @@
+/*
+ * Copyright (c) 2015 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 "control-renderer-data-impl.h"
+
+// EXTERNAL HEADER
+#include <dali/public-api/common/dali-common.h>
+#include <dali/integration-api/debug.h>
+#include <dali/public-api/object/property-array.h>
+
+// EXTERNAL HEADER
+
+namespace Dali
+{
+
+namespace Toolkit
+{
+
+namespace Internal
+{
+
+namespace
+{
+//custom shader
+const char * const CUSTOM_SHADER( "shader" );
+const char * const CUSTOM_VERTEX_SHADER( "vertex-shader" );
+const char * const CUSTOM_FRAGMENT_SHADER( "fragment-shader" );
+const char * const CUSTOM_SUBDIVIDE_GRID_X( "subdivide-grid-x" );
+const char * const CUSTOM_SUBDIVIDE_GRID_Y( "subdivide-grid-y" );
+const char * const CUSTOM_SHADER_HINTS( "hints" ); ///< type STRING for a hint from the below hint strings or an ARRAY of of hint strings
+
+/**
+ * where hints should be contain strings of the following shader hints:
+ *   "none"                       | corresponds to HINT_NONE
+ *   "requires-self-depth-test"   | corresponds to HINT_REQUIRES_SELF_DEPTH_TEST
+ *   "output-is-transparent"      | corresponds to HINT_OUTPUT_IS_TRANSPARENT
+ *   "output-is-opaque"           | corresponds to HINT_OUTPUT_IS_OPAQUE
+ *   "modifies-geometry"          | corresponds to HINT_MODIFIES_GEOMETRY
+ */
+
+Shader::ShaderHints HintFromString( std::string hintString )
+{
+  if( hintString == "none" )
+  {
+    return Shader::HINT_NONE;
+  }
+  else if( hintString == "requires-self-depth-test" )
+  {
+    return Shader::HINT_REQUIRES_SELF_DEPTH_TEST;
+  }
+  else if( hintString == "output-is-transparent" )
+  {
+    return Shader::HINT_OUTPUT_IS_TRANSPARENT;
+  }
+  else if( hintString == "output-is-opaque" )
+  {
+    return Shader::HINT_OUTPUT_IS_OPAQUE;
+  }
+  else if( hintString == "modifies-geometry" )
+  {
+    return Shader::HINT_MODIFIES_GEOMETRY;
+  }
+  else
+  {
+    DALI_LOG_ERROR( "'%s' hint string is not recognised", hintString.c_str() );
+  }
+
+  return Shader::HINT_NONE;
+}
+
+}// unnamed namespace
+
+Internal::ControlRenderer::Impl::Impl()
+: mCustomShader(NULL),
+  mDepthIndex( 0.0f ),
+  mIsOnStage( false )
+{
+}
+
+Internal::ControlRenderer::Impl::~Impl()
+{
+  delete mCustomShader;
+}
+
+Internal::ControlRenderer::Impl::CustomShader::CustomShader( const Property::Map& map )
+: mGridSize( 1, 1 ),
+  mHints( Shader::HINT_NONE )
+{
+  SetPropertyMap( map );
+}
+
+void Internal::ControlRenderer::Impl::CustomShader::SetPropertyMap( const Property::Map& propertyMap )
+{
+  Property::Value* shaderValue = propertyMap.Find( CUSTOM_SHADER );
+  if( shaderValue )
+  {
+    mVertexShader.clear();
+    mFragmentShader.clear();
+    mGridSize = ImageDimensions( 1, 1 );
+    mHints = Shader::HINT_NONE;
+
+    Property::Map shaderMap;
+    if( shaderValue->Get( shaderMap ) )
+    {
+      Property::Value* vertexShaderValue = shaderMap.Find( CUSTOM_VERTEX_SHADER );
+      if( vertexShaderValue )
+      {
+        if( !vertexShaderValue->Get( mVertexShader ) )
+        {
+          DALI_LOG_ERROR( "'%s' parameter does not correctly specify a string", CUSTOM_VERTEX_SHADER );
+        }
+      }
+
+      Property::Value* fragmentShaderValue = shaderMap.Find( CUSTOM_FRAGMENT_SHADER );
+      if( fragmentShaderValue )
+      {
+        if( !fragmentShaderValue->Get( mFragmentShader ) )
+        {
+          DALI_LOG_ERROR( "'%s' parameter does not correctly specify a string", CUSTOM_FRAGMENT_SHADER );
+        }
+      }
+
+      Property::Value* subdivideXValue = shaderMap.Find( CUSTOM_SUBDIVIDE_GRID_X );
+      if( subdivideXValue )
+      {
+        int subdivideX;
+        if( !subdivideXValue->Get( subdivideX ) || subdivideX < 1 )
+        {
+          DALI_LOG_ERROR( "'%s' parameter does not correctly specify a value greater than 1", CUSTOM_SUBDIVIDE_GRID_X );
+        }
+        else
+        {
+          mGridSize = ImageDimensions( subdivideX, mGridSize.GetY() );
+        }
+      }
+
+      Property::Value* subdivideYValue = shaderMap.Find( CUSTOM_SUBDIVIDE_GRID_Y );
+      if( subdivideYValue )
+      {
+        int subdivideY;
+        if( !subdivideYValue->Get( subdivideY ) || subdivideY < 1 )
+        {
+          DALI_LOG_ERROR( "'%s' parameter does not correctly specify a value greater than 1", CUSTOM_SUBDIVIDE_GRID_Y );
+        }
+        else
+        {
+          mGridSize = ImageDimensions( mGridSize.GetX(), subdivideY );
+        }
+      }
+
+      Property::Value* hintsValue = shaderMap.Find( CUSTOM_SHADER_HINTS );
+      if( hintsValue )
+      {
+        std::string hintString;
+        Property::Array hintsArray;
+
+        if( hintsValue->Get( hintString ) )
+        {
+          mHints = HintFromString( hintString );
+        }
+        else if( hintsValue->Get( hintsArray ) )
+        {
+          int hints = Shader::HINT_NONE;
+          for( Property::Array::SizeType i = 0; i < hintsArray.Count(); ++i)
+          {
+            Property::Value hintValue = hintsArray[ i ];
+            if( hintValue.Get( hintString ) )
+            {
+              hints |= static_cast< int >( HintFromString( hintString ) );
+            }
+            else
+            {
+              DALI_LOG_ERROR( "'%s' parameter does not correctly specify an hint string at index %d", CUSTOM_SHADER_HINTS, i );
+            }
+
+            mHints = static_cast< Shader::ShaderHints >( hints );
+          }
+        }
+        else
+        {
+          DALI_LOG_ERROR( "'%s' parameter does not correctly specify a hint string or an array of hint strings", CUSTOM_SHADER_HINTS );
+        }
+      }
+    }
+    else
+    {
+      //use value with no type to mean reseting the shader back to default
+      if( shaderValue->GetType() != Dali::Property::NONE )
+      {
+        DALI_LOG_ERROR( "'%s' parameter does not correctly specify a property map", CUSTOM_SHADER );
+      }
+    }
+  }
+}
+
+void Internal::ControlRenderer::Impl::CustomShader::CreatePropertyMap( Property::Map& map ) const
+{
+  if( !mVertexShader.empty() || !mFragmentShader.empty() )
+  {
+    Property::Map customShader;
+    if( !mVertexShader.empty() )
+    {
+      customShader.Insert(CUSTOM_VERTEX_SHADER, mVertexShader );
+    }
+    if( !mFragmentShader.empty() )
+    {
+      customShader.Insert(CUSTOM_FRAGMENT_SHADER, mFragmentShader );
+    }
+
+    if( mGridSize.GetWidth() != 1 )
+    {
+      customShader.Insert(CUSTOM_SUBDIVIDE_GRID_X, mGridSize.GetWidth() );
+    }
+    if( mGridSize.GetHeight() != 1 )
+    {
+      customShader.Insert(CUSTOM_SUBDIVIDE_GRID_Y, mGridSize.GetHeight() );
+    }
+
+    if( mHints != Dali::Shader::HINT_NONE )
+    {
+      customShader.Insert(CUSTOM_SHADER_HINTS, static_cast< int >(mHints) );
+    }
+
+    map.Insert( CUSTOM_SHADER, customShader );
+  }
+}
+
+} // namespace Internal
+
+} // namespace Toolkit
+
+} // namespace Dali
index e865a0e..47095c9 100644 (file)
  *
  */
 
-// INTERNAL INCLUDES
+// EXTERNAL INCLUDES
 #include <dali/public-api/math/vector2.h>
 #include <dali/devel-api/rendering/renderer.h>
 
+#include <dali-toolkit/internal/controls/renderers/control-renderer-impl.h>
+
 namespace Dali
 {
 
@@ -33,15 +35,32 @@ namespace Internal
 
 struct Internal::ControlRenderer::Impl
 {
+  struct CustomShader
+  {
+    std::string mVertexShader;
+    std::string mFragmentShader;
+    Dali::ImageDimensions mGridSize;
+    Dali::Shader::ShaderHints mHints; //(bitfield) values from enum Shader::Hints
+
+    CustomShader( const Property::Map& map );
+    void SetPropertyMap( const Property::Map& map );
+    void CreatePropertyMap( Property::Map& map ) const;
+  };
+
   Geometry mGeometry;
   Shader   mShader;
   Renderer mRenderer;
 
+  CustomShader* mCustomShader;
+
   Vector2   mSize;
   Vector2   mOffset;
   Rect<int> mClipRect;
   float     mDepthIndex;
   bool      mIsOnStage;
+
+  Impl();
+  ~Impl();
 };
 
 } // namespace Internal
index acc3ead..91343a4 100644 (file)
 
 // EXTERNAL HEADER
 #include <dali/public-api/common/dali-common.h>
+#include <dali/integration-api/debug.h>
 
 //INTERNAL HEARDER
 #include <dali-toolkit/internal/controls/renderers/control-renderer-data-impl.h>
 
+namespace
+{
+//custom shader
+const char * const CUSTOM_SHADER( "shader" );
+const char * const CUSTOM_VERTEX_SHADER( "vertex-shader" );
+const char * const CUSTOM_FRAGMENT_SHADER( "fragment-shader" );
+const char * const CUSTOM_SUBDIVIDE_GRID_X( "subdivide-grid-x" );
+const char * const CUSTOM_SUBDIVIDE_GRID_Y( "subdivide-grid-y" );
+const char * const CUSTOM_SHADER_HINTS( "hints" ); ///< type INTEGER; (bitfield) values from enum Shader::Hints
+}
+
 namespace Dali
 {
 
@@ -36,7 +48,6 @@ namespace Internal
 ControlRenderer::ControlRenderer()
 : mImpl( new Impl() )
 {
-  mImpl->mIsOnStage = false;
 }
 
 ControlRenderer::~ControlRenderer()
@@ -44,11 +55,42 @@ ControlRenderer::~ControlRenderer()
   delete mImpl;
 }
 
+void ControlRenderer::Initialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap )
+{
+  if( mImpl->mCustomShader )
+  {
+    mImpl->mCustomShader->SetPropertyMap( propertyMap );
+  }
+  else
+  {
+    Property::Value* customShaderValue = propertyMap.Find( CUSTOM_SHADER );
+    if( customShaderValue )
+    {
+      Property::Map customShader;
+      if( customShaderValue->Get( customShader ) )
+      {
+        mImpl->mCustomShader = new Impl::CustomShader( propertyMap );
+      }
+    }
+  }
+  DoInitialize( factoryCache, propertyMap );
+}
+
 void ControlRenderer::SetSize( const Vector2& size )
 {
   mImpl->mSize = size;
 }
 
+const Vector2& ControlRenderer::GetSize() const
+{
+  return mImpl->mSize;
+}
+
+void ControlRenderer::GetNaturalSize( Vector2& naturalSize ) const
+{
+  naturalSize = Vector2::ZERO;
+}
+
 void ControlRenderer::SetClipRect( const Rect<int>& clipRect )
 {
   mImpl->mClipRect = clipRect;
@@ -68,6 +110,11 @@ void ControlRenderer::SetDepthIndex( float index )
   }
 }
 
+float ControlRenderer::GetDepthIndex() const
+{
+  return mImpl->mDepthIndex;
+}
+
 void ControlRenderer::SetOnStage( Actor& actor )
 {
   Material material = Material::New( mImpl->mShader );
@@ -81,12 +128,15 @@ void ControlRenderer::SetOnStage( Actor& actor )
 
 void ControlRenderer::SetOffStage( Actor& actor )
 {
-  DoSetOffStage( actor );
+  if( mImpl->mIsOnStage )
+  {
+    DoSetOffStage( actor );
 
-  actor.RemoveRenderer( mImpl->mRenderer );
-  mImpl->mRenderer.Reset();
+    actor.RemoveRenderer( mImpl->mRenderer );
+    mImpl->mRenderer.Reset();
 
-  mImpl->mIsOnStage = false;
+    mImpl->mIsOnStage = false;
+  }
 }
 
 void ControlRenderer::DoSetOnStage( Actor& actor )
@@ -97,6 +147,15 @@ void ControlRenderer::DoSetOffStage( Actor& actor )
 {
 }
 
+void ControlRenderer::CreatePropertyMap( Property::Map& map ) const
+{
+  if( mImpl->mCustomShader )
+  {
+    mImpl->mCustomShader->CreatePropertyMap( map );
+  }
+  DoCreatePropertyMap( map );
+}
+
 } // namespace Internal
 
 } // namespace Toolkit
index 7c72734..4dea2d9 100644 (file)
 
 // EXTERNAL INCLUDES
 #include <dali/public-api/object/base-object.h>
+#include <dali/public-api/images/image-operations.h>
+#include <dali/devel-api/rendering/shader.h>
 
+// INTERNAL INCLUDES
 #include <dali-toolkit/devel-api/controls/renderer-factory/renderer-factory.h>
 #include <dali-toolkit/devel-api/controls/renderer-factory/control-renderer.h>
 
@@ -40,6 +43,21 @@ class RendererFactoryCache;
  * Base class for all Control rendering logic. A control may have multiple control renderers.
  *
  * Note: The control renderer responds to the the Actor::COLOR by blending it with the 'Multiply' operator.
+ *
+ * The following properties are optional
+ *
+ * | %Property Name            | Type             |
+ * |---------------------------|------------------|
+ * | custom-shader             | MAP              |
+ *
+ * where custom-shader is a map with the following properties:
+ * | %Property Name            | Type             |
+ * |---------------------------|------------------|
+ * | vertex-shader             | STRING           |
+ * | fragment-shader           | STRING           |
+ * | subdivide-grid-x          | INT              |
+ * | subdivide-grid-y          | INT              |
+ * | shader-hints              | INT              |
  */
 class ControlRenderer : public BaseObject
 {
@@ -53,7 +71,7 @@ public:
    * @param[in] factoryCache A pointer pointing to the RendererFactoryCache object
    * @param[in] propertyMap The properties for the requested ControlRenderer object.
    */
-  virtual void Initialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap ) = 0;
+  void Initialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap );
 
   /**
    * @copydoc Toolkit::ControlRenderer::SetSize
@@ -61,6 +79,16 @@ public:
   virtual void SetSize( const Vector2& size );
 
   /**
+   * @copydoc Toolkit::ControlRenderer::GetSize
+   */
+  const Vector2& GetSize() const;
+
+  /**
+   * @copydoc Toolkit::ControlRenderer::GetNaturalSize
+   */
+  virtual void GetNaturalSize( Vector2& naturalSize ) const;
+
+  /**
    * ToDo: Add this function to Toolkit::ControlRenderer when it is fully implemented.
    *
    * Set the clip rectangular of this renderer.
@@ -85,21 +113,26 @@ public:
   void SetDepthIndex( float index );
 
   /**
+   * @copydoc Toolkit::ControlRenderer::GetDepthIndex
+   */
+  float GetDepthIndex() const;
+
+  /**
    * @copydoc Toolkit::ControlRenderer::SetOnStage
    * @pre Impl->mGeometry must be created before this method is called
    */
   void SetOnStage( Actor& actor );
 
   /**
-   * ToDo: Add this function to Toolkit::ControlRenderer when the Renderer can be removed from actor properly.
-   *
-   * Renderer is destroyed when control is off stage.
-   * This function should be called when the control removes from stage
-   *
-   * @param[in] actor The actor applying this renderer.
+   * @copydoc Toolkit::ControlRenderer::SetOffStage
    */
   void SetOffStage( Actor& actor );
 
+  /**
+   * @copydoc Toolkit::ControlRenderer::CreatePropertyMap
+   */
+  void CreatePropertyMap( Property::Map& map ) const;
+
 protected:
 
   /**
@@ -113,16 +146,32 @@ protected:
   virtual ~ControlRenderer();
 
 protected:
+  /**
+   * @brief Called by CreatePropertyMap() allowing sub classes to respond to the CreatePropertyMap event
+   *
+   * @param[out] map The renderer property map.
+   */
+  virtual void DoCreatePropertyMap( Property::Map& map ) const = 0;
 
   /**
-   * Called by SetOnStage() allowing sub classes to respond to the SetOnStage event
+   * @brief Called by Initialize() allowing sub classes to respond to the Initialize event
+   *
+   * @param[in] factoryCache A pointer pointing to the RendererFactoryCache object
+   * @param[in] propertyMap The properties for the requested ControlRenderer object.
+   */
+  virtual void DoInitialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap ) = 0;
+
+protected:
+
+  /**
+   * @brief Called by SetOnStage() allowing sub classes to respond to the SetOnStage event
    *
    * @param[in] actor The actor applying this renderer.
    */
   virtual void DoSetOnStage( Actor& actor );
 
   /**
-   * Called by SetOffStage() allowing sub classes to respond to the SetOffStage event
+   * @brief Called by SetOffStage() allowing sub classes to respond to the SetOffStage event
    *
    * @param[in] actor The actor applying this renderer.
    */
@@ -137,7 +186,6 @@ private:
   ControlRenderer& operator=( const ControlRenderer& renderer );
 
 protected:
-
   struct Impl;
   Impl* mImpl;
 };
index 85beb72..0e502da 100644 (file)
@@ -19,6 +19,7 @@
 #include "gradient-renderer.h"
 
 // EXTERNAL INCLUDES
+#include <typeinfo>
 #include <dali/integration-api/debug.h>
 #include <dali/public-api/common/dali-vector.h>
 #include <dali/public-api/images/buffer-image.h>
@@ -42,6 +43,9 @@ namespace Internal
 
 namespace
 {
+const char * const RENDERER_TYPE("renderer-type");
+const char * const RENDERER_TYPE_VALUE("gradient-renderer");
+
 // properties: linear gradient
 const char * const GRADIENT_START_POSITION_NAME("gradient-start-position"); // Property::VECTOR2
 const char * const GRADIENT_END_POSITION_NAME("gradient-end-position"); // Property::VECTOR2
@@ -58,6 +62,8 @@ const char * const GRADIENT_SPREAD_METHOD_NAME("gradient-spread-method"); // Pro
 
 // string values
 const char * const UNIT_USER_SPACE("user-space");
+const char * const UNIT_BOUNDING_BOX("object-bounding-box");
+const char * const SPREAD_PAD("pad");
 const char * const SPREAD_REFLECT("reflect");
 const char * const SPREAD_REPEAT("repeat");
 
@@ -137,7 +143,7 @@ GradientRenderer::~GradientRenderer()
 {
 }
 
-void GradientRenderer::Initialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap )
+void GradientRenderer::DoInitialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap )
 {
   mImpl->mGeometry = factoryCache.GetGeometry( RendererFactoryCache::QUAD_GEOMETRY );
   if( !(mImpl->mGeometry) )
@@ -208,6 +214,61 @@ void GradientRenderer::SetOffset( const Vector2& offset )
   //ToDo: renderer applies the offset
 }
 
+void GradientRenderer::DoCreatePropertyMap( Property::Map& map ) const
+{
+  map.Clear();
+  map.Insert( RENDERER_TYPE, RENDERER_TYPE_VALUE );
+
+  Gradient::GradientUnits units = mGradient->GetGradientUnits();
+  if( units == Gradient::USER_SPACE_ON_USE )
+  {
+    map.Insert( GRADIENT_UNITS_NAME, UNIT_USER_SPACE );
+  }
+  else // if( units == Gradient::OBJECT_BOUNDING_BOX )
+  {
+    map.Insert( GRADIENT_UNITS_NAME, UNIT_BOUNDING_BOX );
+  }
+
+  Gradient::SpreadMethod spread = mGradient->GetSpreadMethod();
+  if( spread == Gradient::PAD )
+  {
+    map.Insert( GRADIENT_SPREAD_METHOD_NAME, SPREAD_PAD );
+  }
+  else if( spread == Gradient::REFLECT )
+  {
+    map.Insert( GRADIENT_SPREAD_METHOD_NAME, SPREAD_REFLECT );
+  }
+  else // if( units == Gradient::REPEAT )
+  {
+    map.Insert( GRADIENT_SPREAD_METHOD_NAME, SPREAD_REPEAT );
+  }
+
+  const Vector<Gradient::GradientStop>& stops( mGradient->GetStops() );
+  Property::Array offsets;
+  Property::Array colors;
+  for( unsigned int i=0; i<stops.Count(); i++ )
+  {
+    offsets.PushBack( stops[i].mOffset );
+    colors.PushBack( stops[i].mStopColor );
+  }
+
+  map.Insert( GRADIENT_STOP_OFFSET_NAME, offsets );
+  map.Insert( GRADIENT_STOP_COLOR_NAME, colors );
+
+  if( &typeid( *mGradient ) == &typeid(LinearGradient) )
+  {
+    LinearGradient* gradient = static_cast<LinearGradient*>( mGradient.Get() );
+    map.Insert( GRADIENT_START_POSITION_NAME, gradient->GetStartPosition() );
+    map.Insert( GRADIENT_END_POSITION_NAME, gradient->GetEndPosition() );
+  }
+  else // if( &typeid( *mGradient ) == &typeid(RadialGradient) )
+  {
+    RadialGradient* gradient = static_cast<RadialGradient*>( mGradient.Get() );
+    map.Insert( GRADIENT_CENTER_NAME, gradient->GetCenter() );
+    map.Insert( GRADIENT_RADIUS_NAME, gradient->GetRadius() );
+  }
+}
+
 void GradientRenderer::DoSetOnStage( Actor& actor )
 {
   mGradientTransformIndex = (mImpl->mRenderer).RegisterProperty( UNIFORM_ALIGNMENT_MATRIX_NAME, mGradientTransform );
@@ -265,25 +326,24 @@ bool GradientRenderer::NewGradient(Type gradientType, const Property::Map& prope
   Property::Value* stopColorValue = propertyMap.Find( GRADIENT_STOP_COLOR_NAME );
   if( stopOffsetValue && stopColorValue )
   {
-    Property::Array* offsetArray = stopOffsetValue->GetArray();
+    Vector<float> offsetArray;
     Property::Array* colorArray = stopColorValue->GetArray();
-    if( offsetArray && colorArray )
+    if( colorArray && GetStopOffsets( stopOffsetValue, offsetArray ))
     {
-      unsigned int numStop = offsetArray->Count() < colorArray->Count() ?
-                             offsetArray->Count() : colorArray->Count();
-      float offset;
+      unsigned int numStop = offsetArray.Count() < colorArray->Count() ?
+                             offsetArray.Count() : colorArray->Count();
       Vector4 color;
       for( unsigned int i=0; i<numStop; i++ )
       {
-        if( (offsetArray->GetElementAt(i)).Get(offset)
-         && (colorArray->GetElementAt(i)).Get(color) )
+        if( (colorArray->GetElementAt(i)).Get(color) )
         {
-          mGradient->AddStop( offset, color);
+          mGradient->AddStop( offsetArray[i], color);
           numValidStop++;
         }
       }
     }
   }
+
   if( numValidStop < 1u ) // no valid stop
   {
     return false;
@@ -317,6 +377,53 @@ bool GradientRenderer::NewGradient(Type gradientType, const Property::Map& prope
   return true;
 }
 
+bool GradientRenderer::GetStopOffsets(const Property::Value* value, Vector<float>& stopOffsets)
+{
+  Vector2 offset2;
+  if( value->Get( offset2 ) )
+  {
+    stopOffsets.PushBack( offset2.x );
+    stopOffsets.PushBack( offset2.y );
+    return true;
+  }
+
+  Vector3 offset3;
+  if( value->Get( offset3 ) )
+  {
+    stopOffsets.PushBack( offset3.x );
+    stopOffsets.PushBack( offset3.y );
+    stopOffsets.PushBack( offset3.z );
+    return true;
+  }
+
+  Vector4 offset4;
+  if( value->Get( offset4 ) )
+  {
+    stopOffsets.PushBack( offset4.x );
+    stopOffsets.PushBack( offset4.y );
+    stopOffsets.PushBack( offset4.z );
+    stopOffsets.PushBack( offset4.w );
+    return true;
+  }
+
+  Property::Array* offsetArray = value->GetArray();
+  if( offsetArray )
+  {
+    unsigned int numStop = offsetArray->Count();
+    float offset;
+    for( unsigned int i=0; i<numStop; i++ )
+    {
+      if( offsetArray->GetElementAt(i).Get(offset) )
+      {
+        stopOffsets.PushBack( offset );
+      }
+    }
+    return true;
+  }
+
+  return false;
+}
+
 } // namespace Internal
 
 } // namespace Toolkit
index 4d595db..1ee3f36 100644 (file)
@@ -84,9 +84,9 @@ public:
 public:  // from ControlRenderer
 
   /**
-   * @copydoc ControlRenderer::Initialize
+   * @copydoc ControlRenderer::DoInitialize
    */
-  virtual void Initialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap );
+  virtual void DoInitialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap );
 
   /**
    * @copydoc ControlRenderer::SetSize
@@ -103,6 +103,11 @@ public:  // from ControlRenderer
    */
   virtual void SetOffset( const Vector2& offset );
 
+  /**
+   * @copydoc ControlRenderer::CreatePropertyMap
+   */
+  virtual void DoCreatePropertyMap( Property::Map& map ) const;
+
 protected:
   /**
    * @copydoc ControlRenderer::DoSetOnStage
@@ -127,6 +132,15 @@ private:
    */
   bool NewGradient(Type gradientType, const Property::Map& propertyMap);
 
+  /**
+   * Get the stop-offsets from the property.
+   * The valid property type are ARRAY, VECTOR2, VECTOR3, VECTOR4.
+   *
+   * @param[in] value The property value of stop-offsets
+   * @param[out] stopOffsets The vector contains the stop offset values.
+   */
+  static bool GetStopOffsets(const Property::Value* value, Vector<float>& stopOffsets);
+
   // Undefined
   GradientRenderer( const GradientRenderer& gradientRenderer );
 
index 920fddd..d87d132 100644 (file)
@@ -49,6 +49,11 @@ void Gradient::AddStop( float offset, const Vector4& color )
   mGradientStops.PushBack( GradientStop( Clamp( offset, 0.f, 1.f ), color) );
 }
 
+const Vector<Gradient::GradientStop>& Gradient::GetStops()
+{
+  return mGradientStops;
+}
+
 void Gradient::SetGradientUnits( GradientUnits gradientUnits )
 {
   mGradientUnits = gradientUnits;
index 82b58cb..36e6ee4 100644 (file)
@@ -91,6 +91,12 @@ public:
   void AddStop(float offset, const Vector4& color);
 
   /**
+   * Get the gradient stops.
+   * @return The vector of gradient stops.
+   */
+  const Vector<GradientStop>& GetStops();
+
+  /**
    * Set the coordinate system used by the gradient attributes.
    * @param[in] gradientUnits The the attributes are defined using the current user coordinate system or the bounding box of the shape.
    */
index 50fa5b8..4770960 100644 (file)
 // CLASS HEADER
 #include "image-renderer.h"
 
+// EXTERNAL HEADER
+#include <dali/public-api/images/resource-image.h>
+#include <dali/integration-api/debug.h>
+
+// INTERNAL HEADER
 #include <dali-toolkit/internal/controls/renderers/renderer-factory-impl.h>
 #include <dali-toolkit/internal/controls/renderers/renderer-factory-cache.h>
 #include <dali-toolkit/internal/controls/renderers/control-renderer-impl.h>
 #include <dali-toolkit/internal/controls/renderers/control-renderer-data-impl.h>
-#include <dali/public-api/images/resource-image.h>
 
 namespace Dali
 {
@@ -35,12 +39,31 @@ namespace Internal
 
 namespace
 {
-
-const char * const IMAGE_URL_NAME("image-url");
-const char * const IMAGE_FITTING_MODE("image-fitting-mode");
-const char * const IMAGE_SAMPLING_MODE("image-sampling-mode");
-const char * const IMAGE_DESIRED_WIDTH("image-desired-width");
-const char * const IMAGE_DESIRED_HEIGHT("image-desired-height");
+const char * const RENDERER_TYPE("renderer-type");
+const char * const RENDERER_TYPE_VALUE("image-renderer");
+
+// property names
+const char * const IMAGE_URL_NAME( "image-url" );
+const char * const IMAGE_FITTING_MODE( "image-fitting-mode" );
+const char * const IMAGE_SAMPLING_MODE( "image-sampling-mode" );
+const char * const IMAGE_DESIRED_WIDTH( "image-desired-width" );
+const char * const IMAGE_DESIRED_HEIGHT( "image-desired-height" );
+
+// fitting modes
+const char * const SHRINK_TO_FIT("shrink-to-fit");
+const char * const SCALE_TO_FILL("scale-to-fill");
+const char * const FIT_WIDTH("fit-width");
+const char * const FIT_HEIGHT("fit-height");
+const char * const DEFAULT("default");
+
+// sampling modes
+const char * const BOX("box");
+const char * const NEAREST("nearest");
+const char * const LINEAR("linear");
+const char * const BOX_THEN_NEAREST("box-then-nearest");
+const char * const BOX_THEN_LINEAR("box-then-linear");
+const char * const NO_FILTER("no-filter");
+const char * const DONT_CARE("dont-care");
 
 std::string TEXTURE_UNIFORM_NAME = "sTexture";
 
@@ -72,6 +95,93 @@ const char* FRAGMENT_SHADER = DALI_COMPOSE_SHADER(
   }\n
 );
 
+void AddQuadIndices( Vector< unsigned int >& indices, unsigned int rowIdx, unsigned int nextRowIdx )
+{
+  indices.PushBack( rowIdx );
+  indices.PushBack( nextRowIdx + 1 );
+  indices.PushBack( rowIdx + 1 );
+
+  indices.PushBack( rowIdx );
+  indices.PushBack( nextRowIdx );
+  indices.PushBack( nextRowIdx + 1 );
+}
+
+Geometry GenerateGeometry( const Vector< Vector2 >& vertices, const Vector< unsigned int >& indices )
+{
+  Property::Map vertexFormat;
+  vertexFormat[ "aPosition" ] = Property::VECTOR2;
+  PropertyBuffer vertexPropertyBuffer = PropertyBuffer::New( vertexFormat, vertices.Size() );
+  if( vertices.Size() > 0 )
+  {
+    vertexPropertyBuffer.SetData( &vertices[ 0 ] );
+  }
+
+  Property::Map indexFormat;
+  indexFormat[ "indices" ] = Property::INTEGER;
+  PropertyBuffer indexPropertyBuffer = PropertyBuffer::New( indexFormat, indices.Size() );
+  if( indices.Size() > 0 )
+  {
+    indexPropertyBuffer.SetData( &indices[ 0 ] );
+  }
+
+  // Create the geometry object
+  Geometry geometry = Geometry::New();
+  geometry.AddVertexBuffer( vertexPropertyBuffer );
+  geometry.SetIndexBuffer( indexPropertyBuffer );
+
+  return geometry;
+}
+
+Geometry CreateGeometry( RendererFactoryCache& factoryCache, ImageDimensions gridSize )
+{
+  Geometry geometry;
+
+  if( gridSize == ImageDimensions( 1, 1 ) )
+  {
+    geometry = factoryCache.GetGeometry( RendererFactoryCache::QUAD_GEOMETRY );
+    if( !geometry )
+    {
+      geometry =  factoryCache.CreateQuadGeometry();
+      factoryCache.SaveGeometry( RendererFactoryCache::QUAD_GEOMETRY, geometry );
+    }
+  }
+  else
+  {
+    uint16_t gridWidth = gridSize.GetWidth();
+    uint16_t gridHeight = gridSize.GetHeight();
+
+    // Create vertices
+    Vector< Vector2 > vertices;
+    vertices.Reserve( ( gridWidth + 1 ) * ( gridHeight + 1 ) );
+
+    for( int y = 0; y < gridHeight + 1; ++y )
+    {
+      for( int x = 0; x < gridWidth + 1; ++x )
+      {
+        vertices.PushBack( Vector2( (float)x/gridWidth - 0.5f, (float)y/gridHeight  - 0.5f) );
+      }
+    }
+
+    // Create indices
+    Vector< unsigned int > indices;
+    indices.Reserve( gridWidth * gridHeight * 6 );
+
+    unsigned int rowIdx     = 0;
+    unsigned int nextRowIdx = gridWidth + 1;
+    for( int y = 0; y < gridHeight; ++y, ++nextRowIdx, ++rowIdx )
+    {
+      for( int x = 0; x < gridWidth; ++x, ++nextRowIdx, ++rowIdx )
+      {
+        AddQuadIndices( indices, rowIdx, nextRowIdx );
+      }
+    }
+
+    return GenerateGeometry( vertices, indices );
+  }
+
+  return geometry;
+}
+
 } //unnamed namespace
 
 ImageRenderer::ImageRenderer()
@@ -86,7 +196,7 @@ ImageRenderer::~ImageRenderer()
 {
 }
 
-void ImageRenderer::Initialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap )
+void ImageRenderer::DoInitialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap )
 {
   Initialize(factoryCache);
 
@@ -94,6 +204,10 @@ void ImageRenderer::Initialize( RendererFactoryCache& factoryCache, const Proper
   if( imageURLValue )
   {
     imageURLValue->Get( mImageUrl );
+    if( !mImageUrl.empty() )
+    {
+      mImage.Reset();
+    }
 
     Property::Value* fittingValue = propertyMap.Find( IMAGE_FITTING_MODE );
     if( fittingValue )
@@ -102,23 +216,23 @@ void ImageRenderer::Initialize( RendererFactoryCache& factoryCache, const Proper
       fittingValue->Get( fitting );
 
       mFittingMode = FittingMode::DEFAULT;
-      if( fitting == "shrink-to-fit" )
+      if( fitting == SHRINK_TO_FIT )
       {
         mFittingMode = FittingMode::SHRINK_TO_FIT;
       }
-      else if( fitting == "scale-to-fill" )
+      else if( fitting == SCALE_TO_FILL )
       {
         mFittingMode = FittingMode::SCALE_TO_FILL;
       }
-      else if( fitting == "fit-width" )
+      else if( fitting == FIT_WIDTH )
       {
         mFittingMode = FittingMode::FIT_WIDTH;
       }
-      else if( fitting == "fit-height" )
+      else if( fitting == FIT_HEIGHT )
       {
         mFittingMode = FittingMode::FIT_HEIGHT;
       }
-      else if( fitting == "default" )
+      else if( fitting == DEFAULT )
       {
         mFittingMode = FittingMode::DEFAULT;
       }
@@ -135,35 +249,35 @@ void ImageRenderer::Initialize( RendererFactoryCache& factoryCache, const Proper
       samplingValue->Get( sampling );
 
       mSamplingMode = SamplingMode::DEFAULT;
-      if( sampling == "box" )
+      if( sampling == BOX )
       {
         mSamplingMode = SamplingMode::BOX;
       }
-      else if( sampling == "nearest" )
+      else if( sampling == NEAREST )
       {
         mSamplingMode = SamplingMode::NEAREST;
       }
-      else if( sampling == "linear" )
+      else if( sampling == LINEAR )
       {
         mSamplingMode = SamplingMode::LINEAR;
       }
-      else if( sampling == "box-then-nearest" )
+      else if( sampling == BOX_THEN_NEAREST )
       {
         mSamplingMode = SamplingMode::BOX_THEN_NEAREST;
       }
-      else if( sampling == "box-then-linear" )
+      else if( sampling == BOX_THEN_LINEAR )
       {
         mSamplingMode = SamplingMode::BOX_THEN_LINEAR;
       }
-      else if( sampling == "no-filter" )
+      else if( sampling == NO_FILTER )
       {
         mSamplingMode = SamplingMode::NO_FILTER;
       }
-      else if( sampling == "dont-care" )
+      else if( sampling == DONT_CARE )
       {
         mSamplingMode = SamplingMode::DONT_CARE;
       }
-      else if( sampling == "default" )
+      else if( sampling == DEFAULT )
       {
         mSamplingMode = SamplingMode::DEFAULT;
       }
@@ -189,25 +303,45 @@ void ImageRenderer::Initialize( RendererFactoryCache& factoryCache, const Proper
 
     mDesiredSize = ImageDimensions( desiredWidth, desiredHeight );
   }
-
-  mImage.Reset();
 }
 
 void ImageRenderer::SetSize( const Vector2& size )
 {
   ControlRenderer::SetSize( size );
-  // ToDo: renderer responds to the size change
+}
+
+void ImageRenderer::GetNaturalSize( Vector2& naturalSize ) const
+{
+  if(mImage)
+  {
+    naturalSize.x = mImage.GetWidth();
+    naturalSize.y = mImage.GetHeight();
+    return;
+  }
+  else if( mDesiredSize.GetWidth()>0 && mDesiredSize.GetHeight()>0)
+  {
+    naturalSize.x = mDesiredSize.GetWidth();
+    naturalSize.y = mDesiredSize.GetHeight();
+    return;
+  }
+  else if( !mImageUrl.empty() )
+  {
+    ImageDimensions dimentions = ResourceImage::GetImageSize( mImageUrl );
+    naturalSize.x = dimentions.GetWidth();
+    naturalSize.y = dimentions.GetHeight();
+    return;
+  }
+
+  naturalSize = Vector2::ZERO;
 }
 
 void ImageRenderer::SetClipRect( const Rect<int>& clipRect )
 {
   ControlRenderer::SetClipRect( clipRect );
-  //ToDo: renderer responds to the clipRect change
 }
 
 void ImageRenderer::SetOffset( const Vector2& offset )
 {
-  //ToDo: renderer applies the offset
 }
 
 void ImageRenderer::DoSetOnStage( Actor& actor )
@@ -229,26 +363,147 @@ void ImageRenderer::DoSetOffStage( Actor& actor )
   }
 }
 
-void ImageRenderer::Initialize( RendererFactoryCache& factoryCache )
+void ImageRenderer::DoCreatePropertyMap( Property::Map& map ) const
 {
-  mImpl->mGeometry = factoryCache.GetGeometry( RendererFactoryCache::QUAD_GEOMETRY );
-  if( !(mImpl->mGeometry) )
+  map.Clear();
+  map.Insert( RENDERER_TYPE, RENDERER_TYPE_VALUE );
+  if( !mImageUrl.empty() )
   {
-    mImpl->mGeometry =  factoryCache.CreateQuadGeometry();
-    factoryCache.SaveGeometry( RendererFactoryCache::QUAD_GEOMETRY, mImpl->mGeometry );
+    map.Insert( IMAGE_URL_NAME, mImageUrl );
+    map.Insert( IMAGE_DESIRED_WIDTH, mDesiredSize.GetWidth() );
+    map.Insert( IMAGE_DESIRED_HEIGHT, mDesiredSize.GetHeight() );
   }
+  else if( mImage )
+  {
+    map.Insert( IMAGE_DESIRED_WIDTH, static_cast<int>(mImage.GetWidth()) );
+    map.Insert( IMAGE_DESIRED_HEIGHT, static_cast<int>(mImage.GetHeight()) );
 
-  mImpl->mShader = factoryCache.GetShader( RendererFactoryCache::IMAGE_SHADER );
-  if( !mImpl->mShader )
+    ResourceImage resourceImage = ResourceImage::DownCast(mImage);
+    if( resourceImage )
+    {
+      map.Insert( IMAGE_URL_NAME, resourceImage.GetUrl() );
+    }
+  }
+
+  switch( mFittingMode )
   {
-    mImpl->mShader = Shader::New( VERTEX_SHADER, FRAGMENT_SHADER );
-    factoryCache.SaveShader( RendererFactoryCache::IMAGE_SHADER, mImpl->mShader );
+    case Dali::FittingMode::FIT_HEIGHT:
+    {
+      map.Insert( IMAGE_FITTING_MODE, FIT_HEIGHT );
+      break;
+    }
+    case Dali::FittingMode::FIT_WIDTH:
+    {
+      map.Insert( IMAGE_FITTING_MODE, FIT_WIDTH );
+      break;
+    }
+    case Dali::FittingMode::SCALE_TO_FILL:
+    {
+      map.Insert( IMAGE_FITTING_MODE, SCALE_TO_FILL );
+      break;
+    }
+    case Dali::FittingMode::SHRINK_TO_FIT:
+    {
+      map.Insert( IMAGE_FITTING_MODE, SHRINK_TO_FIT );
+      break;
+    }
+    default:
+    {
+      map.Insert( IMAGE_FITTING_MODE, DEFAULT );
+      break;
+    }
   }
 
-  mDesiredSize = ImageDimensions();
-  mFittingMode = FittingMode::DEFAULT;
-  mSamplingMode = SamplingMode::DEFAULT;
-  mImageUrl.clear();
+  switch( mSamplingMode )
+  {
+    case Dali::SamplingMode::BOX:
+    {
+      map.Insert( IMAGE_SAMPLING_MODE, BOX );
+      break;
+    }
+    case Dali::SamplingMode::NEAREST:
+    {
+      map.Insert( IMAGE_SAMPLING_MODE, NEAREST );
+      break;
+    }
+    case Dali::SamplingMode::LINEAR:
+    {
+      map.Insert( IMAGE_SAMPLING_MODE, LINEAR );
+      break;
+    }
+    case Dali::SamplingMode::BOX_THEN_LINEAR:
+    {
+      map.Insert( IMAGE_SAMPLING_MODE, BOX_THEN_LINEAR );
+      break;
+    }
+    case Dali::SamplingMode::BOX_THEN_NEAREST:
+    {
+      map.Insert( IMAGE_SAMPLING_MODE, BOX_THEN_NEAREST );
+      break;
+    }
+    case Dali::SamplingMode::NO_FILTER:
+    {
+      map.Insert( IMAGE_SAMPLING_MODE, NO_FILTER );
+      break;
+    }
+    case Dali::SamplingMode::DONT_CARE:
+    {
+      map.Insert( IMAGE_SAMPLING_MODE, DONT_CARE );
+      break;
+    }
+    default:
+    {
+      map.Insert( IMAGE_SAMPLING_MODE, DEFAULT );
+      break;
+    }
+  }
+}
+
+void ImageRenderer::Initialize( RendererFactoryCache& factoryCache )
+{
+  if( !mImpl->mCustomShader )
+  {
+    mImpl->mGeometry = CreateGeometry( factoryCache, ImageDimensions( 1, 1 ) );
+
+    mImpl->mShader = factoryCache.GetShader( RendererFactoryCache::IMAGE_SHADER );
+
+    if( !mImpl->mShader )
+    {
+      mImpl->mShader = Shader::New( VERTEX_SHADER, FRAGMENT_SHADER );
+      factoryCache.SaveShader( RendererFactoryCache::IMAGE_SHADER, mImpl->mShader );
+    }
+  }
+  else
+  {
+    mImpl->mGeometry = CreateGeometry( factoryCache, mImpl->mCustomShader->mGridSize );
+
+    if( mImpl->mCustomShader->mVertexShader.empty() && mImpl->mCustomShader->mFragmentShader.empty() )
+    {
+      mImpl->mShader = factoryCache.GetShader( RendererFactoryCache::IMAGE_SHADER );
+
+      if( !mImpl->mShader )
+      {
+        mImpl->mShader = Shader::New( VERTEX_SHADER, FRAGMENT_SHADER );
+        factoryCache.SaveShader( RendererFactoryCache::IMAGE_SHADER, mImpl->mShader );
+      }
+    }
+    else
+    {
+      mImpl->mShader = Shader::New( mImpl->mCustomShader->mVertexShader.empty() ? VERTEX_SHADER : mImpl->mCustomShader->mVertexShader,
+                                    mImpl->mCustomShader->mFragmentShader.empty() ? FRAGMENT_SHADER : mImpl->mCustomShader->mFragmentShader,
+                                    mImpl->mCustomShader->mHints );
+    }
+  }
+
+  if( mImpl->mRenderer )
+  {
+    mImpl->mRenderer.SetGeometry( mImpl->mGeometry );
+    Material material = mImpl->mRenderer.GetMaterial();
+    if( material )
+    {
+      material.SetShader( mImpl->mShader );
+    }
+  }
 }
 
 void ImageRenderer::SetImage( const std::string& imageUrl )
index be9c2af..367ae31 100644 (file)
@@ -85,9 +85,9 @@ public:
 public:  // from ControlRenderer
 
   /**
-   * @copydoc ControlRenderer::Initialize
+   * @copydoc ControlRenderer::DoInitialize
    */
-  virtual void Initialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap );
+  virtual void DoInitialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap );
 
   /**
    * @copydoc ControlRenderer::SetSize
@@ -95,6 +95,11 @@ public:  // from ControlRenderer
   virtual void SetSize( const Vector2& size );
 
   /**
+   * @copydoc ControlRenderer::GetNaturalSize
+   */
+  virtual void GetNaturalSize( Vector2& naturalSize ) const;
+
+  /**
    * @copydoc ControlRenderer::SetClipRect
    */
   virtual void SetClipRect( const Rect<int>& clipRect );
@@ -104,6 +109,11 @@ public:  // from ControlRenderer
    */
   virtual void SetOffset( const Vector2& offset );
 
+  /**
+   * @copydoc ControlRenderer::CreatePropertyMap
+   */
+  virtual void DoCreatePropertyMap( Property::Map& map ) const;
+
 protected:
   /**
    * @copydoc ControlRenderer::DoSetOnStage
index d757712..842a099 100644 (file)
@@ -41,6 +41,8 @@ namespace Internal
 
 namespace
 {
+const char * const RENDERER_TYPE("renderer-type");
+const char * const RENDERER_TYPE_VALUE("n-patch-renderer");
 
 const char * const IMAGE_URL_NAME("image-url");
 const char * const BORDER_ONLY("border-only");
@@ -158,7 +160,7 @@ NPatchRenderer::~NPatchRenderer()
 {
 }
 
-void NPatchRenderer::Initialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap )
+void NPatchRenderer::DoInitialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap )
 {
   Initialize(factoryCache);
 
@@ -185,6 +187,25 @@ void NPatchRenderer::Initialize( RendererFactoryCache& factoryCache, const Prope
   }
 }
 
+void NPatchRenderer::GetNaturalSize( Vector2& naturalSize ) const
+{
+  if( mImage )
+  {
+    naturalSize.x = mImage.GetWidth();
+    naturalSize.y = mImage.GetHeight();
+    return;
+  }
+  else if( !mImageUrl.empty() )
+  {
+    ImageDimensions dimentions = ResourceImage::GetImageSize( mImageUrl );
+    naturalSize.x = dimentions.GetWidth();
+    naturalSize.y = dimentions.GetHeight();
+    return;
+  }
+
+  naturalSize = Vector2::ZERO;
+}
+
 void NPatchRenderer::SetClipRect( const Rect<int>& clipRect )
 {
   ControlRenderer::SetClipRect( clipRect );
@@ -222,6 +243,21 @@ void NPatchRenderer::DoSetOffStage( Actor& actor )
   mCroppedImage.Reset();
 }
 
+void NPatchRenderer::DoCreatePropertyMap( Property::Map& map ) const
+{
+  map.Clear();
+  map.Insert( RENDERER_TYPE, RENDERER_TYPE_VALUE );
+  if( !mImageUrl.empty() )
+  {
+    map.Insert( IMAGE_URL_NAME, mImageUrl );
+  }
+  else if( mImage )
+  {
+    map.Insert( IMAGE_URL_NAME, mImage.GetUrl() );
+  }
+  map.Insert( BORDER_ONLY, mBorderOnly );
+}
+
 void NPatchRenderer::Initialize( RendererFactoryCache& factoryCache )
 {
   mNinePatchGeometry = factoryCache.GetGeometry( RendererFactoryCache::NINE_PATCH_GEOMETRY );
index b2ead54..6e5bd5d 100644 (file)
@@ -46,6 +46,7 @@ namespace Internal
  * | %Property Name            | Type             |
  * |---------------------------|------------------|
  * | image-url                 | STRING           |
+ * | border-only               | BOOLEAN
  *
  */
 class NPatchRenderer: public ControlRenderer
@@ -65,9 +66,14 @@ public:
 public:  // from ControlRenderer
 
   /**
-   * @copydoc ControlRenderer::Initialize
+   * @copydoc ControlRenderer::DoInitialize
    */
-  virtual void Initialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap );
+  virtual void DoInitialize( RendererFactoryCache& factoryCache, const Property::Map& propertyMap );
+
+  /**
+   * @copydoc ControlRenderer::GetNaturalSize
+   */
+  virtual void GetNaturalSize( Vector2& naturalSize ) const;
 
   /**
    * @copydoc ControlRenderer::SetClipRect
@@ -79,6 +85,11 @@ public:  // from ControlRenderer
    */
   virtual void SetOffset( const Vector2& offset );
 
+  /**
+   * @copydoc ControlRenderer::CreatePropertyMap
+   */
+  virtual void DoCreatePropertyMap( Property::Map& map ) const;
+
 protected:
   /**
    * @copydoc ControlRenderer::DoSetOnStage
index 92fd3bf..afcc452 100644 (file)
@@ -274,6 +274,48 @@ bool RendererFactory::ResetRenderer( Toolkit::ControlRenderer& renderer, const s
   }
 }
 
+bool RendererFactory::ResetRenderer( Toolkit::ControlRenderer& renderer, const Property::Map& propertyMap )
+{
+  Property::Value* type = propertyMap.Find( RENDERER_TYPE_NAME );
+  std::string typeValue ;
+  if( type && type->Get( typeValue ))
+  {
+    //If there's been a renderer type change then we have to return a new shader
+    if( typeValue ==  COLOR_RENDERER && typeid( renderer ) != typeid( ColorRenderer ) )
+    {
+      renderer = GetControlRenderer( propertyMap );
+      return true;
+    }
+    else if( typeValue ==  GRADIENT_RENDERER && typeid( renderer ) != typeid( GradientRenderer ) )
+    {
+      renderer = GetControlRenderer( propertyMap );
+      return true;
+    }
+    else if( typeValue ==  IMAGE_RENDERER && typeid( renderer ) != typeid( ImageRenderer ) )
+    {
+      renderer = GetControlRenderer( propertyMap );
+      return true;
+    }
+    else if( typeValue ==  N_PATCH_RENDERER && typeid( renderer ) != typeid( NPatchRenderer ) )
+    {
+      renderer = GetControlRenderer( propertyMap );
+      return true;
+    }
+    else if( typeValue ==  BORDER_RENDERER && typeid( renderer ) != typeid( BorderRenderer ) )
+    {
+      renderer = GetControlRenderer( propertyMap );
+      return true;
+    }
+  }
+
+  if( !mFactoryCache )
+  {
+    mFactoryCache = new RendererFactoryCache();
+  }
+  GetImplementation( renderer ).Initialize( *( mFactoryCache.Get() ), propertyMap );
+  return false;
+}
+
 } // namespace Internal
 
 } // namespace Toolkit
index 4ed7e7f..99ef2b8 100644 (file)
@@ -52,7 +52,12 @@ public:
   /**
    * @copydoc Toolkit::RenderFactory::GetControlRenderer( const Property::Map& )
    */
-  Toolkit::ControlRenderer GetControlRenderer( const Property::Map& propertyMap  );
+  Toolkit::ControlRenderer GetControlRenderer( const Property::Map& propertyMap );
+
+  /**
+   * @copydoc Toolkit::RenderFactory::ResetRenderer( Toolkit::ControlRenderer& renderer, const Property::Map& propertyMap )
+   */
+  bool ResetRenderer( Toolkit::ControlRenderer& renderer, const Property::Map& propertyMap );
 
   /**
    * @copydoc Toolkit::RenderFactory::GetControlRenderer( const Vector4& )
index 9c3d4c8..f5dda09 100644 (file)
@@ -205,11 +205,7 @@ void TextField::SetProperty( BaseObject* object, Property::Index index, const Pr
         {
           const std::string fontFamily = value.Get< std::string >();
           DALI_LOG_INFO( gLogFilter, Debug::General, "TextField %p FONT_FAMILY %s\n", impl.mController.Get(), fontFamily.c_str() );
-
-          if( impl.mController->GetDefaultFontFamily() != fontFamily )
-          {
-            impl.mController->SetDefaultFontFamily( fontFamily, true ); // "true" as SetProperty means user defined font so don't change when system font changes.
-          }
+          impl.mController->SetDefaultFontFamily( fontFamily );
         }
         break;
       }
index 1c31449..153b34c 100644 (file)
@@ -148,10 +148,7 @@ void TextLabel::SetProperty( BaseObject* object, Property::Index index, const Pr
           const std::string fontFamily = value.Get< std::string >();
 
           DALI_LOG_INFO( gLogFilter, Debug::General, "TextLabel::SetProperty Property::FONT_FAMILY newFont(%s)\n", fontFamily.c_str() );
-          if( impl.mController->GetDefaultFontFamily() != fontFamily )
-          {
-            impl.mController->SetDefaultFontFamily( fontFamily, true );
-          }
+          impl.mController->SetDefaultFontFamily( fontFamily );
         }
         break;
       }
index 6c8c9b7..9ecd378 100644 (file)
@@ -13,6 +13,7 @@ toolkit_src_files = \
    $(toolkit_src_dir)/builder/tree-node-manipulator.cpp \
    $(toolkit_src_dir)/builder/replacement.cpp \
    $(toolkit_src_dir)/controls/renderers/control-renderer-impl.cpp \
+   $(toolkit_src_dir)/controls/renderers/control-renderer-data-impl.cpp \
    $(toolkit_src_dir)/controls/renderers/renderer-factory-cache.cpp \
    $(toolkit_src_dir)/controls/renderers/renderer-factory-impl.cpp \
    $(toolkit_src_dir)/controls/renderers/border/border-renderer.cpp \
index c94129f..6541b77 100644 (file)
@@ -273,6 +273,7 @@ struct Decorator::Impl : public ConnectionTracker
     mScrollDistance( SCROLL_DISTANCE ),
     mTextDepth( 0u ),
     mActiveCopyPastePopup( false ),
+    mPopupSetNewPosition( true ),
     mCursorBlinkStatus( true ),
     mDelayCursorBlink( false ),
     mPrimaryCursorVisible( false ),
@@ -422,6 +423,7 @@ struct Decorator::Impl : public ConnectionTracker
       if( mCopyPastePopup.actor )
       {
         mCopyPastePopup.actor.HidePopup();
+        mPopupSetNewPosition = true;
       }
     }
   }
@@ -459,19 +461,22 @@ struct Decorator::Impl : public ConnectionTracker
       return;
     }
 
-    if ( mHandle[LEFT_SELECTION_HANDLE].active || mHandle[RIGHT_SELECTION_HANDLE].active )
+    if( mPopupSetNewPosition )
     {
-      float minHandleXPosition = std::min (  mHandle[LEFT_SELECTION_HANDLE].position.x, mHandle[RIGHT_SELECTION_HANDLE].position.x );
-      float maxHandleXPosition = std::max (  mHandle[LEFT_SELECTION_HANDLE].position.x, mHandle[RIGHT_SELECTION_HANDLE].position.x );
+      if ( mHandle[LEFT_SELECTION_HANDLE].active || mHandle[RIGHT_SELECTION_HANDLE].active )
+      {
+        float minHandleXPosition = std::min (  mHandle[LEFT_SELECTION_HANDLE].position.x, mHandle[RIGHT_SELECTION_HANDLE].position.x );
+        float maxHandleXPosition = std::max (  mHandle[LEFT_SELECTION_HANDLE].position.x, mHandle[RIGHT_SELECTION_HANDLE].position.x );
 
-      float minHandleYPosition = std::min (  mHandle[LEFT_SELECTION_HANDLE].position.y, mHandle[RIGHT_SELECTION_HANDLE].position.y );
+        float minHandleYPosition = std::min (  mHandle[LEFT_SELECTION_HANDLE].position.y, mHandle[RIGHT_SELECTION_HANDLE].position.y );
 
-      mCopyPastePopup.position.x = minHandleXPosition + ( ( maxHandleXPosition - minHandleXPosition ) *0.5f );
-      mCopyPastePopup.position.y = minHandleYPosition + mCopyPastePopup.offset;
-    }
-    else
-    {
-      mCopyPastePopup.position = Vector3( mCursor[PRIMARY_CURSOR].position.x, mCursor[PRIMARY_CURSOR].position.y -100.0f , 0.0f ); //todo 100 to be an offset Property
+        mCopyPastePopup.position.x = minHandleXPosition + ( ( maxHandleXPosition - minHandleXPosition ) *0.5f );
+        mCopyPastePopup.position.y = minHandleYPosition + mCopyPastePopup.offset;
+      }
+      else
+      {
+        mCopyPastePopup.position = Vector3( mCursor[PRIMARY_CURSOR].position.x, mCursor[PRIMARY_CURSOR].position.y -100.0f , 0.0f ); //todo 100 to be an offset Property
+      }
     }
 
     Vector3 popupSize = Vector3( mCopyPastePopup.actor.GetRelayoutSize( Dimension::WIDTH ), mCopyPastePopup.actor.GetRelayoutSize( Dimension::HEIGHT ), 0.0f );
@@ -481,6 +486,7 @@ struct Decorator::Impl : public ConnectionTracker
     SetUpPopupPositionNotifications();
 
     mCopyPastePopup.actor.SetPosition( mCopyPastePopup.position );
+    mPopupSetNewPosition = false;
   }
 
   void PopupRelayoutComplete( Actor actor )
@@ -1405,6 +1411,7 @@ struct Decorator::Impl : public ConnectionTracker
   int                 mTextDepth;               ///< The depth used to render the text.
 
   bool                mActiveCopyPastePopup              : 1;
+  bool                mPopupSetNewPosition               : 1;
   bool                mCursorBlinkStatus                 : 1; ///< Flag to switch between blink on and blink off.
   bool                mDelayCursorBlink                  : 1; ///< Used to avoid cursor blinking when entering text.
   bool                mPrimaryCursorVisible              : 1; ///< Whether the primary cursor is visible.
@@ -1677,19 +1684,19 @@ bool Decorator::IsPopupActive() const
 
 void Decorator::SetEnabledPopupButtons( TextSelectionPopup::Buttons& enabledButtonsBitMask )
 {
-   mImpl->mEnabledPopupButtons = enabledButtonsBitMask;
+  mImpl->mEnabledPopupButtons = enabledButtonsBitMask;
 
-   if ( !mImpl->mCopyPastePopup.actor )
-   {
-     mImpl->mCopyPastePopup.actor = TextSelectionPopup::New( &mImpl->mTextSelectionPopupCallbackInterface );
+  if ( !mImpl->mCopyPastePopup.actor )
+  {
+    mImpl->mCopyPastePopup.actor = TextSelectionPopup::New( &mImpl->mTextSelectionPopupCallbackInterface );
 #ifdef DECORATOR_DEBUG
-     mImpl->mCopyPastePopup.actor.SetName("mCopyPastePopup");
+    mImpl->mCopyPastePopup.actor.SetName("mCopyPastePopup");
 #endif
-     mImpl->mCopyPastePopup.actor.SetAnchorPoint( AnchorPoint::CENTER );
-     mImpl->mCopyPastePopup.actor.OnRelayoutSignal().Connect( mImpl,  &Decorator::Impl::PopupRelayoutComplete  ); // Position popup after size negotiation
-   }
+    mImpl->mCopyPastePopup.actor.SetAnchorPoint( AnchorPoint::CENTER );
+    mImpl->mCopyPastePopup.actor.OnRelayoutSignal().Connect( mImpl,  &Decorator::Impl::PopupRelayoutComplete  ); // Position popup after size negotiation
+  }
 
-   mImpl->mCopyPastePopup.actor.EnableButtons( mImpl->mEnabledPopupButtons );
+  mImpl->mCopyPastePopup.actor.EnableButtons( mImpl->mEnabledPopupButtons );
 }
 
 TextSelectionPopup::Buttons& Decorator::GetEnabledPopupButtons()
index b655772..7c629fd 100644 (file)
@@ -358,6 +358,7 @@ struct AtlasRenderer::Impl : public ConnectionTracker
     // Now remove references for the old text
     RemoveText();
     mTextCache.Swap( newTextCache );
+    RemoveAllShadowRenderTasks();
 
     if( thereAreUnderlinedGlyphs )
     {
@@ -759,36 +760,33 @@ struct AtlasRenderer::Impl : public ConnectionTracker
     subActor.SetSize( actorSize );
     subActor.SetColor( shadowColor );
 
-    // Discard redundant render-tasks
-    RemoveShadowRenderTask();
-
     // Create a render task to render the effect
-    mShadowTask = Stage::GetCurrent().GetRenderTaskList().CreateTask();
-    mShadowTask.SetTargetFrameBuffer( meshRecord.mBuffer );
-    mShadowTask.SetSourceActor( subActor );
-    mShadowTask.SetClearEnabled( true );
-    mShadowTask.SetClearColor( Vector4::ZERO );
-    mShadowTask.SetExclusive( true );
-    mShadowTask.SetRefreshRate( RenderTask::REFRESH_ONCE );
-    mShadowTask.FinishedSignal().Connect( this, &AtlasRenderer::Impl::RenderComplete );
+    RenderTask shadowTask = Stage::GetCurrent().GetRenderTaskList().CreateTask();
+    shadowTask.SetTargetFrameBuffer( meshRecord.mBuffer );
+    shadowTask.SetSourceActor( subActor );
+    shadowTask.SetClearEnabled( true );
+    shadowTask.SetClearColor( Vector4::ZERO );
+    shadowTask.SetExclusive( true );
+    shadowTask.SetRefreshRate( RenderTask::REFRESH_ONCE );
+    shadowTask.FinishedSignal().Connect( this, &AtlasRenderer::Impl::RenderComplete );
+    mShadowTasks.push_back( shadowTask );
     actor.Add( subActor );
 
     return actor;
   }
 
-  void RemoveShadowRenderTask()
+  void RemoveShadowRenderTask( RenderTask renderTask )
   {
-    if( mShadowTask )
+    if( renderTask )
     {
-      mShadowTask.FinishedSignal().Disconnect( this, &AtlasRenderer::Impl::RenderComplete );
+      renderTask.FinishedSignal().Disconnect( this, &AtlasRenderer::Impl::RenderComplete );
 
       // Guard to prevent accessing Stage after dali-core destruction
       if( Stage::IsInstalled() )
       {
-        Stage::GetCurrent().GetRenderTaskList().RemoveTask( mShadowTask );
+        Stage::GetCurrent().GetRenderTaskList().RemoveTask( renderTask );
       }
-
-      mShadowTask.Reset();
+      renderTask.Reset();
     }
   }
 
@@ -805,12 +803,21 @@ struct AtlasRenderer::Impl : public ConnectionTracker
       }
     }
 
-    RemoveShadowRenderTask();
+    RemoveShadowRenderTask( renderTask );
+  }
+
+  void RemoveAllShadowRenderTasks()
+  {
+    for ( std::vector< RenderTask >::iterator shadowIterator = mShadowTasks.begin();
+          shadowIterator != mShadowTasks.end(); ++shadowIterator )
+    {
+      RemoveShadowRenderTask( *shadowIterator );
+    }
   }
 
   Actor mActor;                                       ///< The actor parent which renders the text
   AtlasGlyphManager mGlyphManager;                    ///< Glyph Manager to handle upload and caching
-  RenderTask mShadowTask;                             ///< Used to render shadows
+  std::vector< RenderTask > mShadowTasks;             ///< Used to render shadows
   TextAbstraction::FontClient mFontClient;            ///> The font client used to supply glyph information
   std::vector< MaxBlockSize > mBlockSizes;            ///> Maximum size needed to contain a glyph in a block within a new atlas
   std::vector< uint32_t > mFace;                      ///> Face indices for a quad
@@ -865,7 +872,7 @@ AtlasRenderer::AtlasRenderer()
 
 AtlasRenderer::~AtlasRenderer()
 {
-  mImpl->RemoveShadowRenderTask();
+  mImpl->RemoveAllShadowRenderTasks();
 
   mImpl->RemoveText();
   delete mImpl;
index eb02202..6b1e31f 100644 (file)
@@ -229,7 +229,7 @@ int Controller::GetMaximumNumberOfCharacters()
   return mImpl->mMaximumNumberOfCharacters;
 }
 
-void Controller::SetDefaultFontFamily( const std::string& defaultFontFamily, bool userDefined )
+void Controller::SetDefaultFontFamily( const std::string& defaultFontFamily )
 {
   if( !mImpl->mFontDefaults )
   {
@@ -237,8 +237,8 @@ void Controller::SetDefaultFontFamily( const std::string& defaultFontFamily, boo
   }
 
   mImpl->mFontDefaults->mFontDescription.family = defaultFontFamily;
-  DALI_LOG_INFO( gLogFilter, Debug::General, "Controller::SetDefaultFontFamily %s userDefined: %s\n", defaultFontFamily.c_str(), userDefined ? "true":"false" );
-  mImpl->mUserDefinedFontFamily = userDefined;
+  DALI_LOG_INFO( gLogFilter, Debug::General, "Controller::SetDefaultFontFamily %s\n", defaultFontFamily.c_str());
+  mImpl->mUserDefinedFontFamily = true;
 
   // Clear the font-specific data
   ClearFontData();
index 3c6125d..5a80e35 100644 (file)
@@ -178,9 +178,8 @@ public:
    * @brief Set the default font family.
    *
    * @param[in] defaultFontFamily The default font family.
-   * @param[in] userDefined If set by the user
    */
-  void SetDefaultFontFamily( const std::string& defaultFontFamily, bool userDefined );
+  void SetDefaultFontFamily( const std::string& defaultFontFamily );
 
   /**
    * @brief Retrieve the default font family.
index 4c40ac8..abb119f 100644 (file)
@@ -326,46 +326,46 @@ public:
   // Deprecated API
 
   /**
-   * @brief Sets the label with an actor.
-   *
    * @deprecated DALi 1.0.50
    *
+   * @brief Sets the label with an actor.
+   *
    * @param[in]  label The actor to use as a label
    */
   void SetLabel( Actor label );
 
   /**
-   * @brief Sets the button image.
-   *
    * @deprecated DALi 1.0.50
    *
+   * @brief Sets the button image.
+   *
    * @param[in]  image The button image.
    */
   void SetButtonImage( Image image );
 
   /**
-   * @brief Sets the selected image.
-   *
    * @deprecated DALi 1.0.50
    *
+   * @brief Sets the selected image.
+   *
    * @param[in]  image The selected image.
    */
   void SetSelectedImage( Image image );
 
   /**
-   * @brief Gets the button image.
-   *
    * @deprecated DALi 1.0.50
    *
+   * @brief Gets the button image.
+   *
    * @return     An actor with the button image.
    */
   Actor GetButtonImage() const;
 
   /**
-   * @brief Gets the selected image.
-   *
    * @deprecated DALi 1.0.50
    *
+   * @brief Gets the selected image.
+   *
    * @return     An actor with the selected image.
    */
   Actor GetSelectedImage() const;
index 31684b3..c887574 100644 (file)
@@ -126,10 +126,10 @@ public:
   using Button::SetButtonImage;
 
   /**
-   * @brief Sets the unselected image with an Actor.
-   *
    * @deprecated DALi 1.0.50
    *
+   * @brief Sets the unselected image with an Actor.
+   *
    * @param[in] image The Actor to use.
    */
   void SetButtonImage( Actor image );
@@ -137,10 +137,10 @@ public:
   using Button::SetBackgroundImage;
 
   /**
-   * @brief Sets the background image with an Actor.
-   *
    * @deprecated DALi 1.0.50
    *
+   * @brief Sets the background image with an Actor.
+   *
    * @param[in] image The Actor to use.
    */
   void SetBackgroundImage( Actor image );
@@ -148,10 +148,10 @@ public:
   using Button::SetSelectedImage;
 
   /**
-   * @brief Sets the selected image with an Actor.
-   *
    * @deprecated DALi 1.0.50
    *
+   * @brief Sets the selected image with an Actor.
+   *
    * @param[in] image The Actor to use.
    */
   void SetSelectedImage( Actor image );
@@ -159,10 +159,10 @@ public:
   using Button::SetSelectedBackgroundImage;
 
   /**
-   * @brief Sets the selected background image with an Actor.
-   *
    * @deprecated DALi 1.0.50
    *
+   * @brief Sets the selected background image with an Actor.
+   *
    * @param[in] image The Actor to use.
    */
   void SetSelectedBackgroundImage( Actor image );
@@ -170,10 +170,10 @@ public:
   using Button::SetDisabledBackgroundImage;
 
   /**
-   * @brief Sets the disabled background image with an Actor.
-   *
    * @deprecated DALi 1.0.50
    *
+   * @brief Sets the disabled background image with an Actor.
+   *
    * @param[in] image The Actor to use.
    */
   void SetDisabledBackgroundImage( Actor image );
@@ -181,10 +181,10 @@ public:
   using Button::SetDisabledImage;
 
   /**
-   * @brief Sets the disabled image with an Actor.
-   *
    * @deprecated DALi 1.0.50
    *
+   * @brief Sets the disabled image with an Actor.
+   *
    * @param[in] image The Actor to use.
    */
   void SetDisabledImage( Actor image );
@@ -192,10 +192,10 @@ public:
   using Button::SetDisabledSelectedImage;
 
   /**
-   * @brief Sets the disabled selected image with an Actor.
-   *
    * @deprecated DALi 1.0.50
    *
+   * @brief Sets the disabled selected image with an Actor.
+   *
    * @param[in] image The Actor to use.
    */
   void SetDisabledSelectedImage( Actor image );
index af2f4ca..c3ca785 100644 (file)
@@ -164,98 +164,8 @@ TypeAction registerAction( typeRegistration, ACTION_ACCESSIBILITY_ACTIVATED, &Do
 
 DALI_TYPE_REGISTRATION_END()
 
-
 const char * const BACKGROUND_COLOR_NAME("color");
 
-/**
- * Structure which holds information about the background of a control
- */
-struct Background
-{
-  //ToDo: remove this actor and apply the Renderer on the Control
-  //      when the implementation of Actor::RemoveRenderer(Renderer&) is in place.
-  Actor actor;                      ///< Background actor
-  ControlRenderer controlRenderer;  ///< The control renderer to render the background
-  // The background can either be an image or a solid color.
-  Image image;                      ///< The background image
-  Vector4 color;                    ///< The background color
-
-  /**
-   * Constructor
-   */
-  Background()
-  : actor(),
-    controlRenderer(),
-    image(),
-    color( Color::TRANSPARENT )
-  {
-  }
-};
-
-//ToDo: skip this actor creation and apply the Renderer on the Control
-//      when the implementation of Actor::RemoveRenderer(Renderer&) is in place.
-Actor CreateBackgroundActor()
-{
-  // Create the actor
-  Actor actor = Actor::New();
-  actor.SetSize( Vector3::ONE );
-  actor.SetPositionInheritanceMode( USE_PARENT_POSITION_PLUS_LOCAL_POSITION );
-  actor.SetColorMode( USE_PARENT_COLOR );
-
-  //Constraint scale of the background actor to the size of the control
-  Constraint constraint = Constraint::New<Vector3>( actor,
-                                                    Actor::Property::SCALE,
-                                                    EqualToConstraint() );
-  constraint.AddSource( ParentSource( Actor::Property::SIZE ) );
-  constraint.Apply();
-
-  return actor;
-}
-
-/**
- * @brief Create the background actor for the control.
- *
- * @param[in] actor The parent actor of the background
- * @param[in] color The background color
- */
-void CreateBackground( Background& background, const Vector4& color )
-{
-  background.actor = CreateBackgroundActor();
-
-  background.image.Reset();
-  background.color = color;
-
- // Create the control renderer
-  RendererFactory rendererFactory = Toolkit::RendererFactory::Get();
-  background.controlRenderer = rendererFactory.GetControlRenderer(color);
-
-  // ToDo: Call SetOnStage at Control::OnStageConnection and call SetOffStage at Control::OnStageDisconnection;
-  //       Currently Actor::RemoveRenderer doesnot work yet.
-  background.controlRenderer.SetOnStage( background.actor );
-}
-
-/**
- * @brief Create the background actor for the control.
- *
- * @param[in] actor The parent actor of the background
- * @param[in] image The background image
- */
-void CreateBackground( Background& background, const Image& image )
-{
-  background.actor = CreateBackgroundActor();
-
-  background.color = Color::TRANSPARENT;
-  background.image = image;
-
-  // Create the control renderer
-  RendererFactory rendererFactory = Toolkit::RendererFactory::Get();
-  background.controlRenderer = rendererFactory.GetControlRenderer(image);
-
-  // ToDo: Call SetOnStage at Control::OnStageConnection and call SetOffStage at Control::OnStageDisconnection;
-  //       Currently Actor::RemoveRenderer doesnot work yet.
-  background.controlRenderer.SetOnStage( background.actor );
-}
-
 } // unnamed namespace
 
 namespace Internal
@@ -269,7 +179,7 @@ public:
   Impl(Control& controlImpl)
 : mControlImpl( controlImpl ),
   mStyleName(""),
-  mBackground( NULL ),
+  mBackgroundRenderer(),
   mStartingPinchScale( NULL ),
   mKeyEventSignal(),
   mPinchGestureDetector(),
@@ -286,7 +196,6 @@ public:
   ~Impl()
   {
     // All gesture detectors will be destroyed so no need to disconnect.
-    delete mBackground;
     delete mStartingPinchScale;
   }
 
@@ -312,21 +221,6 @@ public:
     mControlImpl.OnLongPress(longPress);
   }
 
-  // Background Methods
-
-  /**
-   * Only creates an instance of the background if we actually use it.
-   * @return A reference to the Background structure.
-   */
-  Background& GetBackground()
-  {
-    if ( !mBackground )
-    {
-      mBackground = new Background;
-    }
-    return *mBackground;
-  }
-
   // Properties
 
   /**
@@ -361,16 +255,11 @@ public:
           const Property::Map* map = value.GetMap();
           if( map )
           {
-            const Property::Value* colorValue = map->Find( BACKGROUND_COLOR_NAME );
-            Vector4 color;
-            if( colorValue && colorValue->Get(color))
-            {
-              controlImpl.SetBackgroundColor( color );
-              break;
-            }
+            controlImpl.SetBackground( *map );
+            break;
           }
 
-          // The background is neither an valid image nor a valid color, so it is no longer required
+          // The background is neither a valid image nor a property map, so it is no longer required
           controlImpl.ClearBackground();
           break;
         }
@@ -418,18 +307,9 @@ public:
         case Toolkit::Control::Property::BACKGROUND:
         {
           Property::Map map;
-
-          Background* back = controlImpl.mImpl->mBackground;
-          if ( back && back->actor)
+          if( controlImpl.mImpl->mBackgroundRenderer )
           {
-            if( back->image )
-            {
-              Scripting::CreatePropertyMap( back->image, map );
-            }
-            else
-            {
-              map[BACKGROUND_COLOR_NAME] = back->color;
-            }
+            (controlImpl.mImpl->mBackgroundRenderer).CreatePropertyMap( map );
           }
 
           value = map;
@@ -451,7 +331,7 @@ public:
 
   Control& mControlImpl;
   std::string mStyleName;
-  Background* mBackground;           ///< Only create the background if we use it
+  Toolkit::ControlRenderer mBackgroundRenderer;   ///< The control renderer to render the background
   Vector3* mStartingPinchScale;      ///< The scale when a pinch gesture starts, TODO: consider removing this
   Toolkit::Control::KeyEventSignalType mKeyEventSignal;
   Toolkit::Control::KeyInputFocusSignalType mKeyInputFocusGainedSignal;
@@ -521,81 +401,93 @@ const std::string& Control::GetStyleName() const
 
 void Control::SetBackgroundColor( const Vector4& color )
 {
-  Background& background( mImpl->GetBackground() );
+  Actor self( Self() );
+  Toolkit::RendererFactory factory = Toolkit::RendererFactory::Get();
 
-  // The background renderer exits and it is a color renderer, we continue to use the current renderer
-  if ( background.actor && (!background.image)
-      &&  (!Toolkit::RendererFactory::Get().ResetRenderer( background.controlRenderer, color ) ))
+  if( mImpl->mBackgroundRenderer )
   {
-    background.color = color;
+    Toolkit::ControlRenderer currentRenderer( mImpl->mBackgroundRenderer );
+    // if ResetRenderer returns false, we continue to use the current renderer with a new color set to it.
+    if( ! factory.ResetRenderer( mImpl->mBackgroundRenderer, color ) )
+    {
+      return;
+    }
+    // ResetRenderer returns true, a new renderer is created. Remove the current renderer and reset.
+    currentRenderer.RemoveAndReset( self );
   }
   else
   {
-    // TODO: Apply the new renderer directly, as Actor::RemoveRenderer is not working yet, we create a new actor
-    if( background.actor )
-    {
-      mImpl->mAddRemoveBackgroundChild = true;
-      Self().Remove( background.actor );
-      mImpl->mAddRemoveBackgroundChild = false;
-    }
-    // Create background actor
-    CreateBackground(background, color );
-    mImpl->mAddRemoveBackgroundChild = true;
-    // The actor does not need to be inserted to guarantee order.
-    Self().Add( background.actor );
-    mImpl->mAddRemoveBackgroundChild = false;
+    mImpl->mBackgroundRenderer = factory.GetControlRenderer( color );
+  }
+
+  if( self.OnStage() )
+  {
+    mImpl->mBackgroundRenderer.SetDepthIndex( BACKGROUND_DEPTH_INDEX );
+    mImpl->mBackgroundRenderer.SetOnStage( self );
   }
 }
 
 Vector4 Control::GetBackgroundColor() const
 {
-  if ( mImpl->mBackground )
+  return Color::TRANSPARENT;
+}
+
+void Control::SetBackground(const Property::Map& map)
+{
+  const Property::Value* colorValue = map.Find( BACKGROUND_COLOR_NAME );
+  Vector4 color;
+  if( colorValue && colorValue->Get(color))
   {
-    return mImpl->mBackground->color;
+    SetBackgroundColor( color );
+    return;
+  }
+
+  Actor self( Self() );
+  mImpl->mBackgroundRenderer.RemoveAndReset( self );
+
+  Toolkit::RendererFactory factory = Toolkit::RendererFactory::Get();
+  mImpl->mBackgroundRenderer = factory.GetControlRenderer( map );
+
+  // mBackgroundRenderer might be empty, if an invalid map is provided, no background.
+  if( self.OnStage() && mImpl->mBackgroundRenderer)
+  {
+    mImpl->mBackgroundRenderer.SetDepthIndex( BACKGROUND_DEPTH_INDEX );
+    mImpl->mBackgroundRenderer.SetOnStage( self );
   }
-  return Color::TRANSPARENT;
 }
 
 void Control::SetBackgroundImage( Image image )
 {
-  Background& background( mImpl->GetBackground() );
+  Actor self( Self() );
+  Toolkit::RendererFactory factory = Toolkit::RendererFactory::Get();
 
-  // The background renderer exits and it is an image renderer, we continue to use the current renderer
-  if( background.actor && background.image
-      && (! Toolkit::RendererFactory::Get().ResetRenderer( background.controlRenderer, image ) ) )
+  if(  mImpl->mBackgroundRenderer  )
   {
-    background.image = image;
+    Toolkit::ControlRenderer currentRenderer( mImpl->mBackgroundRenderer );
+    // if ResetRenderer returns false, we continue to use the current renderer with a new image set to it.
+    if( ! factory.ResetRenderer( mImpl->mBackgroundRenderer, image )  )
+    {
+      return;
+    }
+    // ResetRenderer returns true, a new renderer is created. Remove the current renderer and reset.
+    currentRenderer.RemoveAndReset( self );
   }
   else
   {
-    // TODO: Apply the new renderer directly, as Actor::RemoveRenderer is not working yet, we create a new actor
-    if( background.actor )
-    {
-      mImpl->mAddRemoveBackgroundChild = true;
-      Self().Remove( background.actor );
-      mImpl->mAddRemoveBackgroundChild = false;
-    }
-    // Create background actor
-    CreateBackground(background, image);
-    mImpl->mAddRemoveBackgroundChild = true;
-    // The actor does not need to be inserted to guarantee order.
-    Self().Add( background.actor );
-    mImpl->mAddRemoveBackgroundChild = false;
+    mImpl->mBackgroundRenderer = factory.GetControlRenderer( image );
+  }
+
+  if( self.OnStage() )
+  {
+    mImpl->mBackgroundRenderer.SetDepthIndex( BACKGROUND_DEPTH_INDEX );
+    mImpl->mBackgroundRenderer.SetOnStage( self );
   }
 }
 
 void Control::ClearBackground()
 {
-  if ( mImpl->mBackground )
-  {
-    Background& background( mImpl->GetBackground() );
-    mImpl->mAddRemoveBackgroundChild = true;
-    Self().Remove( background.actor );
-    mImpl->mAddRemoveBackgroundChild = false;
-
-    delete mImpl->mBackground;
-    mImpl->mBackground = NULL;
-  }
+  Actor self(Self());
+  mImpl->mBackgroundRenderer.RemoveAndReset( self );
 }
 
 void Control::EnableGestureDetection(Gesture::Type type)
@@ -928,14 +820,21 @@ void Control::OnStageConnection( int depth )
     }
   }
 
-  if( mImpl->mBackground && mImpl->mBackground->controlRenderer)
+  if( mImpl->mBackgroundRenderer)
   {
-    mImpl->mBackground->controlRenderer.SetDepthIndex( BACKGROUND_DEPTH_INDEX+depth );
+    mImpl->mBackgroundRenderer.SetDepthIndex( BACKGROUND_DEPTH_INDEX );
+    Actor self(Self());
+    mImpl->mBackgroundRenderer.SetOnStage( self );
   }
 }
 
 void Control::OnStageDisconnection()
 {
+  if( mImpl->mBackgroundRenderer)
+  {
+    Actor self(Self());
+    mImpl->mBackgroundRenderer.SetOffStage( self );
+  }
 }
 
 void Control::OnKeyInputFocusGained()
@@ -1016,30 +915,13 @@ void Control::OnSetResizePolicy( ResizePolicy::Type policy, Dimension::Type dime
 
 Vector3 Control::GetNaturalSize()
 {
-  //Control's natural size is the size of its background image if it has been set, or ZERO otherwise
-  Vector3 naturalSize = Vector3::ZERO;
-  if( mImpl->mBackground )
+  if( mImpl->mBackgroundRenderer )
   {
-    if( mImpl->mBackground->actor.GetRendererCount() > 0 )
-    {
-      Material backgroundMaterial = mImpl->mBackground->actor.GetRendererAt(0).GetMaterial();
-      if( backgroundMaterial.GetNumberOfSamplers() > 0 )
-      {
-        Image backgroundImage =  backgroundMaterial.GetSamplerAt(0).GetImage();
-        if( backgroundImage )
-        {
-          naturalSize.x = backgroundImage.GetWidth();
-          naturalSize.y = backgroundImage.GetHeight();
-        }
-      }
-    }
-    else
-    {
-      return mImpl->mBackground->actor.GetNaturalSize();
-    }
+    Vector2 naturalSize;
+    mImpl->mBackgroundRenderer.GetNaturalSize(naturalSize);
+    return Vector3(naturalSize);
   }
-
-  return naturalSize;
+  return Vector3::ZERO;
 }
 
 float Control::CalculateChildSize( const Dali::Actor& child, Dimension::Type dimension )
@@ -1049,27 +931,11 @@ float Control::CalculateChildSize( const Dali::Actor& child, Dimension::Type dim
 
 float Control::GetHeightForWidth( float width )
 {
-  if( mImpl->mBackground )
-  {
-    Actor actor = mImpl->mBackground->actor;
-    if( actor )
-    {
-      return actor.GetHeightForWidth( width );
-    }
-  }
   return GetHeightForWidthBase( width );
 }
 
 float Control::GetWidthForHeight( float height )
 {
-  if( mImpl->mBackground )
-  {
-    Actor actor = mImpl->mBackground->actor;
-    if( actor )
-    {
-      return actor.GetWidthForHeight( height );
-    }
-  }
   return GetWidthForHeightBase( height );
 }
 
index 4a8466d..aa86d6a 100644 (file)
@@ -102,6 +102,13 @@ public:
   void SetBackgroundImage( Image image );
 
   /**
+   * @brief Set the background with a property map.
+   *
+   * @param[in] map The background property map.
+   */
+  void SetBackground(const Property::Map& map);
+
+  /**
    * @copydoc Dali::Toolkit::Control::ClearBackground
    */
   void ClearBackground();
index d6425e2..51f6bd1 100644 (file)
@@ -89,7 +89,7 @@ public:
     enum
     {
       STYLE_NAME = PROPERTY_START_INDEX,       ///< name "style-name",       @see SetStyleName,       type std::string
-      BACKGROUND,                              ///< name "background",       @see SetBackgroundImage, type Map,         @since DALi 1.1.4
+      BACKGROUND,                              ///< name "background",       @since DALi 1.1.4,       type Map
       KEY_INPUT_FOCUS,                         ///< name "key-input-focus",  @see SetKeyInputFocus,   type bool
     };
   };
index a65f649..4e98ccb 100644 (file)
@@ -141,9 +141,9 @@ public:
    *
    * If the handle is empty, ImageView will display nothing
    *
-   * @param[in] url The Image resource to display.
-   *
    * @since DALi 1.1.4
+   *
+   * @param[in] url The Image resource to display.
    */
   void SetImage( const std::string& url );
 
index 8099c26..9898791 100644 (file)
@@ -36,7 +36,8 @@ class PageTurnView;
 }
 
 /**
- * PageTurnView is a base class of different mode of pageTurnViews ( portrait or landscape )
+ * @brief PageTurnView is a base class of different mode of pageTurnViews ( portrait or landscape )
+ *
  * Page actors are provided from an external PageFactory
  * PanGesture is used to activate the page bending, streching and tuning forward/backward
  *
index 6e63182..a7b1d49 100644 (file)
@@ -31,7 +31,7 @@ namespace Toolkit
 
 const unsigned int TOOLKIT_MAJOR_VERSION = 1;
 const unsigned int TOOLKIT_MINOR_VERSION = 1;
-const unsigned int TOOLKIT_MICRO_VERSION = 4;
+const unsigned int TOOLKIT_MICRO_VERSION = 5;
 const char * const TOOLKIT_BUILD_DATE    = __DATE__ " " __TIME__;
 
 #ifdef DEBUG_ENABLED
index e3500ea..b80108a 100644 (file)
@@ -1,6 +1,6 @@
 Name:       dali-toolkit
 Summary:    The OpenGLES Canvas Core Library Toolkit
-Version:    1.1.4
+Version:    1.1.5
 Release:    1
 Group:      System/Libraries
 License:    Apache-2.0, BSD-2.0, MIT