From 961b864deeaffb3216a38b1a19736adaebcd8fce Mon Sep 17 00:00:00 2001 From: Nomango Date: Wed, 31 Jul 2019 16:22:33 +0800 Subject: [PATCH] add GifSprite --- kiwano/2d/GifImage.cpp | 191 ++++++--------------------------- kiwano/2d/GifImage.h | 88 ++++++--------- kiwano/2d/GifSprite.cpp | 194 ++++++++++++++++++++++++++++++++++ kiwano/2d/GifSprite.h | 97 +++++++++++++++++ kiwano/2d/Image.cpp | 1 - kiwano/2d/Image.h | 2 +- kiwano/2d/Sprite.cpp | 16 +-- kiwano/2d/include-forwards.h | 3 +- kiwano/Kiwano.vcxproj | 2 + kiwano/Kiwano.vcxproj.filters | 6 ++ kiwano/kiwano.h | 1 + 11 files changed, 375 insertions(+), 226 deletions(-) create mode 100644 kiwano/2d/GifSprite.cpp create mode 100644 kiwano/2d/GifSprite.h diff --git a/kiwano/2d/GifImage.cpp b/kiwano/2d/GifImage.cpp index e3f9fdb6..a099eb70 100644 --- a/kiwano/2d/GifImage.cpp +++ b/kiwano/2d/GifImage.cpp @@ -21,27 +21,19 @@ #include "GifImage.h" #include "../base/logs.h" #include "../platform/modules.h" +#include "../utils/FileUtil.h" namespace kiwano { GifImage::GifImage() - : animating_(false) - , next_index_(0) - , total_loop_count_(1) - , loop_count_(0) - , frames_count_(0) + : frames_count_(0) , disposal_type_(DisposalType::Unknown) , width_in_pixels_(0) , height_in_pixels_(0) + , frame_delay_(0) , frame_position_{} , bg_color_{} { - factory_ = Renderer::Instance()->GetD2DDeviceResources()->GetWICImagingFactory(); - auto ctx = Renderer::Instance()->GetD2DDeviceResources()->GetDeviceContext(); - - ThrowIfFailed( - ctx->CreateCompatibleRenderTarget(&frame_rt_) - ); } GifImage::GifImage(Resource const& res) @@ -54,23 +46,25 @@ namespace kiwano { HRESULT hr = S_OK; - next_index_ = 0; - loop_count_ = 0; frames_count_ = 0; disposal_type_ = DisposalType::None; saved_frame_.Reset(); decoder_.Reset(); + auto factory = Renderer::Instance()->GetD2DDeviceResources()->GetWICImagingFactory(); + if (res.IsFileType()) { - if (!modules::Shlwapi::Get().PathFileExistsW(res.GetFileName().c_str())) +#ifdef KGE_DEBUG + if (!FileUtil::ExistsFile(res.GetFileName().c_str())) { KGE_WARNING_LOG(L"Gif file '%s' not found!", res.GetFileName().c_str()); return false; } +#endif - hr = factory_->CreateDecoderFromFilename( + hr = factory->CreateDecoderFromFilename( res.GetFileName().c_str(), nullptr, GENERIC_READ, @@ -87,7 +81,7 @@ namespace kiwano if (SUCCEEDED(hr)) { - hr = factory_->CreateStream(&stream); + hr = factory->CreateStream(&stream); } if (SUCCEEDED(hr)) @@ -100,7 +94,7 @@ namespace kiwano if (SUCCEEDED(hr)) { - hr = factory_->CreateDecoderFromStream( + hr = factory->CreateDecoderFromStream( stream.Get(), nullptr, WICDecodeMetadataCacheOnLoad, @@ -114,54 +108,9 @@ namespace kiwano hr = GetGlobalMetadata(); } - if (SUCCEEDED(hr)) - { - if (frames_count_ > 0) - { - hr = ComposeNextFrame(); - } - } - return SUCCEEDED(hr); } - void GifImage::Update(Duration dt) - { - VisualNode::Update(dt); - - if (animating_) - { - frame_elapsed_ += dt; - if (frame_delay_ <= frame_elapsed_) - { - frame_delay_ -= frame_elapsed_; - frame_elapsed_ = 0; - ComposeNextFrame(); - } - } - } - - void GifImage::Restart() - { - animating_ = true; - next_index_ = 0; - loop_count_ = 0; - disposal_type_ = DisposalType::None; - } - - void GifImage::OnRender() - { - if (frame_rt_) - { - ComPtr frame_to_render; - if (SUCCEEDED(frame_rt_->GetBitmap(&frame_to_render))) - { - Rect bounds = GetBounds(); - Renderer::Instance()->DrawBitmap(frame_to_render, bounds, bounds); - } - } - } - HRESULT GifImage::GetRawFrame(UINT frame_index) { ComPtr converter; @@ -176,7 +125,8 @@ namespace kiwano if (SUCCEEDED(hr)) { // Format convert to 32bppPBGRA which D2D expects - hr = factory_->CreateFormatConverter(&converter); + auto factory = Renderer::Instance()->GetD2DDeviceResources()->GetWICImagingFactory(); + hr = factory->CreateFormatConverter(&converter); } if (SUCCEEDED(hr)) @@ -269,7 +219,7 @@ namespace kiwano if (SUCCEEDED(hr)) { - unsigned int frame_delay = 0; + frame_delay_ = 0; hr = metadata_reader->GetMetadataByName( L"/grctlext/Delay", @@ -280,24 +230,22 @@ namespace kiwano hr = (prop_val.vt == VT_UI2 ? S_OK : E_FAIL); if (SUCCEEDED(hr)) { - hr = UIntMult(prop_val.uiVal, 10, &frame_delay); + hr = UIntMult(prop_val.uiVal, 10, &frame_delay_); } PropVariantClear(&prop_val); } else { - frame_delay = 0; + frame_delay_ = 0; } if (SUCCEEDED(hr)) { // 插入一个强制延迟 - if (frame_delay < 90) + if (frame_delay_ < 90) { - frame_delay = 90; + frame_delay_ = 90; } - - frame_delay_.SetMilliseconds(static_cast(frame_delay)); } } @@ -341,8 +289,7 @@ namespace kiwano if (SUCCEEDED(hr)) { - hr = decoder_->GetMetadataQueryReader( - &metadata_reader); + hr = decoder_->GetMetadataQueryReader(&metadata_reader); } if (SUCCEEDED(hr)) @@ -428,8 +375,6 @@ namespace kiwano width_in_pixels_ = width; height_in_pixels_ = height; } - - SetSize(static_cast(width_in_pixels_), static_cast(height_in_pixels_)); } ::PropVariantClear(&prop_val); } @@ -439,28 +384,7 @@ namespace kiwano return hr; } - HRESULT GifImage::ComposeNextFrame() - { - HRESULT hr = E_FAIL; - - if (frame_rt_) - { - // 找到延迟大于 0 的帧 (0 延迟帧是不可见的中间帧) - do - { - hr = DisposeCurrentFrame(); - if (SUCCEEDED(hr)) - { - hr = OverlayNextFrame(); - } - } while (SUCCEEDED(hr) && frame_delay_.IsZero() && !IsLastFrame()); - - animating_ = (SUCCEEDED(hr) && !EndOfAnimation() && frames_count_ > 1); - } - return hr; - } - - HRESULT GifImage::DisposeCurrentFrame() + HRESULT GifImage::DisposeCurrentFrame(ComPtr frame_rt) { HRESULT hr = S_OK; @@ -471,11 +395,11 @@ namespace kiwano break; case DisposalType::Background: // 用背景颜色清除当前原始帧覆盖的区域 - hr = ClearCurrentFrameArea(); + hr = ClearCurrentFrameArea(frame_rt); break; case DisposalType::Previous: // 恢复先前构图的帧 - hr = RestoreSavedFrame(); + hr = RestoreSavedFrame(frame_rt); break; default: hr = E_FAIL; @@ -483,59 +407,13 @@ namespace kiwano return hr; } - HRESULT GifImage::OverlayNextFrame() - { - HRESULT hr = GetRawFrame(next_index_); - if (SUCCEEDED(hr)) - { - if (disposal_type_ == DisposalType::Previous) - { - hr = SaveComposedFrame(); - } - } - - if (SUCCEEDED(hr)) - { - frame_rt_->BeginDraw(); - - if (next_index_ == 0) - { - // 重新绘制背景 - frame_rt_->Clear(bg_color_); - - loop_count_++; - } - - frame_rt_->DrawBitmap(raw_frame_.Get(), frame_position_); - - hr = frame_rt_->EndDraw(); - } - - if (SUCCEEDED(hr)) - { - next_index_ = (++next_index_) % frames_count_; - } - - if (IsLastFrame() && loop_cb_) - { - loop_cb_(loop_count_ - 1); - } - - if (EndOfAnimation() && done_cb_) - { - done_cb_(); - } - - return hr; - } - - HRESULT GifImage::SaveComposedFrame() + HRESULT GifImage::SaveComposedFrame(ComPtr frame_rt) { HRESULT hr = S_OK; ComPtr frame_to_be_saved; - hr = frame_rt_->GetBitmap(&frame_to_be_saved); + hr = frame_rt->GetBitmap(&frame_to_be_saved); if (SUCCEEDED(hr)) { if (saved_frame_ == nullptr) @@ -543,7 +421,7 @@ namespace kiwano auto size = frame_to_be_saved->GetPixelSize(); auto prop = D2D1::BitmapProperties(frame_to_be_saved->GetPixelFormat()); - hr = frame_rt_->CreateBitmap(size, prop, &saved_frame_); + hr = frame_rt->CreateBitmap(size, prop, &saved_frame_); } } @@ -554,7 +432,7 @@ namespace kiwano return hr; } - HRESULT GifImage::RestoreSavedFrame() + HRESULT GifImage::RestoreSavedFrame(ComPtr frame_rt) { HRESULT hr = S_OK; @@ -564,7 +442,7 @@ namespace kiwano if (SUCCEEDED(hr)) { - hr = frame_rt_->GetBitmap(&frame_to_copy_to); + hr = frame_rt->GetBitmap(&frame_to_copy_to); } if (SUCCEEDED(hr)) @@ -575,15 +453,15 @@ namespace kiwano return hr; } - HRESULT GifImage::ClearCurrentFrameArea() + HRESULT GifImage::ClearCurrentFrameArea(ComPtr frame_rt) { - frame_rt_->BeginDraw(); + frame_rt->BeginDraw(); - frame_rt_->PushAxisAlignedClip(&frame_position_, D2D1_ANTIALIAS_MODE_PER_PRIMITIVE); - frame_rt_->Clear(bg_color_); - frame_rt_->PopAxisAlignedClip(); + frame_rt->PushAxisAlignedClip(&frame_position_, D2D1_ANTIALIAS_MODE_PER_PRIMITIVE); + frame_rt->Clear(bg_color_); + frame_rt->PopAxisAlignedClip(); - return frame_rt_->EndDraw(); + return frame_rt->EndDraw(); } HRESULT GifImage::GetBackgroundColor(IWICMetadataQueryReader* metadata_reader) @@ -627,7 +505,8 @@ namespace kiwano if (SUCCEEDED(hr)) { - hr = factory_->CreatePalette(&wic_palette); + auto factory = Renderer::Instance()->GetD2DDeviceResources()->GetWICImagingFactory(); + hr = factory->CreatePalette(&wic_palette); } if (SUCCEEDED(hr)) diff --git a/kiwano/2d/GifImage.h b/kiwano/2d/GifImage.h index 00b6a55a..d105559d 100644 --- a/kiwano/2d/GifImage.h +++ b/kiwano/2d/GifImage.h @@ -19,19 +19,16 @@ // THE SOFTWARE. #pragma once -#include "Node.h" +#include "include-forwards.h" #include "../base/Resource.h" #include "../renderer/render.h" namespace kiwano { class KGE_API GifImage - : public VisualNode + : public Object { public: - typedef Closure LoopDoneCallback; - typedef Closure DoneCallback; - GifImage(); GifImage( @@ -42,53 +39,15 @@ namespace kiwano Resource const& res ); - // 设置 GIF 动画循环次数 - inline void SetLoopCount(int loops) { total_loop_count_ = loops; } + inline unsigned int GetWidthInPixels() const { return width_in_pixels_; } - // 设置 GIF 动画每次循环结束回调函数 - inline void SetLoopDoneCallback(LoopDoneCallback const& cb) { loop_cb_ = cb; } + inline unsigned int GetHeightInPixels() const { return height_in_pixels_; } - // 设置 GIF 动画结束回调函数 - inline void SetDoneCallback(DoneCallback const& cb) { done_cb_ = cb; } + inline unsigned int GetFrameDelay() const { return frame_delay_; } - // 重新播放动画 - void Restart(); - - inline int GetFramesCount() const { return static_cast(frames_count_); } - inline int GetLoopCount() const { return total_loop_count_; } - inline LoopDoneCallback GetLoopDoneCallback() const { return loop_cb_; } - inline DoneCallback GetDoneCallback() const { return done_cb_; } - - void OnRender() override; - - protected: - void Update(Duration dt) override; - - HRESULT GetRawFrame(UINT frame_index); - HRESULT GetGlobalMetadata(); - HRESULT GetBackgroundColor(IWICMetadataQueryReader* metadata_reader); - - HRESULT ComposeNextFrame(); - HRESULT DisposeCurrentFrame(); - HRESULT OverlayNextFrame(); - - HRESULT SaveComposedFrame(); - HRESULT RestoreSavedFrame(); - HRESULT ClearCurrentFrameArea(); - - inline bool IsLastFrame() const { return (next_index_ == 0); } - inline bool EndOfAnimation() const { return IsLastFrame() && loop_count_ == total_loop_count_ + 1; } - - protected: - Duration frame_delay_; - Duration frame_elapsed_; - - ComPtr factory_; - ComPtr frame_rt_; - ComPtr raw_frame_; - ComPtr saved_frame_; - ComPtr decoder_; + inline unsigned int GetFramesCount() const { return frames_count_; } + public: enum class DisposalType { Unknown, @@ -97,18 +56,37 @@ namespace kiwano Previous }; - bool animating_; - int total_loop_count_; - int loop_count_; - unsigned int next_index_; + inline DisposalType GetDisposalType() const { return disposal_type_; } + + inline D2D1_COLOR_F GetBackgroundColor() const { return bg_color_; } + + inline D2D1_RECT_F const& GetFramePosition() const { return frame_position_; } + + inline ComPtr GetRawFrame() const { return raw_frame_; } + + inline void SetDisposalType(DisposalType type) { disposal_type_ = type; } + + public: + HRESULT GetRawFrame(UINT frame_index); + HRESULT GetGlobalMetadata(); + HRESULT GetBackgroundColor(IWICMetadataQueryReader* metadata_reader); + + HRESULT DisposeCurrentFrame(ComPtr frame_rt); + HRESULT SaveComposedFrame(ComPtr frame_rt); + HRESULT RestoreSavedFrame(ComPtr frame_rt); + HRESULT ClearCurrentFrameArea(ComPtr frame_rt); + + protected: + ComPtr raw_frame_; + ComPtr saved_frame_; + ComPtr decoder_; + unsigned int frames_count_; + unsigned int frame_delay_; unsigned int width_in_pixels_; unsigned int height_in_pixels_; DisposalType disposal_type_; D2D1_RECT_F frame_position_; D2D1_COLOR_F bg_color_; - - LoopDoneCallback loop_cb_; - DoneCallback done_cb_; }; } diff --git a/kiwano/2d/GifSprite.cpp b/kiwano/2d/GifSprite.cpp new file mode 100644 index 00000000..c007b451 --- /dev/null +++ b/kiwano/2d/GifSprite.cpp @@ -0,0 +1,194 @@ +// Copyright (c) 2016-2018 Kiwano - Nomango +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. + +#include "GifSprite.h" +#include "GifImage.h" +#include "../base/logs.h" +#include "../platform/modules.h" + +namespace kiwano +{ + GifSprite::GifSprite() + : animating_(false) + , next_index_(0) + , total_loop_count_(1) + , loop_count_(0) + { + } + + GifSprite::GifSprite(Resource const& res) + : GifSprite() + { + Load(res); + } + + GifSprite::GifSprite(GifImagePtr image) + { + Load(image); + } + + bool GifSprite::Load(Resource const& res) + { + GifImagePtr image = new (std::nothrow) GifImage; + if (image->Load(res)) + { + return Load(image); + } + return false; + } + + bool GifSprite::Load(GifImagePtr image) + { + if (image && image_ != image) + { + image_ = image; + + next_index_ = 0; + loop_count_ = 0; + + SetSize( + static_cast(image_->GetWidthInPixels()), + static_cast(image_->GetHeightInPixels()) + ); + + if (!frame_rt_) + { + auto ctx = Renderer::Instance()->GetD2DDeviceResources()->GetDeviceContext(); + ThrowIfFailed( + ctx->CreateCompatibleRenderTarget(&frame_rt_) + ); + } + + if (image_->GetFramesCount() > 0) + { + ComposeNextFrame(); + } + return true; + } + return false; + } + + void GifSprite::Update(Duration dt) + { + VisualNode::Update(dt); + + if (image_ && animating_) + { + frame_elapsed_ += dt; + if (frame_delay_ <= frame_elapsed_) + { + frame_delay_ -= frame_elapsed_; + frame_elapsed_ = 0; + ComposeNextFrame(); + } + } + } + + void GifSprite::OnRender() + { + if (frame_to_render_) + { + Rect bounds = GetBounds(); + Renderer::Instance()->DrawBitmap(frame_to_render_, bounds, bounds); + } + } + + void GifSprite::RestartAnimation() + { + animating_ = true; + next_index_ = 0; + loop_count_ = 0; + image_->SetDisposalType(GifImage::DisposalType::None); + } + + void GifSprite::ComposeNextFrame() + { + if (frame_rt_) + { + // 找到延迟大于 0 的帧 (0 延迟帧是不可见的中间帧) + HRESULT hr = E_FAIL; + do + { + hr = image_->DisposeCurrentFrame(frame_rt_); + if (SUCCEEDED(hr)) + { + hr = OverlayNextFrame(); + } + + if (SUCCEEDED(hr)) + { + frame_delay_.SetMilliseconds(static_cast(image_->GetFrameDelay())); + } + } while (SUCCEEDED(hr) && frame_delay_.IsZero() && !IsLastFrame()); + + animating_ = (SUCCEEDED(hr) && !EndOfAnimation() && image_->GetFramesCount() > 1); + } + } + + HRESULT GifSprite::OverlayNextFrame() + { + HRESULT hr = image_->GetRawFrame(next_index_); + if (SUCCEEDED(hr)) + { + if (image_->GetDisposalType() == GifImage::DisposalType::Previous) + { + hr = image_->SaveComposedFrame(frame_rt_); + } + } + + if (SUCCEEDED(hr)) + { + frame_rt_->BeginDraw(); + + if (next_index_ == 0) + { + // 重新绘制背景 + frame_rt_->Clear(image_->GetBackgroundColor()); + loop_count_++; + } + + frame_rt_->DrawBitmap(image_->GetRawFrame().Get(), image_->GetFramePosition()); + hr = frame_rt_->EndDraw(); + } + + if (SUCCEEDED(hr)) + { + frame_to_render_ = nullptr; + hr = frame_rt_->GetBitmap(&frame_to_render_); + } + + if (SUCCEEDED(hr)) + { + next_index_ = (++next_index_) % image_->GetFramesCount(); + } + + if (IsLastFrame() && loop_cb_) + { + loop_cb_(loop_count_ - 1); + } + + if (EndOfAnimation() && done_cb_) + { + done_cb_(); + } + return hr; + } + +} diff --git a/kiwano/2d/GifSprite.h b/kiwano/2d/GifSprite.h new file mode 100644 index 00000000..ed3aae54 --- /dev/null +++ b/kiwano/2d/GifSprite.h @@ -0,0 +1,97 @@ +// Copyright (c) 2016-2018 Kiwano - Nomango +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. + +#pragma once +#include "Node.h" +#include "../base/Resource.h" +#include "../renderer/render.h" + +namespace kiwano +{ + class KGE_API GifSprite + : public VisualNode + { + public: + using LoopDoneCallback = Closure; + using DoneCallback = Closure; + + GifSprite(); + + GifSprite( + Resource const& res + ); + + GifSprite( + GifImagePtr image + ); + + bool Load( + Resource const& res + ); + + bool Load( + GifImagePtr image + ); + + // 设置 GIF 动画循环次数 + inline void SetLoopCount(int loops) { total_loop_count_ = loops; } + + // 设置 GIF 动画每次循环结束回调函数 + inline void SetLoopDoneCallback(LoopDoneCallback const& cb) { loop_cb_ = cb; } + + // 设置 GIF 动画结束回调函数 + inline void SetDoneCallback(DoneCallback const& cb) { done_cb_ = cb; } + + // 重新播放动画 + void RestartAnimation(); + + inline LoopDoneCallback GetLoopDoneCallback() const { return loop_cb_; } + + inline DoneCallback GetDoneCallback() const { return done_cb_; } + + void OnRender() override; + + protected: + void Update(Duration dt) override; + + void ComposeNextFrame(); + + HRESULT OverlayNextFrame(); + + inline bool IsLastFrame() const { return (next_index_ == 0); } + + inline bool EndOfAnimation() const { return IsLastFrame() && loop_count_ == total_loop_count_ + 1; } + + protected: + bool animating_; + int total_loop_count_; + int loop_count_; + unsigned int next_index_; + Duration frame_delay_; + Duration frame_elapsed_; + + LoopDoneCallback loop_cb_; + DoneCallback done_cb_; + + GifImagePtr image_; + ComPtr frame_to_render_; + ComPtr frame_rt_; + }; +} diff --git a/kiwano/2d/Image.cpp b/kiwano/2d/Image.cpp index c1f07bdf..d4ad76a4 100644 --- a/kiwano/2d/Image.cpp +++ b/kiwano/2d/Image.cpp @@ -20,7 +20,6 @@ #include "Image.h" #include "../base/logs.h" -#include "../renderer/render.h" #include "../platform/modules.h" #include "../utils/FileUtil.h" diff --git a/kiwano/2d/Image.h b/kiwano/2d/Image.h index 3e6319d8..3659e0de 100644 --- a/kiwano/2d/Image.h +++ b/kiwano/2d/Image.h @@ -21,7 +21,7 @@ #pragma once #include "include-forwards.h" #include "../base/Resource.h" -#include +#include "../renderer/render.h" namespace kiwano { diff --git a/kiwano/2d/Sprite.cpp b/kiwano/2d/Sprite.cpp index 413ab894..dac76387 100644 --- a/kiwano/2d/Sprite.cpp +++ b/kiwano/2d/Sprite.cpp @@ -53,7 +53,7 @@ namespace kiwano bool Sprite::Load(ImagePtr image) { - if (image) + if (image && image_ != image) { image_ = image; @@ -65,18 +65,10 @@ namespace kiwano bool Sprite::Load(Resource const& res) { - if (!image_) + ImagePtr image = new (std::nothrow) Image; + if (image->Load(res)) { - image_ = new (std::nothrow) Image; - } - - if (image_) - { - if (image_->Load(res)) - { - Node::SetSize(image_->GetWidth(), image_->GetHeight()); - return true; - } + return Load(image); } return false; } diff --git a/kiwano/2d/include-forwards.h b/kiwano/2d/include-forwards.h index eb07832f..16607b34 100644 --- a/kiwano/2d/include-forwards.h +++ b/kiwano/2d/include-forwards.h @@ -35,6 +35,7 @@ namespace kiwano { KGE_DECLARE_SMART_PTR(Image); + KGE_DECLARE_SMART_PTR(GifImage); KGE_DECLARE_SMART_PTR(Frames); KGE_DECLARE_SMART_PTR(Geometry); @@ -49,7 +50,7 @@ namespace kiwano KGE_DECLARE_SMART_PTR(Scene); KGE_DECLARE_SMART_PTR(Layer); KGE_DECLARE_SMART_PTR(Sprite); - KGE_DECLARE_SMART_PTR(GifImage); + KGE_DECLARE_SMART_PTR(GifSprite); KGE_DECLARE_SMART_PTR(Text); KGE_DECLARE_SMART_PTR(Canvas); KGE_DECLARE_SMART_PTR(GeometryNode); diff --git a/kiwano/Kiwano.vcxproj b/kiwano/Kiwano.vcxproj index 15c1e667..703a55bf 100644 --- a/kiwano/Kiwano.vcxproj +++ b/kiwano/Kiwano.vcxproj @@ -1,6 +1,7 @@ + @@ -93,6 +94,7 @@ + diff --git a/kiwano/Kiwano.vcxproj.filters b/kiwano/Kiwano.vcxproj.filters index 925203e2..d8e38d42 100644 --- a/kiwano/Kiwano.vcxproj.filters +++ b/kiwano/Kiwano.vcxproj.filters @@ -261,6 +261,9 @@ base + + 2d + @@ -395,5 +398,8 @@ utils + + 2d + \ No newline at end of file diff --git a/kiwano/kiwano.h b/kiwano/kiwano.h index 8fdc2866..b132b86a 100644 --- a/kiwano/kiwano.h +++ b/kiwano/kiwano.h @@ -98,6 +98,7 @@ #include "2d/Scene.h" #include "2d/Layer.h" #include "2d/Sprite.h" +#include "2d/GifSprite.h" #include "2d/Text.h" #include "2d/Canvas.h" #include "2d/GeometryNode.h"