From b6ad31b0167bfeae4255b79f307d9cf8b400abef Mon Sep 17 00:00:00 2001 From: Tom Shea Date: Thu, 20 Jun 2019 12:41:44 -0700 Subject: [PATCH 1/4] Delay setting ReactImageBrush source until image has actually loaded --- vnext/ReactUWP/Views/Image/ReactImage.cpp | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/vnext/ReactUWP/Views/Image/ReactImage.cpp b/vnext/ReactUWP/Views/Image/ReactImage.cpp index a5fa138b6a7..2c1908ef405 100644 --- a/vnext/ReactUWP/Views/Image/ReactImage.cpp +++ b/vnext/ReactUWP/Views/Image/ReactImage.cpp @@ -97,9 +97,10 @@ namespace react { winrt::LoadedImageSurface::StartLoadFromStream(memoryStream) : winrt::LoadedImageSurface::StartLoadFromUri(uri) }; - surface.LoadCompleted({ this, &ReactImage::LoadedImageSurfaceHandler }); - - m_brush->Source(surface); + // using a lambda here to capture the surface and prevent it from freeing while the image loads + surface.LoadCompleted([this, surface](winrt::LoadedImageSurface const& sender, winrt::LoadedImageSourceLoadCompletedEventArgs const& args) { + this->LoadedImageSurfaceHandler(sender, args); + }); } } catch (winrt::hresult_error const&) From e22af0fbde48f5b21310529c076cb27e69316e6c Mon Sep 17 00:00:00 2001 From: Tom Shea Date: Thu, 20 Jun 2019 14:37:19 -0700 Subject: [PATCH 2/4] Remove LoadedImageSurfaceHandler and move into lambda --- vnext/ReactUWP/Views/Image/ReactImage.cpp | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/vnext/ReactUWP/Views/Image/ReactImage.cpp b/vnext/ReactUWP/Views/Image/ReactImage.cpp index 2c1908ef405..d04b327c575 100644 --- a/vnext/ReactUWP/Views/Image/ReactImage.cpp +++ b/vnext/ReactUWP/Views/Image/ReactImage.cpp @@ -97,10 +97,15 @@ namespace react { winrt::LoadedImageSurface::StartLoadFromStream(memoryStream) : winrt::LoadedImageSurface::StartLoadFromUri(uri) }; - // using a lambda here to capture the surface and prevent it from freeing while the image loads surface.LoadCompleted([this, surface](winrt::LoadedImageSurface const& sender, winrt::LoadedImageSourceLoadCompletedEventArgs const& args) { - this->LoadedImageSurfaceHandler(sender, args); - }); + bool succeeded{ false }; + if (args.Status() == winrt::LoadedImageSourceLoadStatus::Success) { + m_brush->Source(surface); + succeeded = true; + } + + m_onLoadEndEvent(*this, succeeded); + }); } } catch (winrt::hresult_error const&) From a15097b55828e00fbbed6d40c610bea9faa68b48 Mon Sep 17 00:00:00 2001 From: Tom Shea Date: Thu, 20 Jun 2019 15:05:54 -0700 Subject: [PATCH 3/4] actually remove LoadedImageSurfaceHandler (oops) --- vnext/ReactUWP/Views/Image/ReactImage.cpp | 12 ------------ 1 file changed, 12 deletions(-) diff --git a/vnext/ReactUWP/Views/Image/ReactImage.cpp b/vnext/ReactUWP/Views/Image/ReactImage.cpp index d04b327c575..4c671d12b8f 100644 --- a/vnext/ReactUWP/Views/Image/ReactImage.cpp +++ b/vnext/ReactUWP/Views/Image/ReactImage.cpp @@ -114,18 +114,6 @@ namespace react { } } - void ReactImage::LoadedImageSurfaceHandler(winrt::LoadedImageSurface const& sender, winrt::LoadedImageSourceLoadCompletedEventArgs const& args) - { - bool succeeded{ false }; - if (args.Status() == winrt::LoadedImageSourceLoadStatus::Success) - { - m_brush->Source(sender.as()); - succeeded = true; - } - - m_onLoadEndEvent(*this, succeeded); - } - winrt::IAsyncOperation GetImageStreamAsync(ImageSource source) { try From 88fb510869146e0de43e8d8c495b9c5a8d2af8ce Mon Sep 17 00:00:00 2001 From: Tom Shea Date: Thu, 20 Jun 2019 15:07:01 -0700 Subject: [PATCH 4/4] Use weak ref to his in LoadCompleted lambda --- vnext/ReactUWP/Views/Image/ReactImage.cpp | 16 +++++++++------- 1 file changed, 9 insertions(+), 7 deletions(-) diff --git a/vnext/ReactUWP/Views/Image/ReactImage.cpp b/vnext/ReactUWP/Views/Image/ReactImage.cpp index 4c671d12b8f..6fde2d8b508 100644 --- a/vnext/ReactUWP/Views/Image/ReactImage.cpp +++ b/vnext/ReactUWP/Views/Image/ReactImage.cpp @@ -97,14 +97,16 @@ namespace react { winrt::LoadedImageSurface::StartLoadFromStream(memoryStream) : winrt::LoadedImageSurface::StartLoadFromUri(uri) }; - surface.LoadCompleted([this, surface](winrt::LoadedImageSurface const& sender, winrt::LoadedImageSourceLoadCompletedEventArgs const& args) { - bool succeeded{ false }; - if (args.Status() == winrt::LoadedImageSourceLoadStatus::Success) { - m_brush->Source(surface); - succeeded = true; + surface.LoadCompleted([weak_this{ get_weak() }, surface](winrt::LoadedImageSurface const& /*sender*/, winrt::LoadedImageSourceLoadCompletedEventArgs const& args) { + if (auto strong_this{ weak_this.get() }) { + bool succeeded{ false }; + if (args.Status() == winrt::LoadedImageSourceLoadStatus::Success) { + strong_this->m_brush->Source(surface); + succeeded = true; + } + + strong_this->m_onLoadEndEvent(*strong_this, succeeded); } - - m_onLoadEndEvent(*this, succeeded); }); } }