1
+ using UnityEngine ;
2
+
3
+ namespace UIWidgetsGallery . gallery {
4
+ const List < String > _defaultMaterials = < String > [
5
+ 'poker' ,
6
+ 'tortilla' ,
7
+ 'fish and' ,
8
+ 'micro' ,
9
+ 'wood' ,
10
+ ] ;
11
+
12
+ const List < String > _defaultActions = < String > [
13
+ 'flake' ,
14
+ 'cut' ,
15
+ 'fragment' ,
16
+ 'splinter' ,
17
+ 'nick' ,
18
+ 'fry' ,
19
+ 'solder' ,
20
+ 'cash in ' ,
21
+ 'eat' ,
22
+ ] ;
23
+
24
+ const Map < String , String > _results = < String , String > {
25
+ 'flake': 'flaking',
26
+ 'cut': 'cutting',
27
+ 'fragment': 'fragmenting',
28
+ 'splinter': 'splintering',
29
+ 'nick': 'nicking',
30
+ 'fry': 'frying',
31
+ 'solder': 'soldering',
32
+ 'cash in ': 'cashing in ',
33
+ 'eat': 'eating',
34
+ } ;
35
+
36
+ const List < String > _defaultTools = < String > [
37
+ 'hammer' ,
38
+ 'chisel' ,
39
+ 'fryer' ,
40
+ 'fabricator' ,
41
+ 'customer' ,
42
+ ] ;
43
+
44
+ const Map < String , String > _avatars = < String , String > {
45
+ 'hammer': 'people/ square/ ali. png',
46
+ 'chisel ': ' people/ square / sandra . png ',
47
+ 'fryer': ' people / square / trevor . png ',
48
+ 'fabricator': ' people / square / stella . png ',
49
+ 'customer': ' people / square / peter . png ',
50
+ } ;
51
+
52
+ const Map < String , Set < String > > _toolActions = < String, Set< String>> {
53
+ 'hammer' : < String > { 'flake' , 'fragment' , 'splinter' } ,
54
+ 'chisel' : < String > { 'flake' , 'nick' , 'splinter' } ,
55
+ 'fryer' : < String > { 'fry' } ,
56
+ 'fabricator' : < String > { 'solder' } ,
57
+ 'customer' : < String > { 'cash in ' , 'eat' } ,
58
+ } ;
59
+
60
+ const Map < String , Set < String > > _materialActions = < String , Set < String > > {
61
+ 'poker' : < String > { 'cash in ' } ,
62
+ 'tortilla' : < String > { 'fry' , 'eat' } ,
63
+ 'fish and' : < String > { 'fry' , 'eat' } ,
64
+ 'micro' : < String > { 'solder' , 'fragment' } ,
65
+ 'wood' : < String > { 'flake' , 'cut' , 'splinter' , 'nick' } ,
66
+ } ;
67
+
68
+ class _ChipsTile extends StatelessWidget {
69
+ const _ChipsTile ( {
70
+ Key key ,
71
+ this . label ,
72
+ this . children ,
73
+ } ) : super ( key : key ) ;
74
+
75
+ final String label;
76
+ final List < Widget > children ;
77
+
78
+ // Wraps a list of chips into a ListTile for display as a section in the demo.
79
+ @override
80
+ Widget build( BuildContext context ) {
81
+ final List < Widget > cardChildren = < Widget> [
82
+ Container (
83
+ padding : const EdgeInsets . only ( top : 16.0 , bottom : 4.0 ) ,
84
+ alignment : Alignment . center ,
85
+ child : Text ( label , textAlign : TextAlign . start ) ,
86
+ ) ,
87
+ ] ;
88
+ if ( children . isNotEmpty ) {
89
+ cardChildren . add ( Wrap (
90
+ children : children . map < Widget > ( ( Widget chip ) {
91
+ return Padding (
92
+ padding : const EdgeInsets . all ( 2.0 ) ,
93
+ child : chip ,
94
+ ) ;
95
+ } ) . toList ( ) ) ) ;
96
+ } else {
97
+ final TextStyle textStyle = Theme . of ( context ) . textTheme . caption . copyWith ( fontStyle : FontStyle . italic ) ;
98
+ cardChildren . add (
99
+ Semantics (
100
+ container : true ,
101
+ child : Container (
102
+ alignment : Alignment . center ,
103
+ constraints : const BoxConstraints ( minWidth : 48.0 , minHeight : 48.0 ) ,
104
+ padding : const EdgeInsets . all ( 8.0 ) ,
105
+ child : Text ( 'None' , style : textStyle ) ,
106
+ ) ,
107
+ ) ) ;
108
+ }
109
+
110
+ return Card (
111
+ semanticContainer : false ,
112
+ child : Column (
113
+ mainAxisSize : MainAxisSize . min ,
114
+ children : cardChildren ,
115
+ ) ,
116
+ ) ;
117
+ }
118
+ }
119
+
120
+ class ChipDemo extends StatefulWidget {
121
+ static const String routeName = '/material/ chip' ;
122
+
123
+ @override
124
+ _ChipDemoState createState( ) => _ChipDemoState ( ) ;
125
+ }
126
+
127
+ class _ChipDemoState extends State< ChipDemo > {
128
+ _ChipDemoState ( ) {
129
+ _reset ( ) ;
130
+ }
131
+
132
+ final Set < String > _materials = < String > { } ;
133
+ String _selectedMaterial = '';
134
+ String _selectedAction = '';
135
+ final Set < String > _tools = < String> { } ;
136
+ final Set < String > _selectedTools = < String> { } ;
137
+ final Set< String> _actions = < String> { } ;
138
+ bool _showShapeBorder = false ;
139
+
140
+ // Initialize members with the default data.
141
+ void _reset ( ) {
142
+ _materials . clear ( ) ;
143
+ _materials . addAll ( _defaultMaterials ) ;
144
+ _actions . clear ( ) ;
145
+ _actions . addAll ( _defaultActions ) ;
146
+ _tools . clear ( ) ;
147
+ _tools . addAll ( _defaultTools ) ;
148
+ _selectedMaterial = '';
149
+ _selectedAction = '';
150
+ _selectedTools . clear ( ) ;
151
+ }
152
+
153
+ void _removeMaterial ( String name ) {
154
+ _materials . remove ( name ) ;
155
+ if ( _selectedMaterial == name ) {
156
+ _selectedMaterial = '';
157
+ }
158
+ }
159
+
160
+ void _removeTool ( String name ) {
161
+ _tools . remove ( name ) ;
162
+ _selectedTools . remove ( name ) ;
163
+ }
164
+
165
+ String _capitalize ( String name ) {
166
+ assert ( name != null && name . isNotEmpty ) ;
167
+ return name . substring ( 0 , 1 ) . toUpperCase ( ) + name . substring ( 1 ) ;
168
+ }
169
+
170
+ // This converts a String to a unique color, based on the hash value of the
171
+ // String object. It takes the bottom 16 bits of the hash, and uses that to
172
+ // pick a hue for an HSV color, and then creates the color (with a preset
173
+ // saturation and value). This means that any unique strings will also have
174
+ // unique colors, but they'll all be readable, since they have the same
175
+ // saturation and value.
176
+ Color _nameToColor ( String name ) {
177
+ assert ( name . length > 1 ) ;
178
+ final int hash = name . hashCode & 0xffff ;
179
+ final double hue = ( 360.0 * hash / ( 1 << 15 ) ) % 360.0 ;
180
+ return HSVColor . fromAHSV ( 1.0 , hue , 0.4 , 0.90 ) . toColor ( ) ;
181
+ }
182
+
183
+ AssetImage _nameToAvatar ( String name ) {
184
+ assert ( _avatars . containsKey ( name ) ) ;
185
+ return AssetImage (
186
+ _avatars [ name ] ,
187
+ package : 'flutter_gallery_assets' ,
188
+ ) ;
189
+ }
190
+
191
+ String _createResult ( ) {
192
+ if ( _selectedAction . isEmpty ) {
193
+ return '';
194
+ }
195
+ return _capitalize ( _results [ _selectedAction ] ) + '!' ;
196
+ }
197
+
198
+ @override
199
+ Widget build( BuildContext context ) {
200
+ final List < Widget > chips = _materials . map < Widget > ( ( String name ) {
201
+ return Chip (
202
+ key : ValueKey < String > ( name ) ,
203
+ backgroundColor : _nameToColor( name ) ,
204
+ label : Text( _capitalize ( name ) ) ,
205
+ onDeleted : ( ) {
206
+ setState ( ( ) {
207
+ _removeMaterial ( name ) ;
208
+ } ) ;
209
+ } ,
210
+ ) ;
211
+ } ) . toList ( ) ;
212
+
213
+ final List < Widget > inputChips = _tools . map < Widget > ( ( String name ) {
214
+ return InputChip (
215
+ key : ValueKey < String > ( name ) ,
216
+ avatar : CircleAvatar(
217
+ backgroundImage : _nameToAvatar( name) ,
218
+ ) ,
219
+ label : Text ( _capitalize ( name ) ) ,
220
+ onDeleted : ( ) {
221
+ setState ( ( ) {
222
+ _removeTool ( name ) ;
223
+ } ) ;
224
+ } ) ;
225
+ } ) . toList ( ) ;
226
+
227
+ final List < Widget > choiceChips = _materials . map < Widget > ( ( String name ) {
228
+ return ChoiceChip (
229
+ key : ValueKey < String > ( name ) ,
230
+ backgroundColor : _nameToColor( name ) ,
231
+ label : Text( _capitalize ( name ) ) ,
232
+ selected : _selectedMaterial == name,
233
+ onSelected : ( bool value ) {
234
+ setState ( ( ) {
235
+ _selectedMaterial = value ? name : '';
236
+ } ) ;
237
+ } ,
238
+ ) ;
239
+ } ) . toList ( ) ;
240
+
241
+ final List < Widget > filterChips = _defaultTools . map < Widget > ( ( String name ) {
242
+ return FilterChip (
243
+ key : ValueKey < String > ( name ) ,
244
+ label : Text( _capitalize ( name ) ) ,
245
+ selected : _tools. contains( name ) ? _selectedTools . contains ( name ) : false,
246
+ onSelected : ! _tools . contains ( name )
247
+ ? null
248
+ : ( bool value ) {
249
+ setState ( ( ) {
250
+ if ( ! value ) {
251
+ _selectedTools . remove ( name ) ;
252
+ } else {
253
+ _selectedTools . add ( name ) ;
254
+ }
255
+ } ) ;
256
+ } ,
257
+ ) ;
258
+ } ) . toList ( ) ;
259
+
260
+ Set < String > allowedActions = < String > { } ;
261
+ if ( _selectedMaterial != null && _selectedMaterial . isNotEmpty ) {
262
+ for ( String tool in _selectedTools) {
263
+ allowedActions . addAll ( _toolActions [ tool ] ) ;
264
+ }
265
+ allowedActions = allowedActions . intersection ( _materialActions [ _selectedMaterial ] ) ;
266
+ }
267
+
268
+ final List< Widget > actionChips = allowedActions . map < Widget > ( ( String name ) {
269
+ return ActionChip (
270
+ label : Text ( _capitalize ( name ) ) ,
271
+ onPressed : ( ) {
272
+ setState ( ( ) {
273
+ _selectedAction = name ;
274
+ } ) ;
275
+ } ,
276
+ ) ;
277
+ } ) . toList ( ) ;
278
+
279
+ final ThemeData theme = Theme. of ( context ) ;
280
+ final List< Widget> tiles = < Widget > [
281
+ const SizedBox ( height : 8.0 , width : 0.0 ) ,
282
+ _ChipsTile( label : 'Available Materials ( Chip ) ', children: chips) ,
283
+ _ChipsTile ( label : 'Available Tools ( InputChip ) ', children: inputChips ) ,
284
+ _ChipsTile ( label : 'Choose a Material ( ChoiceChip ) ', children: choiceChips ) ,
285
+ _ChipsTile ( label : 'Choose Tools ( FilterChip ) ', children: filterChips ) ,
286
+ _ChipsTile ( label : 'Perform Allowed Action ( ActionChip ) ', children: actionChips ) ,
287
+ const Divider ( ) ,
288
+ Padding(
289
+ padding : const EdgeInsets . all ( 8.0 ) ,
290
+ child : Center (
291
+ child : Text (
292
+ _createResult ( ) ,
293
+ style : theme . textTheme . title ,
294
+ ) ,
295
+ ) ,
296
+ ) ,
297
+ ] ;
298
+
299
+ return Scaffold (
300
+ appBar : AppBar (
301
+ title : const Text ( 'Chips' ) ,
302
+ actions : < Widget > [
303
+ MaterialDemoDocumentationButton ( ChipDemo . routeName ) ,
304
+ IconButton (
305
+ onPressed : ( ) {
306
+ setState ( ( ) {
307
+ _showShapeBorder = ! _showShapeBorder ;
308
+ } ) ;
309
+ } ,
310
+ icon : const Icon ( Icons . vignette , semanticLabel : 'Update border shape' ) ,
311
+ ) ,
312
+ ] ,
313
+ ) ,
314
+ body : ChipTheme (
315
+ data : _showShapeBorder
316
+ ? theme . chipTheme . copyWith (
317
+ shape : BeveledRectangleBorder (
318
+ side : const BorderSide ( width : 0.66 , style : BorderStyle . solid , color : Colors . grey ) ,
319
+ borderRadius : BorderRadius . circular ( 10.0 ) ,
320
+ ) )
321
+ : theme . chipTheme ,
322
+ child : ListView ( children : tiles ) ,
323
+ ) ,
324
+ floatingActionButton : FloatingActionButton (
325
+ onPressed : ( ) => setState ( _reset ) ,
326
+ child : const Icon ( Icons . refresh , semanticLabel : 'Reset chips' ) ,
327
+ ) ,
328
+ ) ;
329
+ }
330
+ }
331
+
332
+ }
0 commit comments