flutter download automatic image and save it in assets - flutter

in my app,I want to use SVG images from the asset file.
but I want to check them in-the app, if the image asset is different from my image network from the server, I download the image network and replace it in my image asset and again read it from the asset to show them.
how can I do that?
bool showSvg = false;
void compareSvg(){
if(value['svgimage']['name'] != Image.profileSvg){
// how download svg network and replace it to assetfile
}else{
showSvg = true; });}
and its my code example :
showSvg
?SvgPicture.asset(Image.profileSvg)
:SvgPicture.asset(Image.newProfileSvg),

You can not compare images (technically you can, but it very complicated task) and replace assets file. You need to cache you image after first downloading, and set your asset as placeholder before your image are downloaded. Look in to dock here.
Edited:
Okay. I don't get your answer about svg, but if true here solution
Add this pub for file caching to your project. And this code may help:
File? _downloaded;
void _fetchImage() async {
const key = "profile";
const url =
"http://upload.wikimedia.org/wikipedia/commons/0/02/SVG_logo.svg";
final file = await DefaultCacheManager().getSingleFile(url, key: key);
setState(() {
_downloaded = file;
});
}
Widget _svgImageFetcher() {
_fetchImage();
Widget networkSvg;
if (_downloaded == null) {
networkSvg = SvgPicture.asset("assets/images/profile.svg");
} else {
networkSvg = SvgPicture.file(_downloaded!);
}
return Column(children: [Expanded(child: networkSvg)]);
}
Just put _svgImageFetcher() Widget where you want to display image. And change default svg image and url.

Related

Loading assets dynamically with Flutter

I'm running a Flutter application with a list of products need to be displayed.
I've an asset folders (loaded in pubspec.yaml) which contains certain of my product images.
I wan't to show the image or a placeholder if not exists
Attempt one :
Image buildImg() {
var img = `assets/img/${product.id}.png`;
if(File(img).existsSync()){
return Image.asset(img);
}else{
return Image.asset('assets/img/placeholder.png');
}
}
Result: condition is always false
Attempt two :
Image buildImg() async {
try{
var img = rootBundle.load(`assets/img/${product.id}.png`);
return Image.memory(img.buffer.asUint8List());
}catch (_){
return Image.asset('assets/img/placeholder.png');
}
}
Result: Working but a lot of warns in terminal.
Is there a better way to dynamically load assets ? Thank's
the Image widget has an error builder which is called when the provided path is not valid,
simply use this code
Image.asset("image path.png" , errorBuilder: (context, error, stackTrace) => Image.asset('placeholder path.png'),),

flutter image picker reduce file size with provider and flutter_image_compress

I am using image picker to pick image from device(App) and after that stored that file in provider class like that.
File? _img;
get img=> _img;
void putbannerimg(File img) {
_img = img;
notifyListeners();
}
I found out that image picker does not compress png images, I tried compressing it with flutter_image_compress
compressFile() async {
final formservice = Provider.of<PostForm>(context, listen: false);
File file = formservice.bannerfile;
final result = await FlutterImageCompress.compressWithFile(
file.absolute.path,
quality: 54,
);
formservice.putbannerimg(File.fromRawPath(result!));
}
I tried this way And other multiple ways but getting different different errors I want to upload this file in firebase storage like this
var task = storageicon.putFile(formservice.iconfile);
please tell me where I am going wrong, without compress file all things are working fine
Edit: I found out that path should be a string how can I parse local code file in that
If you are using the "flutter_image_compress" package
You may have to use the compress function for files stored on the phone like this:
Future<File> testCompressAndGetFile(File file, String targetPath) async {
var result = await FlutterImageCompress.compressAndGetFile(
file.absolute.path, targetPath,
quality: 88,
rotate: 180,
);
print(file.lengthSync());
print(result.lengthSync());
return result;
}
"compressAndGetFile()" returns a file while "compressWithFile()" returns a Uint8List.
If i understand your last question right, you want to use an image built into your application by default.
For this, you have to open your "pubsepc.yaml", go to the "flutter:" mark and add "assets:" like so:
flutter:
assets:
- path
"path", in my example, describes a top level folder containing assets like pictures.
You can freely describe its name.

How to record a video with Camera Plugin in flutter?

I have this page where the camera is initialized and ready with a button that will record and stop the video, so I tried this :
FlatButton(
onPressed: () => {
!isRecording
? {
setState(() {
isRecording = true;
}),
cameraController.prepareForVideoRecording(),
cameraController.startVideoRecording('assets/Videos/test.mp4')
}
: cameraController.stopVideoRecording(),
},
............
but throws this error : nhandled Exception: CameraException(videoRecordingFailed, assets/Videos/test.mp4: open failed: ENOENT (No such file or directory)).
I don't understand, I don't want to open this file I want to save it there, Is there sth wrong with my code ?
In the new version, static method startRecordingVideo doesn't take any string parameter.
When you want to start the recording just see whether a video is already getting recorded, if not start
if (!_controller.value.isRecordingVideo) {
_controller.startVideoRecording();
}
and when you want to finish the recording you can call the static method stopVideoRecording() and it will give you a object of the class XFile, it will have the path to your video.
if (_controller.value.isRecordingVideo) {
XFile videoFile = await _controller.stopVideoRecording();
print(videoFile.path);//and there is more in this XFile object
}
This thing has worked for me. I am new to flutter please improve my answer if you know more.
You are trying to save a video in your assets folder which is not possible ,
What you need to do is to save to device locally either common folders like downloads or app directory.
Here is an example of how to go about it
dependencies:
path_provider:
Flutter plugin for getting commonly used locations on host platform
file systems, such as the temp and app data directories.
We will be saving the video to app directory.
We need to get the path to the directory where the file is or will be. Usually a file is put in the application's document directory, in the application's cache directory, or in the external storage directory. To get the path easily and reduce the chance of type, we can use PathProvider
Future<String> _startVideoRecording() async {
if (!controller.value.isInitialized) {
return null;
}
// Do nothing if a recording is on progress
if (controller.value.isRecordingVideo) {
return null;
}
//get storage path
final Directory appDirectory = await getApplicationDocumentsDirectory();
final String videoDirectory = '${appDirectory.path}/Videos';
await Directory(videoDirectory).create(recursive: true);
final String currentTime = DateTime.now().millisecondsSinceEpoch.toString();
final String filePath = '$videoDirectory/${currentTime}.mp4';
try {
await controller.startVideoRecording(filePath);
videoPath = filePath;
} on CameraException catch (e) {
_showCameraException(e);
return null;
}
//gives you path of where the video was stored
return filePath;
}

Store image uploaded by user into Flutter Web as an actual .jpg file

I am using the flutter_web_image_picker package to allow the user to select -and then upload to Firebase- an image.
However, the package returns an image widget, which I can display, but I cannot upload to Firebase. Therefore, I am trying to read the package's code and update it to fit my needs.
In general, I think the packages main functionalities are:
It gets the file
//...
final reader = html.FileReader();
reader.readAsDataUrl(input.files[0]);
await reader.onLoad.first;
final encoded = reader.result as String;
Then it 'strippes' it
final stripped = encoded.replaceFirst(RegExp(r'data:image/[^;]+;base64,'), '');
final imageName = input.files?.first?.name;
//...
To finally return it as a Widget:
final imageName = imageName;
final imageData = base64.decode(stripped);
return Image.memory(imageData, semanticLabel: imageName);
As I said, it works perfectly, however, I need to adapt it to my needs:
I would like to get the image as a .jpg file so that I can upload it to Firebase.
Is any of the variables above the actual .jpg file? Is there any transformation that I should perform to get a .jpg file?
Thanks!
I based my answer on this post.
Basically, on the flutter_web_image_picker package, before the code I posted, there were a few lines that get an actual html file:
final html.FileUploadInputElement input = html.FileUploadInputElement();
input..accept = 'image/*';
input.click();
await input.onChange.first;
if (input.files.isEmpty) return null;
Then using firebase's pacakge, I uploaded the image as follow:
import 'package:firebase/firebase.dart' as fb;
fb.StorageReference storageRef = fb.storage().ref('myLocation/filename.jpg');
fb.UploadTaskSnapshot uploadTaskSnapshot = await storageRef.put(input.files[0]).future;
Uri imageUri = await uploadTaskSnapshot.ref.getDownloadURL();
return imageUri;

where do I need to store photo images in Flutter App?

I have an app that takes a photo.
I need that photo to be stored where all my assets/images/photos are.
So basically my question is :
a) how can I find the path where these assets are (on the phone)?
b) how can I add files to that same path?
Thanks
As per my knowledge you can not store image in assets package. Just because of when we build android/ios app after that assets folder is read only.
You need to store image in local mobile storage OR cloud OR catch memory
1) You can get storage path using :
Future<String> getStorageDirectory() async {
if (Platform.isAndroid) {
return (await getExternalStorageDirectory()).path; // OR return "/storage/emulated/0/Download";
} else {
return (await getApplicationDocumentsDirectory()).path;
}
}
2) Add image in path
createImage() async{
String dir= getStorageDirectory();
File directory = new File("$dir");
if (directory.exists() != true) {
directory.create();
}
File file = new File('$directory/image.jpeg');
var newFile = await file.writeAsBytes(/* image bytes*/);
await newFile.create();
}