Не удается сохранить изображение на устройстве во Flutter?

avatar
cvsrt
8 августа 2021 в 17:01
130
1
0

Я пытаюсь сохранить изображение на локальном устройстве с помощью sqllite. Я использую библиотеку edge_detection, чтобы получить путь к обрезанному изображению и пытаюсь сохранить его на устройстве. Это моя таблица:

class DBHelper {
  static Future<Database> database() async {
    final dbPath = await sql.getDatabasesPath();
    return sql.openDatabase(path.join(dbPath, 'locations.db'),
        onCreate: (db, version)  => _createDb(db), version: 1);}
  static void _createDb(Database db) {
    db.execute('CREATE TABLE location(id INTEGER PRIMARY KEY AUTOINCREMENT, title TEXT, image TEXT)');
    db.execute('CREATE TABLE images(id INTEGER PRIMARY KEY AUTOINCREMENT, Image TEXT, fileId INTEGER)');
  }

Мой код вставки:

void addImage(int file_id, File pic) {
    final newpicture = Picture(file_id: file_id, image: pic);
    _items.add(newpicture);
    notifyListeners();
    DBHelper.insert('images', {
      'Image': newpicture.image.path,
      'fileId': newpicture.file_id,
    });
  }

И я получаю данные с этим кодом:

Future<void> fetchAndSetPlaces() async {
    final dataList = await DBHelper.getData('images');
    print(dataList);
    _items = dataList
        .map(
          (item) => Picture(
            image:File(item['Image']),
            file_id: item['fileId'],
          ),
        )
        .toList();
    notifyListeners();
  }
}

Моя модель такая:

class Picture{
  int? id;

  final int file_id;
  final File image;

  Picture({required this.file_id,required this.image});



}

И вот как я использую функцию для получения пути к изображению:

Future<void> getImage(int? file_id) async {
    String? imagePath;
    // Platform messages may fail, so we use a try/catch PlatformException.
    // We also handle the message potentially returning null.
    try {
      imagePath = (await EdgeDetection.detectEdge);
      print("$imagePath");
    } on PlatformException {
      imagePath = 'Failed to get cropped image path.';
    }

    // If the widget was removed from the tree while the asynchronous platform
    // message was in flight, we want to discard the reply rather than calling
    // setState to update our non-existent appearance.
    if (!mounted) return;

    var directory = await getApplicationDocumentsDirectory();
    String path=directory.path;



    setState(() {
      _imagePath = imagePath;
    });
    print(_imagePath);

    Provider.of<Images>(context, listen: false)
        .addImage(file_id!  File(_imagePath!));
  }

И вот как я получаю данные в виджете:

Consumer<Images>(
                  builder: (ctx, titles, ch) => GridView.builder(
                      itemCount: titles.items.length,
                      gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
                        crossAxisCount: 3,
                        mainAxisSpacing: 2,
                        crossAxisSpacing: 2,
                      ),
                      itemBuilder: (ctx, index) {
                        return Column(
                          children: <Widget>[
                            Expanded(
                              child: Container(
                                padding:EdgeInsets.symmetric(vertical: 10,horizontal:10),
                                  child: Image.file(titles.items[index].image)),

Это после добавления изображения: This is after adding picture Это после закрытия и повторного открытия приложения: enter image description here

Проблема в том, что я могу видеть изображение после того, как сделал снимок, но когда я закрываю приложение, а затем снова открываю его, изображение не отображается. Как я могу решить эту проблему? Заранее спасибо.

Обновление: поэтому, когда я запускал свой код в режиме выпуска, проблем не было. Я думаю, что проблема в режиме отладки.

Источник

Ответы (1)

avatar
akram abdullah
21 августа 2021 в 14:50
1

первый шаг изменяет тип данных изображения в базе данных на BLOB db.execute('CREATE TABLE images(id INTEGER PRIMARY KEY AUTOINCREMENT, Image BLOB, fileId INTEGER)');

Второй шаг: измените тип данных в вашей модели на Uint8List

финальное изображение Uint8List;

наконец, когда вы читаете изображение, читайте его как Uint8List