components flutter how to
Introducing TwicPics Flutter Widget
Streamline image delivery, improve performance, and enhance user experience in your Flutter app with TwicPics Flutter Widget.
Miguel Beignon June 27, 2023 · 10 min read
In this guide, we will explore the power and ease of use of TwicPics Flutter Widget.
As a reminder, Flutter is a widely used framework for developing stunning and high-performing cross-platform applications. It offers an extensive collection of widgets, including ones designed for displaying local or network images.
However, optimizing image loading times and adapting images to various device specifications is still a complex and time-consuming process.
TwicPics Flutter Widget comes to the rescue to address these challenges.
Following this guide, in less than 10 minutes, you'll be able to streamline the image delivery process, improve performance and enhance the overall user experience.
In less than 10 minutes you will be able to unleash the power of TwicPics in your Flutter Apps with features like:
- Image Caching and Compression
- Lazy Loading
- LQIP
- Pixel Perfect
- Smart Cropping
- Even more with TwicPics Transformations
Get your environnement ready
Before starting your first Flutter project, you will need to configure your working environment.
Here we'll be using Android Studio and a Nexus 6 API 28 emulator. You are of course free to use your favorite IDE
.
Create your Flutter App
Setup Wizard
# creates a new project using flutter cli
flutter create my_app
And that's it. Your project has been created.
All you have to do now is open your project in your favorite IDE
.
Start Flutter
Once the new project is open, choose your emulator and, from the terminal, run the command:
# runs flutter project
flutter run
This is what you should get:
Install and configure TwicPics Flutter Widget
Now that your Flutter App is up and running, it is time to configure TwicPics Flutter Widget.
https://demo.twic.pics
If you don't have a TwicPics domain yet, you can easily create your own for free.
Install TwicPics Flutter Widget
Add the twicpics_components
package to your Flutter project by running:
# adds twicpics_components as a package dependency
flutter pub add twicpics_components
If you want to find out more about using packages in your Flutter projects, follow this link.
Setting-up TwicPics Flutter Widget
The configuration of the TwicPics Flutter Widget must be done in main.dart
file.
Modify the file lib/main.dart
as follows:
// lib/main.dart
// others imports
import 'package:twicpics_components/twicpics_components.dart';
void main() {
install(
domain: "https://demo.twic.pics/", // set your very domain here
debug:true, // this will output useful logs to the terminal
);
runApp(const MyApp());
}
// file rest unchanged
The complete list of configuration options is available here.
TwicPics Flutter Widget
is now ready to be used and you can display your first image within your Flutter App.
Using TwicPics Widget
To display an image using TwicPics
, we just have to add TwicImg
widget to the existing tree.
Let's reopen lib/main.dart
and modify the build method of the _MyHomePageState
class as follows:
// lib/main.dart
...
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
backgroundColor: Theme.of(context).colorScheme.inversePrimary,
title: Text(widget.title),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
const Text(
'You have pushed the button this many times:',
),
Text(
'$_counter',
style: Theme.of(context).textTheme.headlineMedium,
),
// this is where we want to display our new image
TwicImg(
src: "components/N6MAA10816.jpg", // image we want to display
),
// testing CLS optimization
const Text(
'There should be no CLS by the way!!!',
),
],
),
),
floatingActionButton: FloatingActionButton(
onPressed: _incrementCounter,
tooltip: 'Increment',
child: const Icon(Icons.add),
), // This trailing comma makes auto-formatting nicer for build methods.
);
}
...
Here's what you should see now:
What happened here?
- We get a square image: this is the default behavior.
- The display area has been reserved: there is no CLS.
- We haven't defined a size for our image: it occupies the entire width of the area reserved for the widget.
This last point is crucial: TwicImg
widget does not expose any height or width properties. To control its size, you need to control the size of its container.
This is what we call the layout-driven pattern and we'll come back to this in the next paragraph.
Finally, if we look at the terminal, we find 2 interesting logs:
-
https://demo.twic.pics/components/N6MAA10816.jpg?twic=v1/cover=1000x1000/output=preview represents the preview image (the Low Quality version). This is the one displayed until the final version is actually loaded.
-
https://demo.twic.pics/components/N6MAA10816.jpg?twic=v1/cover=800x800 represents the final image. Here we have requested, loaded an displayed an 800 pixel x 800 pixel version of our master image.
Let's go a step further and try to modify the displayed size of our image.
The layout-driven pattern
Let's modify the build
method of the _MyHomePageState
class once again.
This time, we want to constrain the display width to 200 pixels:
// lib/main.dart
...
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
backgroundColor: Theme.of(context).colorScheme.inversePrimary,
title: Text(widget.title),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
const Text(
'You have pushed the button this many times:',
),
Text(
'$_counter',
style: Theme.of(context).textTheme.headlineMedium,
),
// this is where we want to display our new image
Center(
child: SizedBox(
width: 200, // constrains width to 200px
child: TwicImg(
src: "components/N6MAA10816.jpg", // image we want to display
),
),
),
// testing CLS optimization
const Text(
'There should be no CLS by the way!!!',
),
],
),
),
floatingActionButton: FloatingActionButton(
onPressed: _incrementCounter,
tooltip: 'Increment',
child: const Icon(Icons.add),
), // This trailing comma makes auto-formatting nicer for build methods.
);
}
...
This is what we get:
The image size has been modified, but why do we get the following request: https://demo.twic.pics/components/N6MAA10816.jpg?twic=v1/cover=400x400 ?
In fact, our Nexus6 screen has a value of dpr = 2
. That's why we don't load the 200 pixel variant as we might have expected.
Actually, it's good news. It means that TwicPics Flutter Widget manages the pixel density of the target device. We just have to focus on providing a high quality master image file.
What about smart cropping ?
So far, we've displayed square images. Let's take a look at the effect of the ratio
property.
In this case, we aim to present one image in a 2.35 aspect ratio and the other in a vertical orientation.
Let's make the following changes to our widget's build
method:
// lib/main.dart
...
@override
Widget build(BuildContext context) {
...
Center(
child: Padding( padding: const EdgeInsets.all(20),
child: TwicImg(
src: "components/N6MAA10816.jpg", // image we want to display
ratio: "2.35", // displays an image with aspect ratio = 2.35
),
),
),
const Text(
'There is no CLS here',
),
Center(
child: Padding( padding: const EdgeInsets.all(20),
child: SizedBox(
width: 200,
child: TwicImg(
src: "components/N6MAA10816.jpg", // image we want to display
ratio: "3/4", // displays an image with aspect ratio = 3/4
),
),
),
),
...
}
...
And this is the result:
What happened here ?
-
From the same master file, we obtain 2 variants, perfectly cropped and whose intrinsic size corresponds exactly to the size displayed.
-
2 display areas have been reserved in accordance with the aspect ratio requested: there is still no CLS.
-
Images come from the application cache.
Can we use TwicPics Api Transformation ?
The introduction to this guide mentioned the possibility of using TwicPics Transformations: it is "time to check it out".
Let's modify our build
method one last time, using the preTransform
property:
@override
Widget build(BuildContext context) {
...
Center(
child: Padding( padding: const EdgeInsets.all(20),
child: TwicImg(
src: "components/N6MAA10816.jpg", // image we want to display
ratio: "2.35", // displays an image with aspect ratio = 2.35
preTransform: "background=remove+pink", // removes background and adds a pink colored one
),
),
),
const Text(
'There is no CLS here',
),
Center(
child: Padding( padding: const EdgeInsets.all(20),
child: SizedBox(
width: 200,
child: TwicImg(
src: "components/N6MAA10816.jpg",
preTransform: "focus=60px55p/zoom=2.5", // change focus point + zooms into image
),
),
),
),
...
}
...
This is the result:
Here we have displayed 2 new variants of our master image.
These variants are the result of applying the requested transformations:
- https://demo.twic.pics/components/N6MAA10816.jpg?twic=v1/background=remove+pink/cover=700x298
- https://demo.twic.pics/components/N6MAA10816.jpg?twic=v1/focus=60px55p/zoom=2.5/cover=400x400
The various properties of TwicImg
provide quick access to the most common TwicPics Transformations.
But preTransform
unleashes the full power of TwicPics in your Flutter applications.
Conclusion
We've just discovered TwicPics Flutter Widget. We know how to integrate it into our Flutter
applications, and we've taken a quick tour of its features.
If you want to discover TwicImg
's other features, feel free to launch the example project from it's repository.
TwicPics Flutter Widget is free and open-source, as are TwicPics Components (the version adapted to the most popular JS frameworks). The only requirement to use them is to have a TwicPics account. If you don't already have one, you can easily create your own TwicPics account for free.
Finally, if you come across any problems, feel free to open an issue.