Skip to content

home screen performance pass#690

Open
broken-droid wants to merge 20 commits into
Moonfin-Client:mainfrom
broken-droid:fix/home_performance_improvements
Open

home screen performance pass#690
broken-droid wants to merge 20 commits into
Moonfin-Client:mainfrom
broken-droid:fix/home_performance_improvements

Conversation

@broken-droid

@broken-droid broken-droid commented Jul 1, 2026

Copy link
Copy Markdown
Contributor

Summary

home screen performance improvements, cutting down on the need for widget builds and reducing build times. This reduces HomeShell and ContentRows rebuilds massively on scrolling. Most builds now will be from horizontal scrolling within the rows.

The visibility, repaintboundary's should help with gpu.

Preview player building is still something that's going to cause large build times.

Related Issues

  • Closes #
  • Fixes #
  • Related to #

Type of Change

  • Bug fix
  • New feature
  • Refactor
  • Performance improvement
  • UI/UX update
  • Documentation update
  • Build/CI change
  • Other (describe):

Changes Made

  • Visibility wrappers on rows, replacing opacity
  • RepaintBoundary wrappers in: _Backdrop, _GradientScrim, _buildTitledRow, and around the media bar
  • moved to ValueNotifiers: _selectedItem, _isHoverPaused, _activeFocusedRowIndex, _isScrolledToTop, _isActivelyScrolling, _infoRevealed, _mediaBarVisible, _chromeFocusActive, _chromeAudioActive, _backdropUrl, _activePreviewKey, _previewReady, _v2AdditionalRatingsByKey
  • added ValueListenableBuilders to listen to notifiers and do builds when they change and cleaned up a lot of setState calls
  • added a cache to store the calculated row heights instead of re-calculating every build
  • refactor _onScroll handling so it only fires when it has moved at least _activeRowRecalcDistance
  • added a cache for row target offsets
  • moved the viewmodel listener out of _HomeShellState and into _ContentRowsState
  • added _updateOffsets to centralize needed calculations

Platform

  • Android
  • iOS
  • tvOS
  • Web
  • macOS
  • Windows
  • Linux
  • All / Shared code

Testing

  • Tested on emulator / simulator
  • Tested on physical device
  • Manual testing completed
  • Not tested (explain why):

Test Steps

1.you can try to use flutter devtools if it doesn't crash, otherwise you can add some prints to count builds, and stopwatch to measure times.
2. scroll down several rows, then back up
3. scroll horizontally in rows to get offscreen, and then back

Screenshots (if applicable)

Checklist

  • Code builds successfully
  • Code follows project style and conventions
  • No unnecessary commented-out code
  • No new warnings introduced

@broken-droid broken-droid force-pushed the fix/home_performance_improvements branch from 96a8f55 to c13c450 Compare July 2, 2026 01:45
@broken-droid broken-droid marked this pull request as ready for review July 2, 2026 02:58
add RepaintBoundary wrappers around _Backdrop, and _Gradientscrim

remove redudant non-null assertion
… instead of re-calculating every build

added didUpdateWidget, and _invalidateStaticRowHeightCache to handle _staticRowHeightCache invalidation
wrap the Stack in _ContentRowsState build with a ValueListenableBuilder that will only build when the _scrollOffsetNotifier changes
…d active row recalculation

add _activerowRecalcDistance - scroll distance gate for active row recalculation

updated _ContenRowsState - _onScroll:
When scrolling is happening, active row calculation is throttled instead of happening on every pixel.
Active row calculation is skipped unless there's no active row yet, scroll distance has moved at least _activeRowRecalcDistance number of pixels, or user is at the top.
…edRowTargetFullScreenRows - variables to handle caching of row target offsets

added _invalidateRowTargetOffsetCache - invalidate the row target offset cache

added _rowTargetOffsetsForScroll - calculate the row target offsets
update rest of home screen to use the notifiers

wrapped MediaBar related widgets and InfoArea widget in _contentRowsState - build with ValueListenableBuilders
…tifiers

updated _onRowFocusTracked, _onScroll, and _buildV2ExtendedSection to update notifier instead of calling setState

use a ValueListenableBuilder in _v2AdditionalRatingsByKey tied to _v2AdditionalRatingsNotifier

wrapped AnimatedPadding around the _buildShiftedRow to use a ValueListenableBuilder tied to _activeFocusedRowNotifier

wrapped rows in RepaintBoundary
use notifier in home screen

added isScrolledToTopNotifier parameter to _ContentRows

changed onScrolledToTopChanged to update the notifier instead of setState

used a ValueListenableBuilder tied to _isScrolledToTopNotifier to wrap the media bar widgets
_mediaBarVisible
_chromeFocusActive
_chromeAudioActive
_activePreviewKey
_previewReady

clean up setState's in _schedulePreview, _finishSharedPreview, _startSharedPreview, _moveFocusFromMediaBarToRows

use ValueListenableBuilder's tied to the new notifiers, wrapping media bar and preview widgets
_isActivelyScrolling
_infoRevealed

clean up setState's in _revealAndScrollToPinnedInfo, _onScroll

added a builder for infoPlaceholderHeight and
used ValueListenableBuilder's tied to _infoRevealedNotifier

added a ValueListenableBuilder around the InfoArea tied to _infoRevealedNotifier
_backdropUrl

used ValueListenableBuilder tied to _backdropUrlNotifier to wrap _Backdrop
…c out of build

call _updateOffsets in _onViewModelChanged, _onMediaBarStateChanged, and whenever _activeFocusedRowNotifier changes or build runs
removed RepaintBoundary's from each row, and moved it to _buildTitledRow
…RowExtents

use listEquals for list comparison in _computeRowExtents

change hasSubtitle to also check if not empty

formatting changes
@broken-droid broken-droid force-pushed the fix/home_performance_improvements branch from 296de43 to e004998 Compare July 2, 2026 19:37
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant