刚刚接一个电话,然后继续,下午时间都浪费在怎么研究下依赖了,先不管哪些,先挑能做的能学的学。用 Flutter 做一个画板。学习新技术有时候也就像一场赌博,大家到看好当然赢得概率就大,不过收益也被均摊。但是那些冷门技术一旦押对了,当然会收益匪浅。
import 'package:flutter/material.dart';
void main()=> runApp(MyApp());
class MyApp extends StatelessWidget{
@override
Widget build(BuildContext context) {
// TODO: implement build
return MaterialApp(
debugShowCheckedModeBanner: false,
title: 'custom painter',
theme: ThemeData(
primarySwatch: Colors.blue
),
home: MyHomePage(),
);
}
}
class MyHomePage extends StatefulWidget{
@override
State<StatefulWidget> createState() {
// TODO: implement createState
return null;
}
}
class _MyHomePageState extends State<MyHomePage>{
@override
Widget build(BuildContext context) {
// TODO: implement build
return Scaffold(
);
}
}
有两个方法要实现
class Draw extends CustomPainter{
@override
void paint(Canvas canvas, Size size) {
// TODO: implement paint
}
@override
bool shouldRepaint(CustomPainter oldDelegate) {
// TODO: implement shouldRepaint
return null;
}
}
Draw 继承了 CustomPainter 有两个方法需要实现
- paint 方法中我们可以通过使用 Canvas (画布)和 Size(画布的尺寸)来进行绘制图案
- shouldRepaint 决定我们是否要进行重新绘制画布,如果为返回值为 true 则将重新绘制。那么我们如何判断呢,方法提供了 CustomPainter 对象,这一个对象也就是上一次给画布绘制对象
void paint(Canvas canvas, Size size) {
// TODO: implement paint
final paint = Paint();
paint.color = Colors.blue;
var c = Offset(size.width/2,size.height/2);
canvas.drawCircle(c, 50, paint);
}
在上面代码中我们要画圆,首先就需要一个画笔或者叫喷枪,然后可以利用 canvas 给我们提供一些基本图形进行绘制,这里绘制出一个圆形。
- drawCircle 方法需要给一个圆形位置和大小来确定其结构(位置)paint 决定其样式
- Offset 对象是现对于左上角的偏移量。
var rect = Rect.fromLTWH(size.width/3, size.height/2, 120, 150);
paint.color = Colors.orange;
canvas.drawRect(rect, paint);
paint.color = Colors.lightGreenAccent;
paint.strokeWidth=10;
var p1 = Offset(0,500);
var p2 = Offset(size.width/2, 100);
canvas.drawLine(p1, p2, paint);
绘制一个随手势而动小圆
body: GestureDetector(
onPanUpdate: (DragUpdateDetails details){
setState(() {
RenderBox box = context.findRenderObject();
pos = box.globalToLocal(details.globalPosition);
});
},
child: Container(
child: CustomPaint(
painter: Draw(pos),
child: Container(),
),
),
),
);
- 在 body 的 child 属性上包裹一个监听手势的组件,
RenderBox box = context.findRenderObject();
pos = box.globalToLocal(details.globalPosition);
通过这两行代码可以获取手指在屏幕上移动的位置。
class Draw extends CustomPainter{
Draw(this.pos);
final Offset pos;
@override
void paint(Canvas canvas, Size size) {
// TODO: implement paint
final paint = Paint();
paint.color = Colors.blue;
canvas.drawCircle(pos, 30, paint);
}
@override
bool shouldRepaint(Draw oldDelegate) {
// TODO: implement shouldRepaint
return oldDelegate.pos != pos;
}
}
- 这里将 Draw 作为 shouldRepaint 参数的类型
- Draw 构造函数接受一个表示位置的 pos
- 通过判断位置是否改变来决定是否进行重新绘制