relatica/lib/services/media_upload_attachment_hel...

107 wiersze
3.2 KiB
Dart

import 'dart:io';
import 'dart:math';
import 'package:file_picker/file_picker.dart';
import 'package:image/image.dart';
import 'package:image_picker/image_picker.dart';
import 'package:logging/logging.dart';
import 'package:result_monad/result_monad.dart';
import '../globals.dart';
import '../models/exec_error.dart';
import '../models/media_attachment_uploads/image_types_enum.dart';
import '../models/media_attachment_uploads/media_upload_attachment.dart';
class MediaUploadAttachmentHelper {
static final _logger = Logger('$MediaUploadAttachmentHelper');
static FutureResult<List<MediaUploadAttachment>, ExecError>
getNewImagesFromCamera() async {
final file = await ImagePicker().pickImage(source: ImageSource.camera);
if (file != null) {
return Result.ok([MediaUploadAttachment.newItem(file.path)]);
}
{
return Result.ok([]);
}
}
static FutureResult<List<MediaUploadAttachment>, ExecError>
getImagesFromGallery() async {
final files = <XFile>[];
if (useImagePicker) {
final picker = ImagePicker();
final selectedFiles = await picker.pickMultiImage();
files.addAll(selectedFiles);
} else {
await _desktopImagesFromDisk().match(
onSuccess: (selectedFiles) => files.addAll(selectedFiles),
onError: (error) => _logger.severe(error),
);
}
return Result.ok(
files.map((f) => MediaUploadAttachment.newItem(f.path)).toList());
}
static FutureResult<List<XFile>, dynamic> _desktopImagesFromDisk() async {
final result = await FilePicker.platform.pickFiles(
type: FileType.image,
allowMultiple: true,
);
if (result == null) {
return Result.ok([]);
}
final files = result.files.map((f) => XFile(f.path!)).toList();
return Result.ok(files);
}
static Result<List<int>, dynamic> getUploadableImageBytes(String path,
{int maxSizeBytes = 800000}) {
return runCatching(() {
final file = File(path);
final fileBytes = file.readAsBytesSync();
var size = file.statSync().size;
if (size <= maxSizeBytes) {
return Result.ok(fileBytes);
}
final imageType = ImageTypes.fromExtension(path);
var scale = maxSizeBytes / size;
late final Image original;
switch (imageType) {
case ImageTypes.gif:
original = decodeGif(fileBytes)!;
break;
case ImageTypes.png:
original = decodePng(fileBytes)!;
break;
case ImageTypes.jpg:
original = decodeJpg(fileBytes)!;
break;
}
late List<int> resizedBytes;
while (size > maxSizeBytes) {
final newWidth = (original.width * sqrt(scale)).toInt();
final resized = copyResize(original, width: (newWidth).toInt());
switch (imageType) {
case ImageTypes.gif:
resizedBytes = encodeGif(resized);
break;
case ImageTypes.png:
resizedBytes = encodePng(resized);
break;
case ImageTypes.jpg:
resizedBytes = encodeJpg(resized, quality: 80);
break;
}
size = resizedBytes.length;
scale /= 2;
}
return Result.ok(resizedBytes);
});
}
}