Support theming CupertinoSwitch
s (#116510)
* Introduce flag to maximally apply CupertinoTheme * add missing docs * add tests * fix docs * fix test
This commit is contained in:
parent
921f077687
commit
1e696d304c
68
examples/api/lib/material/switch/switch.3.dart
Normal file
68
examples/api/lib/material/switch/switch.3.dart
Normal file
@ -0,0 +1,68 @@
|
|||||||
|
// Copyright 2014 The Flutter Authors. All rights reserved.
|
||||||
|
// Use of this source code is governed by a BSD-style license that can be
|
||||||
|
// found in the LICENSE file.
|
||||||
|
|
||||||
|
/// Flutter code sample for [Switch].
|
||||||
|
import 'package:flutter/cupertino.dart';
|
||||||
|
import 'package:flutter/material.dart';
|
||||||
|
|
||||||
|
void main() => runApp(const SwitchApp());
|
||||||
|
|
||||||
|
class SwitchApp extends StatelessWidget {
|
||||||
|
const SwitchApp({super.key});
|
||||||
|
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
return MaterialApp(
|
||||||
|
theme: ThemeData.light(useMaterial3: true).copyWith(
|
||||||
|
// Use the ambient [CupetinoThemeData] to style all widgets which would
|
||||||
|
// otherwise use iOS defaults.
|
||||||
|
cupertinoOverrideTheme: const CupertinoThemeData(applyThemeToAll: true),
|
||||||
|
),
|
||||||
|
home: Scaffold(
|
||||||
|
appBar: AppBar(title: const Text('Switch Sample')),
|
||||||
|
body: const Center(
|
||||||
|
child: SwitchExample(),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class SwitchExample extends StatefulWidget {
|
||||||
|
const SwitchExample({super.key});
|
||||||
|
|
||||||
|
@override
|
||||||
|
State<SwitchExample> createState() => _SwitchExampleState();
|
||||||
|
}
|
||||||
|
|
||||||
|
class _SwitchExampleState extends State<SwitchExample> {
|
||||||
|
bool light = true;
|
||||||
|
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
return Column(
|
||||||
|
mainAxisAlignment: MainAxisAlignment.center,
|
||||||
|
children: <Widget>[
|
||||||
|
Switch.adaptive(
|
||||||
|
value: light,
|
||||||
|
onChanged: (bool value) {
|
||||||
|
setState(() {
|
||||||
|
light = value;
|
||||||
|
});
|
||||||
|
},
|
||||||
|
),
|
||||||
|
Switch.adaptive(
|
||||||
|
// Don't use the ambient [CupetinoThemeData] to style this switch.
|
||||||
|
applyCupertinoTheme: false,
|
||||||
|
value: light,
|
||||||
|
onChanged: (bool value) {
|
||||||
|
setState(() {
|
||||||
|
light = value;
|
||||||
|
});
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
@ -3,7 +3,7 @@
|
|||||||
// found in the LICENSE file.
|
// found in the LICENSE file.
|
||||||
|
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:flutter_api_samples/material/switch/switch.0.dart' as example;
|
import 'package:flutter_api_samples/material/switch/switch.1.dart' as example;
|
||||||
import 'package:flutter_test/flutter_test.dart';
|
import 'package:flutter_test/flutter_test.dart';
|
||||||
|
|
||||||
void main() {
|
void main() {
|
||||||
|
24
examples/api/test/material/switch/switch.3_test.dart
Normal file
24
examples/api/test/material/switch/switch.3_test.dart
Normal file
@ -0,0 +1,24 @@
|
|||||||
|
// Copyright 2014 The Flutter Authors. All rights reserved.
|
||||||
|
// Use of this source code is governed by a BSD-style license that can be
|
||||||
|
// found in the LICENSE file.
|
||||||
|
|
||||||
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:flutter_api_samples/material/switch/switch.3.dart' as example;
|
||||||
|
import 'package:flutter_test/flutter_test.dart';
|
||||||
|
|
||||||
|
void main() {
|
||||||
|
testWidgets('Can toggle switch', (WidgetTester tester) async {
|
||||||
|
await tester.pumpWidget(
|
||||||
|
const example.SwitchApp(),
|
||||||
|
);
|
||||||
|
|
||||||
|
final Finder switchFinder = find.byType(Switch).first;
|
||||||
|
Switch materialSwitch = tester.widget<Switch>(switchFinder);
|
||||||
|
expect(materialSwitch.value, true);
|
||||||
|
|
||||||
|
await tester.tap(switchFinder);
|
||||||
|
await tester.pumpAndSettle();
|
||||||
|
materialSwitch = tester.widget<Switch>(switchFinder);
|
||||||
|
expect(materialSwitch.value, false);
|
||||||
|
});
|
||||||
|
}
|
@ -14,6 +14,7 @@ import 'package:flutter/services.dart';
|
|||||||
import 'package:flutter/widgets.dart';
|
import 'package:flutter/widgets.dart';
|
||||||
|
|
||||||
import 'colors.dart';
|
import 'colors.dart';
|
||||||
|
import 'theme.dart';
|
||||||
import 'thumb_painter.dart';
|
import 'thumb_painter.dart';
|
||||||
|
|
||||||
// Examples can assume:
|
// Examples can assume:
|
||||||
@ -72,6 +73,7 @@ class CupertinoSwitch extends StatefulWidget {
|
|||||||
this.activeColor,
|
this.activeColor,
|
||||||
this.trackColor,
|
this.trackColor,
|
||||||
this.thumbColor,
|
this.thumbColor,
|
||||||
|
this.applyTheme,
|
||||||
this.dragStartBehavior = DragStartBehavior.start,
|
this.dragStartBehavior = DragStartBehavior.start,
|
||||||
}) : assert(value != null),
|
}) : assert(value != null),
|
||||||
assert(dragStartBehavior != null);
|
assert(dragStartBehavior != null);
|
||||||
@ -105,13 +107,15 @@ class CupertinoSwitch extends StatefulWidget {
|
|||||||
/// ```
|
/// ```
|
||||||
final ValueChanged<bool>? onChanged;
|
final ValueChanged<bool>? onChanged;
|
||||||
|
|
||||||
/// The color to use when this switch is on.
|
/// The color to use for the track when the switch is on.
|
||||||
///
|
///
|
||||||
/// Defaults to [CupertinoColors.systemGreen] when null and ignores
|
/// If null and [applyTheme] is false, defaults to [CupertinoColors.systemGreen]
|
||||||
/// the [CupertinoTheme] in accordance to native iOS behavior.
|
/// in accordance to native iOS behavior. Otherwise, defaults to
|
||||||
|
/// [CupertinoThemeData.primaryColor].
|
||||||
final Color? activeColor;
|
final Color? activeColor;
|
||||||
|
|
||||||
/// The color to use for the background when the switch is off.
|
|
||||||
|
/// The color to use for the track when the switch is off.
|
||||||
///
|
///
|
||||||
/// Defaults to [CupertinoColors.secondarySystemFill] when null.
|
/// Defaults to [CupertinoColors.secondarySystemFill] when null.
|
||||||
final Color? trackColor;
|
final Color? trackColor;
|
||||||
@ -121,6 +125,16 @@ class CupertinoSwitch extends StatefulWidget {
|
|||||||
/// Defaults to [CupertinoColors.white] when null.
|
/// Defaults to [CupertinoColors.white] when null.
|
||||||
final Color? thumbColor;
|
final Color? thumbColor;
|
||||||
|
|
||||||
|
/// {@template flutter.cupertino.CupertinoSwitch.applyTheme}
|
||||||
|
/// Whether to apply the ambient [CupertinoThemeData].
|
||||||
|
///
|
||||||
|
/// If true, the track uses [CupertinoThemeData.primaryColor] for the track
|
||||||
|
/// when the switch is on.
|
||||||
|
///
|
||||||
|
/// Defaults to [CupertinoThemeData.applyThemeToAll].
|
||||||
|
/// {@endtemplate}
|
||||||
|
final bool? applyTheme;
|
||||||
|
|
||||||
/// {@template flutter.cupertino.CupertinoSwitch.dragStartBehavior}
|
/// {@template flutter.cupertino.CupertinoSwitch.dragStartBehavior}
|
||||||
/// Determines the way that drag start behavior is handled.
|
/// Determines the way that drag start behavior is handled.
|
||||||
///
|
///
|
||||||
@ -310,6 +324,7 @@ class _CupertinoSwitchState extends State<CupertinoSwitch> with TickerProviderSt
|
|||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
|
final CupertinoThemeData theme = CupertinoTheme.of(context);
|
||||||
if (needsPositionAnimation) {
|
if (needsPositionAnimation) {
|
||||||
_resumePositionAnimation();
|
_resumePositionAnimation();
|
||||||
}
|
}
|
||||||
@ -320,7 +335,9 @@ class _CupertinoSwitchState extends State<CupertinoSwitch> with TickerProviderSt
|
|||||||
child: _CupertinoSwitchRenderObjectWidget(
|
child: _CupertinoSwitchRenderObjectWidget(
|
||||||
value: widget.value,
|
value: widget.value,
|
||||||
activeColor: CupertinoDynamicColor.resolve(
|
activeColor: CupertinoDynamicColor.resolve(
|
||||||
widget.activeColor ?? CupertinoColors.systemGreen,
|
widget.activeColor
|
||||||
|
?? ((widget.applyTheme ?? theme.applyThemeToAll) ? theme.primaryColor : null)
|
||||||
|
?? CupertinoColors.systemGreen,
|
||||||
context,
|
context,
|
||||||
),
|
),
|
||||||
trackColor: CupertinoDynamicColor.resolve(widget.trackColor ?? CupertinoColors.secondarySystemFill, context),
|
trackColor: CupertinoDynamicColor.resolve(widget.trackColor ?? CupertinoColors.secondarySystemFill, context),
|
||||||
|
@ -22,6 +22,7 @@ const _CupertinoThemeDefaults _kDefaultTheme = _CupertinoThemeDefaults(
|
|||||||
// Values extracted from navigation bar. For toolbar or tabbar the dark color is 0xF0161616.
|
// Values extracted from navigation bar. For toolbar or tabbar the dark color is 0xF0161616.
|
||||||
),
|
),
|
||||||
CupertinoColors.systemBackground,
|
CupertinoColors.systemBackground,
|
||||||
|
false,
|
||||||
_CupertinoTextThemeDefaults(CupertinoColors.label, CupertinoColors.inactiveGray),
|
_CupertinoTextThemeDefaults(CupertinoColors.label, CupertinoColors.inactiveGray),
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -172,6 +173,7 @@ class CupertinoThemeData extends NoDefaultCupertinoThemeData with Diagnosticable
|
|||||||
CupertinoTextThemeData? textTheme,
|
CupertinoTextThemeData? textTheme,
|
||||||
Color? barBackgroundColor,
|
Color? barBackgroundColor,
|
||||||
Color? scaffoldBackgroundColor,
|
Color? scaffoldBackgroundColor,
|
||||||
|
bool? applyThemeToAll,
|
||||||
}) : this.raw(
|
}) : this.raw(
|
||||||
brightness,
|
brightness,
|
||||||
primaryColor,
|
primaryColor,
|
||||||
@ -179,6 +181,7 @@ class CupertinoThemeData extends NoDefaultCupertinoThemeData with Diagnosticable
|
|||||||
textTheme,
|
textTheme,
|
||||||
barBackgroundColor,
|
barBackgroundColor,
|
||||||
scaffoldBackgroundColor,
|
scaffoldBackgroundColor,
|
||||||
|
applyThemeToAll,
|
||||||
);
|
);
|
||||||
|
|
||||||
/// Same as the default constructor but with positional arguments to avoid
|
/// Same as the default constructor but with positional arguments to avoid
|
||||||
@ -193,6 +196,7 @@ class CupertinoThemeData extends NoDefaultCupertinoThemeData with Diagnosticable
|
|||||||
CupertinoTextThemeData? textTheme,
|
CupertinoTextThemeData? textTheme,
|
||||||
Color? barBackgroundColor,
|
Color? barBackgroundColor,
|
||||||
Color? scaffoldBackgroundColor,
|
Color? scaffoldBackgroundColor,
|
||||||
|
bool? applyThemeToAll,
|
||||||
) : this._rawWithDefaults(
|
) : this._rawWithDefaults(
|
||||||
brightness,
|
brightness,
|
||||||
primaryColor,
|
primaryColor,
|
||||||
@ -200,6 +204,7 @@ class CupertinoThemeData extends NoDefaultCupertinoThemeData with Diagnosticable
|
|||||||
textTheme,
|
textTheme,
|
||||||
barBackgroundColor,
|
barBackgroundColor,
|
||||||
scaffoldBackgroundColor,
|
scaffoldBackgroundColor,
|
||||||
|
applyThemeToAll,
|
||||||
_kDefaultTheme,
|
_kDefaultTheme,
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -210,6 +215,7 @@ class CupertinoThemeData extends NoDefaultCupertinoThemeData with Diagnosticable
|
|||||||
CupertinoTextThemeData? textTheme,
|
CupertinoTextThemeData? textTheme,
|
||||||
Color? barBackgroundColor,
|
Color? barBackgroundColor,
|
||||||
Color? scaffoldBackgroundColor,
|
Color? scaffoldBackgroundColor,
|
||||||
|
bool? applyThemeToAll,
|
||||||
this._defaults,
|
this._defaults,
|
||||||
) : super(
|
) : super(
|
||||||
brightness: brightness,
|
brightness: brightness,
|
||||||
@ -218,6 +224,7 @@ class CupertinoThemeData extends NoDefaultCupertinoThemeData with Diagnosticable
|
|||||||
textTheme: textTheme,
|
textTheme: textTheme,
|
||||||
barBackgroundColor: barBackgroundColor,
|
barBackgroundColor: barBackgroundColor,
|
||||||
scaffoldBackgroundColor: scaffoldBackgroundColor,
|
scaffoldBackgroundColor: scaffoldBackgroundColor,
|
||||||
|
applyThemeToAll: applyThemeToAll,
|
||||||
);
|
);
|
||||||
|
|
||||||
final _CupertinoThemeDefaults _defaults;
|
final _CupertinoThemeDefaults _defaults;
|
||||||
@ -239,6 +246,9 @@ class CupertinoThemeData extends NoDefaultCupertinoThemeData with Diagnosticable
|
|||||||
@override
|
@override
|
||||||
Color get scaffoldBackgroundColor => super.scaffoldBackgroundColor ?? _defaults.scaffoldBackgroundColor;
|
Color get scaffoldBackgroundColor => super.scaffoldBackgroundColor ?? _defaults.scaffoldBackgroundColor;
|
||||||
|
|
||||||
|
@override
|
||||||
|
bool get applyThemeToAll => super.applyThemeToAll ?? _defaults.applyThemeToAll;
|
||||||
|
|
||||||
@override
|
@override
|
||||||
NoDefaultCupertinoThemeData noDefault() {
|
NoDefaultCupertinoThemeData noDefault() {
|
||||||
return NoDefaultCupertinoThemeData(
|
return NoDefaultCupertinoThemeData(
|
||||||
@ -248,6 +258,7 @@ class CupertinoThemeData extends NoDefaultCupertinoThemeData with Diagnosticable
|
|||||||
textTheme: super.textTheme,
|
textTheme: super.textTheme,
|
||||||
barBackgroundColor: super.barBackgroundColor,
|
barBackgroundColor: super.barBackgroundColor,
|
||||||
scaffoldBackgroundColor: super.scaffoldBackgroundColor,
|
scaffoldBackgroundColor: super.scaffoldBackgroundColor,
|
||||||
|
applyThemeToAll: super.applyThemeToAll,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -262,6 +273,7 @@ class CupertinoThemeData extends NoDefaultCupertinoThemeData with Diagnosticable
|
|||||||
super.textTheme?.resolveFrom(context),
|
super.textTheme?.resolveFrom(context),
|
||||||
convertColor(super.barBackgroundColor),
|
convertColor(super.barBackgroundColor),
|
||||||
convertColor(super.scaffoldBackgroundColor),
|
convertColor(super.scaffoldBackgroundColor),
|
||||||
|
applyThemeToAll,
|
||||||
_defaults.resolveFrom(context, super.textTheme == null),
|
_defaults.resolveFrom(context, super.textTheme == null),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -274,6 +286,7 @@ class CupertinoThemeData extends NoDefaultCupertinoThemeData with Diagnosticable
|
|||||||
CupertinoTextThemeData? textTheme,
|
CupertinoTextThemeData? textTheme,
|
||||||
Color? barBackgroundColor,
|
Color? barBackgroundColor,
|
||||||
Color? scaffoldBackgroundColor,
|
Color? scaffoldBackgroundColor,
|
||||||
|
bool? applyThemeToAll,
|
||||||
}) {
|
}) {
|
||||||
return CupertinoThemeData._rawWithDefaults(
|
return CupertinoThemeData._rawWithDefaults(
|
||||||
brightness ?? super.brightness,
|
brightness ?? super.brightness,
|
||||||
@ -282,6 +295,7 @@ class CupertinoThemeData extends NoDefaultCupertinoThemeData with Diagnosticable
|
|||||||
textTheme ?? super.textTheme,
|
textTheme ?? super.textTheme,
|
||||||
barBackgroundColor ?? super.barBackgroundColor,
|
barBackgroundColor ?? super.barBackgroundColor,
|
||||||
scaffoldBackgroundColor ?? super.scaffoldBackgroundColor,
|
scaffoldBackgroundColor ?? super.scaffoldBackgroundColor,
|
||||||
|
applyThemeToAll ?? super.applyThemeToAll,
|
||||||
_defaults,
|
_defaults,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -295,6 +309,7 @@ class CupertinoThemeData extends NoDefaultCupertinoThemeData with Diagnosticable
|
|||||||
properties.add(createCupertinoColorProperty('primaryContrastingColor', primaryContrastingColor, defaultValue: defaultData.primaryContrastingColor));
|
properties.add(createCupertinoColorProperty('primaryContrastingColor', primaryContrastingColor, defaultValue: defaultData.primaryContrastingColor));
|
||||||
properties.add(createCupertinoColorProperty('barBackgroundColor', barBackgroundColor, defaultValue: defaultData.barBackgroundColor));
|
properties.add(createCupertinoColorProperty('barBackgroundColor', barBackgroundColor, defaultValue: defaultData.barBackgroundColor));
|
||||||
properties.add(createCupertinoColorProperty('scaffoldBackgroundColor', scaffoldBackgroundColor, defaultValue: defaultData.scaffoldBackgroundColor));
|
properties.add(createCupertinoColorProperty('scaffoldBackgroundColor', scaffoldBackgroundColor, defaultValue: defaultData.scaffoldBackgroundColor));
|
||||||
|
properties.add(DiagnosticsProperty<bool>('applyThemeToAll', applyThemeToAll, defaultValue: defaultData.applyThemeToAll));
|
||||||
textTheme.debugFillProperties(properties);
|
textTheme.debugFillProperties(properties);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -322,6 +337,7 @@ class NoDefaultCupertinoThemeData {
|
|||||||
this.textTheme,
|
this.textTheme,
|
||||||
this.barBackgroundColor,
|
this.barBackgroundColor,
|
||||||
this.scaffoldBackgroundColor,
|
this.scaffoldBackgroundColor,
|
||||||
|
this.applyThemeToAll,
|
||||||
});
|
});
|
||||||
|
|
||||||
/// The brightness override for Cupertino descendants.
|
/// The brightness override for Cupertino descendants.
|
||||||
@ -389,6 +405,22 @@ class NoDefaultCupertinoThemeData {
|
|||||||
/// Defaults to [CupertinoColors.systemBackground].
|
/// Defaults to [CupertinoColors.systemBackground].
|
||||||
final Color? scaffoldBackgroundColor;
|
final Color? scaffoldBackgroundColor;
|
||||||
|
|
||||||
|
/// Flag to apply this theme to all descendant Cupertino widgets.
|
||||||
|
///
|
||||||
|
/// Certain Cupertino widgets previously didn't use theming, matching past
|
||||||
|
/// versions of iOS. For example, [CupertinoSwitch]s always used
|
||||||
|
/// [CupertinoColors.systemGreen] when active.
|
||||||
|
///
|
||||||
|
/// Today, however, these widgets can indeed be themed on iOS. Moreover on
|
||||||
|
/// macOS, the accent color is reflected in these widgets. Turning this flag
|
||||||
|
/// on ensures that descendant Cupertino widgets will be themed accordingly.
|
||||||
|
///
|
||||||
|
/// This flag currently applies to the following widgets:
|
||||||
|
/// - [CupertinoSwitch] & [Switch.adaptive]
|
||||||
|
///
|
||||||
|
/// Defaults to false.
|
||||||
|
final bool? applyThemeToAll;
|
||||||
|
|
||||||
/// Returns an instance of the theme data whose property getters only return
|
/// Returns an instance of the theme data whose property getters only return
|
||||||
/// the construction time specifications with no derived values.
|
/// the construction time specifications with no derived values.
|
||||||
///
|
///
|
||||||
@ -412,6 +444,7 @@ class NoDefaultCupertinoThemeData {
|
|||||||
textTheme: textTheme?.resolveFrom(context),
|
textTheme: textTheme?.resolveFrom(context),
|
||||||
barBackgroundColor: convertColor(barBackgroundColor),
|
barBackgroundColor: convertColor(barBackgroundColor),
|
||||||
scaffoldBackgroundColor: convertColor(scaffoldBackgroundColor),
|
scaffoldBackgroundColor: convertColor(scaffoldBackgroundColor),
|
||||||
|
applyThemeToAll: applyThemeToAll,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -428,6 +461,7 @@ class NoDefaultCupertinoThemeData {
|
|||||||
CupertinoTextThemeData? textTheme,
|
CupertinoTextThemeData? textTheme,
|
||||||
Color? barBackgroundColor ,
|
Color? barBackgroundColor ,
|
||||||
Color? scaffoldBackgroundColor,
|
Color? scaffoldBackgroundColor,
|
||||||
|
bool? applyThemeToAll,
|
||||||
}) {
|
}) {
|
||||||
return NoDefaultCupertinoThemeData(
|
return NoDefaultCupertinoThemeData(
|
||||||
brightness: brightness ?? this.brightness,
|
brightness: brightness ?? this.brightness,
|
||||||
@ -436,6 +470,7 @@ class NoDefaultCupertinoThemeData {
|
|||||||
textTheme: textTheme ?? this.textTheme,
|
textTheme: textTheme ?? this.textTheme,
|
||||||
barBackgroundColor: barBackgroundColor ?? this.barBackgroundColor,
|
barBackgroundColor: barBackgroundColor ?? this.barBackgroundColor,
|
||||||
scaffoldBackgroundColor: scaffoldBackgroundColor ?? this.scaffoldBackgroundColor,
|
scaffoldBackgroundColor: scaffoldBackgroundColor ?? this.scaffoldBackgroundColor,
|
||||||
|
applyThemeToAll: applyThemeToAll ?? this.applyThemeToAll,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -448,6 +483,7 @@ class _CupertinoThemeDefaults {
|
|||||||
this.primaryContrastingColor,
|
this.primaryContrastingColor,
|
||||||
this.barBackgroundColor,
|
this.barBackgroundColor,
|
||||||
this.scaffoldBackgroundColor,
|
this.scaffoldBackgroundColor,
|
||||||
|
this.applyThemeToAll,
|
||||||
this.textThemeDefaults,
|
this.textThemeDefaults,
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -456,6 +492,7 @@ class _CupertinoThemeDefaults {
|
|||||||
final Color primaryContrastingColor;
|
final Color primaryContrastingColor;
|
||||||
final Color barBackgroundColor;
|
final Color barBackgroundColor;
|
||||||
final Color scaffoldBackgroundColor;
|
final Color scaffoldBackgroundColor;
|
||||||
|
final bool applyThemeToAll;
|
||||||
final _CupertinoTextThemeDefaults textThemeDefaults;
|
final _CupertinoTextThemeDefaults textThemeDefaults;
|
||||||
|
|
||||||
_CupertinoThemeDefaults resolveFrom(BuildContext context, bool resolveTextTheme) {
|
_CupertinoThemeDefaults resolveFrom(BuildContext context, bool resolveTextTheme) {
|
||||||
@ -467,6 +504,7 @@ class _CupertinoThemeDefaults {
|
|||||||
convertColor(primaryContrastingColor),
|
convertColor(primaryContrastingColor),
|
||||||
convertColor(barBackgroundColor),
|
convertColor(barBackgroundColor),
|
||||||
convertColor(scaffoldBackgroundColor),
|
convertColor(scaffoldBackgroundColor),
|
||||||
|
applyThemeToAll,
|
||||||
resolveTextTheme ? textThemeDefaults.resolveFrom(context) : textThemeDefaults,
|
resolveTextTheme ? textThemeDefaults.resolveFrom(context) : textThemeDefaults,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -117,6 +117,7 @@ class Switch extends StatelessWidget {
|
|||||||
this.onFocusChange,
|
this.onFocusChange,
|
||||||
this.autofocus = false,
|
this.autofocus = false,
|
||||||
}) : _switchType = _SwitchType.material,
|
}) : _switchType = _SwitchType.material,
|
||||||
|
applyCupertinoTheme = false,
|
||||||
assert(dragStartBehavior != null),
|
assert(dragStartBehavior != null),
|
||||||
assert(activeThumbImage != null || onActiveThumbImageError == null),
|
assert(activeThumbImage != null || onActiveThumbImageError == null),
|
||||||
assert(inactiveThumbImage != null || onInactiveThumbImageError == null);
|
assert(inactiveThumbImage != null || onInactiveThumbImageError == null);
|
||||||
@ -161,6 +162,7 @@ class Switch extends StatelessWidget {
|
|||||||
this.focusNode,
|
this.focusNode,
|
||||||
this.onFocusChange,
|
this.onFocusChange,
|
||||||
this.autofocus = false,
|
this.autofocus = false,
|
||||||
|
this.applyCupertinoTheme,
|
||||||
}) : assert(autofocus != null),
|
}) : assert(autofocus != null),
|
||||||
assert(activeThumbImage != null || onActiveThumbImageError == null),
|
assert(activeThumbImage != null || onActiveThumbImageError == null),
|
||||||
assert(inactiveThumbImage != null || onInactiveThumbImageError == null),
|
assert(inactiveThumbImage != null || onInactiveThumbImageError == null),
|
||||||
@ -381,6 +383,9 @@ class Switch extends StatelessWidget {
|
|||||||
|
|
||||||
final _SwitchType _switchType;
|
final _SwitchType _switchType;
|
||||||
|
|
||||||
|
/// {@macro flutter.cupertino.CupertinoSwitch.applyTheme}
|
||||||
|
final bool? applyCupertinoTheme;
|
||||||
|
|
||||||
/// {@macro flutter.cupertino.CupertinoSwitch.dragStartBehavior}
|
/// {@macro flutter.cupertino.CupertinoSwitch.dragStartBehavior}
|
||||||
final DragStartBehavior dragStartBehavior;
|
final DragStartBehavior dragStartBehavior;
|
||||||
|
|
||||||
@ -495,6 +500,7 @@ class Switch extends StatelessWidget {
|
|||||||
onChanged: onChanged,
|
onChanged: onChanged,
|
||||||
activeColor: activeColor,
|
activeColor: activeColor,
|
||||||
trackColor: inactiveTrackColor,
|
trackColor: inactiveTrackColor,
|
||||||
|
applyTheme: applyCupertinoTheme,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
|
@ -2703,6 +2703,7 @@ class MaterialBasedCupertinoThemeData extends CupertinoThemeData {
|
|||||||
_cupertinoOverrideTheme.textTheme,
|
_cupertinoOverrideTheme.textTheme,
|
||||||
_cupertinoOverrideTheme.barBackgroundColor,
|
_cupertinoOverrideTheme.barBackgroundColor,
|
||||||
_cupertinoOverrideTheme.scaffoldBackgroundColor,
|
_cupertinoOverrideTheme.scaffoldBackgroundColor,
|
||||||
|
_cupertinoOverrideTheme.applyThemeToAll,
|
||||||
);
|
);
|
||||||
|
|
||||||
final ThemeData _materialTheme;
|
final ThemeData _materialTheme;
|
||||||
@ -2738,6 +2739,7 @@ class MaterialBasedCupertinoThemeData extends CupertinoThemeData {
|
|||||||
CupertinoTextThemeData? textTheme,
|
CupertinoTextThemeData? textTheme,
|
||||||
Color? barBackgroundColor,
|
Color? barBackgroundColor,
|
||||||
Color? scaffoldBackgroundColor,
|
Color? scaffoldBackgroundColor,
|
||||||
|
bool? applyThemeToAll,
|
||||||
}) {
|
}) {
|
||||||
return MaterialBasedCupertinoThemeData._(
|
return MaterialBasedCupertinoThemeData._(
|
||||||
_materialTheme,
|
_materialTheme,
|
||||||
@ -2748,6 +2750,7 @@ class MaterialBasedCupertinoThemeData extends CupertinoThemeData {
|
|||||||
textTheme: textTheme,
|
textTheme: textTheme,
|
||||||
barBackgroundColor: barBackgroundColor,
|
barBackgroundColor: barBackgroundColor,
|
||||||
scaffoldBackgroundColor: scaffoldBackgroundColor,
|
scaffoldBackgroundColor: scaffoldBackgroundColor,
|
||||||
|
applyThemeToAll: applyThemeToAll,
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -764,6 +764,66 @@ void main() {
|
|||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
testWidgets('Switch can apply the ambient theme and be opted out', (WidgetTester tester) async {
|
||||||
|
final Key switchKey = UniqueKey();
|
||||||
|
bool value = false;
|
||||||
|
await tester.pumpWidget(
|
||||||
|
CupertinoTheme(
|
||||||
|
data: const CupertinoThemeData(primaryColor: Colors.amber, applyThemeToAll: true),
|
||||||
|
child: Directionality(
|
||||||
|
textDirection: TextDirection.ltr,
|
||||||
|
child: StatefulBuilder(
|
||||||
|
builder: (BuildContext context, StateSetter setState) {
|
||||||
|
return Center(
|
||||||
|
child: RepaintBoundary(
|
||||||
|
child: Column(
|
||||||
|
children: <Widget>[
|
||||||
|
CupertinoSwitch(
|
||||||
|
key: switchKey,
|
||||||
|
value: value,
|
||||||
|
dragStartBehavior: DragStartBehavior.down,
|
||||||
|
applyTheme: true,
|
||||||
|
onChanged: (bool newValue) {
|
||||||
|
setState(() {
|
||||||
|
value = newValue;
|
||||||
|
});
|
||||||
|
},
|
||||||
|
),
|
||||||
|
CupertinoSwitch(
|
||||||
|
value: value,
|
||||||
|
dragStartBehavior: DragStartBehavior.down,
|
||||||
|
applyTheme: false,
|
||||||
|
onChanged: (bool newValue) {
|
||||||
|
setState(() {
|
||||||
|
value = newValue;
|
||||||
|
});
|
||||||
|
},
|
||||||
|
),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
},
|
||||||
|
),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
|
||||||
|
await expectLater(
|
||||||
|
find.byType(Column),
|
||||||
|
matchesGoldenFile('switch.tap.off.themed.png'),
|
||||||
|
);
|
||||||
|
|
||||||
|
await tester.tap(find.byKey(switchKey));
|
||||||
|
expect(value, isTrue);
|
||||||
|
|
||||||
|
await tester.pumpAndSettle();
|
||||||
|
await expectLater(
|
||||||
|
find.byType(Column),
|
||||||
|
matchesGoldenFile('switch.tap.on.themed.png'),
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
testWidgets('Hovering over Cupertino switch updates cursor to clickable on Web', (WidgetTester tester) async {
|
testWidgets('Hovering over Cupertino switch updates cursor to clickable on Web', (WidgetTester tester) async {
|
||||||
const bool value = false;
|
const bool value = false;
|
||||||
// Disabled CupertinoSwitch does not update cursor on Web.
|
// Disabled CupertinoSwitch does not update cursor on Web.
|
||||||
|
@ -52,6 +52,7 @@ void main() {
|
|||||||
expect(theme.brightness, isNull);
|
expect(theme.brightness, isNull);
|
||||||
expect(theme.primaryColor, CupertinoColors.activeBlue);
|
expect(theme.primaryColor, CupertinoColors.activeBlue);
|
||||||
expect(theme.textTheme.textStyle.fontSize, 17.0);
|
expect(theme.textTheme.textStyle.fontSize, 17.0);
|
||||||
|
expect(theme.applyThemeToAll, false);
|
||||||
});
|
});
|
||||||
|
|
||||||
testWidgets('Theme attributes cascade', (WidgetTester tester) async {
|
testWidgets('Theme attributes cascade', (WidgetTester tester) async {
|
||||||
@ -122,10 +123,12 @@ void main() {
|
|||||||
(WidgetTester tester) async {
|
(WidgetTester tester) async {
|
||||||
const CupertinoThemeData originalTheme = CupertinoThemeData(
|
const CupertinoThemeData originalTheme = CupertinoThemeData(
|
||||||
brightness: Brightness.dark,
|
brightness: Brightness.dark,
|
||||||
|
applyThemeToAll: true,
|
||||||
);
|
);
|
||||||
|
|
||||||
final CupertinoThemeData theme = await testTheme(tester, originalTheme.copyWith(
|
final CupertinoThemeData theme = await testTheme(tester, originalTheme.copyWith(
|
||||||
primaryColor: CupertinoColors.systemGreen,
|
primaryColor: CupertinoColors.systemGreen,
|
||||||
|
applyThemeToAll: false,
|
||||||
));
|
));
|
||||||
|
|
||||||
expect(theme.brightness, Brightness.dark);
|
expect(theme.brightness, Brightness.dark);
|
||||||
@ -133,6 +136,8 @@ void main() {
|
|||||||
// Now check calculated derivatives.
|
// Now check calculated derivatives.
|
||||||
expect(theme.textTheme.actionTextStyle.color, isSameColorAs(CupertinoColors.systemGreen.darkColor));
|
expect(theme.textTheme.actionTextStyle.color, isSameColorAs(CupertinoColors.systemGreen.darkColor));
|
||||||
expect(theme.scaffoldBackgroundColor, isSameColorAs(CupertinoColors.black));
|
expect(theme.scaffoldBackgroundColor, isSameColorAs(CupertinoColors.black));
|
||||||
|
|
||||||
|
expect(theme.applyThemeToAll, false);
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -181,6 +186,7 @@ void main() {
|
|||||||
'primaryContrastingColor',
|
'primaryContrastingColor',
|
||||||
'barBackgroundColor',
|
'barBackgroundColor',
|
||||||
'scaffoldBackgroundColor',
|
'scaffoldBackgroundColor',
|
||||||
|
'applyThemeToAll',
|
||||||
'textStyle',
|
'textStyle',
|
||||||
'actionTextStyle',
|
'actionTextStyle',
|
||||||
'tabLabelTextStyle',
|
'tabLabelTextStyle',
|
||||||
|
Loading…
x
Reference in New Issue
Block a user