Is there a map of Material design colors for Flutt

2020-02-28 05:22发布

问题:

I have a widget that I'd ideally like to take in a base Material color and output a widget themed with shades of that color. For example:

return new Container(
  color: Colors.pink.shade50,
  child: new Text(
    'hello',
    style: new TextStyle(
      color: Colors.pink.shade100,
    ),
  ),
);

requires me to specify both shades of pink. Ideally, I could do something like:

Color color = getBaseColorForThisPage(); // returns something like Colors.pink, but on another page, it'll return something like Colors.purple
return new Container(
  color: color.shade50,
  child: new Text(
    'hello',
    style: new TextStyle(
      color: color.shade100,
    ),
  ),
);

Is there a way to return a "map" of Material colors within a color palette, instead of just a single color? When I look at the autocomplete in IntelliJ, I see that after typing Colors.pink, I'm able to specify the shade. But if I set the color to a variable, e.g. Color color = Colors.pink, I am later not able to do color.shade100 or color[100]. Thanks!

回答1:

MaterialColor extends ColorSwatch which is kind of like a Map of colors. You can use ColorSwatch anywhere you could use a Color and get the 500 shade, but you can also index into it with [].

To get a List of all the primary material color swatches, use Colors.primaries.



回答2:

If you take a look the Dart documentation about Flutter here

you will notice how some of the MaterialColor objects are created.

Obviously Flutter has really good conception about the MaterialDesign and most of the colours described here are already predefined inside the main flutter package "package:flutter/material.dart". All this is going to be available to be used out of the box, but

If somebody still wants to create his own MaterialColor with specific shades you can do something like this:

MaterialColor myGreen = const MaterialColor(0xFFAAD400,
  const {
    50 : const Color(hex_value1),
    100 : const Color(hex_value2),
    200 : const Color(hex_value3),
    300 : const Color(hex_value4),
    400 : const Color(hex_value5),
    500 : const Color(hex_value6),
    600 : const Color(hex_value7),
    700 : const Color(hex_value8),
    800 : const Color(hex_value9),
    900 : const Color(hex_value10)});

The first parameter in MaterialColor object constructor is the default HEX value of your colour, in this case 0xFFAAD400. The second parameter is a Map with all swatches of your colour. All values about "hex_value1" .... "hex_value10" need to be different colours. To get some idea how to select (create) these swatches, for example take a look here

For those who don't know how to read the colours HEX values, here I will post some additional information:

For example, to get a fully opaque orange (0xFFFF9000), you could use const Color(0xFFFF9000), where:

  • first two characters (FF) are about the alpha (transparency),

  • second two characters (FF) are for the red,

  • third two characters (90) are for the green,

  • and last two (00) for the blue.

Thanks, Hope it will help to somebody



回答3:

You can create your material color just like this:

const MaterialColor primaryColorShades = MaterialColor(
  0xFF181861,
  <int, Color>{
    50: Color(0xFFA4A4BF),
    100: Color(0xFFA4A4BF),
    200: Color(0xFFA4A4BF),
    300: Color(0xFF9191B3),
    400: Color(0xFF7F7FA6),
    500: Color(0xFF181861),
    600: Color(0xFF6D6D99),
    700: Color(0xFF5B5B8D),
    800: Color(0xFF494980),
    900: Color(0xFF181861),
  },
);


回答4:

Sorry, I know this already has a lot of good answers but here's the naive implementation I've been using to turn any color into a material color in case anyone finds it useful:

import 'package:flutter/material.dart';

Map<int, Color> getSwatch(Color color) {
  final hslColor = HSLColor.fromColor(color);
  final lightness = hslColor.lightness;

  /// if [500] is the default color, there are at LEAST five
  /// steps below [500]. (i.e. 400, 300, 200, 100, 50.) A
  /// divisor of 5 would mean [50] is a lightness of 1.0 or
  /// a color of #ffffff. A value of six would be near white
  /// but not quite.
  final lowDivisor = 6;

  /// if [500] is the default color, there are at LEAST four
  /// steps above [500]. A divisor of 4 would mean [900] is
  /// a lightness of 0.0 or color of #000000
  final highDivisor = 5;

  final lowStep = (1.0 - lightness) / lowDivisor;
  final highStep = lightness / highDivisor;

  return {
    50: (hslColor.withLightness(lightness + (lowStep * 5))).toColor(),
    100: (hslColor.withLightness(lightness + (lowStep * 4))).toColor(),
    200: (hslColor.withLightness(lightness + (lowStep * 3))).toColor(),
    300: (hslColor.withLightness(lightness + (lowStep * 2))).toColor(),
    400: (hslColor.withLightness(lightness + lowStep)).toColor(),
    500: (hslColor.withLightness(lightness)).toColor(),
    600: (hslColor.withLightness(lightness - highStep)).toColor(),
    700: (hslColor.withLightness(lightness - (highStep * 2))).toColor(),
    800: (hslColor.withLightness(lightness - (highStep * 3))).toColor(),
    900: (hslColor.withLightness(lightness - (highStep * 4))).toColor(),
  };
}

The function just adds a relative amount of lightness both above and below your target color. Getting the final material color would be:

final materialColor = MaterialColor(color.value, getSwatch(color));


回答5:

We have to use a map for it:

If you want to create your own MaterialColor with specific shades you can do something like this by creating own map of color in RGBO(Red, Gree, Blue, Opacity) form:

Map<int, Color> colorMap = {
  50: Color.fromRGBO(147, 205, 72, .1),
  100: Color.fromRGBO(147, 205, 72, .2),
  200: Color.fromRGBO(147, 205, 72, .3),
  300: Color.fromRGBO(147, 205, 72, .4),
  400: Color.fromRGBO(147, 205, 72, .5),
  500: Color.fromRGBO(147, 205, 72, .6),
  600: Color.fromRGBO(147, 205, 72, .7),
  700: Color.fromRGBO(147, 205, 72, .8),
  800: Color.fromRGBO(147, 205, 72, .9),
  900: Color.fromRGBO(147, 205, 72, 1),
};
// Green color code: 93cd48 and first two characters (FF) are alpha values (transparency)
MaterialColor customColor = MaterialColor(0xFF93cd48, colorMap); 

If you have color code value like 93cd48 then for converting it to RGB value use https://www.rapidtables.com/convert/color/hex-to-rgb.html

For more reference: https://medium.com/@jits619/flutter-material-color-conversion-ad1574f25828

https://www.youtube.com/watch?v=U19hRU9e0yw&list=PLQ7fSTYH_bV06SWG1IPnyFbavN5NB_h2o&index=7&t=345s



回答6:

Why not just create your own material color instead, its easy. I also use a simple website to pick colors for flutter. Flutter Doctor Color Picker