Я просмотрел практически всю информацию, которую смог найти по этому вопросу, но ни одно из решений, похоже, не работает для меня. У меня есть постоянная верхняя панель навигации, через которую я передаю представления с помощью функции построителя MaterialApp, как показано ниже. Внутри этого класса NavFrame у меня просто две кнопки для переключения между представлениями. Второе представление имеет GridView с привязанным к нему PageStorageKey. Если вы прокручиваете и переключаетесь между представлениями, вы увидите, что позиция прокрутки не загружается при возврате к сетке в представлении 2. Я использую последний пакет Auto-Route для создания своих маршрутов.
main.dart
void main() {
runApp(MyApp());
}
final _navKey = GlobalKey<NavigatorState>();
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'PageStorageKey Debugging',
theme: ThemeData(
primarySwatch: Colors.green,
visualDensity: VisualDensity.adaptivePlatformDensity,
),
initialRoute: Routes.view1,
navigatorKey: _navKey,
onGenerateRoute: Router().onGenerateRoute,
builder: (context, child) => NavFrame(_navKey, child),
);
}
}
nav_frame.dart
class NavFrame extends StatelessWidget {
final Widget child;
final GlobalKey<NavigatorState> _navKey;
const NavFrame(this._navKey, this.child, {Key key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Stack(
children: [
Positioned(
top: 0,
left: 0,
right: 0,
child: Container(
color: Colors.black,
height: 100,
child: Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
RaisedButton(
onPressed: () {
_navKey.currentState.pushReplacementNamed(Routes.view1);
},
child: Text('View 1'),
),
SizedBox(
width: 50,
),
RaisedButton(
onPressed: () {
_navKey.currentState.pushReplacementNamed(Routes.view2);
},
child: Text('View 2'),
),
],
),
)),
Positioned(
top: 100,
left: 0,
right: 0,
bottom: 0,
child: Container(
child: child,
),
),
],
);
}
}
view1.dart
class View1 extends StatelessWidget {
const View1({Key key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Column(
children: [
Expanded(
child: Container(
color: Colors.blue,
))
],
);
}
}
view2.dart
class View2 extends StatefulWidget {
const View2({Key key}) : super(key: key);
@override
_View2State createState() => _View2State();
}
class _View2State extends State<View2>
with AutomaticKeepAliveClientMixin<View2> {
final bucket = PageStorageBucket();
@override
Widget build(BuildContext context) {
super.build(context);
return Column(
children: [
Expanded(
child: GridView.builder(
key: new PageStorageKey('test-key'),
addAutomaticKeepAlives: true,
padding: EdgeInsets.all(30),
shrinkWrap: true,
gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
crossAxisCount: 1,
childAspectRatio: 2,
crossAxisSpacing: 30,
mainAxisSpacing: 30,
),
itemCount: 10,
itemBuilder: (BuildContext context, int index) {
return Container(
decoration: BoxDecoration(
border: Border.all(width: 1.5, color: Colors.black),
borderRadius: BorderRadius.all(Radius.circular(10.0)),
),
child: Center(
child: Material(
child: Text(
index.toString(),
style: TextStyle(fontSize: 20),
),
),
));
},
),
)
],
);
}
@override
bool get wantKeepAlive => true;
}
router.dart
@MaterialAutoRouter(
generateNavigationHelperExtension: true,
routes: <AutoRoute>[
MaterialRoute(page: View1, initial: true),
MaterialRoute(page: View2, path: "/view2"),
],
)
class $Router {}
pubspe c .yaml
name: PageStorageKeyTest
description: Debugging PageStorageKey.
publish_to: "none"
version: 1.0.0+1
environment:
sdk: ">=2.7.0 <3.0.0"
dependencies:
flutter:
sdk: flutter
# Navigation
auto_route: 0.6.6
# Cupertino
cupertino_icons: ^0.1.3
dev_dependencies:
flutter_test:
sdk: flutter
build_runner: 1.10.1
auto_route_generator:
flutter:
uses-material-design: true
Как уже упоминалось, я пробовал много различных предлагаемых решений, которые мне удалось найти. В настоящее время в View2 вы увидите, что я использую AutomaticKeepAliveCluentMixin
с wantKeepAlive
, установленным в true. Я также убедился, что позвонил по номеру super.build(context)
, как я видел в одном вопросе здесь. Я также пробовал использовать PageStoreBucket
практически во всех местах, которые я могу себе представить, и, похоже, он ничего не делает. (В настоящее время не используется в приведенном выше коде). Я пытался установить для maintainState
значение true в MaterialRoute
. В моем фактическом проекте, где я сталкиваюсь с этим, я использую архитектуру Stacked и даже пытался передавать ключи через viewModel, а построитель viewModel строил только один раз, и, похоже, ничто не помогло. Выполнение приведенного выше кода должно привести к возникновению именно той проблемы, с которой я столкнулся. Я также использую последнюю версию разработчика (1.21.0-1.0.pre). Есть предложения?