Почему переменные класса Flutter CustomPainter не сохраняются
Во Flutter настраивается ли Custom Painter и все его переменные класса с нуля каждый раз, когда вызывается метод рисования? -- когда setState вызывается у родителя?? Я этого не ожидал, но, похоже, так оно и есть:
Я спрашиваю, потому что у меня есть Custom Painter, который содержит объект внутри метода рисования (последовательность точек), который является основой всех последующих эффектов рисования. Но... этот объект в первую очередь требует математики только для того, чтобы быть созданным... и ему требуются размеры холста как часть этого создания... вот почему он находится внутри метода рисования.
Итак... я подумал... вместо того, чтобы вычислять одну и ту же точную форму скелета каждый раз, когда вызывается краска, я сделаю ее переменной класса, допускающей значение NULL, и инициализирую ее один раз... а затем просто проверяю, является ли она нулевой каждый раз, когда вызывается краска. воссоздавать его каждый раз.
Я подумал, что лучше всего «по возможности вывести расчеты из метода рисования».
НО... неожиданный результат заключается в том, что когда я проверяю, Flutter всегда говорит, что мой объект равен нулю (в любом случае он каждый раз воссоздается).
Пользовательский художник:
import 'package:flutter/material.dart';
import 'dart:math';
class StackPainter02 extends CustomPainter {
final List<double> brightnessValues;
Paint backgroundPaint = Paint();
Paint segmentPaint = Paint();
List<Offset>? myShape;
StackPainter02({
required this.brightnessValues,
}) {
backgroundPaint.color = Colors.black;
backgroundPaint.style = PaintingStyle.fill;
segmentPaint.style = PaintingStyle.stroke;
}
@override
void paint(Canvas canvas, Size size) {
final W = size.width;
final H = size.height;
segmentPaint.strokeWidth = W / 100;
canvas.drawPaint(backgroundPaint);
// unfortunately, we must initialize this here because we need the view dimensions
if (myShape == null) {
myShape = _myShapePoints(brightnessValues.length, 0.8, W, H, Offset(W/2,H/2));
}
for (int i = 0; i<myShape!.length; i++) {
// bug fix... problem: using "i+1" results in index out-of-range on wrap-around
int modifiedIndexPlusOne = i;
if (modifiedIndexPlusOne == myShape!.length-1) {
modifiedIndexPlusOne = 0;
} else {
modifiedIndexPlusOne++;
}
// draw from point i to point i+1
Offset segmentStart = myShape![i];
Offset segmentEnd = myShape![modifiedIndexPlusOne];
double b = brightnessValues[i];
if (b < 0) {
b = 0; // !!!- temp debug... problem: brightness array algorithm is not perfect
}
int segmentAlpha = (255*b).toInt();
segmentPaint.color = Color.fromARGB(segmentAlpha, 255, 255, 200);
canvas.drawLine(segmentStart, segmentEnd, segmentPaint);
}
}
@override
bool shouldRepaint(covariant StackPainter02 oldDelegate) {
//return (oldDelegate.brightnessValues[32] != brightnessValues[32]); // nevermind
return true;
}
}
Метод сборки в родительском:
@override
Widget build(BuildContext context) {
return Scaffold(
body: SafeArea(
child: CustomPaint(
painter: //MyCustomPainter(val1: val1, val2: val2),
StackPainter02(
brightnessValues: brightnessValues,
),
size: Size.infinite,
),
),
);
}
PS - тикер используется в родительском элементе, а «brightnessValues» пересчитываются при каждом тике тикера -> setState