.netmauiabsolutelayoutchildviews

.NET Maui Code Stopping after Children.Remove()


I've run into a very odd problem with .NET Maui that has never happened to me with Xamarin before. On occasion, when I remove a child element from its parent, the rest of the code in the function fails to execute and there is no exception thrown.

The following output is from a Console.WriteLine() immediately preceeding the view.Remove(childview):

[DOTNET] removing view: 'Microsoft.Maui.Controls.Image' from parent 'Microsoft.Maui.Controls.AbsoluteLayout', child count is: 4

Immediately after the Remove(), I do a Console.WriteLine("CP1"); and I do not see that line in the output. I also set a breakpoint on this line and it doesn't hit.

Forgive me for not posting my source but it's proprietary code. I could put together an example if you need me to but there really isn't anything else to this. Code stops executing on the Remove() without an exception. Since .NET Maui is pretty new, maybe it's a bug in the platform. I couldn't find anything about such a bug so I'm asking if anyone might know. Thanks in advance!

Microsoft Visual Studio Enterprise 2022 Version 17.6.3 VisualStudio.17.Release/17.6.3+33801.468 Microsoft .NET Framework Version 4.8.09032

Installed Version: Enterprise

ASP.NET and Web Tools 17.6.326.62524 ASP.NET and Web Tools

Azure App Service Tools v3.0.0 17.6.326.62524 Azure App Service Tools v3.0.0

Azure Functions and Web Jobs Tools 17.6.326.62524 Azure Functions and Web Jobs Tools

C# Tools 4.6.0-3.23259.8+c3cc1d0ceeab1a65da0217e403851a1e8a30086a C# components used in the IDE. Depending on your project type and settings, a different version of the compiler may be used.

Common Azure Tools 1.10 Provides common services for use by Azure Mobile Services and Microsoft Azure Tools.

Extensibility Message Bus 1.4.21 (main@8f226a8) Provides common messaging-based MEF services for loosely coupled Visual Studio extension components communication and integration.

Microsoft Azure Tools for Visual Studio 2.9 Support for Azure Cloud Services projects

Microsoft JVM Debugger 1.0 Provides support for connecting the Visual Studio debugger to JDWP compatible Java Virtual Machines

Mono Debugging for Visual Studio 17.6.41 (790a401) Support for debugging Mono processes with Visual Studio.

NuGet Package Manager 6.6.0 NuGet Package Manager in Visual Studio. For more information about NuGet, visit https://docs.nuget.org/

Razor (ASP.NET Core)
17.6.0.2327201+a6a61fdfa748eaa65aab53dab583276e26af4a3e Provides languages services for ASP.NET Core Razor.

SQL Server Data Tools 17.6.13.0 Microsoft SQL Server Data Tools

TypeScript Tools 17.0.20329.2001 TypeScript Tools for Microsoft Visual Studio

Visual Basic Tools
4.6.0-3.23259.8+c3cc1d0ceeab1a65da0217e403851a1e8a30086a Visual Basic components used in the IDE. Depending on your project type and settings, a different version of the compiler may be used.

Visual F# Tools
17.6.0-beta.23174.5+0207bea1afae48d9351ac26fb51afc8260de0a97 Microsoft Visual F# Tools

Visual Studio IntelliCode 2.2 AI-assisted development for Visual Studio.

VisualStudio.DeviceLog 1.0 Information about my package

VisualStudio.Mac 1.0 Mac Extension for Visual Studio

VSPackage Extension 1.0 VSPackage Visual Studio Extension Detailed Info

Xamarin 17.6.0.251 (d17-6@318364c) Visual Studio extension to enable development for Xamarin.iOS and Xamarin.Android.

Xamarin Designer 17.6.6.0 (remotes/origin/d17-6@cb430751d1) Visual Studio extension to enable Xamarin Designer tools in Visual Studio.

Xamarin.Android SDK 13.2.0.6 (d17-5/a200af1) Xamarin.Android Reference Assemblies and MSBuild support. Mono: 6dd9def Java.Interop: xamarin/java.interop/d17-5@149d70fe SQLite: xamarin/sqlite/3.40.1@68c69d8 Xamarin.Android Tools: xamarin/xamarin-android-tools/d17-5@9f02d77


Solution

  • Wrap code in:
    MainThread.BeginInvokeOnMainThread( () => { ...your code... });.

    This has two benefits:


    IMPORTANT: For this specific purpose, DO NOT use an await variant; the goal is to allow current method to finish, BEFORE your code runs.

    // NO; AVOID "await", if you suspect you have caught UI in an "unsafe state".
    await MainThread.InvokeOnMainThreadAsync( ... );
    

    This isn't a hard-and-fast rule; if this variant would be more convenient, test thoroughly; it is often okay. I don't know an easy way to define when it is safe.


    Note that when it is safe to touch UI is dependent on target platform.
    It is essential to test on all target platforms.

    Even in Xamarin.Forms, there were operations that worked on one platform, but sometimes failed on another. For example, altering a collection (such as children) in your code, might execute while UI thread was in the middle of looping over the collection. (IIRC, iOS is especially susceptible to this, compared to Android. I don't know about Windows.)

    Queueing to MainThread avoids such problems.