我一直在try 通过自己创建一个新的RenderObject来对堆栈中的子元素使用图像滤镜模糊.由于某些原因,我必须使用renderObject,所以我不能使用预构建的(Backdrop filter和ClipPath)小部件.
以下是代码:
import 'dart:ui';
import 'package:flutter/material.dart';
import 'package:flutter/rendering.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter image filter blur demo',
theme: ThemeData(
colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple),
useMaterial3: true,
),
home: const Demo(),
);
}
}
class Demo extends StatefulWidget {
const Demo({super.key});
@override
State<Demo> createState() => _DemoState();
}
class _DemoState extends State<Demo> {
Offset offset = Offset.zero;
@override
Widget build(BuildContext context) {
return Scaffold(
body: Stack(
children: [
// if i comment this it will clip the element
const Text("hello welcome to the demo of the backdrop blur"),
Positioned(
top: offset.dy,
left: offset.dx,
child: GestureDetector(
onPanUpdate: (d) {
setState(() {
offset += d.delta;
});
},
child: SizedBox(
width: 100,
height: 100,
child: Blur(
child: Container(
width: 100,
height: 100,
color: Colors.red.withOpacity(0.3),
)),
),
),
),
],
),
);
}
}
class Blur extends SingleChildRenderObjectWidget {
const Blur({
Key? key,
Widget? child,
}) : super(key: key, child: child);
@override
RenderObject createRenderObject(BuildContext context) {
return RenderBlur();
}
@override
void updateRenderObject(
BuildContext context, RenderBlur renderObject) {}
}
class RenderBlur extends RenderProxyBox {
@override
void paint(PaintingContext context, Offset offset) {
//paint child
context.paintChild(child!, offset);
final blurLayer = BackdropFilterLayer(
filter: ImageFilter.blur(sigmaX: 5, sigmaY: 5),
blendMode: BlendMode.srcOver,
);
final clipLayer = ClipPathLayer(
clipPath: Path()..addRect(offset & size),
);
context.addLayer(blurLayer);
context.addLayer(clipLayer);
// needs to `Path`
super.paint(context, offset);
}
}
通过对堆栈的第一个子级进行注释,它可以正常工作: