Skip to content

Commit 1e50518

Browse files
authored
Add ExpansionPanelList and ExpansionPanelList.radio Examples (flutter#30343)
1 parent eb4b3e4 commit 1e50518

File tree

1 file changed

+151
-0
lines changed

1 file changed

+151
-0
lines changed

packages/flutter/lib/src/material/expansion_panel.dart

Lines changed: 151 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -56,12 +56,15 @@ typedef ExpansionPanelHeaderBuilder = Widget Function(BuildContext context, bool
5656
/// Expansion panels are only intended to be used as children for
5757
/// [ExpansionPanelList].
5858
///
59+
/// See [ExpansionPanelList] for a sample implementation.
60+
///
5961
/// See also:
6062
///
6163
/// * [ExpansionPanelList]
6264
/// * <https://material.io/design/components/lists.html#types>
6365
class ExpansionPanel {
6466
/// Creates an expansion panel to be used as a child for [ExpansionPanelList].
67+
/// See [ExpansionPanelList] for an example on how to use this widget.
6568
///
6669
/// The [headerBuilder], [body], and [isExpanded] arguments must not be null.
6770
ExpansionPanel({
@@ -88,8 +91,14 @@ class ExpansionPanel {
8891
}
8992

9093
/// An expansion panel that allows for radio-like functionality.
94+
/// This means that at any given time, at most, one [ExpansionPanelRadio]
95+
/// can remain expanded.
9196
///
9297
/// A unique identifier [value] must be assigned to each panel.
98+
/// This identifier allows the [ExpansionPanelList] to determine
99+
/// which [ExpansionPanelRadio] instance should be expanded.
100+
///
101+
/// See [ExpansionPanelList.radio] for a sample implementation.
93102
class ExpansionPanelRadio extends ExpansionPanel {
94103

95104
/// An expansion panel that allows for radio functionality.
@@ -111,9 +120,82 @@ class ExpansionPanelRadio extends ExpansionPanel {
111120
/// A material expansion panel list that lays out its children and animates
112121
/// expansions.
113122
///
123+
/// {@tool snippet --template=stateful_widget_material}
124+
///
125+
/// Here is a simple example of how to implement ExpansionPanelList.
126+
///
127+
/// ```dart preamble
128+
/// // stores ExpansionPanel state information
129+
/// class Item {
130+
/// Item({
131+
/// this.expandedValue,
132+
/// this.headerValue,
133+
/// this.isExpanded = false,
134+
/// });
135+
///
136+
/// String expandedValue;
137+
/// String headerValue;
138+
/// bool isExpanded;
139+
/// }
140+
///
141+
/// List<Item> generateItems(int numberOfItems) {
142+
/// return List.generate(numberOfItems, (int index) {
143+
/// return Item(
144+
/// headerValue: 'Panel $index',
145+
/// expandedValue: 'This is item number $index',
146+
/// );
147+
/// });
148+
/// }
149+
/// ```
150+
///
151+
/// ```dart
152+
/// List<Item> _data = generateItems(8);
153+
///
154+
/// @override
155+
/// Widget build(BuildContext context) {
156+
/// return SingleChildScrollView(
157+
/// child: Container(
158+
/// child: _buildPanel(),
159+
/// ),
160+
/// );
161+
/// }
162+
///
163+
/// Widget _buildPanel() {
164+
/// return ExpansionPanelList(
165+
/// expansionCallback: (int index, bool isExpanded) {
166+
/// setState(() {
167+
/// _data[index].isExpanded = !isExpanded;
168+
/// });
169+
/// },
170+
/// children: _data.map<ExpansionPanel>((Item item) {
171+
/// return ExpansionPanel(
172+
/// headerBuilder: (BuildContext context, bool isExpanded) {
173+
/// return ListTile(
174+
/// title: Text(item.headerValue),
175+
/// );
176+
/// },
177+
/// body: ListTile(
178+
/// title: Text(item.expandedValue),
179+
/// subtitle: Text('To delete this panel, tap the trash can icon'),
180+
/// trailing: Icon(Icons.delete),
181+
/// onTap: () {
182+
/// setState(() {
183+
/// _data.removeWhere((currentItem) => item == currentItem);
184+
/// });
185+
/// }
186+
/// ),
187+
/// isExpanded: item.isExpanded,
188+
/// );
189+
/// }).toList(),
190+
/// );
191+
/// }
192+
/// ```
193+
/// {@end-tool}
194+
///
114195
/// See also:
115196
///
116197
/// * [ExpansionPanel]
198+
/// * [ExpansionPanelList.radio]
117199
/// * <https://material.io/design/components/lists.html#types>
118200
class ExpansionPanelList extends StatefulWidget {
119201
/// Creates an expansion panel list widget. The [expansionCallback] is
@@ -138,6 +220,75 @@ class ExpansionPanelList extends StatefulWidget {
138220
/// expand/collapse button is pushed. The [children] and [animationDuration]
139221
/// arguments must not be null. The [children] objects must be instances
140222
/// of [ExpansionPanelRadio].
223+
///
224+
/// {@tool snippet --template=stateful_widget_material}
225+
///
226+
/// Here is a simple example of how to implement ExpansionPanelList.radio.
227+
///
228+
/// ```dart preamble
229+
/// // stores ExpansionPanel state information
230+
/// class Item {
231+
/// Item({
232+
/// this.id,
233+
/// this.expandedValue,
234+
/// this.headerValue,
235+
/// });
236+
///
237+
/// int id;
238+
/// String expandedValue;
239+
/// String headerValue;
240+
/// }
241+
///
242+
/// List<Item> generateItems(int numberOfItems) {
243+
/// return List.generate(numberOfItems, (int index) {
244+
/// return Item(
245+
/// id: index,
246+
/// headerValue: 'Panel $index',
247+
/// expandedValue: 'This is item number $index',
248+
/// );
249+
/// });
250+
/// }
251+
/// ```
252+
///
253+
/// ```dart
254+
/// List<Item> _data = generateItems(8);
255+
///
256+
/// @override
257+
/// Widget build(BuildContext context) {
258+
/// return SingleChildScrollView(
259+
/// child: Container(
260+
/// child: _buildPanel(),
261+
/// ),
262+
/// );
263+
/// }
264+
///
265+
/// Widget _buildPanel() {
266+
/// return ExpansionPanelList.radio(
267+
/// initialOpenPanelValue: 2,
268+
/// children: _data.map<ExpansionPanelRadio>((Item item) {
269+
/// return ExpansionPanelRadio(
270+
/// value: item.id,
271+
/// headerBuilder: (BuildContext context, bool isExpanded) {
272+
/// return ListTile(
273+
/// title: Text(item.headerValue),
274+
/// );
275+
/// },
276+
/// body: ListTile(
277+
/// title: Text(item.expandedValue),
278+
/// subtitle: Text('To delete this panel, tap the trash can icon'),
279+
/// trailing: Icon(Icons.delete),
280+
/// onTap: () {
281+
/// setState(() {
282+
/// _data.removeWhere((currentItem) => item == currentItem);
283+
/// });
284+
/// }
285+
/// )
286+
/// );
287+
/// }).toList(),
288+
/// );
289+
/// }
290+
/// ```
291+
/// {@end-tool}
141292
const ExpansionPanelList.radio({
142293
Key key,
143294
this.children = const <ExpansionPanelRadio>[],

0 commit comments

Comments
 (0)