In this paper, the self-defined view of Flutter will be used to realize the curve statistics graph to learn some knowledge about the self-defined view, and to use the self-defined view more skillfully. The final result is shown below.

The text start

Basic use

If you want to use a custom view, you first create a class that extends from CustomPainter

class BaseLineChart extends CustomPainter { @override void paint(Canvas canvas, } @override bool shouldRepaint(CustomPainter oldDelegate) {return true; / / /true] allows redrawing}}Copy the code

Once built, you can use it as a normal Widget in CustomPaint

Container(
    child: CustomPaint(painter: BaseLineChart()),
)
Copy the code

Mapping rules

The drawing method is basically the same as the original drawing rules of Android. In the screen coordinate system, the upper left corner of the screen is taken as the origin, which is the positive axis of X axis to the right and the positive axis of Y axis to the bottom. As follows:

X
Y

Began to draw

Initialize brush

Set to a member variable

Paint painter = Paint().. StrokeWidth = 1.2.. style = PaintingStyle.stroke; TextPainter = textDirection (textDirection: textdirection. LTR, maxLines: 1,);Copy the code

Set the area and determine the width and height

Determine the proportion based on the width and height of the parent component, and specify the width and height of the drawing content to ensure the same proportion of different mobile phone screens.

@override void paint(Canvas Canvas, Size Size) {// [Size] specifies the Size of the parent component, and any content that exceeds the parent component is cut out. canvas.clipRect(rect); // Set the background color painter.color = colors.white; painter.style = PaintingStyle.fill; canvas.drawRect(rect, painter); // Set the width of the custom view according to the size of the parent component. yTextwidth = width / 7; unitWidth = (width - yTextwidth) / 4; . }Copy the code

Draw a background line

To draw a horizontal line, draw from left to right and top to bottom.

@override void paint(Canvas canvas, Size size) { ... Painter. StrokeWidth = 1.2; // Line width painter. Color = color (0xffEBECF0); [LINE_NUM] Specifies the number of line segmentsfor(int i = 0; i < LINE_NUM - 1; I++) {// drawLine('Starting point'.'Terminal coordinates') canvas.drawLine(Offset(yTextwidth, i * LINE_SPACE + Y_TEXT_HEIGHT), Offset(width, i * LINE_SPACE + Y_TEXT_HEIGHT), painter); } painter. StrokeWidth = 1.4; Color = color (0xffC4C6CF); DrawLine (Offset(yTextwidth, (LINE_NUM - 1) * LINE_SPACE + Y_TEXT_HEIGHT), Offset(width, (LINE_NUM - 1) * LINE_SPACE + Y_TEXT_HEIGHT), painter); . }Copy the code

Draw text,X,Y values, and title

Call textPainter. Paint (Canvas,’ start coordinate ‘) to draw the text. This method only has the start coordinate, which is the top left corner of the text.

@override void paint(Canvas canvas, Size size) { ... TextPainter. Text = TextSpan(text:'Text content', style: new TextStyle( color: Color(0xff303133), fontSize: S(20), ), ); textPainter.paint(canvas, Offset(0, 0)); // Y-axis textfor (int i = 0; i < LINE_NUM; i++) {
      textPainter.text = TextSpan(
        text: '${(LINE_NUM - i - 1) * 1000}'Style: new TextStyle(color: color.black, fontSize: S(24),); // This method is called to get the width and height of the text entered above. // Subtract textPainter. Width / 2,textPainter. Height / 2 to center textPainter. Offset((yTextwidth - textPainter.width) / 2, i * LINE_SPACE - textPainter.height / 2 + Y_TEXT_HEIGHT)); } double xTextWidth = width - yTextwidth; var temp = xTextWidth / 4; / / xfor (int i = 1; i < 5; i++) {
      textPainter.text = TextSpan(
        text: '$I month', style: new TextStyle( color: Colors.black, fontSize: 12, ), ); // This method is called to get the width and height of the text entered above. TextPainter. Paint (Canvas,getCurvePath(Offset(yTextwidth + temp * i-temp / 2 -) textPainter.width / 2, (LINE_NUM - 1) * LINE_SPACE + 6 + Y_TEXT_HEIGHT)); }... }Copy the code

Draw the curve

Get curvilinear coordinates

In flutter, lines can be drawn using Path to connect four known points, which is the basic broken line graph. However, to draw a smooth transition curve from point to point, another method is needed to obtain the coordinates of the curve. This method is the cosine function.

So before we do that, let’s remember what the cosine looks like.

All you need to plot is a curve between 0 and 2 PI.

Double v1, double v2, int index, double v1, double v2, int index, Path path) { int clipNum = 30; Double temp = 1 / clipNum; double temp = 1 / clipNum; // temporary value bool isNegativeNumber; Double diff = (v1 - v2).abs(); // isNegativeNumber = (v1 - v2) < 0; // Determine positive and negativefor(int i = 0; i < clipNum; I ++) {path.lineto (temp * I + index. ToDouble ()), // y = cos(v) + 1, // y = cos(v) + 1, IsNegativeNumber fortrue, the curve between π and 2π is usedfalse// Add to Path getY((cos((isNegativeNumber? pi : 0) + pi * temp * i) + 1) * diff / 2 + (isNegativeNumber ? v1 : v2))); } // return Pathreturnpath; } double getY(double value) => (MAX_VALUE - value)/MAX_VALUE * (LINE_NUM - 1) * LINE_SPACE + Y_TEXT_HEIGHT;  Double getX(double index) => yTextwidth + unitWidth / 2 + index * unitWidth;Copy the code

The above code is the method to get the coordinates of each point of the curve, and then draw the curve

draw

@override
void paint(Canvas canvas, Size size) {

    ...

   List<double> values = List();
    for(int i = 0; i < 4; I ++) {values.add(700.0 * I + 1000); } Path Path = Path(); // Add the curve path point to'Path'In the pathfor (int i = 0; i < values.length - 1; i++) {
      double v1 = values[i];
      double v2 = values[i + 1];
      if(i == 0) { path.moveTo(getX(i.toDouble()), getY(v1)); } path = getCurvePath(v1, v2, i, path); DrawPath (path, painter); drawPath(path, painter); path.close(); . }Copy the code

Complete the curve statistical drawing.

The last

This is the basic method of using the Flutter custom View. There are many details not shown here. Please download the complete code for more details.

The above is all content, if there are mistakes please correct. Welcome to reprint, comments.

Full code address article address