Skip to content

SelectableRegion web: right-click during a route transition crashes with 'getTransformTo cannot be called before SelectionContainer is laid out' #189575

Closed

Description

@davidmigloz

Steps to reproduce

  1. Run the code sample below on the web (flutter run -d chrome).
  2. Click "Open detail" to start a route transition.
  3. Right-click during the transition window (roughly the ~300 ms while the page animation is running).

The crash is timing-dependent: the right-click has to land while the outgoing route's SelectableRegion is detached from layout, so it may take a few attempts to hit locally. We hit it regularly in a production web app (both dart2js and wasm builds). It is not reproducible via flutter test because tester.pump() is synchronous and can't race the JS event loop — a live-engine repro needs a synthesized dispatchEvent('mousedown', {button: 2}) against the HtmlElementView element during the transition frame.

Expected results

Right-clicking during a route transition either shows the browser/Flutter context menu or does nothing.

Actual results

Assertion failure (debug) / DartError (release):

Assertion failed: .../widgets/selection_container.dart:303:7
_selectionContainerContext?.findRenderObject() != null
"getTransformTo cannot be called before SelectionContainer is laid out."

Analysis (updated after digging into the lifecycle): the stale _activeClient is caused by three concrete defects in the framework, not just an unguarded geometry read:

  1. PlatformSelectableRegionContextMenu.detach has an inverted condition — if (_activeClient != client) { _activeClient = null; }. Detaching the active client leaves it registered, while detaching an unrelated client wipes another region's registration.
  2. SelectableRegionState._handleFocusChanged calls attach unconditionally at the end of the method, so a region that just lost focus is immediately re-registered.
  3. SelectableRegionState.dispose never detaches, so the static can keep pointing at a disposed delegate.

The mousedown listener then calls client.getTransformTo(null) on that stale delegate (_platform_selectable_region_context_menu_web.dart, line 96 on current master) and hits the assertion above. Same bug family as #151536 / PR #184900 ("geometry read on an unlaid-out SelectionContainer"), different read path.

Fixing the three lifecycle defects is the primary fix — done in #189587, including hardening for BrowserContextMenu.enabled changing at runtime. A guard at the geometry read could stay as defense-in-depth, but note it is incomplete on its own: with assertions compiled out (release mode), a disposed delegate fails the _selectionContainerContext! null-check with a TypeError, which an on AssertionError / on StateError catch would not cover.

Code sample

Code sample
import 'package:flutter/material.dart';

void main() => runApp(const App());

class App extends StatelessWidget {
  const App({super.key});

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Builder(
        builder: (BuildContext context) => SelectionArea(
          child: Scaffold(
            body: Center(
              child: TextButton(
                onPressed: () => Navigator.of(context).push(
                  MaterialPageRoute<void>(
                    builder: (_) => const Scaffold(
                      body: Center(child: Text('Detail page')),
                    ),
                  ),
                ),
                child: const Text('Open detail'),
              ),
            ),
          ),
        ),
      ),
    );
  }
}

Screenshots or Video

Screenshots / Video demonstration

N/A (crash, no visual artifact beyond the exception).

Logs

Logs
DartError: Assertion failed: .../widgets/selection_container.dart:303:7
_selectionContainerContext?.findRenderObject() != null
"getTransformTo cannot be called before SelectionContainer is laid out."
package:flutter/src/widgets/selection_container.dart 303:35                           getTransformTo
package:flutter/src/widgets/_platform_selectable_region_context_menu_web.dart 96:41   <fn>
package:flutter/src/widgets/_platform_selectable_region_context_menu_web.dart 136:11  <fn>

Flutter Doctor output

Doctor output
[✓] Flutter (Channel stable, 3.44.4, on macOS 26.5.2 25F84 darwin-arm64, locale en-US) [609ms]
    • Flutter version 3.44.4 on channel stable at ~/repos/flutter
    • Upstream repository https://github.com/flutter/flutter.git
    • Framework revision ad70ec4617 (3 weeks ago), 2026-06-24 11:07:06 -0700
    • Engine revision a10d8ac38d
    • Dart version 3.12.2
    • DevTools version 2.57.0
    • Feature flags: enable-web, enable-linux-desktop, enable-macos-desktop, enable-windows-desktop, enable-android, enable-ios, cli-animations, enable-native-assets, enable-swift-package-manager, omit-legacy-version-file, enable-lldb-debugging, enable-uiscene-migration

[✓] Android toolchain - develop for Android devices (Android SDK version 36.0.0) [1,824ms]
    • Android SDK at ~/Library/Android/sdk
    • Emulator version unknown
    • Platform android-36, build-tools 36.0.0
    • ANDROID_HOME = ~/Library/Android/sdk
    • Java binary at: ~/Applications/Android Studio.app/Contents/jbr/Contents/Home/bin/java
      This is the JDK bundled with the latest Android Studio installation on this machine.
      To manually set the JDK path, use: `flutter config --jdk-dir="path/to/jdk"`.
    • Java version OpenJDK Runtime Environment (build 21.0.6+-13391695-b895.109)
    • All Android licenses accepted.

[✓] Xcode - develop for iOS and macOS (Xcode 26.6) [1,335ms]
    • Xcode at /Applications/Xcode.app/Contents/Developer
    • Build 17F113
    • CocoaPods version 1.16.2

[✓] Chrome - develop for the web [6ms]
    • Chrome at /Applications/Google Chrome.app/Contents/MacOS/Google Chrome

[✓] Connected device (2 available) [6.8s]
    • macOS (desktop) • macos  • darwin-arm64   • macOS 26.5.2 25F84 darwin-arm64
    • Chrome (web)    • chrome • web-javascript • Google Chrome 150.0.7871.116

[✓] Network resources [789ms]
    • All expected network resources are available.

• No issues found!

First observed on Flutter 3.41.6 stable in production; the affected code path is unchanged on current stable (3.44.4) and master.

Activity

  1. added
    in triagePresently being triaged by the triage team
    a: text inputEntering text in a text field or keyboard related problems
    c: crashStack traces logged to the console
    platform-webWeb applications specifically
    f: selectionSelectableRegion, SelectionArea, SelectionContainer, Selectable, and related APIs
    on Jul 16, 2026
  2. moved this from Incoming Issues to In progress in SelectableRegion Improvementson Jul 16, 2026
  3. mbcorona commented on Jul 16, 2026

    @mbcorona
    Member

    Thanks for the report and linked PR.

    Following the provided code sample I was not able to reproduce the crash after several attempts, it appears to be a tight timing race (consistent with your note that it may take multiple tries and isn't reproducible in flutter test). That said, the root cause is clear from the code: detach() used an inverted condition (_activeClient != client), leaving _activeClient dangling when a SelectableRegion loses focus during a route transition, so the web right-click handler calls getTransformTo on an unlaid-out SelectionContainer.

    PR #189587 fixes this and adds a regression test. Routing to the text input team.

  4. added
    P2Important issues not at the top of the work list
    on Jul 20, 2026
  5. github-actions commented on Aug 12, 2026

    @github-actions

    This thread has been automatically locked since there has not been any recent activity after it was closed. If you are still experiencing a similar issue, please open a new bug, including the output of flutter doctor -v and a minimal reproduction of the issue.

  6. locked as resolved and limited conversation to collaborators on Aug 12, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    P2Important issues not at the top of the work lista: text inputEntering text in a text field or keyboard related problemsc: crashStack traces logged to the consolef: selectionSelectableRegion, SelectionArea, SelectionContainer, Selectable, and related APIsin triagePresently being triaged by the triage teamplatform-webWeb applications specificallyteam-text-inputOwned by Text Input teamtriaged-text-inputTriaged by Text Input team

    Type

    No type

    Projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions