🕌

【Flutter Widget of the Week #24】BackdropFilterを使ってみた

2022/11/14に公開

はじめに

Flutter Widget of the Week #24 BackdropFilter についてまとめましたので、紹介します。
https://youtu.be/dYRs7Q1vfYI

BackdropFilter

Flutter ではアセットやネットワーク経由で画像を読み込み表示することができます。
画像を扱うときに表示した画像を回転させたり、傾けたり、ぼかしたりしたいこともあると思います。
そんなとき BackdropFilter が効果的です。
では、さっそくサンプルを動かして使い方を見てみましょう。

BackdropFilter サンプルコード

BackdropFilter サンプル実行画面
BackdropFilter サンプル実行画面

サンプルコード全体

main.dart
import 'dart:ui' as ui;

class BackdropFilterSample extends StatelessWidget {
  const BackdropFilterSample({super.key});

  
  Widget build(BuildContext context) {
    const TextStyle style = TextStyle(color: Colors.white);

    return Container(
      color: Colors.white,
      child: Center(
        child: Stack(
          fit: StackFit.expand,
          children: <Widget>[
            Text('0' * 10000),
            Center(
              child: ClipRect(
                // <-- clips to the 200x200 [Container] below
                child: BackdropFilter(
                  filter: ui.ImageFilter.blur(
                    sigmaX: 5.0,
                    sigmaY: 5.0,
                  ),
                  child: Container(
                    alignment: Alignment.center,
                    width: 200.0,
                    height: 200.0,
                    child: const Text('Hello World'),
                  ),
                ),
              ),
            ),
          ],
        ),
      ),
    );
  }
}

使い方としては、BackdropFilter の filterパラメータ に ImageFilter を指定して、フィルターでどのようなぼかしを入れるかを決めます。

BackdropFilter(
  filter: ui.ImageFilter.blur(
    sigmaX: 5.0,
    sigmaY: 5.0,
  ),
),

次に child に 子widget を入れます。
ここで注意として、フィルターの影響を受けるのはその 子widget(Container部分) ではなく、その下にある widget です。

BackdropFilter(
  filter: ui.ImageFilter.blur(
    sigmaX: 5.0,
    sigmaY: 5.0,
  ),
  child: Container(
    alignment: Alignment.center,
    width: 200.0,
    height: 200.0,
    child: const Text('Hello World'),
  ),
),

なので、もしこのサンプルコードで ClipRect がない場合は、child に指定している Container の下にある widget にフィルターがかかり、下図のような表示になります。
ClipRect がない場合
ClipRect がない場合

ClipRect がない場合のサンプルコード
import 'dart:ui' as ui;

class BackdropFilterSample extends StatelessWidget {
  const BackdropFilterSample({super.key});

  
  Widget build(BuildContext context) {
    const TextStyle style = TextStyle(color: Colors.white);

    return Container(
      color: Colors.white,
      child: Center(
        child: Stack(
          fit: StackFit.expand,
          children: <Widget>[
            Text('0' * 10000),
            Center(
              child: BackdropFilter(
                filter: ui.ImageFilter.blur(
                  sigmaX: 5.0,
                  sigmaY: 5.0,
                ),
                child: Container(
                  alignment: Alignment.center,
                  width: 200.0,
                  height: 200.0,
                  child: const Text('Hello World'),
                ),
              ),
            ),
          ],
        ),
      ),
    );
  }
}

今回のサンプルコードでは ClipRectという widget をくり抜いてくれる widget が使われているので、ClipRect でくり抜いた部分(Containerで指定した width と height のサイズ分)だけにフィルターがかかるようになります。
基本的な使い方としては以上です。

BackdropFilter のプロパティについて

BackdropFilter にはプロパティが少しありますので、紹介します。

(new) BackdropFilter BackdropFilter({
  Key? key,
  required ImageFilter filter,
  Widget? child,
  BlendMode blendMode = BlendMode.srcOver,
})

①filter

子要素を描画する前に、描画済みのコンテンツに適用する画像フィルタを設定する
型は ImageFilter 型

②blendMode

フィルタリングされた背景コンテンツを背景表面に適用するために使用するブレンドモードを指定する
デフォルトは BlendMode.srcOver
型は BlendMode 型

最後に

今回は BackdropFilter を紹介しました。何かをぼかすことは有料会員でないと見れないページなどで使うことがあると思います。そんな画面を作りたいとき、BackdropFilter を知っていれば簡単にできるので、覚えておきたい widget ですね。気になる方は是非使ってみてください。
次は #25 Align です。またお会いしましょう。

参考記事

https://api.flutter.dev/flutter/widgets/BackdropFilter-class.html

Discussion