I have created a simple note app using Hive, the app works perfectly on the emulator but after building the app with flutter build apk --release and installing it on my android device I face this problem :
if I choose an image from the gallery everything works normally ✔️
When I try to pick an image from the camera then it doesn't work ✖️
After trying to access the camera then also accessing the gallery stop working ✖️.
This is a screenshot from my mobile : screenshot_from_app
this is the code where I'm accessing the camera and gallery :
//Camera Functions
//Phot from Camera
getImageCamera() async {
final pickedimage =
await ImagePicker.platform.getImage(source: ImageSource.camera);
if (pickedimage != null) {
setState(() {
_image = File(pickedimage.path);
});
Navigator.of(context).pop();
}
}
//Photo From the gallery
getImageGallery() async {
final pickedimage =
await ImagePicker.platform.getImage(source: ImageSource.gallery);
if (pickedimage != null) {
setState(() {
_image = File(pickedimage.path);
});
Navigator.of(context).pop();
}
}
//AlertDialog Appear when pressing add phot buttom
showBottomSheet(context) {
return showDialog(
context: context,
builder: (context) {
return AlertDialog(
title: const Text(
"Choose photo from",
style: TextStyle(fontWeight: FontWeight.bold),
),
actions: [
IconButton(
onPressed: () async {
await getImageCamera();
},
icon: const Icon(Icons.photo_camera),
),
IconButton(
onPressed: () async {
await getImageGallery();
},
icon: const Icon(Icons.image),
)
],
);
},
);
}
//End Camera Function
it seems you didn't add permissions read about this package and
Add this to pubspec.yaml File:
dependencies:
permission_handler: ^9.1.0
i fixed my problem by adding this permission
<uses-permission android:name="com.google.android.providers.gsf.permission.READ_GSERVICES" />
Related
I am trying to download a file from the server using flutter. It was working perfectly but I uninstalled app from the android emulator and now it is not asking for the permission and generating the following error.
Unhandled Exception: FileSystemException: Cannot create file, path = '/storage/emulated/0/Download/Salary-Sheet.xlsx'
code
Future<bool> getStoragePermission() async {
return await Permission.storage.request().isGranted;
}
Future<String> getDownloadPath() async {
return await ExternalPath.getExternalStoragePublicDirectory(
ExternalPath.DIRECTORY_DOWNLOADS);
}
downloaddd(String downloadPath) async {
var path = '$downloadPath/Salary-Sheet.xlsx';
String url =
"http://salary/export/${widget.masterID}";
await dio.download(url, path, onReceiveProgress: (received, total) {
if (total != -1) {
Navigator.pop(context);
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(
behavior: SnackBarBehavior.floating,
content: Row(
children: const [
Icon(Icons.cloud_download),
SizedBox(
width: 10,
),
Text("Salary sheet has been downloaded !"),
],
),
),
);
//you can build progressbar feature too
}
});
}
doDownloadFile() async {
if (await getStoragePermission()) {
String downloadDirectory = await getDownloadPath();
await downloaddd(downloadDirectory);
}
}
Please check the emulator path again.
you also follow this question
Flutter - save file to download folder - downloads_path_provider
I am using ImagePicker in a flutter app, but we should specify the source of the Image.
How can I let the choice to the user?
File? selectedImage;
getImage() async {
XFile? file = await ImagePicker().pickImage(source: ImageSource.camera);
selectedImage = File(file!.path);
setState(() {});
}
You can show a dialog for to choose option.
getImage() async {
bool? isCamera = await showDialog(
context: context,
builder: (context) => AlertDialog(
content: Column(
mainAxisSize: MainAxisSize.min,
children: [
ElevatedButton(
onPressed: () {
Navigator.of(context).pop(true);
},
child: Text("Camera"),
),
SizedBox(
height: 20,
),
ElevatedButton(
onPressed: () {
Navigator.of(context).pop(false);
},
child: Text("gallery "),
),
],
),
),
);
if (isCamera == null) return;
XFile? file = await ImagePicker()
.pickImage(source: isCamera ? ImageSource.camera : ImageSource.gallery);
selectedImage = File(file!.path);
setState(() {});
}
You need to make two Text one for gallery and one for Camera and on thier onTap() you should pass a function which will be like
void imageGalleryBottomSheet(
{BuildContext context,
VoidCallback onCameraTap,
VoidCallback onGalleryTap}) {
//your code logic
}
The sdk that I use is as follows.
sdk: ">=2.7.0 <3.0.0"
image_picker: ^0.6.7
image_picker_for_web: ^0.1.0
firebase_storage: ^3.1.6
cloud_firestore: ^0.13.7
When uploading an image to storage, I try to reduce the size of the image file.
And this is the code for image upload.
import 'package:image_picker/image_picker.dart';
import 'package:firebase/firebase.dart' as fb;
import 'package:omd_test/widget/custom_loading.dart';
class TestScreen extends StatefulWidget {
#override
State<TestScreen> createState() => _TestScreenState();
}
class _TestScreenState extends State<TestScreen> {
PickedFile _image;
String imageUrl;
#override
Widget build(BuildContext context) {
return SafeArea(
child: Padding(
padding: const EdgeInsets.all(8.0),
child: Scaffold(
appBar: AppBar(
title: Text("TEST"),
),
body: Padding(
padding: const EdgeInsets.all(12.0),
child: Column(
children: [
Container(
width: 200,
height: 200,
child: _image == null
? Container()
: Image.network(
_image.path,
)),
TextButton(
onPressed: () {
_getImagesPicker();
},
child: Text(
"Pick",
style: TextStyle(color: Colors.black),
)),
SizedBox(
height: 20,
),
TextButton(
onPressed: () async {
if (_image != null) {
await imageUpload(_image);
setState(() {
_image = null;
});
} else
print("No Image");
},
child: Text(
"Upload"
)),
],
),
),
),
),
);
}
Future<void> _getImagesPicker() async {
try {
final _imagePath = await ImagePicker().getImage(
source: ImageSource.gallery,
imageQuality: 10,
maxHeight: 50,
maxWidth: 50
);
setState(() {
_image = _imagePath;
});
} catch (err) {
print(err);
}
}
Future<String> imageUpload(PickedFile image) async {
var bytes = await image.readAsBytes();
fb.StorageReference _storage =
fb.storage().ref('testScreen/${image.path}.jpg');
fb.UploadTaskSnapshot uploadTaskSnapshot = await _storage
.put(bytes, fb.UploadMetadata(contentType: 'image/png'))
.future;
var imageUri = await uploadTaskSnapshot.ref.getDownloadURL();
imageUrl = imageUri.toString();
return imageUrl;
}
}
I tested by changing the value of 'imageQuality' of ImagePicker, but when uploaded to storage, all image files were the same size.
enter image description here
Can I know what the problem is?
Is it a problem to upload to storage?
Thank you.
From the image_picker repository, there's some inconsistency in what adjustments can be made to what type of images.
Here's an overview that might give some important lead.
Can I know what the problem is?
The comments in the actual implementation of the package has some lines[here]:
//Note that the `maxWidth`, `maxHeight` and `imageQuality` arguments are not supported on the web. If any of these arguments is supplied, it'll be silently ignored by the web version of the plugin.
However, there's still an implementation of the resizing of a selected image though.
Is it a problem to upload to storage?
Seemingly no.
Here's what you may wish to try going forward; run your app on other platforms and try to establish if the image is resized, this will help you single out if it's only on the web that the quality is not being adjusted.
If you establish this to be so, you may wish to have your own implementation of quality/size adjustment of the picked media, you can utilise kIsWeb boolean property to determine if it's web, then apply your own implementation.
if(kIsWeb){
//Adjust quality/size
}else{
//use the already adjusted media
}
Note this comment as well:
//Compression is only supported for certain image types such as JPEG and on Android PNG and WebP, too. If compression is not supported for the image that is picked, a warning message will be logged.
I am coding a plant species recognition app. App takes image from gallery and predict the plant species. So i should pick image from gallery and show the accuracy score.
I did everything exactly the same from the flutter machine learning book but app doesnt show the picked image and accuracy score. I pick image from gallery but it still says "no image selected".
If i delete these lines, i can pick the image from gallery and show on the screen. But then i cant apply AI operations.
await analyzeTFLite();
await recognizeImage(File(image.path));
Screen should be as first pic. But mine is as second pic. The whole code is below. Thanks for your help.
import 'dart:io';
import 'package:tflite/tflite.dart';
import 'package:flutter/material.dart';
import 'package:image_picker/image_picker.dart';
class PlantSpeciesRecognition extends StatefulWidget {
var model;
PlantSpeciesRecognition(this.model);
#override
_PlantSpeciesRecognitionState createState() =>
_PlantSpeciesRecognitionState();
}
class _PlantSpeciesRecognitionState extends State<PlantSpeciesRecognition> {
File _image;
bool _busy = false;
List _recognitions;
Future chooseImageGallery() async {
debugPrint("choose image function");
var image = await ImagePicker().getImage(source: ImageSource.gallery);
//var image = await ImagePicker.pickImage(source: ImageSource.gallery);
if (image == null) {
debugPrint("choose image if");
return;
}
setState(() {
_busy = true;
});
await analyzeTFLite();
await recognizeImage(File(image.path));
setState(() {
debugPrint("choose image set state");
_busy = false;
//_image = image as File;
_image = File(image.path);
});
}
Future analyzeTFLite() async {
Tflite.close();
String res = await Tflite.loadModel(
model: "assets/model.tflite",
labels: "assets/labels.txt"
);
print('Model Loaded: $res');}
Future recognizeImage(File image) async{
var recognitions = await Tflite.runModelOnImage(path: _image.path);
setState(() {
_recognitions = recognitions;
});
print("Recognition Result: $_recognitions");
}
#override
Widget build(BuildContext context) {
List<Widget> stackChildren = [];
Size size = MediaQuery.of(context).size;
stackChildren.clear();
stackChildren.add(Positioned(
top: 0.0,
left: 0.0,
width: size.width,
child: _image == null
? Center(child: Text("No Image Selected"))
: Image.file(_image),
));
stackChildren.add(Center(
child: Column(
children: _recognitions != null
? _recognitions.map((res) {
return Text(
"${res["label"]}: ${res["confidence"].toStringAsFixed(3)}",
style: TextStyle(
color: Colors.black,
fontSize: 20.0,
background: Paint()
..color = Colors.white,
),
);
}).toList() : [],
),
));
return Scaffold(
appBar: AppBar(
title: const Text('Plant Species Recognition'),
),
floatingActionButton: FloatingActionButton(
onPressed: chooseImageGallery,
tooltip: 'Pick Image',
child: Icon(Icons.image),
),
body: Stack(
children: stackChildren,
),
);
}
}
Am working on a project that I was suppose to finished by next week latest, but am facing issue of not redirecting to destined page in flutter google and firebase sign up/sign in.
Here's my dependencies version:
google_sign_in: ^4.0.14
cloud_firestore: ^0.12.11
fluttertoast: ^3.1.3
shared_preferences: ^0.4.3
Here's my login code logic.
import 'package:shared_preferences/shared_preferences.dart';
import 'package:fluttertoast/fluttertoast.dart';
import 'package:firebase_auth/firebase_auth.dart';
import 'package:google_sign_in/google_sign_in.dart';
import 'package:cloud_firestore/cloud_firestore.dart';
import 'home.dart';
class Login extends StatefulWidget {
#override
_LoginState createState() => _LoginState();
}
class _LoginState extends State<Login> {
final GoogleSignIn googleSignIn = new GoogleSignIn();
final FirebaseAuth firebaseAuth = FirebaseAuth.instance;
SharedPreferences preferences;
bool loading = false;
bool isLogedin = false;
#override
void initState() {
super.initState();
issignedIn();
}
void issignedIn() async {
setState(() {
loading = true;
});
preferences = await SharedPreferences.getInstance();
isLogedin = await googleSignIn.isSignedIn();
if (isLogedin) {
Navigator.pushReplacement(
context, MaterialPageRoute(builder: (context) => HomePage()));
}
setState(() {
loading = false;
});
}
Future handleSignIn() async {
preferences = await SharedPreferences.getInstance();
setState(() {
loading = true;
});
GoogleSignInAccount googleUser = await googleSignIn.signIn();
GoogleSignInAuthentication googleSignInAuthentication =
await googleUser.authentication;
AuthCredential credential = GoogleAuthProvider.getCredential(
idToken: googleSignInAuthentication.idToken,
accessToken: googleSignInAuthentication.accessToken);
FirebaseUser firebaseUser =
(await firebaseAuth.signInWithCredential(credential));
if (firebaseUser != null) {
final QuerySnapshot result = await Firestore.instance
.collection("users")
.where("id", isEqualTo: firebaseUser.uid)
.getDocuments();
final List<DocumentSnapshot> documents = result.documents;
if (documents.length == 0) {
//Insert the user to our collection
Firestore.instance
.collection("users")
.document(firebaseUser.uid)
.setData({
"id": firebaseUser.uid,
"username": firebaseUser.displayName,
"email": firebaseUser.email,
"profilePicture": firebaseUser.photoUrl
});
await preferences.setString("id", firebaseUser.uid);
await preferences.setString("username", firebaseUser.displayName);
await preferences.setString("email", firebaseUser.email);
await preferences.setString("photoUrl", firebaseUser.displayName);
} else {
await preferences.setString("id", documents[0]['id']);
await preferences.setString("username", documents[0]['username']);
await preferences.setString("email", documents[0]['email']);
await preferences.setString("photoUrl", documents[0]['photoUrl']);
}
Fluttertoast.showToast(msg: "Logged in successfully");
setState(() {
loading = false;
});
} else {}
}
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: new AppBar(
elevation: 0.0,
backgroundColor: Colors.red,
centerTitle: true,
title: Text(
"Login",
style: TextStyle(fontWeight: FontWeight.bold),
),
),
body: Stack(
children: <Widget>[
Center(
child: FlatButton(
color: Colors.red,
onPressed: () {
handleSignIn();
},
child: Text(
"Sign in/ Sign up with google",
style: TextStyle(color: Colors.white),
),
),
),
Visibility(
visible: loading ?? true,
child: Container(
alignment: Alignment.center,
color: Colors.white.withOpacity(0.9),
child: Center(
child: CircularProgressIndicator(
valueColor: AlwaysStoppedAnimation<Color>(Colors.red),
),
),
),
)
],
),
);
}
}
It keeps loading like forever. May be am not doing something right. A help with the code is highly appreciated.
Please, help out.
enter image description here
Just check quickly that the build.gradle file edits were made in the correct file as there are two of them and i've seen that mistake often. Also there is a problem with some android x devices as covered here that could cause this.
1) check the indentation of imports at the head of the page and make sure you have included import 'package:flutter/material.dart';.
2) ~line 50 ish: FirebaseUser firebaseUser =(await firebaseAuth.signInWithCredential(credential));
you may want to try replacing with: FirebaseUser firebaseUser = (await firebaseAuth.signInWithCredential(credential)).user;
3) ... will run a test later if i have time ( ゚ヮ゚)
Later => with the change above, this code does work for me. I loaded it into one of my firebase projects and it logs me in. It does not redirect to home as you have not called issignedIn() in the button flow. You could add it in after Fluttertoast.showToast(msg: "Logged in successfully"); replacing setState((){...}); but i would recommend changing this function to a onAuthStateChange method if you are comfortable using listeners. If you still cant get it working, post the content of you build.gradle files and the pubspec.yaml and any errors from the debug console.
and just as a note: adding try, catch logic or then.error with asynchronous functions is recommended, especially when using networks here. I see people ignore it for prototyping but it can really help with Firebase custom error states
I made this video showing how to get firebase auth setup with flutter. It's a bit of a different code structure than what you posted but I think more flexible if you were interested in refactoring. https://youtu.be/iTYD13w6Duo