[Tizen] Use broken image when animated image loading is failed. submit/tizen/20210330.021548
authorseungho <sbsh.baek@samsung.com>
Mon, 15 Feb 2021 06:46:43 +0000 (15:46 +0900)
committerJunsuChoi <jsuya.choi@samsung.com>
Mon, 29 Mar 2021 06:46:58 +0000 (15:46 +0900)
Change-Id: Idd703e51bc8c7d32224cbf9d6898efeba644d47f
Signed-off-by: seungho <sbsh.baek@samsung.com>
dali/devel-api/adaptor-framework/animated-image-loading.cpp
dali/devel-api/adaptor-framework/animated-image-loading.h
dali/internal/imaging/common/animated-image-loading-impl.h
dali/internal/imaging/common/gif-loading.cpp
dali/internal/imaging/common/gif-loading.h
dali/internal/imaging/common/image-operations.cpp
dali/internal/imaging/common/webp-loading.cpp
dali/internal/imaging/common/webp-loading.h

index 265f911..8f6a118 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd.
+ * Copyright (c) 2021 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.
@@ -91,6 +91,11 @@ std::string AnimatedImageLoading::GetUrl() const
   return GetImplementation(*this).GetUrl();
 }
 
+bool AnimatedImageLoading::HasLoadingSucceeded() const
+{
+  return GetImplementation(*this).HasLoadingSucceeded();
+}
+
 AnimatedImageLoading::AnimatedImageLoading(Internal::Adaptor::AnimatedImageLoading* internal)
 : BaseHandle(internal)
 {
index d3549b9..92d825c 100644 (file)
@@ -2,7 +2,7 @@
 #define DALI_ANIMATED_IMAGE_LOADING_H
 
 /*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd.
+ * Copyright (c) 2021 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.
@@ -149,6 +149,13 @@ public:
    */
   std::string GetUrl() const;
 
+  /**
+   * @brief Return whether the animated image loading is succeeded or not.
+   *
+   * @return True when the animated image loading is succeeded.
+   */
+  bool HasLoadingSucceeded() const;
+
 public: // Not intended for application developers
   /// @cond internal
   /**
index 13be270..d2a624c 100644 (file)
@@ -94,6 +94,11 @@ public:
    * @copydoc Dali::AnimatedImageLoading::GetUrl()
    */
   virtual std::string GetUrl() const = 0;
+
+  /**
+   * @copydoc Dali::AnimatedImageLoading::HasLoadingSucceeded()
+   */
+  virtual bool HasLoadingSucceeded() const = 0;
 };
 
 } // namespace Adaptor
index 69d5b7a..6b0d709 100644 (file)
@@ -218,7 +218,7 @@ struct GifAccessor
 
     if(!gif)
     {
-      DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT");
+      DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT\n");
     }
   }
 
@@ -635,6 +635,7 @@ bool DecodeImage(GifFileType* gif, uint32_t* data, int rowpix, int xin, int yin,
 
   if((gifW < w) || (gifH < h))
   {
+    DALI_LOG_ERROR("gifW : %d, w : %d, gifH : %d, h : %d\n", gifW, w, gifH, h);
     DALI_ASSERT_DEBUG(false && "Dimensions are bigger than the Gif image size");
     goto on_error;
   }
@@ -784,7 +785,7 @@ bool ReadHeader(LoaderInfo&      loaderInfo,
   if(!success || !fileData.globalMap)
   {
     success = false;
-    DALI_LOG_ERROR("LOAD_ERROR_CORRUPT_FILE");
+    DALI_LOG_ERROR("LOAD_ERROR_CORRUPT_FILE\n");
   }
   else
   {
@@ -830,7 +831,7 @@ bool ReadHeader(LoaderInfo&      loaderInfo,
             else
             {
               success = false;
-              DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT");
+              DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT\n");
             }
             break;
           }
@@ -845,14 +846,14 @@ bool ReadHeader(LoaderInfo&      loaderInfo,
             if(DGifGetImageDesc(gifAccessor.gif) == GIF_ERROR)
             {
               success = false;
-              DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT");
+              DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT\n");
               break;
             }
             // skip decoding and just walk image to next
             if(DGifGetCode(gifAccessor.gif, &img_code, &img) == GIF_ERROR)
             {
               success = false;
-              DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT");
+              DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT\n");
               break;
             }
             // skip till next...
@@ -999,7 +1000,7 @@ bool ReadNextFrame(LoaderInfo& loaderInfo, ImageProperties& prop, //  use for w
   frame = FindFrame(animated, index);
   if(!frame)
   {
-    DALI_LOG_ERROR("LOAD_ERROR_CORRUPT_FILE");
+    DALI_LOG_ERROR("LOAD_ERROR_CORRUPT_FILE\n");
     return false;
   }
   else if(!(frame->loaded) || !(frame->data))
@@ -1024,13 +1025,13 @@ bool ReadNextFrame(LoaderInfo& loaderInfo, ImageProperties& prop, //  use for w
       loaderInfo.fileInfo.position = 0;
       if(!loaderInfo.fileInfo.map)
       {
-        DALI_LOG_ERROR("LOAD_ERROR_CORRUPT_FILE");
+        DALI_LOG_ERROR("LOAD_ERROR_CORRUPT_FILE\n");
         return false;
       }
       std::unique_ptr<GifAccessor> gifAccessor = std::make_unique<GifAccessor>(loaderInfo.fileInfo);
       if(!gifAccessor->gif)
       {
-        DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT");
+        DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT\n");
         return false;
       }
       loaderInfo.gifAccessor = std::move(gifAccessor);
@@ -1045,7 +1046,7 @@ bool ReadNextFrame(LoaderInfo& loaderInfo, ImageProperties& prop, //  use for w
     {
       if(DGifGetRecordType(loaderInfo.gifAccessor->gif, &rec) == GIF_ERROR)
       {
-        DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT");
+        DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT\n");
         return false;
       }
 
@@ -1073,7 +1074,7 @@ bool ReadNextFrame(LoaderInfo& loaderInfo, ImageProperties& prop, //  use for w
         // get image desc
         if(DGifGetImageDesc(loaderInfo.gifAccessor->gif) == GIF_ERROR)
         {
-          DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT");
+          DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT\n");
           return false;
         }
 
@@ -1147,7 +1148,7 @@ bool ReadNextFrame(LoaderInfo& loaderInfo, ImageProperties& prop, //  use for w
           ClipCoordinates(prop.w, prop.h, &xin, &yin, frameInfo->x, frameInfo->y, frameInfo->w, frameInfo->h, &x, &y, &w, &h);
           if(!DecodeImage(loaderInfo.gifAccessor->gif, thisFrame->data, prop.w, xin, yin, frameInfo->transparent, x, y, w, h, first))
           {
-            DALI_LOG_ERROR("LOAD_ERROR_CORRUPT_FILE");
+            DALI_LOG_ERROR("LOAD_ERROR_CORRUPT_FILE\n");
             return false;
           }
 
@@ -1173,7 +1174,7 @@ bool ReadNextFrame(LoaderInfo& loaderInfo, ImageProperties& prop, //  use for w
             // and decode the gif with overwriting
             if(!DecodeImage(loaderInfo.gifAccessor->gif, reinterpret_cast<uint32_t*>(pixels), prop.w, xin, yin, frameInfo->transparent, x, y, w, h, true))
             {
-              DALI_LOG_ERROR("LOAD_ERROR_CORRUPT_FILE");
+              DALI_LOG_ERROR("LOAD_ERROR_CORRUPT_FILE\n");
               return false;
             }
 
@@ -1187,7 +1188,7 @@ bool ReadNextFrame(LoaderInfo& loaderInfo, ImageProperties& prop, //  use for w
           // skip decoding and just walk image to next
           if(DGifGetCode(loaderInfo.gifAccessor->gif, &img_code, &img) == GIF_ERROR)
           {
-            DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT");
+            DALI_LOG_ERROR("LOAD_ERROR_UNKNOWN_FORMAT\n");
             return false;
           }
 
@@ -1236,14 +1237,15 @@ struct GifLoading::Impl
 {
 public:
   Impl(const std::string& url, bool isLocalResource)
-  : mUrl(url)
+  : mUrl(url),
+    mLoadSucceeded(true)
   {
     loaderInfo.gifAccessor = nullptr;
     int error;
     loaderInfo.fileData.fileName        = mUrl.c_str();
     loaderInfo.fileData.isLocalResource = isLocalResource;
 
-    ReadHeader(loaderInfo, imageProperties, &error);
+    mLoadSucceeded = ReadHeader(loaderInfo, imageProperties, &error);
   }
 
   // Moveable but not copyable
@@ -1255,6 +1257,7 @@ public:
   std::string     mUrl;
   LoaderInfo      loaderInfo;
   ImageProperties imageProperties;
+  bool            mLoadSucceeded;
 };
 
 AnimatedImageLoadingPtr GifLoading::New(const std::string& url, bool isLocalResource)
@@ -1276,6 +1279,10 @@ bool GifLoading::LoadNextNFrames(uint32_t frameStartIndex, int count, std::vecto
 {
   int  error;
   bool ret = false;
+  if(!mImpl->mLoadSucceeded)
+  {
+    return false;
+  }
 
   const int bufferSize = mImpl->imageProperties.w * mImpl->imageProperties.h * sizeof(uint32_t);
 
@@ -1304,6 +1311,10 @@ Dali::Devel::PixelBuffer GifLoading::LoadFrame(uint32_t frameIndex)
 {
   int                      error;
   Dali::Devel::PixelBuffer pixelBuffer;
+  if(!mImpl->mLoadSucceeded)
+  {
+    return pixelBuffer;
+  }
 
   DALI_LOG_INFO(gGifLoadingLogFilter, Debug::Concise, "LoadFrame( frameIndex:%d )\n", frameIndex);
 
@@ -1339,6 +1350,11 @@ std::string GifLoading::GetUrl() const
   return mImpl->mUrl;
 }
 
+bool GifLoading::HasLoadingSucceeded() const
+{
+  return mImpl->mLoadSucceeded;
+}
+
 } // namespace Adaptor
 
 } // namespace Internal
index b817084..6797938 100644 (file)
@@ -117,6 +117,13 @@ public:
    */
   std::string GetUrl() const override;
 
+  /**
+   * @brief Return whether the animated image loading is succeeded or not.
+   *
+   * @return True when the animated image loading is succeeded.
+   */
+  bool HasLoadingSucceeded() const override;
+
 private:
   struct Impl;
   Impl* mImpl;
index 96828b8..0881753 100644 (file)
@@ -510,7 +510,7 @@ ImageDimensions CalculateDesiredDimensions(unsigned int bitmapWidth, unsigned in
  * @param[out] widthOut The width of the output buffer.
  * @param[out] heightOut The height of the output buffer.
  *
- * @return Whether the rotation succeded.
+ * @return Whether the rotation succeeded.
  */
 bool Rotate90(const uint8_t* const pixelsIn,
               unsigned int         widthIn,
@@ -569,7 +569,7 @@ bool Rotate90(const uint8_t* const pixelsIn,
  * @param[in] pixelSize The size of the pixel.
  * @param[out] pixelsOut The rotated output buffer.
  *
- * @return Whether the rotation succeded.
+ * @return Whether the rotation succeeded.
  */
 bool Rotate180(const uint8_t* const pixelsIn,
                unsigned int         widthIn,
@@ -621,7 +621,7 @@ bool Rotate180(const uint8_t* const pixelsIn,
  * @param[out] widthOut The width of the output buffer.
  * @param[out] heightOut The height of the output buffer.
  *
- * @return Whether the rotation succeded.
+ * @return Whether the rotation succeeded.
  */
 bool Rotate270(const uint8_t* const pixelsIn,
                unsigned int         widthIn,
index bd1014b..2068240 100644 (file)
@@ -61,7 +61,8 @@ struct WebPLoading::Impl
 {
 public:
   Impl(const std::string& url, bool isLocalResource)
-  : mUrl(url)
+  : mUrl(url),
+    mLoadSucceeded(true)
   {
 #ifdef DALI_WEBP_ENABLED
     if(ReadWebPInformation(isLocalResource))
@@ -73,6 +74,10 @@ public:
       WebPAnimDecoderGetInfo(mWebPAnimDecoder, &mWebPAnimInfo);
       mTimeStamp.assign(mWebPAnimInfo.frame_count, 0);
     }
+    else
+    {
+      mLoadSucceeded = false;
+    }
 #endif
   }
 
@@ -176,6 +181,7 @@ public:
   std::string           mUrl;
   std::vector<uint32_t> mTimeStamp;
   uint32_t              mLoadingFrame{0};
+  bool                  mLoadSucceeded;
 
 #ifdef DALI_WEBP_ENABLED
   WebPData         mWebPData{0};
@@ -205,7 +211,7 @@ WebPLoading::~WebPLoading()
 bool WebPLoading::LoadNextNFrames(uint32_t frameStartIndex, int count, std::vector<Dali::PixelData>& pixelData)
 {
 #ifdef DALI_WEBP_ENABLED
-  if(frameStartIndex >= mImpl->mWebPAnimInfo.frame_count)
+  if(frameStartIndex >= mImpl->mWebPAnimInfo.frame_count || !mImpl->mLoadSucceeded)
   {
     return false;
   }
@@ -259,13 +265,14 @@ bool WebPLoading::LoadNextNFrames(uint32_t frameStartIndex, int count, std::vect
 Dali::Devel::PixelBuffer WebPLoading::LoadFrame(uint32_t frameIndex)
 {
   Dali::Devel::PixelBuffer pixelBuffer;
+
 #ifdef DALI_WEBP_ENABLED
-  if(frameIndex >= mImpl->mWebPAnimInfo.frame_count)
+  if(frameIndex >= mImpl->mWebPAnimInfo.frame_count || !mImpl->mLoadSucceeded)
   {
     return pixelBuffer;
   }
 
-  DALI_LOG_INFO(gWebPLoadingLogFilter, Debug::Concise, "LoadNextNFrames( frameIndex:%d )\n", frameIndex);
+  DALI_LOG_INFO(gWebPLoadingLogFilter, Debug::Concise, "LoadFrame( frameIndex:%d )\n", frameIndex);
 
   if(mImpl->mLoadingFrame > frameIndex)
   {
@@ -340,6 +347,11 @@ std::string WebPLoading::GetUrl() const
   return mImpl->mUrl;
 }
 
+bool WebPLoading::HasLoadingSucceeded() const
+{
+  return mImpl->mLoadSucceeded;
+}
+
 } // namespace Adaptor
 
 } // namespace Internal
index 5806353..ecf8bbb 100644 (file)
@@ -113,8 +113,20 @@ public:
    */
   uint32_t GetFrameInterval(uint32_t frameIndex) const override;
 
+  /**
+   * @brief Get the animated image file URL
+   *
+   * @return The URL string of the animated image file
+   */
   std::string GetUrl() const override;
 
+  /**
+   * @brief Return whether the animated image loading is succeeded or not.
+   *
+   * @return True when the animated image loading is succeeded.
+   */
+  bool HasLoadingSucceeded() const override;
+
 private:
   struct Impl;
   Impl* mImpl;