StateX — Story 4
This article of the series demonstrates the built-in FutureBuilder in the StateX class. As always, we use the example app that accompanies the state_extended package to demonstrate this. In this case, we’ve actually gone right back to the beginning of the example app to show how it starts up. A Flutter app begins from a Dart file containing the main() function. In many of my own apps, there’s literally a Dart file called, main, and that function is essentially the only thing found in it. See the screenshot below.
Ready Your Future
Please, stop and watch the little video below for a moment. I purposely slapped in a delay of 10 seconds to demonstrate a typical requirement of most Flutter apps when they first start up. More often than not, Flutter apps need some time before they’re ready for the user: Time to open up databases, log into servers, utilize web services, initialize third-party plugins, etc. In such cases, the state_extended package presents a circular progress indicator to the user at startup. That’s right — a FutureBuilder and circular progress indicator are built into the extended State object, StateX. It was such a common and essential capability in my own apps, I built them in. Fun!
Of course, if you don’t want to use it — don’t. However, being such a common requirement, I bet you will. The StateX class supplies the ready means to run ‘time-consuming’ operations in an asynchronous function called, initAsync(), It’s available to every State object extending the class. StateX. You’re welcome.
Of course, that means there’s then an initAsync() function in every controller linked to that StateX object as well. For example, in the second screenshot above, you can see that 10-second delay was implemented in the controller, AppController. We’ll now continue with further examples.
I Like Screenshots. Tap Caption For Gists.
As always, I prefer using screenshots in my articles over gists to show concepts rather than just show code. I find them easier to work with frankly. However, you can click or tap on their captions to see the code in a gist or in Github. Tap or click on the screenshots themselves to zoom in on them for a closer look.
No Moving Pictures, No Social Media
There will be gif files in this article demonstrating aspects of the topic at hand. However, it’s said viewing such gif files is not possible when reading this article on platforms like Instagram, Facebook, etc. They may come out as static pictures or simply blank placeholder boxes. Please, be aware of this and maybe read this article on medium.com
Build Your Child Widget
Of course, you’re free to override the build() function if you wish. However, using the buildChild() function instead will allow you to utilize the built-in FutureBuilder and InheritedWidget. Think of it as your screen is now the ‘child’ widget for a StateX object — don’t use the build() function and use the buildChild() function instead. The screenshot below of the state_extended source code shows how the FutureBuilder and subsequent InhertedWidget are currently implemented in the build() function.
As an example, in the _MyAppState class, we see its buildChild() function is implemented to take advantage of the built-in InheritedWidget and FutureBuilder. Uncomment the different ‘build’ functions to see the changes in functionality if you like.
In the ‘InheritedWidget example’, a selection of web services are called all at once to draw up photographs of animals from public API’s. A video below displays this example with each image being an independent StateX object with its own FutureBuilder. Thus, as you see in the video, each StateX object has a circular progress indicator running until its image has completed its download and is displayed — and this results by simply implementing a initAsync() function.
The first screenshot above is the StateX class again with the controller, ImageAPIController, being linked to it. Doing so, allows its initAsync() function to be later called (see the second screenshot above) and proceed to download an image from the Net.
In the first screenshot above, you see where the AppController object is introduced to the app by passing it as a parameter to the AppStateX class. In the last screenshot, you can see where a FutureWidget calls the AppStateX State object’s initAysnc() function, which in turn, calls that controller’s initAsync() function. See how this works? You can have anything in that initAsync() functions.
You can have any number of Controllers with their initAsync() functions being called, in turn, before the app is ready for the user. That’s demonstrated in the screenshot of the AppStateX class initAysnc() function below. A For-loop calls any and all suitable Controllers in turn before the app is ready for the user.
By the way, AppController object could have just as easily been introduced in that List with those other Controllers. I simply chose to use the named parameter, controller, as in many of my apps, the named parameter, controllers, is never used. However, that doesn’t mean it won’t be needed someday by other apps making it relatively convenient to introduce any number of Controllers — each deligated to supply any number of functions and features to your Flutter app. That’s what a framework is to do for you — provide options.
Last but not least, there’s the property, _dataObj, and is provided a value from the formal parameter, object. Inspired by the Scoped_Model framework with its Model class passed down the widget tree, this AppStateX class also allows for the property, _dataObj, to be made available throughout the app. Both this class and the Scoped Model use the same mechanism (InheritedWidget) to perform this. However, unlike the Scoped Model with its Model object, I wanted this class to accommodate the developer as much as possible, and so the property, _dataObj, is of type, Object, and is nullable. However, like the Scoped Model framework with its Model object available to every instance of its ScopedModelDescendant class, this object is available to every instance of the SetState() class as the parameter, dataObject.
I needed a framework to help build Flutter apps, but, as Dave Farley suggests, one that wouldn’t impede my code to fulfill the needs of each unique project. As it happens, I had to write one. Again, when writing the state_extended package, I worked to ‘keep it Flutter’ and implement these classes in a fashion readily recognized by a Flutter developer.
Again, it’s the package, fluttery_framework, but at its core is this package, and now you know why.