Download remote svg file 24/221424/9
authorhuiyu.eun <huiyu.eun@samsung.com>
Mon, 30 Dec 2019 04:23:27 +0000 (13:23 +0900)
committerhuiyu.eun <huiyu.eun@samsung.com>
Thu, 30 Jan 2020 00:33:15 +0000 (09:33 +0900)
Change-Id: I115ba51843a448015b3c136de0570a3078a92ab6
Signed-off-by: huiyu.eun <huiyu.eun@samsung.com>
automated-tests/src/dali-toolkit/utc-Dali-ImageView.cpp
automated-tests/src/dali-toolkit/utc-Dali-Visual.cpp
dali-toolkit/internal/visuals/svg/svg-rasterize-thread.cpp
dali-toolkit/internal/visuals/svg/svg-rasterize-thread.h
dali-toolkit/internal/visuals/svg/svg-visual.cpp
dali-toolkit/internal/visuals/svg/svg-visual.h
dali-toolkit/internal/visuals/visual-factory-cache.cpp

index 7d709d8..5b58193 100644 (file)
@@ -2400,3 +2400,28 @@ int UtcDaliImageViewReloadFailedOnResourceReadySignal(void)
 
   END_TEST;
 }
 
   END_TEST;
 }
+
+int UtcDaliImageViewLoadRemoteSVG(void)
+{
+  tet_infoline("Test reloading failed image from within signal handler.");
+
+  ToolkitTestApplication application;
+  Toolkit::ImageView mImageView;
+  mImageView = Toolkit::ImageView::New(  );
+  mImageView.SetImage("http://bar.org/foobar.svg");
+  mImageView.SetParentOrigin( ParentOrigin::TOP_LEFT );
+  mImageView.SetAnchorPoint( AnchorPoint::TOP_LEFT );
+  mImageView.SetSize(300, 300);
+  mImageView.SetPosition( Vector3( 150.0f , 150.0f , 0.0f ) );
+
+  Stage::GetCurrent().Add( mImageView );
+
+  application.SendNotification();
+  application.Render();
+  DALI_TEST_EQUALS( Test::WaitForEventThreadTrigger( 1 ), true, TEST_LOCATION );
+
+  DALI_TEST_CHECK( mImageView );
+
+  END_TEST;
+}
+
index 374afe0..d1df2ac 100644 (file)
@@ -346,7 +346,6 @@ int UtcDaliVisualSize(void)
 
   // svg visual
   Visual::Base svgVisual = factory.CreateVisual( TEST_SVG_FILE_NAME, ImageDimensions() );
 
   // svg visual
   Visual::Base svgVisual = factory.CreateVisual( TEST_SVG_FILE_NAME, ImageDimensions() );
-  svgVisual.SetTransformAndSize(DefaultTransform(), controlSize );
   svgVisual.GetNaturalSize(naturalSize);
   // TEST_SVG_FILE:
   //  <svg width="100" height="100">
   svgVisual.GetNaturalSize(naturalSize);
   // TEST_SVG_FILE:
   //  <svg width="100" height="100">
index 13140a7..174183e 100644 (file)
 // CLASS HEADER
 #include "svg-rasterize-thread.h"
 
 // CLASS HEADER
 #include "svg-rasterize-thread.h"
 
+// EXTERNAL INCLUDES
+#include <dali/devel-api/adaptor-framework/thread-settings.h>
+#include <dali/devel-api/adaptor-framework/file-loader.h>
+#include <dali/integration-api/debug.h>
+
 // INTERNAL INCLUDES
 #include <dali-toolkit/third-party/nanosvg/nanosvgrast.h>
 #include <dali-toolkit/internal/visuals/svg/svg-visual.h>
 // INTERNAL INCLUDES
 #include <dali-toolkit/third-party/nanosvg/nanosvgrast.h>
 #include <dali-toolkit/internal/visuals/svg/svg-visual.h>
-#include <dali/devel-api/adaptor-framework/thread-settings.h>
 
 namespace Dali
 {
 
 namespace Dali
 {
@@ -32,20 +36,49 @@ namespace Toolkit
 namespace Internal
 {
 
 namespace Internal
 {
 
-RasterizingTask::RasterizingTask( SvgVisual* svgRenderer, NSVGimage* parsedSvg, unsigned int width, unsigned int height )
+namespace
+{
+const char * const UNITS("px");
+}
+
+RasterizingTask::RasterizingTask( SvgVisual* svgRenderer, NSVGimage* parsedSvg, const VisualUrl& url, float dpi, unsigned int width, unsigned int height)
 : mSvgVisual( svgRenderer ),
   mParsedSvg( parsedSvg ),
 : mSvgVisual( svgRenderer ),
   mParsedSvg( parsedSvg ),
+  mUrl( url ),
+  mDpi( dpi ),
   mWidth( width ),
   mHeight( height )
 {
 }
 
   mWidth( width ),
   mHeight( height )
 {
 }
 
+void RasterizingTask::Load()
+{
+  if( mParsedSvg != NULL)
+  {
+    return;
+  }
+
+  if( !mUrl.IsLocalResource() )
+  {
+    Dali::Vector<uint8_t> remoteBuffer;
+
+    if( !Dali::FileLoader::DownloadFileSynchronously( mUrl.GetUrl(), remoteBuffer ))
+    {
+      DALI_LOG_ERROR("Failed to download file!\n");
+      return;
+    }
+
+    remoteBuffer.PushBack( '\0' );
+    mParsedSvg = nsvgParse( reinterpret_cast<char*>(remoteBuffer.begin()), UNITS, mDpi );
+  }
+}
+
 void RasterizingTask::Rasterize( NSVGrasterizer* rasterizer )
 {
 void RasterizingTask::Rasterize( NSVGrasterizer* rasterizer )
 {
-  if( mWidth > 0u && mHeight > 0u )
+  if( mParsedSvg != NULL && mWidth > 0u && mHeight > 0u )
   {
   {
-    float scaleX =  static_cast<float>( mWidth ) /  mParsedSvg->width;
-    float scaleY =  static_cast<float>( mHeight ) /  mParsedSvg->height;
+    float scaleX = static_cast<float>( mWidth ) /  mParsedSvg->width;
+    float scaleY = static_cast<float>( mHeight ) /  mParsedSvg->height;
     float scale = scaleX < scaleY ? scaleX : scaleY;
     unsigned int bufferStride = mWidth*Pixel::GetBytesPerPixel( Pixel::RGBA8888 );
     unsigned int bufferSize = bufferStride * mHeight;
     float scale = scaleX < scaleY ? scaleX : scaleY;
     unsigned int bufferStride = mWidth*Pixel::GetBytesPerPixel( Pixel::RGBA8888 );
     unsigned int bufferSize = bufferStride * mHeight;
@@ -59,6 +92,11 @@ void RasterizingTask::Rasterize( NSVGrasterizer* rasterizer )
   }
 }
 
   }
 }
 
+NSVGimage* RasterizingTask::GetParsedImage() const
+{
+  return mParsedSvg;
+}
+
 SvgVisual* RasterizingTask::GetSvgVisual() const
 {
   return mSvgVisual.Get();
 SvgVisual* RasterizingTask::GetSvgVisual() const
 {
   return mSvgVisual.Get();
@@ -225,6 +263,7 @@ void SvgRasterizeThread::Run()
   SetThreadName( "SVGThread" );
   while( RasterizingTaskPtr task = NextTaskToProcess() )
   {
   SetThreadName( "SVGThread" );
   while( RasterizingTaskPtr task = NextTaskToProcess() )
   {
+    task->Load( );
     task->Rasterize( mRasterizer );
     AddCompletedTask( task );
   }
     task->Rasterize( mRasterizer );
     AddCompletedTask( task );
   }
index f30c459..1c94ca9 100644 (file)
@@ -28,6 +28,7 @@
 #include <dali/public-api/common/vector-wrapper.h>
 #include <dali/public-api/object/ref-object.h>
 #include <dali/public-api/rendering/texture-set.h>
 #include <dali/public-api/common/vector-wrapper.h>
 #include <dali/public-api/object/ref-object.h>
 #include <dali/public-api/rendering/texture-set.h>
+#include <dali-toolkit/internal/visuals/visual-url.h>
 
 struct NSVGimage;
 struct NSVGrasterizer;
 
 struct NSVGimage;
 struct NSVGrasterizer;
@@ -65,10 +66,11 @@ public:
    * @param[in] parsedSvg The parsed svg for rasterizing.
    *            Note, after the task is added to the worker thread, the worker thread takes over the ownership.
    *            When the image is to be deleted, delete it in the worker thread by calling SvgRasterizeThread::DeleteImage( parsedSvg ).
    * @param[in] parsedSvg The parsed svg for rasterizing.
    *            Note, after the task is added to the worker thread, the worker thread takes over the ownership.
    *            When the image is to be deleted, delete it in the worker thread by calling SvgRasterizeThread::DeleteImage( parsedSvg ).
+   * @param[in] url The URL to svg resource to use.
    * @param[in] width The rasterization width.
    * @param[in] height The rasterization height.
    */
    * @param[in] width The rasterization width.
    * @param[in] height The rasterization height.
    */
-  RasterizingTask( SvgVisual* svgRenderer, NSVGimage* parsedSvg, unsigned int width, unsigned int height );
+  RasterizingTask( SvgVisual* svgRenderer, NSVGimage* parsedSvg, const VisualUrl& url, float dpi, unsigned int width, unsigned int height );
 
   /**
    * Do the rasterization with the given rasterizer.
 
   /**
    * Do the rasterization with the given rasterizer.
@@ -87,8 +89,18 @@ public:
    */
   PixelData GetPixelData() const;
 
    */
   PixelData GetPixelData() const;
 
-private:
+  /**
+   * Get the parsed data.
+   * @return parsed image data.
+   */
+  NSVGimage* GetParsedImage() const;
+
+  /**
+   * Load svg file
+   */
+  void Load();
 
 
+private:
   // Undefined
   RasterizingTask( const RasterizingTask& task );
 
   // Undefined
   RasterizingTask( const RasterizingTask& task );
 
@@ -96,14 +108,15 @@ private:
   RasterizingTask& operator=( const RasterizingTask& task );
 
 private:
   RasterizingTask& operator=( const RasterizingTask& task );
 
 private:
-  SvgVisualPtr  mSvgVisual;
-  PixelData       mPixelData;
+  SvgVisualPtr    mSvgVisual;
   NSVGimage*      mParsedSvg;
   NSVGimage*      mParsedSvg;
+  VisualUrl       mUrl;
+  PixelData       mPixelData;
+  float           mDpi;
   unsigned int    mWidth;
   unsigned int    mHeight;
 };
 
   unsigned int    mWidth;
   unsigned int    mHeight;
 };
 
-
 /**
  * The worker thread for SVG rasterization.
  */
 /**
  * The worker thread for SVG rasterization.
  */
index fccd5e7..051affe 100644 (file)
 // CLASS HEADER
 #include "svg-visual.h"
 
 // CLASS HEADER
 #include "svg-visual.h"
 
-// EXTERNAL INCLUDES
-#include <dali/public-api/images/buffer-image.h>
-#include <dali/public-api/common/stage.h>
-#include <dali/public-api/math/vector4.h>
-#include <dali/devel-api/images/texture-set-image.h>
-#include <dali/integration-api/debug.h>
-#include <dali/devel-api/adaptor-framework/file-loader.h>
-
 // INTERNAL INCLUDES
 // INTERNAL INCLUDES
-#include <dali-toolkit/public-api/visuals/image-visual-properties.h>
-#include <dali-toolkit/public-api/visuals/visual-properties.h>
 #include <dali-toolkit/third-party/nanosvg/nanosvg.h>
 #include <dali-toolkit/internal/visuals/svg/svg-rasterize-thread.h>
 #include <dali-toolkit/internal/visuals/image-atlas-manager.h>
 #include <dali-toolkit/third-party/nanosvg/nanosvg.h>
 #include <dali-toolkit/internal/visuals/svg/svg-rasterize-thread.h>
 #include <dali-toolkit/internal/visuals/image-atlas-manager.h>
-#include <dali-toolkit/internal/visuals/visual-factory-cache.h>
 #include <dali-toolkit/internal/visuals/visual-string-constants.h>
 #include <dali-toolkit/internal/visuals/visual-base-data-impl.h>
 #include <dali-toolkit/internal/visuals/image-visual-shader-factory.h>
 #include <dali-toolkit/internal/visuals/visual-string-constants.h>
 #include <dali-toolkit/internal/visuals/visual-base-data-impl.h>
 #include <dali-toolkit/internal/visuals/image-visual-shader-factory.h>
+#include <dali/devel-api/adaptor-framework/file-loader.h>
 
 
-namespace
-{
-const char * const UNITS("px");
-
-// property name
-const char * const IMAGE_ATLASING( "atlasing" );
-
-const Dali::Vector4 FULL_TEXTURE_RECT(0.f, 0.f, 1.f, 1.f);
-}
+// EXTERNAL INCLUDES
+#include <dali/public-api/common/stage.h>
 
 namespace Dali
 {
 
 namespace Dali
 {
@@ -56,9 +39,19 @@ namespace Toolkit
 namespace Internal
 {
 
 namespace Internal
 {
 
+namespace
+{
+// property name
+const char * const UNITS("px");
+
+const char * const IMAGE_ATLASING( "atlasing" );
+
+const Dali::Vector4 FULL_TEXTURE_RECT(0.f, 0.f, 1.f, 1.f);
+}
+
 SvgVisualPtr SvgVisual::New( VisualFactoryCache& factoryCache, ImageVisualShaderFactory& shaderFactory, const VisualUrl& imageUrl, const Property::Map& properties )
 {
 SvgVisualPtr SvgVisual::New( VisualFactoryCache& factoryCache, ImageVisualShaderFactory& shaderFactory, const VisualUrl& imageUrl, const Property::Map& properties )
 {
-  SvgVisualPtr svgVisual( new SvgVisual( factoryCache, shaderFactory ) );
+  SvgVisualPtr svgVisual( new SvgVisual( factoryCache, shaderFactory, imageUrl ) );
   svgVisual->ParseFromUrl( imageUrl );
   svgVisual->SetProperties( properties );
 
   svgVisual->ParseFromUrl( imageUrl );
   svgVisual->SetProperties( properties );
 
@@ -67,17 +60,17 @@ SvgVisualPtr SvgVisual::New( VisualFactoryCache& factoryCache, ImageVisualShader
 
 SvgVisualPtr SvgVisual::New( VisualFactoryCache& factoryCache, ImageVisualShaderFactory& shaderFactory, const VisualUrl& imageUrl )
 {
 
 SvgVisualPtr SvgVisual::New( VisualFactoryCache& factoryCache, ImageVisualShaderFactory& shaderFactory, const VisualUrl& imageUrl )
 {
-  SvgVisualPtr svgVisual( new SvgVisual( factoryCache, shaderFactory ) );
+  SvgVisualPtr svgVisual( new SvgVisual( factoryCache, shaderFactory, imageUrl ) );
   svgVisual->ParseFromUrl( imageUrl );
 
   return svgVisual;
 }
 
   svgVisual->ParseFromUrl( imageUrl );
 
   return svgVisual;
 }
 
-SvgVisual::SvgVisual( VisualFactoryCache& factoryCache, ImageVisualShaderFactory& shaderFactory )
+SvgVisual::SvgVisual( VisualFactoryCache& factoryCache, ImageVisualShaderFactory& shaderFactory, const VisualUrl& imageUrl )
 : Visual::Base( factoryCache, Visual::FittingMode::FILL ),
   mImageVisualShaderFactory( shaderFactory ),
   mAtlasRect( FULL_TEXTURE_RECT ),
 : Visual::Base( factoryCache, Visual::FittingMode::FILL ),
   mImageVisualShaderFactory( shaderFactory ),
   mAtlasRect( FULL_TEXTURE_RECT ),
-  mImageUrl( ),
+  mImageUrl( imageUrl ),
   mParsedImage( NULL ),
   mPlacementActor(),
   mVisualSize(Vector2::ZERO),
   mParsedImage( NULL ),
   mPlacementActor(),
   mVisualSize(Vector2::ZERO),
@@ -216,22 +209,25 @@ void SvgVisual::ParseFromUrl( const VisualUrl& imageUrl )
 
 void SvgVisual::AddRasterizationTask( const Vector2& size )
 {
 
 void SvgVisual::AddRasterizationTask( const Vector2& size )
 {
-  if( mImpl->mRenderer && mParsedImage )
+  if( mImpl->mRenderer )
   {
     unsigned int width = static_cast<unsigned int>(size.width);
     unsigned int height = static_cast<unsigned int>( size.height );
 
   {
     unsigned int width = static_cast<unsigned int>(size.width);
     unsigned int height = static_cast<unsigned int>( size.height );
 
-    RasterizingTaskPtr newTask = new RasterizingTask( this, mParsedImage, width, height );
+    Vector2 dpi = Stage::GetCurrent().GetDpi();
+    float meanDpi = ( dpi.height + dpi.width ) * 0.5f;
+
+    RasterizingTaskPtr newTask = new RasterizingTask( this, mParsedImage, mImageUrl, meanDpi, width, height );
     mFactoryCache.GetSVGRasterizationThread()->AddTask( newTask );
   }
 }
 
     mFactoryCache.GetSVGRasterizationThread()->AddTask( newTask );
   }
 }
 
-void SvgVisual::ApplyRasterizedImage( PixelData rasterizedPixelData )
+void SvgVisual::ApplyRasterizedImage( NSVGimage* parsedSvg, PixelData rasterizedPixelData )
 {
 {
-  if( IsOnStage()  )
+  if( mParsedImage && IsOnStage() )
   {
     TextureSet currentTextureSet = mImpl->mRenderer.GetTextures();
   {
     TextureSet currentTextureSet = mImpl->mRenderer.GetTextures();
-    if( mImpl->mFlags |= Impl::IS_ATLASING_APPLIED )
+    if( mImpl->mFlags & Impl::IS_ATLASING_APPLIED )
     {
       mFactoryCache.GetAtlasManager()->Remove( currentTextureSet, mAtlasRect );
     }
     {
       mFactoryCache.GetAtlasManager()->Remove( currentTextureSet, mAtlasRect );
     }
@@ -298,7 +294,7 @@ void SvgVisual::OnSetTransform()
 {
   Vector2 visualSize = mImpl->mTransform.GetVisualSize( mImpl->mControlSize );
 
 {
   Vector2 visualSize = mImpl->mTransform.GetVisualSize( mImpl->mControlSize );
 
-  if( mParsedImage && IsOnStage() )
+  if( IsOnStage() )
   {
     if( visualSize != mVisualSize )
     {
   {
     if( visualSize != mVisualSize )
     {
index 8fc2ad8..87e9d43 100644 (file)
@@ -106,8 +106,9 @@ protected:
    *
    * @param[in] factoryCache A pointer pointing to the VisualFactoryCache object
    * @param[in] shaderFactory The ImageVisualShaderFactory object
    *
    * @param[in] factoryCache A pointer pointing to the VisualFactoryCache object
    * @param[in] shaderFactory The ImageVisualShaderFactory object
+   * @param[in] imageUrl The URL to svg resource to use
    */
    */
-  SvgVisual( VisualFactoryCache& factoryCache, ImageVisualShaderFactory& shaderFactory );
+  SvgVisual( VisualFactoryCache& factoryCache, ImageVisualShaderFactory& shaderFactory, const VisualUrl& imageUrl );
 
   /**
    * @brief A reference counted object may only be deleted by calling Unreference().
 
   /**
    * @brief A reference counted object may only be deleted by calling Unreference().
@@ -139,18 +140,18 @@ public:
   /**
    * @bried Apply the rasterized image to the visual.
    *
   /**
    * @bried Apply the rasterized image to the visual.
    *
+   * @param[in] parsedSvg The data of parsed image.
    * @param[in] rasterizedPixelData The pixel buffer with the rasterized pixels
    */
    * @param[in] rasterizedPixelData The pixel buffer with the rasterized pixels
    */
-  void ApplyRasterizedImage( PixelData rasterizedPixelData );
+  void ApplyRasterizedImage( NSVGimage* parsedSvg, PixelData rasterizedPixelData );
 
 private:
 
 private:
-
   /**
   /**
-   * @brief Parses the SVG Image from the set URL.
-   *
-   * @param[in] imageUrl The URL of the image to parse the SVG from.
-   */
-  void ParseFromUrl( const VisualUrl& imageUrl );
+    * @brief Parses the SVG Image from the set URL.
+    *
+    * @param[in] imageUrl The URL of the image to parse the SVG from.
+    */
+   void ParseFromUrl( const VisualUrl& imageUrl );
 
   /**
    * @bried Rasterize the svg with the given size, and add it to the visual.
 
   /**
    * @bried Rasterize the svg with the given size, and add it to the visual.
@@ -166,7 +167,6 @@ private:
    */
   void DoSetProperty( Property::Index index, const Property::Value& value );
 
    */
   void DoSetProperty( Property::Index index, const Property::Value& value );
 
-
   // Undefined
   SvgVisual( const SvgVisual& svgRenderer );
 
   // Undefined
   SvgVisual( const SvgVisual& svgRenderer );
 
index 3852361..594c12f 100644 (file)
@@ -150,7 +150,7 @@ void VisualFactoryCache::ApplyRasterizedSVGToSampler()
 {
   while( RasterizingTaskPtr task = mSvgRasterizeThread->NextCompletedTask() )
   {
 {
   while( RasterizingTaskPtr task = mSvgRasterizeThread->NextCompletedTask() )
   {
-    task->GetSvgVisual()->ApplyRasterizedImage( task->GetPixelData() );
+    task->GetSvgVisual()->ApplyRasterizedImage( task->GetParsedImage(), task->GetPixelData() );
   }
 }
 
   }
 }