Turn images to grayscale in Flutter: The ColorFiltered widget

Samarth Agarwal
2 min readMar 7, 2020

--

Recently, I came up with a requirement in a project where I needed to turn an image to grayscale when a certain condition was met. For example, there is a list of cards on the page, where each card has some text and an image. Some of these items are enabled and some of them are disabled, based on the data. I needed to change the color of the image to grayscale if the item is disabled. This seems easy, right?

I look into Flutter BlendMode and it turns out they work really well, only if your images are JPEGs or PNGs with no transparency. Here is the code I used to have a colored transparent PNG image be displayed as a grayscale image.

ColorFiltered(
colorFilter: _item.enabled ? ColorFilter.mode(
Colors.transparent,
BlendMode.multiply,
) : ColorFilter.mode(
Colors.grey,
BlendMode.saturation,
),
child: Container(
padding: const EdgeInsets.all(32.0),
child: FadeInImage.memoryNetwork(
width: (MediaQuery.of(context).size.width * 0.9),
height: (MediaQuery.of(context).size.width * 0.9) * 9 / 16,
placeholder: kTransparentImage,
fit: BoxFit.fitHeight,
image: _item.imageUrl,
),
),
)

Here is the result when the imageUrl property contains a URL to an image that contains transparency.

Clearly, it looks terrible. The BlendMode also affects the transparent bits in the image and converts them to gray as well. I need them to be unaffected.

After some research, I found this deep down in the Flutter documentation. It mentions another constructor that can be used to define a matrix to have finer control over how to apply BlendModes.

So I replaced the ColorFilter.mode constructor with ColorFilter.matrix and passed in these magical numbers.

ColorFilter.matrix(<double>[
0.2126,0.7152,0.0722,0,0,
0.2126,0.7152,0.0722,0,0,
0.2126,0.7152,0.0722,0,0,
0,0,0,1,0,
])

Here is the result.

And that was exactly what I was looking for. The docs also mention a few more examples. Feel free to try them out and play around with the numbers.

Hope this helps you out. Happy coding.

--

--