Skip to content

Commit

Permalink
feat: offline search for youtube
Browse files Browse the repository at this point in the history
  • Loading branch information
MSOB7YY committed Dec 12, 2023
1 parent 628ba9b commit 447469f
Show file tree
Hide file tree
Showing 6 changed files with 685 additions and 84 deletions.
10 changes: 10 additions & 0 deletions lib/controller/navigator_controller.dart
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,10 @@ class NamidaNavigator {

final navKey = Get.nestedKey(1);

final ytLocalSearchNavigatorKey = Get.nestedKey(9);

bool isytLocalSearchInFullPage = false;

final RxList<NamidaRoute> currentWidgetStack = <NamidaRoute>[].obs;
NamidaRoute? get currentRoute => currentWidgetStack.lastOrNull;
int _currentDialogNumber = 0;
Expand Down Expand Up @@ -313,6 +317,12 @@ class NamidaNavigator {
MiniPlayerController.inst.ytMiniplayerKey.currentState?.animateToState(false);
return;
}
final ytsnvks = ytLocalSearchNavigatorKey?.currentState;
if (ytsnvks != null) {
ytsnvks.pop();
isytLocalSearchInFullPage = false;
return;
}
if (ScrollSearchController.inst.isGlobalSearchMenuShown.value) {
_hideSearchMenuAndUnfocus();
return;
Expand Down
1 change: 1 addition & 0 deletions lib/core/translations/keys.dart
Original file line number Diff line number Diff line change
Expand Up @@ -375,6 +375,7 @@ abstract class LanguageKeys {
String get NOTE => _getKey('NOTE');
String get NUMBER_OF_TRACKS => _getKey('NUMBER_OF_TRACKS');
String get OF => _getKey('OF');
String get OFFLINE_SEARCH => _getKey('OFFLINE_SEARCH');
String get OFFSET => _getKey('OFFSET');
String get OLDEST_WATCH => _getKey('OLDEST_WATCH');
String get OLD_DIRECTORY => _getKey('OLD_DIRECTORY');
Expand Down
37 changes: 24 additions & 13 deletions lib/youtube/controller/youtube_controller.dart
Original file line number Diff line number Diff line change
Expand Up @@ -133,11 +133,11 @@ class YoutubeController {
final downloadedFilesMap = <String, Map<String, File?>>{}.obs;

/// Temporarely saves StreamInfoItem info for flawless experience while waiting for real info.
final _tempVideoInfosFromStreams = <String, StreamInfoItem>{}; // {id: StreamInfoItem()}
final tempVideoInfosFromStreams = <String, StreamInfoItem>{}; // {id: StreamInfoItem()}

/// Used for easily displaying title & channel inside history directly without needing to fetch or rely on cache.
/// This comes mainly after a youtube history import
final _tempBackupVideoInfo = <String, YoutubeVideoHistory>{}; // {id: YoutubeVideoHistory()}
final tempBackupVideoInfo = <String, YoutubeVideoHistory>{}; // {id: YoutubeVideoHistory()}

/// [renameCacheFiles] requires you to stop the download first, otherwise it might result in corrupted files.
Future<void> renameConfigFilename({
Expand Down Expand Up @@ -200,21 +200,19 @@ class YoutubeController {
await _writeTaskGroupToStorage(groupName: groupName);
}

YoutubeVideoHistory? getBackupVideoInfo(String id) {
_tempVideoInfosFromStreams.remove('');
return _tempBackupVideoInfo[id];
}
YoutubeVideoHistory? getBackupVideoInfo(String id) => tempBackupVideoInfo[id];

Future<void> fillBackupInfoMap() async {
final map = await _fillBackupInfoMapIsolate.thready(AppDirs.YT_STATS);
_tempBackupVideoInfo
tempBackupVideoInfo
..clear()
..addAll(map);
tempBackupVideoInfo.remove('');
}

static Map<String, YoutubeVideoHistory> _fillBackupInfoMapIsolate(String dirPath) {
final map = <String, YoutubeVideoHistory>{};
for (final f in Directory(dirPath).listSync()) {
for (final f in Directory(dirPath).listSyncSafe()) {
if (f is File) {
try {
final response = f.readAsJsonSync();
Expand All @@ -235,15 +233,28 @@ class YoutubeController {
String getYoutubeLink(String id) => id.toYTUrl();

VideoInfo? getTemporarelyVideoInfo(String id, {bool checkFromStorage = true}) {
_tempVideoInfosFromStreams.remove('');
final si = _tempVideoInfosFromStreams[id];
final si = tempVideoInfosFromStreams[id];
if (si != null) return VideoInfo.fromStreamInfoItem(si);
if (checkFromStorage) {
final file = File('${AppDirs.YT_METADATA_TEMP}$id.txt');
final res = file.readAsJsonSync();
try {
final strInfo = StreamInfoItem.fromMap(res);
return VideoInfo.fromStreamInfoItem(strInfo);
return strInfo.toVideoInfo();
} catch (_) {}
}
return null;
}

StreamInfoItem? getTemporarelyStreamInfo(String id, {bool checkFromStorage = true}) {
final si = tempVideoInfosFromStreams[id];
if (si != null) si;
if (checkFromStorage) {
final file = File('${AppDirs.YT_METADATA_TEMP}$id.txt');
final res = file.readAsJsonSync();
try {
final strInfo = StreamInfoItem.fromMap(res);
return strInfo;
} catch (_) {}
}
return null;
Expand All @@ -252,7 +263,7 @@ class YoutubeController {
/// Keeps the map at max 2000 items. maintained by least recently used.
void _fillTempVideoInfoMap(Iterable<StreamInfoItem>? items) async {
if (items != null) {
final map = _tempVideoInfosFromStreams;
final map = tempVideoInfosFromStreams;

final entriesForStorage = <MapEntry<String, Map<String, String?>>>[];
for (final e in items) {
Expand Down Expand Up @@ -464,7 +475,7 @@ class YoutubeController {
}
}

final channelUrl = _tempVideoInfosFromStreams[id]?.uploaderUrl;
final channelUrl = tempVideoInfosFromStreams[id]?.uploaderUrl;

if (channelUrl != null) {
await Future.wait([
Expand Down
Loading

0 comments on commit 447469f

Please sign in to comment.