Flutter撕裂效果插件tornpaper的使用
Flutter撕裂效果插件tornpaper的使用
TornPaper
是一个用于 Flutter 的容器组件,可以使其看起来像是一张可能被撕裂过的纸。以下是该插件的使用方法。
使用
TornPaper(
key: UniqueKey(),
backgroundColor: backgroundColor,
hasNoise: hasNoise,
noiseColor: noiseColor,
hasBorder: hasBorder,
tornWidth: tornWidth,
tornColor: tornColor,
tornDeepness: tornDeepness,
seed: seedValue.toInt(),
stepWidth: stepWidth,
hasShadow: hasShadow,
shadowColor: shadowColor,
shadowOffset: Offset(shadowOffsetBottom.toDouble(), shadowOffsetRight.toDouble()),
tornedSides: [
if (tornedTop) TornedSide.top,
if (tornedRight) TornedSide.right,
if (tornedLeft) TornedSide.left,
if (tornedBottom) TornedSide.bottom
],
child: [...child...]
)
大多数参数都很好理解,但有些参数可能需要解释一下:
参数说明
- seed: 随机种子,用于生成随机撕裂效果。
- tornWidth: 撕裂宽度。
- tornDeepness: 撕裂深度。
- stepWidth: 撕裂步长。
这些参数会影响撕裂效果的外观。
完整示例
以下是一个完整的示例,展示了如何使用 TornPaper
组件并调整其参数。
import 'package:flutter/material.dart';
import 'package:flutter_colorpicker/flutter_colorpicker.dart';
import 'package:tornpaper/tornpaper.dart';
void main() {
runApp(MyApp());
}
/// Example App
class MyApp extends StatelessWidget {
[@override](/user/override)
Widget build(BuildContext context) {
return MaterialApp(
title: 'Tornpaper Example',
theme: ThemeData(
primarySwatch: Colors.green,
),
home: MyHomePage(title: 'Tornpaper Example'),
);
}
}
/// Example Mainpage
class MyHomePage extends StatefulWidget {
/// Constructor
MyHomePage({Key? key, required this.title}) : super(key: key);
/// Example title
final String title;
[@override](/user/override)
_MyHomePageState createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
// 设置初始值
bool tornedTop = true;
bool tornedBottom = true;
bool tornedLeft = true;
bool tornedRight = true;
bool hasBorder = true;
Color tornColor = Colors.black;
double tornDeepness = 5.0;
double seedValue = 200;
int stepWidth = 8;
double tornWidth = 1.0;
Color backgroundColor = const Color.fromRGBO(215, 215, 160, 1.0);
bool hasNoise = false;
Color noiseColor = Colors.white;
bool hasShadow = true;
Color shadowColor = Colors.black;
int shadowOffsetBottom = 8;
int shadowOffsetRight = 8;
void changeShadowColor(Color color) {
setState(() => shadowColor = color);
}
[@override](/user/override)
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text(widget.title),
),
body: Container(
color: Colors.green,
child: Center(
child: Padding(
padding: const EdgeInsets.all(50.0),
child: SizedBox.expand(
child: Stack(
children: [
TornPaper(
key: UniqueKey(),
backgroundColor: backgroundColor,
hasNoise: hasNoise,
noiseColor: noiseColor,
hasBorder: hasBorder,
tornWidth: tornWidth,
tornColor: tornColor,
tornDeepness: tornDeepness,
seed: seedValue.toInt(),
stepWidth: stepWidth,
hasShadow: hasShadow,
shadowColor: shadowColor,
shadowOffset: Offset(shadowOffsetBottom.toDouble(), shadowOffsetRight.toDouble()),
tornedSides: [
if (tornedTop) TornedSide.top,
if (tornedRight) TornedSide.right,
if (tornedLeft) TornedSide.left,
if (tornedBottom) TornedSide.bottom
],
child: Container()),
Container(
child: Padding(
padding: const EdgeInsets.all(8.0),
child: SingleChildScrollView(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
const Text(
"TornPaper - Settings",
style: TextStyle(fontWeight: FontWeight.bold, fontSize: 30),
),
Row(
children: const [
const Text("Torned Sides"),
],
),
Row(
children: [
Checkbox(
value: tornedTop,
onChanged: (bool? value) {
setState(() {
tornedTop = value!;
});
},
),
const Text("Top"),
],
),
Row(
children: [
Checkbox(
value: tornedBottom,
onChanged: (bool? value) {
setState(() {
tornedBottom = value!;
});
},
),
const Text("Bottom"),
],
),
Row(
children: [
Checkbox(
value: tornedLeft,
onChanged: (bool? value) {
setState(() {
tornedLeft = value!;
});
},
),
const Text("Left"),
],
),
Row(
children: [
Checkbox(
value: tornedRight,
onChanged: (bool? value) {
setState(() {
tornedRight = value!;
});
},
),
const Text("Right"),
],
),
Row(
children: [
const Text("Torn StepWidth"),
Slider(
value: stepWidth.toDouble(),
min: 1,
max: 50,
divisions: 49,
label: stepWidth.round().toString(),
onChanged: (double value) {
setState(() {
stepWidth = value.toInt();
});
},
),
],
),
Row(
children: [
const Text("Torn Deepness"),
Slider(
value: tornDeepness.toDouble(),
min: 0,
max: 20,
divisions: 200,
label: tornDeepness.toStringAsFixed(2),
onChanged: (double value) {
setState(() {
tornDeepness = value;
});
},
),
],
),
Row(
children: [
Checkbox(
value: hasBorder,
onChanged: (bool? value) {
setState(() {
hasBorder = value!;
});
},
),
const Text("Has Border "),
],
),
Padding(
padding: const EdgeInsets.only(left: 30.0),
child: Row(
children: [
const Text("Border Color "),
IconButton(
icon: const Icon(Icons.color_lens),
color: tornColor,
onPressed: !hasBorder
? null
: () => showShadowColorDialog(
context,
tornColor,
(color) => setState(() => tornColor = color)))
],
),
),
Padding(
padding: const EdgeInsets.only(left: 30.0),
child: Row(
children: [
const Text("Torn width"),
Slider(
value: tornWidth.toDouble(),
min: 0.1,
max: 10.0,
divisions: 99,
label: tornWidth.round().toString(),
onChanged: (double value) {
setState(() {
tornWidth = value;
});
},
),
],
),
),
Row(
children: [
const Text("Seed"),
Slider(
value: seedValue.toDouble(),
min: 0,
max: 1000,
divisions: 500,
label: seedValue.round().toString(),
onChanged: (double value) {
setState(() {
seedValue = value;
});
},
),
],
),
Row(
children: [
const Text("Background Color "),
IconButton(
icon: const Icon(Icons.color_lens),
color: Colors.black,
onPressed: () => showShadowColorDialog(
context,
backgroundColor,
(color) => setState(() => backgroundColor = color)))
],
),
Row(
children: [
Checkbox(
value: hasShadow,
onChanged: (bool? value) {
setState(() {
hasShadow = value!;
});
},
),
const Text("Has Shadow"),
],
),
Padding(
padding: const EdgeInsets.only(left: 30.0),
child: Row(
children: [
const Text("Shadow Color "),
IconButton(
icon: const Icon(Icons.color_lens),
color: shadowColor,
onPressed: hasShadow
? () => showShadowColorDialog(
context,
shadowColor,
(color) => setState(() => shadowColor = color))
: null)
],
),
),
Padding(
padding: const EdgeInsets.only(left: 30.0),
child: Row(
children: [
const Text("Shadow Offset "),
Column(
children: [
Slider(
value: shadowOffsetBottom.toDouble(),
min: -100,
max: 100,
divisions: 200,
label: shadowOffsetBottom.round().toString(),
onChanged: (double value) {
setState(() {
shadowOffsetBottom = value.toInt();
});
},
),
Slider(
value: shadowOffsetRight.toDouble(),
min: -100,
max: 100,
divisions: 200,
label: shadowOffsetRight.round().toString(),
onChanged: (double value) {
setState(() {
shadowOffsetRight = value.toInt();
});
},
),
],
),
],
),
),
const Divider(),
const Text("Experimental"),
Row(
children: [
Checkbox(
value: hasNoise,
onChanged: (bool? value) {
setState(() {
hasNoise = value!;
});
},
),
const Text("Has Noise"),
IconButton(
icon: const Icon(Icons.color_lens),
color: noiseColor,
onPressed: () => showShadowColorDialog(
context,
noiseColor,
(color) => setState(() => noiseColor = color))),
const Text("Warning: Extremely unperformant!"),
],
),
],
),
),
),
),
],
),
),
),
),
),
);
}
void showShadowColorDialog(
BuildContext context, Color color, Function(Color color) setColor) {
showDialog(
context: context,
builder: (context) => AlertDialog(
title: const Text('Pick a color!'),
content: SingleChildScrollView(
child: Column(
children: [
ColorPicker(
pickerColor: color,
onColorChanged: setColor,
showLabel: true,
pickerAreaHeightPercent: 0.8,
),
Row(
children: [
const Spacer(),
ElevatedButton(
onPressed: () {
setState(() {
Navigator.of(context).pop();
});
},
child: const Text("OK"))
],
)
],
),
),
),
);
}
}
更多关于Flutter撕裂效果插件tornpaper的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html
1 回复
更多关于Flutter撕裂效果插件tornpaper的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html
当然,关于Flutter中的撕裂效果插件tornpaper
的使用,这里提供一个基本的代码案例来展示如何实现撕裂效果。首先,你需要确保你的Flutter项目中已经添加了tornpaper
依赖。
第一步:添加依赖
在你的pubspec.yaml
文件中添加以下依赖:
dependencies:
flutter:
sdk: flutter
tornpaper: ^最新版本号 # 请替换为实际的最新版本号
然后运行flutter pub get
来安装依赖。
第二步:使用TornPaper插件
下面是一个简单的示例代码,展示了如何在Flutter应用中使用tornpaper
插件来创建撕裂效果。
import 'package:flutter/material.dart';
import 'package:tornpaper/tornpaper.dart';
void main() {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Flutter Torn Paper Effect',
theme: ThemeData(
primarySwatch: Colors.blue,
),
home: TornPaperEffectScreen(),
);
}
}
class TornPaperEffectScreen extends StatefulWidget {
@override
_TornPaperEffectScreenState createState() => _TornPaperEffectScreenState();
}
class _TornPaperEffectScreenState extends State<TornPaperEffectScreen> with SingleTickerProviderStateMixin {
late AnimationController _controller;
late Animation<double> _animation;
@override
void initState() {
super.initState();
_controller = AnimationController(
duration: const Duration(seconds: 2),
vsync: this,
)..repeat(reverse: true);
_animation = Tween<double>(begin: 0, end: 1).animate(_controller);
}
@override
void dispose() {
_controller.dispose();
super.dispose();
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text('Torn Paper Effect'),
),
body: Center(
child: AnimatedBuilder(
animation: _animation,
child: Container(
width: 300,
height: 300,
color: Colors.white,
child: Center(
child: Text(
'Flutter',
style: TextStyle(fontSize: 24, color: Colors.black),
),
),
),
builder: (context, child) {
return TornPaper(
child: child!,
tearStrength: _animation.value, // 调整撕裂强度
seed: 12345, // 随机种子,确保撕裂效果一致
);
},
),
),
);
}
}
解释
- 依赖添加:确保在
pubspec.yaml
中添加了tornpaper
依赖。 - 动画控制:使用
AnimationController
和Tween
来控制撕裂效果的强度。在这个例子中,撕裂强度随着动画的值变化而变化。 - TornPaper组件:
TornPaper
组件接收一个子组件(在这里是一个包含文本的容器),并通过tearStrength
属性控制撕裂效果的强度。seed
属性用于确保每次运行应用时撕裂效果的一致性。
注意事项
tornpaper
插件可能在不同版本的Flutter上表现略有不同,确保使用与你的Flutter SDK版本兼容的插件版本。- 撕裂效果的性能可能会受到子组件复杂度和撕裂强度的影响,因此在实际应用中可能需要进行性能优化。
通过上述代码,你可以在Flutter应用中实现一个简单的撕裂效果。根据实际需求,你可以进一步调整动画参数和撕裂效果的属性。