Unverified Commit 3a2e0d93 authored by Hans Muller's avatar Hans Muller Committed by GitHub

Extended ButtonTheme, RoundedRectangleBorder, gallery buttons demo (#15723)

parent 05ccf56c
......@@ -53,25 +53,40 @@ class ButtonsDemo extends StatefulWidget {
}
class _ButtonsDemoState extends State<ButtonsDemo> {
ShapeBorder _buttonShape;
@override
Widget build(BuildContext context) {
final ButtonThemeData buttonTheme = ButtonTheme.of(context).copyWith(
shape: _buttonShape
);
final List<ComponentDemoTabData> demos = <ComponentDemoTabData>[
new ComponentDemoTabData(
tabName: 'RAISED',
description: _raisedText,
demoWidget: buildRaisedButton(),
demoWidget: new ButtonTheme.fromButtonThemeData(
data: buttonTheme,
child: buildRaisedButton(),
),
exampleCodeTag: _raisedCode,
),
new ComponentDemoTabData(
tabName: 'FLAT',
description: _flatText,
demoWidget: buildFlatButton(),
demoWidget: new ButtonTheme.fromButtonThemeData(
data: buttonTheme,
child: buildFlatButton(),
),
exampleCodeTag: _flatCode,
),
new ComponentDemoTabData(
tabName: 'OUTLINE',
description: _outlineText,
demoWidget: buildOutlineButton(),
demoWidget: new ButtonTheme.fromButtonThemeData(
data: buttonTheme,
child: buildOutlineButton(),
),
exampleCodeTag: _outlineCode,
),
new ComponentDemoTabData(
......@@ -97,6 +112,16 @@ class _ButtonsDemoState extends State<ButtonsDemo> {
return new TabbedComponentDemoScaffold(
title: 'Buttons',
demos: demos,
actions: <Widget>[
new IconButton(
icon: const Icon(Icons.sentiment_very_satisfied),
onPressed: () {
setState(() {
_buttonShape = _buttonShape == null ? const StadiumBorder() : null;
});
},
),
],
);
}
......
......@@ -63,9 +63,9 @@ class ScrollableTabsDemoState extends State<ScrollableTabsDemo> with SingleTicke
});
}
ShapeDecoration getIndicator() {
Decoration getIndicator() {
if (!_customIndicator)
return null;
return const UnderlineTabIndicator();
switch(_demoStyle) {
case TabsDemoStyle.iconsAndText:
......
......@@ -35,11 +35,13 @@ class ComponentDemoTabData {
class TabbedComponentDemoScaffold extends StatelessWidget {
const TabbedComponentDemoScaffold({
this.title,
this.demos
this.demos,
this.actions,
});
final List<ComponentDemoTabData> demos;
final String title;
final List<Widget> actions;
void _showExampleCode(BuildContext context) {
final String tag = demos[DefaultTabController.of(context).index].exampleCodeTag;
......@@ -57,7 +59,8 @@ class TabbedComponentDemoScaffold extends StatelessWidget {
child: new Scaffold(
appBar: new AppBar(
title: new Text(title),
actions: <Widget>[
actions: (actions ?? <Widget>[])..addAll(
<Widget>[
new Builder(
builder: (BuildContext context) {
return new IconButton(
......@@ -68,8 +71,9 @@ class TabbedComponentDemoScaffold extends StatelessWidget {
},
);
},
),
)
],
),
bottom: new TabBar(
isScrollable: true,
tabs: demos.map((ComponentDemoTabData data) => new Tab(text: data.tabName)).toList(),
......
......@@ -80,6 +80,16 @@ class ButtonTheme extends InheritedWidget {
),
super(key: key, child: child);
/// Creates a button theme from [data].
///
/// The [data] argument must not be null.
const ButtonTheme.fromButtonThemeData({
Key key,
@required this.data,
Widget child,
}) : assert(data != null),
super(key: key, child: child);
/// Creates a button theme that is appropriate for button bars, as used in
/// dialog footers and in the headers of data tables.
///
......@@ -248,6 +258,26 @@ class ButtonThemeData extends Diagnosticable {
/// This property only affects [DropdownButton] and its menu.
final bool alignedDropdown;
/// Creates a copy of this button theme data object with the matching fields
/// replaced with the non-null parameter values.
ButtonThemeData copyWith({
ButtonTextTheme textTheme,
double minWidth,
double height,
EdgeInsetsGeometry padding,
ShapeBorder shape,
bool alignedDropdown,
}) {
return new ButtonThemeData(
textTheme: textTheme ?? this.textTheme,
minWidth: minWidth ?? this.minWidth,
height: height ?? this.height,
padding: padding ?? this.padding,
shape: shape ?? this.shape,
alignedDropdown: alignedDropdown ?? this.alignedDropdown,
);
}
@override
bool operator ==(dynamic other) {
if (other.runtimeType != runtimeType)
......
......@@ -454,7 +454,7 @@ class _OutlineBorder extends ShapeBorder {
if (a is _OutlineBorder) {
return new _OutlineBorder(
side: BorderSide.lerp(a.side, side, t),
shape: shape.lerpFrom(a.shape, t),
shape: ShapeBorder.lerp(a.shape, shape, t),
);
}
return super.lerpFrom(a, t);
......@@ -466,7 +466,7 @@ class _OutlineBorder extends ShapeBorder {
if (b is _OutlineBorder) {
return new _OutlineBorder(
side: BorderSide.lerp(side, b.side, t),
shape: shape.lerpTo(b.shape, t),
shape: ShapeBorder.lerp(shape, b.shape, t),
);
}
return super.lerpTo(b, t);
......
......@@ -74,6 +74,31 @@ void main() {
expect(tester.getSize(find.byType(Material)), const Size(88.0, 36.0));
});
test('ButtonThemeData.copyWith', () {
ButtonThemeData theme = const ButtonThemeData().copyWith();
expect(theme.textTheme, ButtonTextTheme.normal);
expect(theme.constraints, const BoxConstraints(minWidth: 88.0, minHeight: 36.0));
expect(theme.padding, const EdgeInsets.symmetric(horizontal: 16.0));
expect(theme.shape, const RoundedRectangleBorder(
borderRadius: const BorderRadius.all(const Radius.circular(2.0)),
));
expect(theme.alignedDropdown, false);
theme = const ButtonThemeData().copyWith(
textTheme: ButtonTextTheme.primary,
minWidth: 100.0,
height: 200.0,
padding: EdgeInsets.zero,
shape: const StadiumBorder(),
alignedDropdown: true,
);
expect(theme.textTheme, ButtonTextTheme.primary);
expect(theme.constraints, const BoxConstraints(minWidth: 100.0, minHeight: 200.0));
expect(theme.padding, EdgeInsets.zero);
expect(theme.shape, const StadiumBorder());
expect(theme.alignedDropdown, true);
});
testWidgets('Theme buttonTheme defaults', (WidgetTester tester) async {
final ThemeData lightTheme = new ThemeData.light();
ButtonTextTheme textTheme;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment