Flutter Riverpod Setting a Value Without Context

Viewed 3289

I have an app where a video uploading progress indicator needs to be shown on the Feed Screen. The code that returns the upload progress is in a Video Client Class that is not in the widget tree of the Feed Screen and the Feed Screen is not even open at the time the video starts uploading.

What I am trying to do is use Riverpod to update the upload value globally in the Video Client Class so when the Feed Screen is opened it shows the upload progress.

The problem is the Video Client is a seperate class without any build context and I am trying to update the value. I have heard Riverpod can set state without build context. But the only way I can see to update the state still requires context.

In the main function I add the provider scope here:

void main() {
  FlowRouter.setupRouter();
  runApp(ProviderScope(child: MyApp()));
}

I have a upload model that extends change notifier for updating the values:

class UploadModel extends ChangeNotifier{

  UploadModel();

  int _bytesTotal = 0;
  int _bytesUploaded = 0;
  bool _uploadVisible = false;
  
  void setBytesTotal(int value){
    _bytesTotal = value;
    notifyListeners();
  }
  int get getBytesTotal => _bytesTotal;
  
  void setBytesUploaded(int value){
    _bytesUploaded = value;
    notifyListeners();
  }
  int get getBytesUploaded => _bytesUploaded;
  
  void setUploadVisible(bool value){
    _uploadVisible = value;
    notifyListeners();
  }
  bool get getUploadVisible => _uploadVisible;
}

In the Feed Widget I have the following code to watch for and update the upload widget:

final uploadProvider = riverpod.ChangeNotifierProvider((ref) => UploadModel());

class  UploaderProgressWheel extends riverpod.ConsumerWidget {
  @override
  Widget build(BuildContext context, ScopedReader watch) {

    final uploadInfo = watch(uploadProvider);

    return Text(uploadInfo.getBytesUploaded.toString());
}

But then when I go to update the the upload values in the Video Client Class I can't see any way to do it without needing context, I think I need to add the provider in in the video client class again like this:

final uploadProvider = riverpod.ChangeNotifierProvider((ref) => UploadModel());

then I want to access set the value with setBytesUploaded() from the UploadModel class but I have no access to it and the only examples I have found are like below which requires context:

context.read(uploadProvider).state = 

Thanks

1 Answers
class VideoClient { //Example class
   final Reader read; //so you can read other providers inside this
   int _i = 0; //just for example

   VideoClient(this.read);

   void exampleMethod(){
     read(uploadProvider).setBytesUploaded(_i++);
     // each time this method is called a new int is sent to notify the uploadModel
   }

   //.... your methods
}

final VideoProvider = Provider((ref) => VideoClient(ref.read)); // to have a single instance of your VideoClient across all your app

And now when you want to upload a video or do something specific with your VideoClient you call this provider from anywhere in your app

RaisedButton(
  onTap: () {
    context.read(VideoProvider).upload(); //or whatever method you use to initilize an action
  }
);
Related