Xamarin.forms: [Bug] ImageSource.FromStream() causes Android to crash with animated .gif files.

Created on 29 May 2020  路  9Comments  路  Source: xamarin/Xamarin.Forms

Description

I started with the following working example code that loads using a string in Xaml.

I've tried to modify his example to load an animated gif that is an EmbeddedResource in the NetStandard shared library of the project but have been unsuccessful. I'm using the ImageSource.FromStream( () => assembly.GetManifestResourceStream( resourcePath ) ); method to create the ImageSource from a stream in a binding converter. I can load static gif images without problems this way. I can even load the animated image, as a static image without issue (the IsAnimationPlaying property must be absent from the xaml), but when I add/set the IsAnimationPlaying property in xaml the Android app crashes.

Steps to Reproduce

  1. Download example solution included.
  2. Comment in/out the Crash/No Crash sections of xaml in the MainPage.xaml file.
  3. Execute on an emulator. I've used 2 different emulators, A Nougat 7.1-API 25/Base Device:None/Processor:x86 and a Pie 9.0-API 28/Base Device:Phone M-DPI5.4/Processor:x86. Both show same results.

Expected Behavior

No crash

Actual Behavior

=================================================================
    Native Crash Reporting
=================================================================
Got a SEGV while executing native code. This usually indicates
a fatal error in the mono runtime or one of the native libraries 
used by your application.
=================================================================

No native Android stacktrace (see debuggerd output).

=================================================================
    Basic Fault Address Reporting
=================================================================
Memory around native instruction pointer (0x8c83a896):
0x8c83a886  10 8d 4d e4 8b 4d 10 89 4d e4 8d 4d e4 8b 4d e4  ..M..M..M..M..M.
0x8c83a896  89 4c 24 08 89 44 24 04 89 3c 24 8b c0 e8 c0 fe  .L$..D$..<$.....
0x8c83a8a6  ff ff 89 45 c4 8b 4d f0 8d 64 24 00 90 90 90 8b  ...E..M..d$.....
0x8c83a8b6  45 c4 e9 77 00 00 00 8b 4d f0 8d 64 24 00 90 90  E..w....M..d$...

=================================================================
    Managed Stacktrace:
=================================================================
      at Xamarin.Forms.Platform.Android.FormsAnimationDrawable:LoadImageAnimationAsync <0x0012e>
      at Xamarin.Forms.Platform.Android.FormsAnimationDrawable:LoadImageAnimationAsync <0x0013f>
      at Xamarin.Forms.Platform.Android.FormsAnimationDrawable:LoadImageAnimationAsync <0x0013f>
      at Xamarin.Forms.Platform.Android.FormsAnimationDrawable:LoadImageAnimationAsync <0x0013f>
      at Xamarin.Forms.Platform.Android.FormsAnimationDrawable:LoadImageAnimationAsync <0x0013f>
      at Xamarin.Forms.Platform.Android.FormsAnimationDrawable:LoadImageAnimationAsync <0x0


Continues ad nauseam for pages and then it just dies.


      at Xamarin.Forms.Platform.Android.FormsAnimationDrawable:LoadImageAnimationAsync <0x0013f>
      at Xamarin.Forms.Platform.Android.FormsAnimationDrawable:LoadImageAnimationAsync <0x0013f>
      at Xamarin.Forms.Platform
.Android.FormsAnimationDrawable:LoadImageAnimationAsync <0x0013f>
      at Xamarin.Forms.Platform.Android.StreamImagesourceHandler:LoadImageAnimationAsync <0x0005b>
      at <UpdateBitmap>d__2:MoveNext <0x00768>
      at System.Runtime.CompilerServices.AsyncTaskMethodBuilder:Start <0x00127>
      at Xamarin.Forms.Platform.Android.ImageViewExtensions:UpdateBitmap <0x001bf>
      at Xamarin.Forms.Platform.Android.ImageViewExtensions:UpdateBitmap <0x00067>
      at <TryUpdateBitmap>d__6:MoveNext <0x0028f>
      at System.Runtime.CompilerServices.AsyncTaskMethodBuilder:Start <0x00147>
      at Xamarin.Forms.Platform.Android.FastRenderers.ImageElementManager:TryUpdateBitmap <0x0019b>
      at <OnElementChanged>d__3:MoveNext <0x004b7>
      at System.Runtime.CompilerServices.AsyncVoidMethodBuilder:Start <0x00127>
      at Xamarin.Forms.Platform.Android.FastRenderers.ImageElementManager:OnElementChanged <0x0015f>
      at System.EventHandler`1:invoke_void_object_TEventArgs <0x00143>
      at Xamarin.Forms.Platform.Android.FastRenderers.ImageRenderer:OnEl
ementChanged <0x0011b>
      at Xamarin.Forms.Platform.Android.FastRenderers.ImageRenderer:Xamarin.Forms.Platform.Android.IVisualElementRenderer.SetElement <0x005d7>
      at Xamarin.Forms.Platform.Android.Platform:CreateRenderer <0x0013f>
      at Xamarin.Forms.Platform.Android.VisualElementPackager:AddChild <0x00487>
      at Xamarin.Forms.Platform.Android.VisualElementPackager:SetElement <0x00837>
      at Xamarin.Forms.Platform.Android.VisualElementPackager:Load <0x00057>
      at Xamarin.Forms.Platform.Android.VisualElementRenderer`1:SetPackager <0x00077>
      at Xamarin.Forms.Platform.Android.VisualElementRenderer`1:SetElement <0x007b7>
      at Xamarin.Forms.Platform.Android.VisualElementRenderer`1:Xamarin.Forms.Platform.Android.IVisualElementRenderer.SetElement <0x00187>
      at Xamarin.Forms.Platform.Android.Platform:CreateRenderer <0x0013f>
      at Xamarin.Forms.Platform.Android.VisualElementPackager:AddChild <0x00487>
      at Xamarin.Forms.Platform.Android.VisualElementPackager:SetElement <0x00837>
      at Xamarin.Forms.Platform
.Android.VisualElementPackager:Load <0x00057>
      at Xamarin.Forms.Platform.Android.VisualElementRenderer`1:SetPackager <0x00077>
      at Xamarin.Forms.Platform.Android.VisualElementRenderer`1:SetElement <0x007b7>
      at Xamarin.Forms.Platform.Android.VisualElementRenderer`1:Xamarin.Forms.Platform.Android.IVisualElementRenderer.SetElement <0x00187>
      at Xamarin.Forms.Platform.Android.Platform:CreateRenderer <0x0013f>
      at Xamarin.Forms.Platform.Android.AppCompat.Platform:AddChild <0x000b3>
      at Xamarin.Forms.Platform.Android.AppCompat.Platform:SetPageInternal <0x00297>
      at Xamarin.Forms.Platform.Android.AppCompat.Platform:SetPage <0x0067f>
      at Xamarin.Forms.Platform.Android.FormsAppCompatActivity:InternalSetPage <0x001b7>
      at Xamarin.Forms.Platform.Android.FormsAppCompatActivity:SetMainPage <0x00077>
      at Xamarin.Forms.Platform.Android.FormsAppCompatActivity:LoadApplication <0x0067b>
      at AnimatedGifForms.Droid.MainActivity:OnCreate <0x00143>
      at Android.App.Activity:n_OnCreate_Landroid_os_Bundle_ <0
x000ab>
      at Android.Runtime.DynamicMethodNameCounter:8 <0x000c3>
      at Android.Runtime.DynamicMethodNameCounter:8 <0x000b3>
=================================================================
[HotReload] (2020-05-29 10:24:00.4): ERROR: Caught exception in AgentStatusChangedHandler at 212: Xamarin.HotReload.DebuggerTimeoutException: Failed to Inject Assembly
   at Microsoft.VisualStudio.Telemetry.WindowsErrorReporting.WatsonReport.GetClrWatsonExceptionInfo(Exception exceptionObject)
   at Microsoft.VisualStudio.Telemetry.WindowsErrorReporting.WatsonReport.GetClrWatsonExceptionInfo(Exception exceptionObject)

Basic Information

  • Version with issue: Original example had Xamarin.Forms (4.4.0.991220-pre3) and Essentials (1.3.1) I've upgraded to Xamarin.Forms (4.6.0.772) and Essentials (1.5.3.2) with no change in outcome.
  • Last known good version: None
  • IDE: Visual Studio 2019 16.6.0
  • Platform Target Frameworks:

    • Android: TargetFramework 9.0 Pie
  • Android Support Library Version: These are the SDKs installed for the images I ran against. Built against 9 API 28
    Android SDK Platform 25 version 3
    Android SDK Platform 28 version 6

  • Nuget Packages: See included Example solution

  • Affected Devices: Android is all I tried.

Screenshots

None

Reproduction Link

Uploaded a zip solution.
AnimatedGifAndroidCrash.zip

Workaround

Could not determine a workaround.

4.6.0 image high regression Android bug

Most helpful comment

I try it, works but on Android took more seconds to be rendered.
On iOS the gif is rendered as soon y open the page but on Android took more seconds to be rendered.

All 9 comments

So I've been playing around with this in my production application (not the example I've uploaded) and noted the following:

If I load a .png Image and the IsAnimationPlaying property is present in xaml I see the same crash. True or False makes no difference. Simply present in the .xaml file and load an image using the ImageSource.FromStream( () => assembly.GetManifestResourceStream( resourcePath ) ); method and it crashes.

I am seeing the same thing of needing a .png and .gif depending on what is loaded but can't have the IsAnimationPlaying bound as it crashes but without it I can't get the .gif files to animate...

Observing the same behaviour.

Attempting to load a gif which is an embedded resources within the NetStandard shared library. If the IsAnimationPlaying is false then the gif is rendered but not animated. As soon as this value is switched to true, the crash occurs.

I'm seeing the same error. Time before was working but now is crashing the app.
On Android the app is crashing when the following code is loading in a content page:

<Image IsAnimationPlaying="True"
             Source="{extentions:EmbeddedResourceExtention Source=AppTest.Images.Test.gif}"
             WidthRequest="300"
             HeightRequest="300"/>

EmbeddedResourceExtention code works with others images like *.png or *.jpg but not with gif

[ContentProperty(nameof(Source))] // This property is used as a parameter in XAML.
    public class EmbeddedResourceExtention : IMarkupExtension
    {
        public string Source { get; set; }

        public object ProvideValue(IServiceProvider serviceProvider)
        {
            if (Source == null)
            {
                return null;
            }

            // Search for the image resource and return and object that
            // represents the image path.
            var imageSource = ImageSource.FromResource(Source,
                            typeof(EmbeddedResourceExtention).GetTypeInfo().Assembly);
            return imageSource;
        }
    }

On iOS is not rendering.
Is very frustrating because I'm working this requirement for a Enterprise Application.

Xamarin.Forms 4.8.0.1269
VS for Mac 8.7 Build 2037

I'm seeing the same error. Time before was working but now is crashing the app.
On Android the app is crashing when the following code is loading in a content page:

<Image IsAnimationPlaying="True"
             Source="{extentions:EmbeddedResourceExtention Source=AppTest.Images.Test.gif}"
             WidthRequest="300"
             HeightRequest="300"/>

EmbeddedResourceExtention code works with others images like *.png or *.jpg but not with gif

[ContentProperty(nameof(Source))] // This property is used as a parameter in XAML.
    public class EmbeddedResourceExtention : IMarkupExtension
    {
        public string Source { get; set; }

        public object ProvideValue(IServiceProvider serviceProvider)
        {
            if (Source == null)
            {
                return null;
            }

            // Search for the image resource and return and object that
            // represents the image path.
            var imageSource = ImageSource.FromResource(Source,
                            typeof(EmbeddedResourceExtention).GetTypeInfo().Assembly);
            return imageSource;
        }
    }

On iOS is not rendering.
Is very frustrating because I'm working this requirement for a Enterprise Application.

Xamarin.Forms 4.8.0.1269
VS for Mac 8.7 Build 2037

Hey @xamiell if you want you can still render the gif but you cannot use this method

For android put your gif in the resources/drawable folder and for iOS put it in the resources folder, then use a normal image component in XAML and set IsAnimationPlaying = true

This issue seems to happen if we use the gifs from within the .NET shared library as embedded resources .. Hope this helps .. let me know if you manage 鈽猴笍 I worked around this issue in this way

I'm seeing the same error. Time before was working but now is crashing the app.
On Android the app is crashing when the following code is loading in a content page:

<Image IsAnimationPlaying="True"
             Source="{extentions:EmbeddedResourceExtention Source=AppTest.Images.Test.gif}"
             WidthRequest="300"
             HeightRequest="300"/>

EmbeddedResourceExtention code works with others images like *.png or *.jpg but not with gif

[ContentProperty(nameof(Source))] // This property is used as a parameter in XAML.
    public class EmbeddedResourceExtention : IMarkupExtension
    {
        public string Source { get; set; }

        public object ProvideValue(IServiceProvider serviceProvider)
        {
            if (Source == null)
            {
                return null;
            }

            // Search for the image resource and return and object that
            // represents the image path.
            var imageSource = ImageSource.FromResource(Source,
                            typeof(EmbeddedResourceExtention).GetTypeInfo().Assembly);
            return imageSource;
        }
    }

On iOS is not rendering.
Is very frustrating because I'm working this requirement for a Enterprise Application.

Xamarin.Forms 4.8.0.1269
VS for Mac 8.7 Build 2037

Hey @xamiell if you want you can still render the gif but you cannot use this method

For android put your gif in the resources/drawable folder and for iOS put it in the resources folder, then use a normal image component in XAML and set IsAnimationPlaying = true

This issue seems to happen if we use the gifs from within the .NET shared library as embedded resources .. Hope this helps .. let me know if you manager 鈽猴笍 i worked around this issue in this way

Hi, @ognamala thanks for the reply!
I will try and let you know

I try it, works but on Android took more seconds to be rendered.
On iOS the gif is rendered as soon y open the page but on Android took more seconds to be rendered.

@xamiell The gifs are notoriously slow on Android. The larger the gif, the sower the initial load will be. Just to keep that in mind. If it is very large, I am using the new Media element and I'm playing them as a mp4 file.

Hi, @mduchev thanks for the reply, yes but some time dealing with Dark mode a video can be complicated.

I made a gif with less size, now is working perfectly with resources/drawable. I'm wonder that gif are not working with Embedded Resource.
Thanks for the quick and precise replies, that help me a lot! :)

Was this page helpful?
0 / 5 - 0 ratings