I have a form that the user can fill out. This form has one text field and one custom field (ImagePickerWidget()) with the ability to add a photo. The custom field is moved to a separate class.
.......
new Text('What is problem', style: TextStyle(fontSize: 20.0),),
new TextFormField(decoration: const InputDecoration(
hintText: 'Describe the problem',),
validator: (value){if (value!.isEmpty) return 'Please, describe the problem ';}),
new SizedBox(height: 20.0),
ImagePickerWidget(),
new SizedBox(height: 20.0),
ElevatedButton(
onPressed: (){if(_formKey.currentState!.validate()) {
_formKey.currentState?.reset();
ScaffoldMessenger.of(context).showSnackBar(
const SnackBar(content: Text('Form completed successfully',
style: TextStyle(color: Colors.black),),
backgroundColor: Colors.yellow,));
}},
child: const Text('Submit', style: TextStyle(color: Colors.black),),
style: ButtonStyle(backgroundColor: MaterialStateProperty.all(Colors.yellow)),)
......
my custom widget
class ImagePickerWidget extends StatefulWidget {
const ImagePickerWidget( {Key? key}) : super(key: key);
@override
State<ImagePickerWidget> createState() => _ImagePickerWidgetState();
}
class _ImagePickerWidgetState extends State<ImagePickerWidget> {
late List<CustomImage> images;
late double size;
late ImagePicker imagePicker;
late int idGenerator;
@override
void initState() {
images = [];
size = 100;
idGenerator = 0;
imagePicker = ImagePicker();
}
@override
Widget build(BuildContext context) {
return Column(
crossAxisAlignment: CrossAxisAlignment.center,
children: [
ElevatedButton(
onPressed: () {
pickImage();
},
child: Text('Pick Image')),
Wrap(
children: images.map((image) {
return Stack(children: [
SizedBox(
height: size,
width: size,
child: ClipRRect(
child: Image.memory(
image.imageData,
fit: BoxFit.fill,
))),
Positioned(
right: 4,
top: 4,
child: InkWell(
onTap: () {
//delete image
images.removeWhere(
(element) => element.imageData == image.imageData);
setState(() {});
},
child: Container(
color: Colors.white, child: Icon(Icons.clear))))
]);
}).toList())
],
);
}
Future<void> pickImage() async {
//XFile? image = await imagePicker.pickImage(source: ImageSource.camera);
XFile? image = await imagePicker.pickImage(source: ImageSource.gallery);
if (image != null) {
Uint8List imageData = await image.readAsBytes();
int id = idGenerator ;
images.add(CustomImage(imageData: imageData, id: id));
setState(() {});
}
}
}
class CustomImage {
Uint8List imageData;
int id;
CustomImage({required this.imageData, required this.id});
}
but the problem is that when the button is pressed 'Submit' only the text field is erased (_formKey.currentState?.reset();), and the selected photos remain in the form. Tell me what should I do so that when I click on the button 'Submit' the whole form is cleared?
CodePudding user response:
keep the variable outside the class in your imagepick widget
List<CustomImage> images=[];
like this List images=[]; //============look here class _ImagePickerWidgetState extends State {
late double size;
late ImagePicker imagePicker;
late int idGenerator;
do like this in your onpressed
onPressed: () {
if (_formKey.currentState!.validate()) {
_formKey.currentState?.reset();
setState(() {
images=[];
});
ScaffoldMessenger.of(context)
.showSnackBar(const SnackBar(
content: Text(
'Form completed successfully',
style: TextStyle(color: Colors.black),
),
backgroundColor: Colors.yellow,
));
}
}
SampleCode
import 'dart:io';
import 'dart:typed_data';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:image_picker/image_picker.dart';
ImagePicker? picker;
void main() {
WidgetsFlutterBinding.ensureInitialized();
picker = ImagePicker();
runApp(MyApp());
}
class MyApp extends StatelessWidget {
// This widget is the root of your application.
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'MySQL Test',
theme: ThemeData(
primarySwatch: Colors.blue,
visualDensity: VisualDensity.adaptivePlatformDensity,
),
home: MyHomePage(),
);
}
}
class MyHomePage extends StatelessWidget {
const MyHomePage({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(),
body: Column(
children: [FormForDeviceService()],
),
);
}
}
List<File> myfile = [];
List<int> f = [1, 2, 3, 4, 5];
List<bool> fs = [false, false, false, true, true];
class FormForDeviceService extends StatefulWidget {
@override
State<StatefulWidget> createState() => _FormForDeviceService();
}
class _FormForDeviceService extends State {
final _formKey = GlobalKey<FormState>();
Widget build(BuildContext context) {
return Container(
padding: const EdgeInsets.all(10.0),
child: Form(
key: _formKey,
child: Column(
children: <Widget>[
new Text(
'What is problem',
style: TextStyle(fontSize: 20.0),
),
new TextFormField(
decoration: const InputDecoration(
hintText: 'Describe the problem',
),
validator: (value) {
if (value!.isEmpty)
return 'Please, describe the problem ';
}),
new SizedBox(height: 20.0),
ImagePickerWidget(),
new SizedBox(height: 20.0),
ElevatedButton(
onPressed: () {
if (_formKey.currentState!.validate()) {
_formKey.currentState?.reset();
setState(() {
images=[];
});
ScaffoldMessenger.of(context)
.showSnackBar(const SnackBar(
content: Text(
'Form completed successfully',
style: TextStyle(color: Colors.black),
),
backgroundColor: Colors.yellow,
));
}
},
child: const Text(
'Submit',
style: TextStyle(color: Colors.black),
),
style: ButtonStyle(
backgroundColor:
MaterialStateProperty.all(Colors.yellow)))
],
)));
}
}
class ImagePickerWidget extends StatefulWidget {
const ImagePickerWidget({Key? key}) : super(key: key);
@override
State<ImagePickerWidget> createState() => _ImagePickerWidgetState();
}
List<CustomImage> images=[];
class _ImagePickerWidgetState extends State<ImagePickerWidget> {
late double size;
late ImagePicker imagePicker;
late int idGenerator;
@override
void initState() {
images = [];
size = 100;
idGenerator = 0;
imagePicker = ImagePicker();
}
@override
Widget build(BuildContext context) {
return Column(
crossAxisAlignment: CrossAxisAlignment.center,
children: [
ElevatedButton(
onPressed: () {
pickImage();
},
child: Text('Pick Image')),
Wrap(
children: images.map((image) {
return Stack(children: [
SizedBox(
height: size,
width: size,
child: ClipRRect(
child: Image.memory(
image.imageData,
fit: BoxFit.fill,
))),
Positioned(
right: 4,
top: 4,
child: InkWell(
onTap: () {
//delete image
images.removeWhere(
(element) => element.imageData == image.imageData);
setState(() {});
},
child: Container(
color: Colors.white, child: Icon(Icons.clear))))
]);
}).toList())
],
);
}
Future<void> pickImage() async {
//XFile? image = await imagePicker.pickImage(source: ImageSource.camera);
XFile? image = await imagePicker.pickImage(source: ImageSource.gallery);
if (image != null) {
Uint8List imageData = await image.readAsBytes();
int id = idGenerator ;
images.add(CustomImage(imageData: imageData, id: id));
setState(() {});
}
}
}
class CustomImage {
Uint8List imageData;
int id;
CustomImage({required this.imageData, required this.id});
}
CodePudding user response:
Try this.
.......
List<CustomImage> images = [];
new Text('What is problem', style: TextStyle(fontSize: 20.0),),
new TextFormField(decoration: const InputDecoration(
hintText: 'Describe the problem',),
validator: (value){if (value!.isEmpty) return 'Please, describe the problem ';
}),
new SizedBox(height: 20.0),
ImagePickerWidget(images: []),
new SizedBox(height: 20.0),
ElevatedButton(
onPressed: (){if(_formKey.currentState!.validate()) {
_formKey.currentState?.reset();
setState(() {
images = [];
});
ScaffoldMessenger.of(context).showSnackBar(
const SnackBar(content: Text('Form completed successfully',
style: TextStyle(color: Colors.black),),
backgroundColor: Colors.yellow,));
}},
child: const Text('Submit', style: TextStyle(color: Colors.black),),
style: ButtonStyle(backgroundColor: MaterialStateProperty.all(Colors.yellow)),)
......
class ImagePickerWidget extends StatefulWidget {
const ImagePickerWidget( {Key? key, required this.images}) : super(key: key);
List<CustomImage> images = [];
@override
State<ImagePickerWidget> createState() => _ImagePickerWidgetState();
}
class _ImagePickerWidgetState extends State<ImagePickerWidget> {
late double size;
late ImagePicker imagePicker;
late int idGenerator;
@override
void initState() {
size = 100;
idGenerator = 0;
imagePicker = ImagePicker();
}
@override
Widget build(BuildContext context) {
return Column(
crossAxisAlignment: CrossAxisAlignment.center,
children: [
ElevatedButton(
onPressed: () {
pickImage();
},
child: Text('Pick Image')),
Wrap(
children: widget.images.map((image) {
return Stack(children: [
SizedBox(
height: size,
width: size,
child: ClipRRect(
child: Image.memory(
image.imageData,
fit: BoxFit.fill,
))),
Positioned(
right: 4,
top: 4,
child: InkWell(
onTap: () {
//delete image
widget.images.removeWhere(
(element) => element.imageData == image.imageData);
setState(() {});
},
child: Container(
color: Colors.white, child: Icon(Icons.clear))))
]);
}).toList())
],
);
}
Future<void> pickImage() async {
//XFile? image = await imagePicker.pickImage(source: ImageSource.camera);
XFile? image = await imagePicker.pickImage(source: ImageSource.gallery);
if (image != null) {
Uint8List imageData = await image.readAsBytes();
int id = idGenerator ;
widget.images.add(CustomImage(imageData: imageData, id: id));
setState(() {});
}
}
}
class CustomImage {
Uint8List imageData;
int id;
CustomImage({required this.imageData, required this.id});
}