jptsetung
jptsetung

Reputation: 9156

Redraw CustomPaint without updating state / rebuilding widget?

I'm trying to understand how customPaint works, I want to draw a custom frame by frame animation on a canvas.

I can make it work by redrawing the widget every 1/60 seconds, but that doesn't sound very efficient. I would like render the CustomPainter every 1/60 seconds but that doesn't seem to work. Any note or remark very appreciated to help me understand how I'm supposed to achieve this. Thanks.

This is the kind of code I'm working with :

class CustomAnimatedWidgetState extends State<CustomAnimatedWidget> {

  CustomPaint _paint=null;
  MyCustomPainter _painter=null;

  double animationFrame=0;

  void tick() {   
    //called eery 1/60 seconds 
    animationFrame+=1/60;
    _painter.setAnimationFrame(animationFrame);
    _paint.METHOD_I_DONT_KNOW_TO_FORCE_REDRAW();
    // I want to avoid setState({animationFrame+=1/60;}); which works actually, but that doesn't sound very efficient to redraw the widget every 1/60 seconds, unless it's the right way to do it ?
  }


  @override
  Widget build(BuildContext context) {
    //developer.log('axis='+axis.toString(), name: 'DEBUG');


    _painter=MyCustomPainter();
    _painter.setAnimationFrame(animationFrame);

    _paint=CustomPaint(
      painter: _painter,
      child: Container(),
    );

    return _paint;
  }
}

Upvotes: 0

Views: 1784

Answers (1)

jptsetung
jptsetung

Reputation: 9156

Thx to @pskink for the hint in the comments, here is the working solution, using a ChangeNotifier when calling the constructor of the MyCustomPainter class.

class CustomAnimatedWidgetState extends State<CustomAnimatedWidget> {

  CustomPaint _paint=null;
  MyCustomPainter _painter=null;
  ChangeNotifier _repaint=ChangeNotifier();

  double animationFrame=0;

  void tick() {   
    //called eery 1/60 seconds 
    animationFrame+=1/60;
    _painter.setAnimationFrame(animationFrame);
    _repaint.notifyListeners();
  }


  @override
  Widget build(BuildContext context) {
    _painter=MyCustomPainter(repaint:_repaint);
    _painter.setAnimationFrame(animationFrame);

    _paint=CustomPaint(
      painter: _painter,
      child: Container(),
    );

    return _paint;
  }
}

Upvotes: 1

Related Questions