flutter_percent_indicator
flutter_percent_indicator copied to clipboard
[LinearPercentIndicator] Cannot get size from a render object that has not been through layout
Fixes issue https://github.com/diegoveloper/flutter_percent_indicator/issues/175
Description:
It seems like this can at times be called before it has been through layout (in particular when restoring state). Changed to first check hasSize
before using size
.
Reproduction steps:
Using minimal sample code included below:
- In Android emulator, go to developer options and enable "Don’t keep activities"
- Run app
- Click on button to restorablePush second route
- Use device buttons to put app in background
- Use device buttons to return to the app
- It will restore and encounter this error
If relevant, this was reproduced on Android 12, Flutter 3.22.0
Sample code:
import 'package:flutter/material.dart';
import 'package:percent_indicator/linear_percent_indicator.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({super.key});
Widget getView(BuildContext subContext, RouteSettings routeSettings) {
switch (routeSettings.name) {
case WidgetB.routeName:
return const WidgetB();
default:
return const WidgetA();
}
}
@override
Widget build(BuildContext context) {
return MaterialApp(
restorationScopeId: "test",
onGenerateRoute: (RouteSettings routeSettings) {
var uri = Uri.parse(routeSettings.name ?? '');
return MaterialPageRoute<void>(
settings: routeSettings,
builder: (BuildContext subContext) {
return getView(subContext, RouteSettings(
name: uri.path,
arguments: routeSettings.arguments ?? uri.queryParameters));
},
);
},
);
}
}
class WidgetA extends StatelessWidget {
static const routeName = 'widget_a';
const WidgetA({super.key,});
@override
Widget build(BuildContext context) {
return Column(children: [
LinearPercentIndicator(),
ElevatedButton(
onPressed: () => Navigator.of(context).restorablePushNamed(WidgetB.routeName),
child: const Text("Click me")
)
],);
}
}
class WidgetB extends StatelessWidget {
static const routeName = 'widget_b';
const WidgetB({super.key,});
@override
Widget build(BuildContext context) {
return const Text("Now use device buttons to put app in background and then restore");
}
}