Open dxvid-pts opened 3 months ago
Do you use extendBodyBehindAppBar
on Scaffold? Can you share a complete sample code in a main.dart
file so that we can run and confirm this issue?
Here is a full code sample:
import 'dart:ui';
import 'package:flutter/material.dart';
void main() => runApp(const MyApp());
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
debugShowCheckedModeBanner: false,
home: const MyHomePage(),
);
}
}
class MyHomePage extends StatelessWidget {
const MyHomePage({
super.key,
});
@override
Widget build(BuildContext context) {
return Scaffold(
extendBodyBehindAppBar: true,
appBar: AppBar(
forceMaterialTransparency: true,
flexibleSpace: ClipRect(
child: BackdropFilter(
filter: ImageFilter.blur(sigmaX: 30, sigmaY: 30),
child: AnimatedContainer(
decoration: BoxDecoration(
border: Border(
bottom: BorderSide(color: Colors.black.withOpacity(0.09)),
),
color: Colors.white10,
),
duration: const Duration(milliseconds: 300),
),
),
),
title: Text("Title"),
),
body: SizedBox(
height: double.infinity,
width: double.infinity,
child: Image.network(
"https://fastly.picsum.photos/id/428/700/700.jpg?hmac=uGO0h-whSs6ScNzRZ4co4JfKP6otpf16kDrZ0qtEer8",
fit: BoxFit.cover,
),
),
);
}
}
Thanks for the update. It is replicable as reported on latest master version.
Also ran into this issue. @dxvid-pts I think your example is actually working on my Chrome, but I'm on 3.24.0-1.0.pre.542. That said, here's another test case that demonstrates:
void main() {
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Demo',
theme: ThemeData(
colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple),
useMaterial3: true,
),
home: const MyHomePage(title: 'Flutter Demo Home Page'),
);
}
}
class MyHomePage extends StatefulWidget {
const MyHomePage({super.key, required this.title});
final String title;
@override
State<MyHomePage> createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
@override
Widget build(BuildContext context) {
return _FilterTest(Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
DecoratedBox(
decoration: BoxDecoration(
border: Border.all(
color: Colors.red,
width: 2,
strokeAlign: BorderSide.strokeAlignOutside),
),
child: ClipRect(
child: BackdropFilter(
filter: ImageFilter.blur(sigmaX: 10, sigmaY: 10),
// ignore: sized_box_for_whitespace
child: Container(
height: 200,
width: 200,
),
),
),
),
const SizedBox(width: 8),
// Using a transparent color works
DecoratedBox(
decoration: BoxDecoration(
border: Border.all(
color: Colors.blue,
width: 2,
strokeAlign: BorderSide.strokeAlignOutside,
),
),
child: ClipRect(
child: BackdropFilter(
filter: ImageFilter.blur(sigmaX: 10, sigmaY: 10),
child: Container(
color: Colors.transparent,
height: 200,
width: 200,
),
),
),
),
],
));
}
}
// This is just a colorful backdrop
class _FilterTest extends StatelessWidget {
const _FilterTest(Widget child, {this.brightness = Brightness.light})
: _child = child;
final Brightness brightness;
final Widget _child;
@override
Widget build(BuildContext context) {
final Size size = MediaQuery.sizeOf(context);
final double tileHeight = size.height / 4;
final double tileWidth = size.width / 8;
return CupertinoApp(
home: Stack(fit: StackFit.expand, children: <Widget>[
// 512 color tiles
// 4 alpha levels (0.416, 0.25, 0.5, 0.75)
for (int a = 0; a < 4; a++)
for (int h = 0; h < 8; h++) // 8 hues
for (int s = 0; s < 4; s++) // 4 saturation levels
for (int b = 0; b < 4; b++) // 4 brightness levels
Positioned(
left: h * tileWidth + b * tileWidth / 4,
top: a * tileHeight + s * tileHeight / 4,
height: tileHeight,
width: tileWidth,
child: ColoredBox(
color: HSVColor.fromAHSV(
0.5 + a / 8,
h * 45,
0.5 + s / 8,
0.5 + b / 8,
).toColor(),
),
),
Padding(
padding: const EdgeInsets.all(32),
child: CupertinoTheme(
data: CupertinoThemeData(brightness: brightness),
child: _child,
),
),
]),
);
}
}
This only occurs when the BackdropFilter does not have a child that is painted. I'm not sure why this is.
I did some investigation on this, and it turns out there are two things causing this:
1) If the saveLayer operation has no pictures within it, we skip it entirely: https://github.com/flutter/engine/blob/4b7306dc7fd42463787b508dc23a14b17f13c53d/lib/web_ui/lib/src/engine/layers.dart#L774 We shouldn't do that, the operation should be applied anyway.
2) There is a skia issue where if the actual drawn contents of the layer that go on top of the backdrop filter are clipped out of the region of the canvas, the backdrop filter does not apply. I filed https://g-issues.skia.org/issues/362552959. Essentially the reason this happens in Skwasm and not CanvasKit is because Skwasm uses a SkBBHFactory
to let skia accurately calculate the bounds of the picture. In this case the picture is "empty" in that there is nothing drawn over the backdrop, but we still want the backdrop filter to apply. There are more nitty gritty details and minimal examples in the linked skia issue.
I fixed (1) here but the issue is still occurring until (2) is fixed (the skia issue).
Related: https://github.com/flutter/flutter/issues/154698 , which should be fixable once this issue is addressed.
Steps to reproduce
Use the provided
AppBar
. When targettingCanvasKit
everything works as expected. When compiling using--wasm
blur is not applied.Expected results (CanvasKit)
Actual results (WASM + skwasm)
Code sample
Code sample
```dart AppBar( forceMaterialTransparency: true, flexibleSpace: ClipRect( child: BackdropFilter( filter: ImageFilter.blur(sigmaX: 10, sigmaY: 10), ), ), ); ```Screenshots or Video
Screenshots / Video demonstration
[Upload media here]Logs
Logs
```console [Paste your logs here] ```Flutter Doctor output
Doctor output
```console [✓] Flutter (Channel master, 3.24.0-1.0.pre.197, on macOS 14.5 23F79 darwin-arm64, locale en-DE) [✓] Android toolchain - develop for Android devices (Android SDK version 34.0.0) [✓] Xcode - develop for iOS and macOS (Xcode 15.4) [✓] Chrome - develop for the web [✓] Android Studio (version 2023.3) [✓] Android Studio (version 2021.3) [✓] Android Studio (version 2022.2) [✓] VS Code (version 1.91.1) [✓] Connected device (3 available) [✓] Network resources • No issues found! ```