Search code examples
imageflutterdartfile-uploaddio

Solve the error or give a Complete working example to upload images with multi image picker as a List<file> with Dio


I am trying to upload images for some days and it's not working so please if you have a working code put it as an answer or just solve the code

Here is the code

import 'dart:typed_data';

import 'package:dio/dio.dart';
import 'package:flutter/material.dart';
import 'package:mazadi/Models/ImageUpload.dart';
import 'package:multi_image_picker/multi_image_picker.dart';

class AddAd3 extends StatefulWidget {
  AddAd3({
    Key key,
  }) : super(key: key);

  @override
  _AddAd3State createState() => _AddAd3State();
}

class _AddAd3State extends State<AddAd3> {
  bool _isUploading = false;

  @override
  Widget build(BuildContext context) {
    return Scaffold(
        body: Padding(
      padding: const EdgeInsets.all(12.0),
      child: ListView(
        children: <Widget>[
          Row(
            mainAxisAlignment: MainAxisAlignment.center,
            children: <Widget>[
              SizedBox(
                width: 100,
                height: 100,
                child: RaisedButton(
                  onPressed: () {
                    getImage();
                  },
                  color: Colors.white,
                  shape: new RoundedRectangleBorder(
                      borderRadius: new BorderRadius.circular(7.0)),
                  child: SizedBox(
                    width: 90,
                    height: 90,
                    child: Center(
                      child: Icon(
                        Icons.add,
                        color: Colors.deepOrange,
                        size: 30.0,
                      ),
                    ),
                  ),
                ),
              ),
            ],
          ),
          SizedBox(
            height: 40,
          ),
          SizedBox(
            width: 500,
            height: 500,
            child: _isUploading == true
                ? FutureBuilder(
                    future: uploadImage(),
                    builder: (BuildContext context, AsyncSnapshot snapshot) {
                      switch (snapshot.connectionState) {
                        case ConnectionState.none:
                        case ConnectionState.waiting:
                          return new Text('loading...');
                        default:
                          if (snapshot.hasError)
                            return new Text('${snapshot.error}');
                          else
                            return createListView(context, snapshot);
                      }
                    },
                  )
                : Text(""),
          ),
        ],
      ),
    ));
  }

  Future getImage() async {
    files.clear();

    List<Asset> resultList = List<Asset>();
    resultList = await MultiImagePicker.pickImages(
      maxImages: 10,
      enableCamera: false,
    );

    for (var asset in resultList) {
      int MAX_WIDTH = 500; //keep ratio
      int height = ((500 * asset.originalHeight) / asset.originalWidth).round();

      ByteData byteData =
          await asset.getThumbByteData(MAX_WIDTH, height, quality: 80);

      if (byteData != null) {
        List<int> imageData = byteData.buffer.asUint8List();
        MultipartFile u = MultipartFile.fromBytes(
          imageData,
          filename: asset.name,
        );
        files.add(u);
      }
    }

    setState(() {
      _isUploading = true;
    });
  }

  List<MultipartFile> files = new List<MultipartFile>();
  Future<List<String>> uploadImage() async {
    FormData formData = new FormData.fromMap({"thumb": files});

    Dio dio = new Dio();
    var response = await dio.post(
        "https://mazadyy.com/index.php?route=api/customer_product/uploadImages",
        data: formData);

    UploadImage image = UploadImage.fromJson(response.data);
    return image.images;
  }

  Widget createListView(BuildContext context, AsyncSnapshot snapshot) {
    if (snapshot.hasError) {
      return Text("error createListView");
    }

    if (!snapshot.hasData) {
      return Text("");
    }

    List<String> values = snapshot.data;

    return new ListView.builder(
      shrinkWrap: true,
      itemCount: values.length,
      itemBuilder: (BuildContext context, int index) {
        return new Column(
          children: <Widget>[
            Image.network(
              values[index],
              width: 300,
              height: 100,
            ),
            SizedBox(
              height: 40,
            ),
          ],
        );
      },
    );
  }
}

and here it the model

class UploadImage {
  List<String> images;

  UploadImage({this.images});

  factory UploadImage.fromJson(Map<String, dynamic> json) {
    return UploadImage(images: parseImage(json['images']));
  }

  static List<String> parseImage(json) {
    return new List<String>.from(json);
  }
}
 

the exception that I get is

type String is not a subtype of 'Map<String, dynamic>'

so if you solved the error I will really appreciate it and give him 50 reputation as a reward because I saw many struggle with the same problem

any help will be appreciated whatever it's


Solution

  • if (images.isEmpty || images[0] != null) {
                        for (int i = 0; i < images.length; i++) {
                          ByteData byteData = await images[i].getByteData();
                          List<int> imageData = byteData.buffer.asUint8List();
                          http.MultipartFile multipartFile =
                              http.MultipartFile.fromBytes('image', imageData,
                                  filename: images[i].name,
                                  contentType: MediaType('image', 'jpg'));
                          imagestoEdit.add(multipartFile);
                          print(imagestoEdit.length);
                        }
                      }
    Dio.post(url,formdata:{images:imagestoEdit})