Flutter primarySwatch changes text colors and icon colors - flutter

I am currently getting into using Themes in Flutter. I don't fully understand the primarySwatch yet.
I am setting an app wide theme in the MaterialApp class. I wan tto change the primarySwatch, so all the buttons I use within the app have the same color. When I use primarySwatch: Colors.blue, the text and icons inside the buttons, inside the appBar and so on are white. When I use primarySwatch: Colors.orange, the text is black. I found out that there are "bright" and "dark" colors, and probably according to that, the text color changes from white to black. But is there a way to use a "bright" color and still have white texts and icons without overriding all of them?

EDIT: I didn't see that the question asked "without overriding all of them"
You may want to create a TextButtonThemeData in your ThemeData like so:
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
debugShowCheckedModeBanner: false,
theme: ThemeData(
textButtonTheme: TextButtonThemeData(
style: ButtonStyle(
textStyle: MaterialStateProperty.all<TextStyle>(
TextStyle(color: Colors.white),
),
),
),
),
title: 'Flutter Demo',
home: MyHomePage(title: 'Flutter Demo Home Page'),
);
}
}

Related

ThemeData primaryColor not changing appBar background color

class BMICalculator extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
theme: ThemeData(
primaryColor: Colors.red,
),
home: InputPage(),
);
I am taking this course: https://www.udemy.com/course/flutter-bootcamp-with-dart/
and with the section on themes she uses this exact code to turn her appBar red. My code does not display any errors, however my appBar remains the default theme.
The description of primary color here: https://api.flutter.dev/flutter/material/ThemeData-class.html
It doesn't say it is depreciated, or indicate any recent changes.
My question is not "how can I make my app bar red", but rather, "why does this code not perform as expected?"
PrimaryColor won't work in themeData directly you have to declare it in colorScheme
theme: ThemeData(colorScheme: ColorScheme.light(primary: Colors.red)),
You can either use primarySwatch
theme: ThemeData(primarySwatch: Colors.red),
or you can use appBarTheme
appBarTheme: AppBarTheme(
backgroundColor: Colors.red
),
primarySwatch is not a Color. It's MaterialColor. Which means it's a the different shades of a color a material app will use.
primaryColor is one of those shades. To be exact, primaryColor is normally equal to primarySwatch[500]
ThemeData is one holding all of your theme settings, and the one controlling how the app will look, but ColorScheme is just a set of colors that you create to easily maintain the app's colors. Notice that ThemeData class has a parameter colorScheme, so you can create your own colorScheme and add it to the ThemeData object.
all of widgets styling inherits from colors or themes from ThemeData (defined in MaterialApp) not ColorScheme, colorScheme is just extra colors that you define to use whether in ThemeData or anywhere across the app.
AppBar background color comes from appBarTheme(color:..).
I prefer extending parent theme,
return MaterialApp(
primaryColor: Colors.green,// no effect on AppBar
theme: Theme.of(context).copyWith(
appBarTheme: Theme.of(context).appBarTheme.copyWith(
color: Colors.red,
),
),
More about theme.
MaterialApp(
theme: ThemeData.dark().copyWith(
primaryColor: Color(0xFF090C22),
backgroundColor: Color(0xFF090C22),
scaffoldBackgroundColor: Color(0xFF090C22),
appBarTheme: AppBarTheme(
backgroundColor: Color(0xFF090C22),
),
),
);

Changing navigation bar color to white, icons to dark, does not stick when hiding/showing app

I am trying to make the bottom navigation bar white, with dark icons (Versus the default of black background with white buttons.
I am using this code in main.dart, where I us the SystemChrome method to set the background color and icon color. This looks great when I first open up the app.
class MyApp extends StatelessWidget {
// This widget is the root of your application.
#override
Widget build(BuildContext context) {
SystemChrome.setPreferredOrientations([
DeviceOrientation.portraitUp,
]);
// this sets bottom bar to white
var mySystemTheme= SystemUiOverlayStyle.light.copyWith(systemNavigationBarColor: Colors.white,systemNavigationBarIconBrightness: Brightness.dark);
SystemChrome.setSystemUIOverlayStyle(mySystemTheme);
return ChangeNotifierProvider(
create: (ctx) => GBUserInfo(),
child: MaterialApp(
title: 'test',
debugShowCheckedModeBanner: false,
theme: ThemeData(
primarySwatch: Colors.blue,
backgroundColor: Colors.pink,
accentColor: Colors.yellow,
accentColorBrightness: Brightness.dark,
buttonTheme: ButtonTheme.of(context).copyWith(
buttonColor: Colors.blue,
textTheme: ButtonTextTheme.primary,
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(20),
),
),
),
home: StreamBuilder(
stream: FirebaseAuth.instance.authStateChanges(),
builder: (ctx, userSnapshot) {
if (userSnapshot.connectionState == ConnectionState.waiting) {
return SplashScreen();
}
if (userSnapshot.hasData) {
return ZonesScreen();
}
return Login();
}),
routes: {},
),
);
}
}
Here it looks like I want when I open app.
But, if I minimize app, then click to bring to foreground again,
The buttons are gone, I'm assuming they defaulted back to white.
How do I set the navigation color/icon colors and have them stick with the app?
Try adding a theme data of your desired choice and also make that theme permanent by passing that theme like Themedata.dark() or ThemeData.light()
MaterialApp(
themeMode: ThemeMode.dark,
home: CounterCoin(),
theme: ThemeData.light().copyWith(
)
Like in the above example.
You can then change that theme using theme mode which has the following enums
ThemeMode.system , ThemeMode.dark , ThemeMode.light and use copy with to alter individual property u don't need system callbacks for changing theme this is a more easy and readable way .

How to remove the elevation (shadow) in a SearchDelegate?

I want to remove the shadow from the search bar when using SearchDelegate but I can't find how to. Any tips?
This is basically all the code:
showSearch(
context: context,
delegate: CustomSearchDelegate(),
);
CustomSearchDelegate() just contains an empty search delegate widget/class.
#override
ThemeData appBarTheme(BuildContext context) {
return super.appBarTheme(context).copyWith(
appBarTheme: super.appBarTheme(context).appBarTheme.copyWith(
elevation: 0.0,
),
);
}
Add this inside the Searchdelegate class:
#override
ThemeData appBarTheme(BuildContext context){
assert(context != null);
final ThemeData theme = Theme.of(context);
assert(theme != null);
return theme.copyWith(
primaryColor: Colors.grey[50],
);
}
and this to the main app theme:
MaterialApp(
theme: ThemeData(
backgroundColor: Colors.white,
appBarTheme: AppBarTheme(elevation: 0.0), //This is important
title: 'Flutter Demo',
home: MyHomePage(),
);
Make changes accordingly in your ThemeData() and add the appBarTheme: AppBarTheme(elevation: 0.0), to remove the elevation and the SearchDelegate theme as it is your search delegate class which will ensure that the elevation defined in the ThemeData of your material app is implemented.
Note: I guess, that the elevation set in the ThemeData will affect the elevation of the appbar in other pages all over the app too.
Result:
Output image

Get Device Brightness when building ThemeData, outside of Material App with MediaQuery

I want to display dark or light mode based on the settings of the device.
I need to get the brightness of the device when building my ThemeData, something like this:
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
final materialLightTheme = ThemeData(
primaryColor: Colors.blueAccent,
brightness: Brightness.light,
scaffoldBackgroundColor: MyColors.backgroundColor0(Brightness.light),
appBarTheme: AppBarTheme(
color: MyColors.backgroundColor1(Brightness.light)
),
);
final materialDarkTheme = ThemeData(
primaryColor: Colors.blueAccent,
brightness: Brightness.dark,
scaffoldBackgroundColor: MyColors.backgroundColor0(Brightness.dark),
appBarTheme: AppBarTheme(
color: MyColors.backgroundColor1(Brightness.dark)
),
);
Brightness brightness = MediaQuery.of(context).platformBrightness;
return MaterialApp(
themeMode: brightness == Brightness.light
? ThemeMode.light
: ThemeMode.dark,
theme: materialLightTheme,
darkTheme: materialDarkTheme,
home: MyHomePage(),
);
}
}
But it seems, MediaQuery is not available in the build Method outside of an Material App. I get the Error
MediaQuery.of() called with a context that does not contain a
MediaQuery.
How can I achieve this behaviour?
First for your use case, if you just want to apply dark and light theme based on system's dark mode, then it is automatically handled by the Flutter, just by providing the darkTheme property in your MaterialApp widget, whenever the system's dark mode is activated, the theme supplied in the darkTheme parameter will automatically activate.
However if you do want to access MediaQuery before you apply themes and other stuff to your app via MaterialApp, from what I know you need either MaterialApp or WidgetsApp before in the widget tree in order to get the MediaQuery.of(context). However, we can workaround that by using, two MaterialApp widgets one for just getting the MediaQuery in the second you apply the theming and all other stuff as below
void main() => runApp(MaterialApp(home: MyApp()));
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
final materialLightTheme = ThemeData(
primaryColor: Colors.blueAccent,
brightness: Brightness.light,
scaffoldBackgroundColor: MyColors.backgroundColor0(Brightness.light),
appBarTheme: AppBarTheme(
color: MyColors.backgroundColor1(Brightness.light)
),
);
final materialDarkTheme = ThemeData(
primaryColor: Colors.blueAccent,
brightness: Brightness.dark,
scaffoldBackgroundColor: MyColors.backgroundColor0(Brightness.dark),
appBarTheme: AppBarTheme(
color: MyColors.backgroundColor1(Brightness.dark)
),
);
Brightness brightness = MediaQuery.of(context).platformBrightness;
return MaterialApp(
themeMode: brightness == Brightness.light
? ThemeMode.light
: ThemeMode.dark,
theme: materialLightTheme,
darkTheme: materialDarkTheme,
home: MyHomePage(),
);
}
}

Change background color used in Recents apps screen with Flutter app

How can I change the color shown in the app switcher of Android. Right now the color comes up with a gray background, but I want it to be red.
This is the app code.
import 'package:flutter/material.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
color: Colors.red,
title: 'Flutter Demo',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: Material(
child: Text('Check color in app switcher.'),
),
);
}
}
The color parameter of MaterialApp has no effect.
If you are using the MaterialApp you would use the color attribute to change the color of the app bar in the switcher.
You could also use the SystemChrome.setApplicationSwitcherDescription method which you would find in package:flutter/services.dart