Flutter:如何在Sqlite中将图像存储为blob以及如何检索它?

iyfjxgzm  于 2023-06-06  发布在  SQLite
关注(0)|答案(1)|浏览(273)

我使用Flutter,我需要在SQLite中将图像保存为BLOB,然后在页面中显示它。
我做了它作为字符串,它的工作很好,但不是图像与1.5 MB的大小,该应用程序得到unhanded异常,我试图做它作为斑点,但我找不到任何教程的任何地方。
我的型号:

import 'package:flutter/services.dart';

const String tablePersonal = 'personal_info';

class PersonalFields {
  static final List<String> values = [
    id,
    name,
    logo,
  ];
  static const String id = '_id';
  static const String name = 'name';
  static const String logo = 'logo';
}

class PersonalInfoModel {
  int? id;
  final String name;
  final Uint8List? logo;

  PersonalInfoModel({
    this.id,
    required this.name,
    this.logo,
  });

  PersonalInfoModel copy({
    int? id,
    String? name,
    Uint8List? logo,
  }) =>
      PersonalInfoModel(
        id: id ?? this.id,
        name: name ?? this.name,
        logo: logo ?? this.logo,
      );

  static PersonalInfoModel fromJson(Map<String, Object?> json) =>
      PersonalInfoModel(
        id: json[PersonalFields.id] as int?,
        name: json[PersonalFields.name] as String,
        logo: json[PersonalFields.logo] as Uint8List?,
      );

  Map<String, dynamic> toJson() => {
        PersonalFields.id: id,
        PersonalFields.name: name,
        PersonalFields.logo: logo,
      };
}

SQL助手:创建表后,我只需要插入空记录来保存id = 1,这样我就可以更新记录了。这意味着该表将只获得一条记录。

batch.execute('''
      CREATE TABLE IF NOT EXISTS $tablePersonal
      (
        ${PersonalFields.id} $idType,
        ${PersonalFields.name} $textType,
        ${PersonalFields.logo} $blobType
      )
    ''');

    batch.execute('''
      INSERT INTO $tablePersonal
      (
        ${PersonalFields.name}
      )
      VALUES
      (
        ''
      )
    ''');

  //read personal info
  Future<List<PersonalInfoModel>> getPesonalInfo() async {
    var db = await instanace.database;
    final result = await db.query(tablePersonal);
    return result.map((json) => PersonalInfoModel.fromJson(json)).toList();
  }

  Future<int> updatePersonalInfo(PersonalInfoModel personalInfoModel) async {
    final db = await instanace.database;
    return db.update(
      tablePersonal,
      personalInfoModel.toJson(),
      where: '${PersonalFields.id} = ?',
      whereArgs: [personalInfoModel.id],
    );
  }

我的页面:

import 'dart:convert';
import 'dart:io';

import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:image_picker/image_picker.dart';
import 'package:ledger/database/sql_helper.dart';
import 'package:ledger/l10n/app_local.dart';
import 'package:ledger/models/personal_info_model.dart';

class PersonalInfoPage extends StatefulWidget {
  const PersonalInfoPage({Key? key}) : super(key: key);

  @override
  State<PersonalInfoPage> createState() => _PersonalInfoPageState();
}

class _PersonalInfoPageState extends State<PersonalInfoPage> {
  final _formKey = GlobalKey<FormState>();
  final TextEditingController _nameController = TextEditingController();

  double boxWidth = 10;
  double boxHieght = 10;
  XFile? xImage;
  var bytes;
  final ImagePicker _picker = ImagePicker();
  late List<PersonalInfoModel> personalList;
  late PersonalInfoModel existPersonal;
  bool isLoading = true;

  @override
  void initState() {
    super.initState();

    getPersonalInfo();
  }

  Future pickImage() async {
    try {
      xImage = await _picker.pickImage(source: ImageSource.gallery);
      if (xImage == null) return;
      final imagePath = File(xImage!.path);
      bytes = imagePath;
      setState(() {});
    } on PlatformException catch (e) {
      print('Failed to pick image: $e');
    }
  }
  
  Future getPersonalInfo() async {
    final data = await SQLHelper.instanace.getPesonalInfo();
    setState(() {
      personalList = data;
      getData();

      isLoading = false;
    });
  }

  getData() {
    existPersonal = personalList.firstWhere((element) => element.id == 1);
    _nameController.text = existPersonal.name;
    bytes = existPersonal.logo;
  }

  Future updatePersonalInfo(PersonalInfoModel personalInfoModel) async {
    await SQLHelper.instanace.updatePersonalInfo(personalInfoModel);
    getPersonalInfo();
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text(AppLocal.loc.personal_info),
        actions: [
          IconButton(
            onPressed: () {
              PersonalInfoModel personalInfoModel = PersonalInfoModel(
                  id: 1,
                  name: _nameController.text,
                  logo: bytes);
              updatePersonalInfo(personalInfoModel);
            },
            icon: const Icon(Icons.save_as_outlined),
          ),
        ],
      ),
      body: isLoading
          ? const Center(child: CircularProgressIndicator())
          : SingleChildScrollView(
              child: Column(
                children: [
                  Padding(
                    padding: const EdgeInsets.symmetric(horizontal: 5.0),
                    child: Form(
                      key: _formKey,
                      child: Column(
                        children: [
                          SizedBox(height: boxHieght),
                          TextFormField(
                            controller: _nameController,
                            decoration: InputDecoration(
                              filled: true,
                              labelText: AppLocal.loc.name,
                              border: const OutlineInputBorder(
                                borderRadius: BorderRadius.all(
                                  Radius.circular(5.0),
                                ),
                              ),
                            ),
                          ),
                        ],
                      ),
                    ),
                  ),
                  Row(
                    mainAxisAlignment: MainAxisAlignment.center,
                    children: [
                      TextButton(
                        onPressed: () {
                          print('xxxxxx');
                          pickImage();
                        },
                        child: Text('from Gallary'),
                      ),
                    ],
                  ),
                  Container(
                    color: Colors.grey.shade100,
                    height: 150,
                    width: 150,
                    child: bytes != null
                        ? Image.memory(bytes)
                        : Image.asset('assets/logo.png'),
                  ),
                ],
              ),
            ),
    );
  }
}
bbmckpt7

bbmckpt71#

下面是如何将其转换为blob并将其保存到SQLite中的方法

Future pickImage(ImageSource source) async {
    try {
      final image = await ImagePicker.pickImage(source: source);

      final imagePath = File(image.path);

     
      List<int> bytes = await image.readAsBytes();
      String base64 = base64Encode(bytes);// here it is. Save it to sqflite
    } on PlatformException catch (e) {
      print(e);
    }
  }

从SQLite获取

String blobImageFromSqflite; //get from sqflite
   Uint8List _bytesImage = Base64Decoder().convert(blobImageFromSqflite);

to display it;
                 Image.memory(
                 _bytesImage,
                 );

相关问题