flutter_file_picker/lib/src/file_picker.dart

130 lines
5.2 KiB
Dart

import 'dart:async';
import 'dart:io';
import 'package:file_picker/src/file_picker_io.dart';
import 'package:file_picker/src/file_picker_linux.dart';
import 'package:file_picker/src/file_picker_macos.dart';
import 'package:file_picker/src/windows/stub.dart'
if (dart.library.io) 'package:file_picker/src/windows/file_picker_windows.dart';
import 'package:plugin_platform_interface/plugin_platform_interface.dart';
import 'file_picker_result.dart';
const String defaultDialogTitle = 'File Picker';
enum FileType {
any,
media,
image,
video,
audio,
custom,
}
enum FilePickerStatus {
picking,
done,
}
/// The interface that implementations of file_picker must implement.
///
/// Platform implementations should extend this class rather than implement it as `file_picker`
/// does not consider newly added methods to be breaking changes. Extending this class
/// (using `extends`) ensures that the subclass will get the default implementation, while
/// platform implementations that `implements` this interface will be broken by newly added
/// [FilePicker] methods.
abstract class FilePicker extends PlatformInterface {
FilePicker() : super(token: _token);
static final Object _token = Object();
static late FilePicker _instance = _setPlatform();
static FilePicker get platform => _instance;
static set platform(FilePicker instance) {
PlatformInterface.verifyToken(instance, _token);
_instance = instance;
}
static FilePicker _setPlatform() {
if (Platform.isAndroid || Platform.isIOS) {
return FilePickerIO();
} else if (Platform.isLinux) {
return FilePickerLinux();
} else if (Platform.isWindows) {
return filePickerWithFFI();
} else if (Platform.isMacOS) {
return FilePickerMacOS();
} else {
throw UnimplementedError(
'The current platform "${Platform.operatingSystem}" is not supported by this plugin.',
);
}
}
/// Retrieves the file(s) from the underlying platform
///
/// Default `type` set to [FileType.any] with `allowMultiple` set to `false`.
/// Optionally, `allowedExtensions` might be provided (e.g. `[pdf, svg, jpg]`.).
///
/// If `withData` is set, picked files will have its byte data immediately available on memory as `Uint8List`
/// which can be useful if you are picking it for server upload or similar. However, have in mind that
/// enabling this on IO (iOS & Android) may result in out of memory issues if you allow multiple picks or
/// pick huge files. Use `withReadStream` instead. Defaults to `true` on web, `false` otherwise.
///
/// If `withReadStream` is set, picked files will have its byte data available as a `Stream<List<int>>`
/// which can be useful for uploading and processing large files. Defaults to `false`.
///
/// If you want to track picking status, for example, because some files may take some time to be
/// cached (particularly those picked from cloud providers), you may want to set [onFileLoading] handler
/// that will give you the current status of picking.
///
/// If `allowCompression` is set, it will allow media to apply the default OS compression.
/// Defaults to `true`.
///
/// `dialogTitle` can be optionally set on desktop platforms to set the modal window title. It will be ignored on
/// other platforms.
///
/// The result is wrapped in a `FilePickerResult` which contains helper getters
/// with useful information regarding the picked `List<PlatformFile>`.
///
/// For more information, check the [API documentation](https://github.com/miguelpruivo/flutter_file_picker/wiki/api).
///
/// Returns `null` if aborted.
Future<FilePickerResult?> pickFiles({
String? dialogTitle,
FileType type = FileType.any,
List<String>? allowedExtensions,
Function(FilePickerStatus)? onFileLoading,
bool allowCompression = true,
bool allowMultiple = false,
bool withData = false,
bool withReadStream = false,
}) async =>
throw UnimplementedError('pickFiles() has not been implemented.');
/// Asks the underlying platform to remove any temporary files created by this plugin.
///
/// This typically relates to cached files that are stored in the cache directory of
/// each platform and it isn't required to invoke this as the system should take care
/// of it whenever needed. However, this will force the cleanup if you want to manage those on your own.
///
/// This method is only available on mobile platforms (Android & iOS).
///
/// Returns `true` if the files were removed with success, `false` otherwise.
Future<bool?> clearTemporaryFiles() async => throw UnimplementedError(
'clearTemporaryFiles() has not been implemented.');
/// Selects a directory and returns its absolute path.
///
/// On Android, this requires to be running on SDK 21 or above, else won't work.
/// Returns `null` if folder path couldn't be resolved.
///
/// `dialogTitle` can be set to display a custom title on desktop platforms. It will be ignored on Web & IO.
///
/// Note: Some Android paths are protected, hence can't be accessed and will return `/` instead.
Future<String?> getDirectoryPath({String? dialogTitle}) async =>
throw UnimplementedError('getDirectoryPath() has not been implemented.');
}