Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Maui Performance Issues #14227

Closed
BECInc opened this issue Mar 28, 2023 · 14 comments
Closed

Maui Performance Issues #14227

BECInc opened this issue Mar 28, 2023 · 14 comments
Labels
legacy-area-perf Startup / Runtime performance platform/iOS 🍎 t/perf The issue affects performance (runtime speed, memory usage, startup time, etc.) (sub: perf)
Milestone

Comments

@BECInc
Copy link

BECInc commented Mar 28, 2023

Description

There are several instances where Maui is considerably slower than Xamarin.Forms in iOS projects, particularly on iPads in debug mode (both simulator and on device) . These issues are also present in release, but not as pronounced when compiling with the LLVM compiler. This is affecting our ability to migrate our current Forms project over to Maui. I have included two sample projects that show the difference in performance between Maui and Xamarin.Forms. They highlight three areas in particular that are causing us difficulties:

  1. Navigation to pages with complex UI - We have large and complicated UI in our iPad application. Forms with nested grids and multiple controls are common. Our current Forms project is capable of navigating to these pages with very short delays. Maui doubles and sometimes triples the amount of time it takes to navigate to these pages. (Run sample projects to see difference. There is a timer at the top of the detail page that shows navigation times).

  2. Animation - Part of our current application relies on animations to clarify for the user where they are in certain form flows. These have become very choppy in Maui. (Run the animation on the animation detail page to see the stutter in Maui, whereas Forms can handled the animation smoothly.)

  3. List Views - Scrolling through long list views in Maui has one of two problems depending on the caching strategy.
    DEFAULT (RetainElements) - Setting the list caching strategy to RetainElements causes the list to drop list items after scrolling up and down the list a few times. More and more cells end up being dropped over time.
    RECYLCEELEMENTS - Setting the list caching strategy to RecycleElements causes scrolling to become very slow, particularly in DEBUG mode.
    Neither of these issues seem to be present in the forms project. (Both of these issues can be demonstrated in the sample projects by changing the caching strategy in the code).

Steps to Reproduce

Run each of the attached projects in Debug mode on and iOS device or in the iOS simulator to see a side-by-side comparison of performance. The projects are setup to be as identical as I could make them.

The projects are:
https://github.com/BECInc/MauiSpeedTest
and
https://github.com/BECInc/XamarinComparison

In each project there is a main page with three buttons:

The first button is a page navigation example. After navigating to the page it will display a label at the top of the page showing how long it takes to perform the transition.

The second button navigates to a page with a button at the top and a grid at the bottom. Tap the button to see the grid animate to a smaller size and then back to its original size.

The third button navigates to a page populated with a ListView. The caching strategy of the list view is set in code to the Default. Scroll through the list in the Maui project several times to see it drop cells. They will appear blank (white). Change the caching strategy of the page in code to RecycleElements. Then open the list view detail page again and scroll through the list to see it stutter and run slowly in Maui.

Link to public reproduction project repository

https://github.com/BECInc/MauiSpeedTest

Version with bug

6.0.312

Last version that worked well

6.0.312

Affected platforms

iOS

Affected platform versions

iPadOS 16.2

Did you find any workaround?

There are currently no workarounds for these issues that I have been able to find.

Relevant log output

No response

@BECInc BECInc added the t/bug Something isn't working label Mar 28, 2023
@jfversluis jfversluis added the legacy-area-perf Startup / Runtime performance label Mar 28, 2023
@jfversluis
Copy link
Member

@jonathanpeppers I think you might be the best person to talk about this?

@jonathanpeppers
Copy link
Member

Run each of the attached projects in Debug mode on and iOS device or in the iOS simulator to see a side-by-side comparison of performance.

This is a red flag, that the comparison here might not be accurate. This means you are comparing the Mono's JIT in Xamarin.iOS to the Mono interpreter in .NET 6+. The interpreter is enabled by default in .NET 6+ to support hot reload.

To get an accurate comparison, I think you would need to:

  1. Use Release builds.
  2. Run on a physical device.
  3. Share screenshots. So, we know what to expect?

Can you do that, and we can take a closer look.

You might also share some .speedscope files, if there is a specific scenario you want us to investigate. (See the iOS instructions at https://aka.ms/profile-maui).

Thanks!

@jonathanpeppers jonathanpeppers added the s/needs-info Issue needs more info from the author label Mar 28, 2023
@ghost
Copy link

ghost commented Mar 28, 2023

Hi @BECInc. We have added the "s/needs-info" label to this issue, which indicates that we have an open question for you before we can take further action. This issue will be closed automatically in 7 days if we do not hear back from you by then - please feel free to re-open it if you come back to this issue after that time.

@BECInc
Copy link
Author

BECInc commented Mar 28, 2023

@jonathanpeppers I will post the items you requested. I'm curious, is there a way to turn off the Mono interpreter so that an apples-to-apples comparison can be achieved in debug mode? If not, can you clarify how this would not still be an issue as it stands? Developers spend at least 90% of their time in debug mode. If the development loop has become worse because of the Mono interpreter vs JIT isn't that an issue all on its own? Not being able to get at least a reasonable assessment of how a navigation, an animation or list scroll is running without switching to a release build is less than ideal.

@ghost ghost added s/needs-attention Issue has more information and needs another look and removed s/needs-info Issue needs more info from the author labels Mar 28, 2023
@jonathanpeppers
Copy link
Member

is there a way to turn off the Mono interpreter so that an apples-to-apples comparison can be achieved in debug mode?

In my opinion, it's not even worth looking at performance at all in Debug mode. A good example of this is BenchmarkDotNet, they abort Debug benchmarks by default and tell you to run them in Release mode.

The UseInterpreter=false setting could be turned off, though.

@jonathanpeppers jonathanpeppers added s/needs-info Issue needs more info from the author and removed s/needs-attention Issue has more information and needs another look labels Mar 28, 2023
@ghost
Copy link

ghost commented Mar 28, 2023

Hi @BECInc. We have added the "s/needs-info" label to this issue, which indicates that we have an open question for you before we can take further action. This issue will be closed automatically in 7 days if we do not hear back from you by then - please feel free to re-open it if you come back to this issue after that time.

@BECInc
Copy link
Author

BECInc commented Mar 28, 2023

@jonathanpeppers Here are some screenshots of the mauispeedtest app and the xamarincomparison app running in release mode on an iOS device (not simulator). This is a screenshot of the navigation test page. The label at the top shows how long it takes to navigate from the previous screen to this one. In the Maui app it takes 4265ms. In the Xamarin app it takes roughly half that.
IMG_0002

IMG_0004

The next two screenshots are of the list view test page in both apps, running in release. You can see that there are multiple dropped cells in the Maui version and none in the Xamarin version.
IMG_0001

IMG_0003

For the animation, you'll still have to run the apps side-by-side in release to get a good comparison, but just running the maui app will show how the animation stutters throughout its run. The Xamarin app's animation is much smoother.

@ghost ghost added s/needs-attention Issue has more information and needs another look and removed s/needs-info Issue needs more info from the author labels Mar 28, 2023
@jonathanpeppers jonathanpeppers removed t/bug Something isn't working s/needs-attention Issue has more information and needs another look labels Mar 28, 2023
@mattleibow mattleibow added this to the Backlog milestone Mar 28, 2023
@ghost
Copy link

ghost commented Mar 28, 2023

We've added this issue to our backlog, and we will work to address it as time and resources allow. If you have any additional information or questions about this issue, please leave a comment. For additional info about issue management, please read our Triage Process.

@drasticactions
Copy link
Contributor

drasticactions commented Mar 30, 2023

Another note on general perf when using Debug: If you are using Visual Studio or Visual Studio for Mac, and have XAML Hot Reload enabled, our communication channel at the moment is the debugger. Every time we send or receive events that will cause the debugger to break so we can send information through it. This happens whenever a new element is added or removed from the MAUI or Forms Visual Tree. Under normal debug operations, you may see hitches in the UI but seeing as you're debugging your application, I feel that's a worthwhile trade-off (At least until we make other transport systems).

(Also, to head this off at the pass, it doesn't matter if you're using C# Markup rather than XAML. The XAML Hot Reload tooling includes the Live Visual Tree support in the IDE, which works regardless of whether you're using XAML.)

In the case of Xamarin Forms, XAML Hot Reload also causes ListView to initialize all elements in its visual tree and break virtualization. That would cause both memory usage to explode, but also make it much faster since it doesn't have to render the elements as it goes. Your Release Mode example shows that's not the case for it, but as a heads up for others trying similar things.

TL;DR, as @jonathanpeppers said, always use Release mode for perf testing.

@drasticactions
Copy link
Contributor

drasticactions commented Mar 30, 2023

In terms of general scrolling in ListView on iOS/Catalyst, that is being tracked (#12388) and I believe is the same as you're seeing.

From what I could tell at the time, the recycling strategy for Cells is causing them to be disposed of and not recreated (As in, if you inspect the iOS Cells, they are empty with no contents), but it's tough to pin down at the moment which exact change from Forms is causing this.

IMO, since that issue already exists, it could be tracked there instead. I don't think the Animation one is, though, so this issue could be for that issue specifically.

@jonathanpeppers
Copy link
Member

Duplicate of #12388

@jonathanpeppers
Copy link
Member

Upvote the other one, I will add a comment with your samples above, thanks!

@drasticactions
Copy link
Contributor

@jonathanpeppers I don't think the animation nor page rendering perf tests have related issues (Although I feel that the Page rendering has less to do with navigation and more with loading the complex UI at all). Should those be created as new issues then?

@jonathanpeppers
Copy link
Member

If we had a .speedscope file that shows what to do, it could be specific enough for a new issue.

An example of narrowing it down: #14222 (comment)

When I get to work on this one ^^, I will know exactly what to do.

@ghost ghost locked as resolved and limited conversation to collaborators Apr 29, 2023
@Eilon Eilon added the t/perf The issue affects performance (runtime speed, memory usage, startup time, etc.) (sub: perf) label May 10, 2024
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
legacy-area-perf Startup / Runtime performance platform/iOS 🍎 t/perf The issue affects performance (runtime speed, memory usage, startup time, etc.) (sub: perf)
Projects
Development

No branches or pull requests

7 participants