136 lines
4 KiB
Dart
136 lines
4 KiB
Dart
import 'dart:io';
|
|
import 'dart:isolate';
|
|
|
|
import 'package:flutter/src/widgets/framework.dart';
|
|
import 'package:flutter_background_service/flutter_background_service.dart';
|
|
import 'package:freezer/api/deezer.dart';
|
|
import 'package:freezer/api/definitions.dart' as d;
|
|
import 'package:freezer/api/download_manager/database.dart';
|
|
import 'package:freezer/api/download_manager/download_service.dart';
|
|
import 'package:freezer/api/download_manager/service_interface.dart';
|
|
import 'package:freezer/api/paths.dart';
|
|
import 'package:freezer/main.dart';
|
|
import 'package:freezer/settings.dart';
|
|
import 'package:freezer/translations.i18n.dart';
|
|
<<<<<<< Updated upstream
|
|
=======
|
|
import 'package:isar/isar.dart';
|
|
import '../download.dart' as dl;
|
|
>>>>>>> Stashed changes
|
|
|
|
class DownloadManager {
|
|
//implements dl.DownloadManager {
|
|
|
|
late Isar _isar;
|
|
|
|
SendPort? _sendPort;
|
|
Isolate? _isolate;
|
|
|
|
Future<bool> configure() async {
|
|
_isar = await Isar.open(
|
|
[
|
|
// collections
|
|
TrackSchema,
|
|
AlbumSchema,
|
|
ArtistSchema,
|
|
PlaylistSchema,
|
|
],
|
|
directory: await Paths.dataDirectory(),
|
|
name: 'offline',
|
|
);
|
|
if (Platform.isAndroid || Platform.isIOS) {
|
|
return FlutterBackgroundService().configure(
|
|
iosConfiguration: IosConfiguration(), // fuck ios
|
|
androidConfiguration: AndroidConfiguration(
|
|
onStart: _startNative,
|
|
isForegroundMode: false,
|
|
autoStart: false,
|
|
autoStartOnBoot: false,
|
|
foregroundServiceNotificationId: DownloadService.NOTIFICATION_ID,
|
|
notificationChannelId: DownloadService.NOTIFICATION_CHANNEL_ID,
|
|
initialNotificationTitle: 'Freezer'.i18n,
|
|
initialNotificationContent: 'Starting download service...'.i18n,
|
|
));
|
|
}
|
|
|
|
// will run in foreground instead, in a separate isolate
|
|
return Future.value(true);
|
|
}
|
|
|
|
Future<bool> startService() async {
|
|
if (Platform.isAndroid) {
|
|
return FlutterBackgroundService().startService();
|
|
}
|
|
|
|
final receivePort = ReceivePort();
|
|
_sendPort = receivePort.sendPort;
|
|
_isolate = await Isolate.spawn(
|
|
_startService, ServiceInterface(receivePort: receivePort));
|
|
|
|
return true;
|
|
}
|
|
|
|
void kill() {
|
|
_isolate?.kill();
|
|
}
|
|
|
|
void invoke(String method, [Map<String, dynamic>? args]) {
|
|
if (_sendPort != null) {
|
|
_sendPort!.send({
|
|
'method': method,
|
|
if (args != null) ...args,
|
|
});
|
|
return;
|
|
}
|
|
FlutterBackgroundService().invoke(method, args);
|
|
}
|
|
|
|
@override
|
|
Future<bool> addOfflineTrack(d.Track track,
|
|
{bool private = true, BuildContext? context, isSingleton = false}) async {
|
|
//Permission
|
|
//if (!private && !(await checkPermission())) return false;
|
|
|
|
//Ask for quality
|
|
//AudioQuality? quality;
|
|
if (!private && settings.downloadQuality == AudioQuality.ASK) {
|
|
// quality = await qualitySelect(context!);
|
|
// if (quality == null) return false;
|
|
}
|
|
if (private) {
|
|
if (track.artists == null ||
|
|
track.artists!.isEmpty ||
|
|
track.album == null) {
|
|
track = await deezerAPI.track(track.id);
|
|
}
|
|
|
|
// cache album art
|
|
cacheManager.getSingleFile(track.albumArt!.thumb);
|
|
cacheManager.getSingleFile(track.albumArt!.full);
|
|
|
|
await _isar.writeTxn(() async {
|
|
await _isar.tracks.put(Track.from(track));
|
|
if (track.album != null) {
|
|
await _isar.albums.put(Album.from(track.album!));
|
|
}
|
|
|
|
if (track.artists != null) {
|
|
await _isar.artists
|
|
.putAll(track.artists!.map(Artist.from).toList(growable: false));
|
|
}
|
|
});
|
|
}
|
|
|
|
// logic for downloading the track
|
|
invoke('addDownloads', {'track': track.toJson()});
|
|
|
|
return true;
|
|
}
|
|
|
|
static void _startNative(ServiceInstance service) =>
|
|
_startService(ServiceInterface(service: service));
|
|
|
|
static void _startService(ServiceInterface? service) =>
|
|
DownloadService(service).run();
|
|
}
|