Flutter构建自定义Widgets的全过程记录

作者:伟雪无痕 时间:2022-01-27 16:37:39 

一.组合widget实现

1.android和flutter自定义控件对比

Android中,一般会继承View或已经存在的某个控件,然后覆盖draw方法来实现自定义View。在Flutter中,一个自定义widget通常是通过组合其它widget来实现的,而不是继承。下面看看如何构建持有一个label的CustomButton。这是通过将Text与RaisedButton组合来实现的,而不是继承RaisedButton并重写其绘制方法实现,eg :custombuttontest.dart

import 'package:flutter/material.dart';

class CustomButtonTest extends StatelessWidget{
 final String textStr;
 CustomButtonTest(this.textStr);

@override
 Widget build(BuildContext context) {
   return RaisedButton(
     onPressed: (){},
     child: Text(
       textStr,
       textAlign: TextAlign.center,
     )
   );
 }

}

上面定义好组件之后,可直接在调用build的方法中现实,eg :

@override
 Widget build(BuildContext context) {
   return new Center(
     child: new CustomButton("Custom Button"),
   );
 }
}

二.通过自定义CustomPainter实现widgets

1.CustomPainter主要属性介绍,和Android开发中的自定义View类似,Flutter中的绘制也是依靠Canvas和Paint来实现的

1).Canvas //画布,为开发者提供了点、线、矩形、圆形、嵌套矩形等绘制方法。

2).Paint //画笔,可以设置抗锯齿,画笔颜色,粗细,填充模式等属性,绘制时可以定义多个画笔以满足不同的绘制需求。eg:

Paint _paint = new Paint()
..color = Colors.red // 画笔颜色
..strokeCap = StrokeCap.round //画笔笔触类型,包括(1.round-画笔笔触呈半圆形轮廓开始和结束;2.butt-笔触开始和结束边缘平坦,没有外延;3.square-笔触开始和结束边缘平坦,向外延伸长度为画笔宽度的一半)
..isAntiAlias = true //是否启动抗锯齿
..style=PaintingStyle.fill //绘画风格,默认为填充,有fill和stroke两种
..blendMode=BlendMode.exclusion //颜色混合模式
..colorFilter=ColorFilter.mode(Colors.blueAccent, BlendMode.exclusion)//颜色渲染模式
..maskFilter=MaskFilter.blur(BlurStyle.inner, 3.0)//模糊遮罩效果
..filterQuality=FilterQuality.high//颜色渲染模式的质量
..strokeWidth = 15.0;//画笔的宽度复制代码

3).Offset //坐标,可以用来表示某个点在画布中的坐标位置。

4).Rect //矩形,在图形的绘制中,一般都是分区域绘制的,这个区域一般都是一个矩形,在绘制中通常使用Rect来存储绘制的位置信息。

5).坐标系 //在Flutter中,坐标系原点(0,0)位于左上角,X轴向右变大,Y轴向下变大。

2.painting.dart中的主要方法,eg:

void drawRect(Rect rect, Paint paint) {...} //画矩形
void drawLine(Offset p1, Offset p2, Paint paint) {...} //画线
void drawPoints(PointMode pointMode, List<Offset> points, Paint paint) {...} //画点
void drawCircle(Offset c, double radius, Paint paint) {...} //画圆
void drawArc(Rect rect, double startAngle, double sweepAngle, bool useCenter, Paint paint) {...} //画圆弧

三.饼状图piechart.dart代码展示

import 'dart:math';
import 'package:flutter/material.dart';

class PieChartTest extends StatelessWidget{
 const PieChartTest({Key? key}) : super(key: key);
 @override
 Widget build(BuildContext context) {
   return Scaffold(
     appBar: AppBar(
       title: const Text('pie chart'),
     ),
     body:Container(
       alignment: Alignment.center,
       child: CustomPaint(
         size: const Size(300, 300),
         painter: PieChartPainter(),
       ),
     )
   );
 }
}

class PieChartPainter extends CustomPainter{

Paint getColoredPaint(Color color){
   Paint paint=Paint();
   paint.color=color;
   return paint;
 }

@override
 void paint(Canvas canvas, Size size) {
   double wheelSize=min(size.width, size.height)/2;
   double nbElem=8;
   double radius=(2*pi)/nbElem;
   Rect boundingRect=Rect.fromCircle(center: Offset(wheelSize,wheelSize), radius: wheelSize);
   canvas.drawArc(boundingRect, 0, radius, true, getColoredPaint(Colors.orange));
   canvas.drawArc(boundingRect, radius, radius, true, getColoredPaint(Colors.black));
   canvas.drawArc(boundingRect, radius*2, radius, true, getColoredPaint(Colors.green));
   canvas.drawArc(boundingRect, radius*3, radius, true, getColoredPaint(Colors.red));
   canvas.drawArc(boundingRect, radius*4, radius, true, getColoredPaint(Colors.blue));
   canvas.drawArc(boundingRect, radius*5, radius, true, getColoredPaint(Colors.yellow));
   canvas.drawArc(boundingRect, radius*6, radius, true, getColoredPaint(Colors.purple));
   canvas.drawArc(boundingRect, radius*7, radius, true, getColoredPaint(Colors.white));
 }

@override
 bool shouldRepaint(covariant CustomPainter oldDelegate)=>oldDelegate!=this;
}

四.实际效果图,eg:

Flutter构建自定义Widgets的全过程记录

附:Flutter中父widget调用子widget的方法

一、定义globalKey,注意<>中的是State类。

final _childWidgetKey = GlobalKey();

二、在父页面初始化子widget

ChildPage(key:_receiveKey),

三、

class ChildPage extends StatefulWidget {undefined
ChildPage({Key key}) : super(key: key);
@override
ChildPageState createState() => ChildPageState();
}

四、在父界面调用子widget中的方法

_childWidgetKey.currentState.onRefresh();

来源:https://blog.csdn.net/j086924/article/details/122406209

标签:flutter,自定义,widgets
0
投稿

猜你喜欢

  • Java中一些关键字的使用技巧总结

    2023-11-19 02:48:49
  • 基于Java解决华为机试之字符串加解密 

    2022-10-12 17:32:39
  • C#集合之链表的用法

    2022-02-07 13:38:34
  • 关于Struts2文件上传与自定义拦截器

    2021-10-31 12:52:44
  • java编程下字符串的16位,32位md5加密实现方法

    2023-07-29 21:34:28
  • Java基于Socket实现HTTP下载客户端

    2022-07-06 01:02:30
  • C#中ref和out的区别浅析

    2021-12-22 23:00:50
  • C#获取Windows进程监听的TCP/UDP端口实例

    2021-11-20 13:06:21
  • Android 实现单线程轮循机制批量下载图片

    2022-11-05 11:03:45
  • C#类中static变量用法分析

    2022-06-20 16:14:23
  • Dockerfile 部署java web的环境详解

    2021-10-02 00:41:44
  • Spring Boot学习入门之AOP处理请求详解

    2023-11-27 10:55:17
  • 关于C#中的Invoke示例详解

    2023-06-20 10:17:14
  • SpringBoot解决Required String parameter xxx is not present问题

    2021-08-08 12:53:15
  • Android自定义view系列之99.99%实现QQ侧滑删除效果实例代码详解

    2022-05-08 15:35:55
  • c# winform时钟的实现代码

    2023-04-05 07:40:53
  • java实现字符串四则运算公式解析工具类的方法

    2021-11-03 09:22:23
  • Java如何实现List自定义排序

    2021-07-03 06:09:15
  • idea手动刷新git分支的详细教程

    2022-04-05 11:53:43
  • MybatisPlus #{param}和${param}的用法详解

    2023-02-02 13:08:10
  • asp之家 软件编程 m.aspxhome.com