在列表上方放置浮动应用栏
本指南介绍了如何在 Flutter 应用中将浮动应用栏或导航栏置于列表上方。
概述
#为了方便用户查看项目列表,您可能希望在用户向下滚动列表时,将应用栏(导航栏)最小化。
将应用栏移入 CustomScrollView
,您就可以创建一个应用栏,该应用栏可以在您滚动 CustomScrollView
中包含的项目列表时最小化或滚动到屏幕外。
本示例介绍了如何使用 CustomScrollView
来显示带有应用栏的项目列表,该应用栏在用户向下滚动列表时会最小化,具体步骤如下:
- 创建
CustomScrollView
。 - 向
CustomScrollView
添加浮动应用栏。 - 向
CustomScrollView
添加项目列表。
1. 创建 CustomScrollView
#要创建浮动应用栏,请将应用栏放置在 CustomScrollView
中,该 CustomScrollView
也包含项目列表。这会将应用栏和项目列表的滚动位置同步。您可以将 CustomScrollView
小部件视为一个 ListView
,它允许您混合和匹配不同类型的可滚动列表和小部件。
提供给 CustomScrollView
的可滚动列表和小部件被称为 *slivers*。有几种类型的 slivers,例如 SliverList
、SliverGrid
和 SliverAppBar
。事实上,ListView
和 GridView
小部件使用 SliverList
和 SliverGrid
小部件来实现滚动。
对于此示例,请创建一个包含 SliverList
的 CustomScrollView
。此外,如果您的代码中存在应用栏属性,请将其移除。
MaterialApp(
title: 'Floating App Bar',
home: Scaffold(
// No app bar property provided yet.
body: CustomScrollView(
// Add the app bar and list of items as slivers in the next steps.
slivers: <widget>[],
),
),
);
CupertinoApp(
title: 'Floating Navigation Bar',
home: CupertinoPageScaffold(
// No navigation bar property provided yet.
child: CustomScrollView(
// Add the navigation bar and list of items as slivers in the next steps.
slivers: <widget>[],
),
),
);
2. 添加浮动应用栏
#接下来,将应用栏添加到 CustomScrollView
。
Flutter 提供了 SliverAppBar
小部件,它与普通的 AppBar
小部件非常相似,用于显示标题、选项卡、图像等。
然而,SliverAppBar
还允许您创建一个“浮动”应用栏,当您不在页面顶部时,它会收缩并浮动。
要创建此效果
- 从仅显示标题的应用栏开始。
- 将
pinned
属性设置为true
。 - 添加一个填充可用
expandedHeight
的flexibleSpace
小部件。
slivers: [
// Add the app bar to the CustomScrollView.
SliverAppBar(
// Provide a standard title.
title: Text('Floating App Bar'),
// Pin the app bar when scrolling.
pinned: true,
// Display a placeholder widget to visualize the shrinking size.
flexibleSpace: Placeholder(),
// Make the initial height of the SliverAppBar larger than normal.
expandedHeight: 200,
),
],
Flutter 提供了 CupertinoSliverNavigationBar
小部件,它允许您拥有一个“浮动”导航栏,当您向下滚动时它会收缩,当您不在页面顶部时它会浮动。
要创建此效果
- 将
CupertinoSliverNavigationBar
添加到CustomScrollView
。 - 从仅显示标题的应用栏开始。
slivers: [
// Add the navigation bar to the CustomScrollView.
CupertinoSliverNavigationBar(
// Provide a standard title.
largeTitle: Text('Floating App Bar'),
),
],
3. 添加项目列表
#现在您已经放置了应用栏,请将项目列表添加到 CustomScrollView
中。您有两个选项:SliverList
或 SliverGrid
。如果您需要一个接一个地显示项目列表,请使用 SliverList
小部件。如果您需要显示网格列表,请使用 SliverGrid
小部件。
// Next, create a SliverList
SliverList.builder(
// The builder function returns a ListTile with a title that
// displays the index of the current item.
itemBuilder: (context, index) =>
ListTile(title: Text('Item #$index')),
// Builds 50 ListTiles
itemCount: 50,
)
// Next, create a SliverList
SliverList.builder(
// The builder function returns a CupertinoListTile with a title
// that displays the index of the current item.
itemBuilder: (context, index) =>
CupertinoListTile(title: Text('Item #$index')),
// Builds 50 CupertinoListTile
itemCount: 50,
)
互动示例
#import 'package:flutter/material.dart';
void main() => runApp(const MyApp());
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
const title = 'Floating App Bar';
return MaterialApp(
title: title,
home: Scaffold(
// No app bar provided to Scaffold, only a body with a
// CustomScrollView.
body: CustomScrollView(
slivers: [
// Add the app bar to the CustomScrollView.
const SliverAppBar(
// Provide a standard title.
title: Text(title),
// Pin the app bar when scrolling
pinned: true,
// Display a placeholder widget to visualize the shrinking size.
flexibleSpace: Placeholder(),
// Make the initial height of the SliverAppBar larger than normal.
expandedHeight: 200,
),
// Next, create a SliverList
SliverList.builder(
// The builder function returns a ListTile with a title that
// displays the index of the current item.
itemBuilder: (context, index) =>
ListTile(title: Text('Item #$index')),
// Builds 50 ListTiles
itemCount: 50,
),
],
),
),
);
}
}
import 'package:flutter/cupertino.dart';
void main() => runApp(const MyApp());
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
const title = 'Floating Navigation Bar';
return CupertinoApp(
title: title,
home: CupertinoPageScaffold(
// No navigation bar provided to CupertinoPageScaffold,
// only a body with a CustomScrollView.
child: CustomScrollView(
slivers: [
// Add the navigation bar to the CustomScrollView.
const CupertinoSliverNavigationBar(
// Provide a standard title.
largeTitle: Text(title),
),
// Next, create a SliverList
SliverList.builder(
// The builder function returns a CupertinoListTile with a title
// that displays the index of the current item.
itemBuilder: (context, index) =>
CupertinoListTile(title: Text('Item #$index')),
// Builds 50 CupertinoListTile
itemCount: 50,
),
],
),
),
);
}
}