From d671030cb3de31e6213715e7e534fa5cd4f8e949 Mon Sep 17 00:00:00 2001 From: Thibault Deckers Date: Thu, 9 Mar 2023 19:56:30 +0100 Subject: [PATCH] wallpaper: fixed video playback, session, controls --- .../deckers/thibault/aves/WallpaperActivity.kt | 15 +++++++++++++++ lib/widgets/home_page.dart | 5 ++++- lib/widgets/viewer/entry_viewer_stack.dart | 8 ++++---- lib/widgets/viewer/overlay/viewer_buttons.dart | 4 +++- lib/widgets/wallpaper_page.dart | 17 ++++++++++++----- 5 files changed, 38 insertions(+), 11 deletions(-) diff --git a/android/app/src/main/kotlin/deckers/thibault/aves/WallpaperActivity.kt b/android/app/src/main/kotlin/deckers/thibault/aves/WallpaperActivity.kt index 202e73090..3c0b0d1f6 100644 --- a/android/app/src/main/kotlin/deckers/thibault/aves/WallpaperActivity.kt +++ b/android/app/src/main/kotlin/deckers/thibault/aves/WallpaperActivity.kt @@ -13,17 +13,20 @@ import deckers.thibault.aves.channel.calls.* import deckers.thibault.aves.channel.calls.window.ActivityWindowHandler import deckers.thibault.aves.channel.calls.window.WindowHandler import deckers.thibault.aves.channel.streams.ImageByteStreamHandler +import deckers.thibault.aves.channel.streams.MediaCommandStreamHandler import deckers.thibault.aves.utils.FlutterUtils import deckers.thibault.aves.utils.FlutterUtils.enableSoftwareRendering import deckers.thibault.aves.utils.LogUtils import deckers.thibault.aves.utils.getParcelableExtraCompat import io.flutter.embedding.android.FlutterFragmentActivity import io.flutter.embedding.engine.FlutterEngine +import io.flutter.plugin.common.EventChannel import io.flutter.plugin.common.MethodCall import io.flutter.plugin.common.MethodChannel class WallpaperActivity : FlutterFragmentActivity() { private lateinit var intentDataMap: MutableMap + private lateinit var mediaSessionHandler: MediaSessionHandler override fun onCreate(savedInstanceState: Bundle?) { if (FlutterUtils.isSoftwareRenderingRequired()) { @@ -42,12 +45,19 @@ class WallpaperActivity : FlutterFragmentActivity() { super.configureFlutterEngine(flutterEngine) val messenger = flutterEngine.dartExecutor + // notification: platform -> dart + val mediaCommandStreamHandler = MediaCommandStreamHandler().apply { + EventChannel(messenger, MediaCommandStreamHandler.CHANNEL).setStreamHandler(this) + } + // dart -> platform -> dart // - need Context + mediaSessionHandler = MediaSessionHandler(this, mediaCommandStreamHandler) MethodChannel(messenger, DeviceHandler.CHANNEL).setMethodCallHandler(DeviceHandler(this)) MethodChannel(messenger, EmbeddedDataHandler.CHANNEL).setMethodCallHandler(EmbeddedDataHandler(this)) MethodChannel(messenger, MediaFetchBytesHandler.CHANNEL, AvesByteSendingMethodCodec.INSTANCE).setMethodCallHandler(MediaFetchBytesHandler(this)) MethodChannel(messenger, MediaFetchObjectHandler.CHANNEL).setMethodCallHandler(MediaFetchObjectHandler(this)) + MethodChannel(messenger, MediaSessionHandler.CHANNEL).setMethodCallHandler(mediaSessionHandler) MethodChannel(messenger, MetadataFetchHandler.CHANNEL).setMethodCallHandler(MetadataFetchHandler(this)) MethodChannel(messenger, StorageHandler.CHANNEL).setMethodCallHandler(StorageHandler(this)) // - need ContextWrapper @@ -79,6 +89,11 @@ class WallpaperActivity : FlutterFragmentActivity() { } } + override fun onDestroy() { + mediaSessionHandler.dispose() + super.onDestroy() + } + private fun onMethodCall(call: MethodCall, result: MethodChannel.Result) { when (call.method) { "getIntentData" -> { diff --git a/lib/widgets/home_page.dart b/lib/widgets/home_page.dart index be46586ce..e03454aaf 100644 --- a/lib/widgets/home_page.dart +++ b/lib/widgets/home_page.dart @@ -229,9 +229,12 @@ class _HomePageState extends State { } } break; + case AppMode.setWallpaper: + // for video playback storage + await metadataDb.init(); + break; case AppMode.pickMediaInternal: case AppMode.pickFilterInternal: - case AppMode.setWallpaper: case AppMode.slideshow: break; } diff --git a/lib/widgets/viewer/entry_viewer_stack.dart b/lib/widgets/viewer/entry_viewer_stack.dart index 427755218..d52c28ed6 100644 --- a/lib/widgets/viewer/entry_viewer_stack.dart +++ b/lib/widgets/viewer/entry_viewer_stack.dart @@ -483,6 +483,10 @@ class _EntryViewerStackState extends State with EntryViewContr } } else if (notification is ToggleOverlayNotification) { _overlayVisible.value = notification.visible ?? !_overlayVisible.value; + } else if (notification is VideoActionNotification) { + final controller = notification.controller; + final action = notification.action; + _onVideoAction(context, controller, action); } else if (notification is TvShowLessInfoNotification) { if (_overlayVisible.value) { _overlayVisible.value = false; @@ -503,10 +507,6 @@ class _EntryViewerStackState extends State with EntryViewContr _goToHorizontalPageByDelta(delta: 1, animate: notification.animate); } else if (notification is ShowEntryNotification) { _goToHorizontalPageByIndex(page: notification.index, animate: notification.animate); - } else if (notification is VideoActionNotification) { - final controller = notification.controller; - final action = notification.action; - _onVideoAction(context, controller, action); } else { return false; } diff --git a/lib/widgets/viewer/overlay/viewer_buttons.dart b/lib/widgets/viewer/overlay/viewer_buttons.dart index 41208da65..2ad237638 100644 --- a/lib/widgets/viewer/overlay/viewer_buttons.dart +++ b/lib/widgets/viewer/overlay/viewer_buttons.dart @@ -1,3 +1,5 @@ +import 'dart:math'; + import 'package:aves/app_mode.dart'; import 'package:aves/model/actions/entry_actions.dart'; import 'package:aves/model/entry.dart'; @@ -79,7 +81,7 @@ class ViewerButtons extends StatelessWidget { return Selector( selector: (context, s) => s.isRotationLocked, builder: (context, s, child) { - final quickActions = (trashed ? EntryActions.trashed : settings.viewerQuickActions).where(isVisible).where(actionDelegate.canApply).take(availableCount - 1).toList(); + final quickActions = (trashed ? EntryActions.trashed : settings.viewerQuickActions).where(isVisible).where(actionDelegate.canApply).take(max(0, availableCount - 1)).toList(); List getMenuActions(List categoryActions) { return categoryActions.where((action) => !quickActions.contains(action)).where(isVisible).toList(); } diff --git a/lib/widgets/wallpaper_page.dart b/lib/widgets/wallpaper_page.dart index e052b4e8e..81d347d08 100644 --- a/lib/widgets/wallpaper_page.dart +++ b/lib/widgets/wallpaper_page.dart @@ -1,3 +1,4 @@ +import 'package:aves/model/actions/entry_actions.dart'; import 'package:aves/model/entry.dart'; import 'package:aves/model/settings/enums/enums.dart'; import 'package:aves/model/settings/settings.dart'; @@ -130,6 +131,10 @@ class _EntryEditorState extends State with EntryViewControllerMixin onNotification: (dynamic notification) { if (notification is ToggleOverlayNotification) { _overlayVisible.value = notification.visible ?? !_overlayVisible.value; + } else if (notification is VideoActionNotification) { + final controller = notification.controller; + final action = notification.action; + _onVideoAction(context, controller, action); } return true; }, @@ -171,11 +176,7 @@ class _EntryEditorState extends State with EntryViewControllerMixin entry: targetEntry, controller: videoController, scale: _overlayVideoControlScale, - onActionSelected: (action) { - if (videoController != null) { - _videoActionDelegate.onActionSelected(context, videoController, action); - } - }, + onActionSelected: (action) => _onVideoAction(context, videoController, action), onActionMenuOpened: () { // if the menu is opened while overlay is hiding, // the popup menu button is disposed and menu items are ineffective, @@ -235,6 +236,12 @@ class _EntryEditorState extends State with EntryViewControllerMixin ); } + void _onVideoAction(BuildContext context, AvesVideoController? videoController, EntryAction action) { + if (videoController != null) { + _videoActionDelegate.onActionSelected(context, videoController, action); + } + } + // overlay Future _onOverlayVisibleChanged({bool animate = true}) async {