Skip to content

Cast Error thrown from DraggableScrollableSheet #112020

@Piinks

Description

@Piinks

b/247858428

Customer reporting error being thrown when providing a DraggableScrollableController to DraggableScrollableSheet.

I have not been able to reproduce this crash yet.
There is a notification listener that is swapping out the DraggableScrollableSheet when it reaches the fully expanded state, and it is in _onExtentReplaced where the _attachedController! is throwing.

_attachedController!.extent._currentSize.addListener(notifyListeners);

This is the redacted stack trace from the customer:

══╡ EXCEPTION CAUGHT BY WIDGETS LIBRARY ╞═══════════════════════════════════════════════════════════
The following _CastError was thrown building NotificationListener<DraggableScrollableNotification>:
Null check operator used on a null value

The relevant error-causing widget was:
  NotificationListener<DraggableScrollableNotification>
  NotificationListener ... **redacted** ...

When the exception was thrown, this was the stack:
#0      DraggableScrollableController._onExtentReplaced (package:[flutter/src/widgets/draggable_scrollable_sheet.dart:195]
#1      _DraggableScrollableSheetState._replaceExtent (package:[flutter/src/widgets/draggable_scrollable_sheet.dart:732]
#2      _DraggableScrollableSheetState.didUpdateWidget (package:[flutter/src/widgets/draggable_scrollable_sheet.dart:675]
#3      StatefulElement.update (package:[flutter/src/widgets/framework.dart:5069]
#4      Element.updateChild (package:[flutter/src/widgets/framework.dart:3590]
#5      RenderObjectElement.updateChildren (package:[flutter/src/widgets/framework.dart:5908]
... **redacted**

Here is the sample code I have been trying (unsuccessfully) to reproduce this crash with:

import 'package:flutter/material.dart';

void main() {
  runApp(const MyApp());
}

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

  @override
  Widget build(BuildContext context) {
    return const MaterialApp(home: MyHomePage());
  }
}

class MyHomePage extends StatefulWidget {
  const MyHomePage({super.key});

  @override
  State<MyHomePage> createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  final _controller = DraggableScrollableController();
  bool useExpanded = false;

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Text('DraggableScrollableSheet'),
      ),
      body: NotificationListener<DraggableScrollableNotification>(
        onNotification: (scrollNotification) {
            if (scrollNotification.extent == scrollNotification.minExtent) {
              print('Fully closed');
              setState((){ useExpanded = false; });
            } else if (scrollNotification.extent == scrollNotification.maxExtent) {
              print('Fully expanded');
              setState((){ useExpanded = true; });
            }
            return true;
          },
        child: !useExpanded
        ? DraggableScrollableSheet(
          initialChildSize: 0.25,
          minChildSize: 0.25,
          controller: _controller,
          snap: true,
          snapSizes: const <double>[0.25, 1.0],
          builder: (BuildContext context, ScrollController scrollController) {
            return Container(
              color: Colors.red[100],
              child: ListView.builder(
                controller: scrollController,
                itemCount: 25,
                itemBuilder: (BuildContext context, int index) {
                  return ListTile(title: Text('Item $index'));
                },
              ),
            );
          },
        )
        : DraggableScrollableSheet(
          initialChildSize: 1,
          minChildSize: 0.25,
          controller: _controller,
          snap: true,
          snapSizes: const <double>[0.25, 1.0],
          builder: (BuildContext context, ScrollController scrollController) {
            return Container(
              color: Colors.blue[100],
              child: ListView.builder(
                controller: scrollController,
                itemCount: 25,
                itemBuilder: (BuildContext context, int index) {
                  return Container(height: 50, child: Text('Item $index'));
                },
              ),
            );
          },
        ),
      ),
    );
  }
}

@xu-baolin does anything jump out at you here?

Metadata

Metadata

Assignees

Labels

P0Critical issues such as a build break or regressionc: crashStack traces logged to the consolecustomer: googleVarious Google teamsf: scrollingViewports, list views, slivers, etc.frameworkflutter/packages/flutter repository. See also f: labels.

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions