diff --git a/mobile/android/app/src/main/AndroidManifest.xml b/mobile/android/app/src/main/AndroidManifest.xml index 5f4de8284a..c6f0232bb6 100644 --- a/mobile/android/app/src/main/AndroidManifest.xml +++ b/mobile/android/app/src/main/AndroidManifest.xml @@ -178,6 +178,67 @@ android:resource="@xml/memory_widget" /> + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/mobile/android/app/src/main/kotlin/app/alextran/immich/widget/FlexWindowReceivers.kt b/mobile/android/app/src/main/kotlin/app/alextran/immich/widget/FlexWindowReceivers.kt new file mode 100644 index 0000000000..fd43f71fcf --- /dev/null +++ b/mobile/android/app/src/main/kotlin/app/alextran/immich/widget/FlexWindowReceivers.kt @@ -0,0 +1,11 @@ +package app.alextran.immich.widget + +// Widget providers for the Samsung Flex Window cover screen. + +class MemoryReceiverFlex2x2 : MemoryReceiver() + +class MemoryReceiverFlex4x2 : MemoryReceiver() + +class RandomReceiverFlex2x2 : RandomReceiver() + +class RandomReceiverFlex4x2 : RandomReceiver() diff --git a/mobile/android/app/src/main/kotlin/app/alextran/immich/widget/MemoryReceiver.kt b/mobile/android/app/src/main/kotlin/app/alextran/immich/widget/MemoryReceiver.kt index 63b32eb6f0..aee4398e58 100644 --- a/mobile/android/app/src/main/kotlin/app/alextran/immich/widget/MemoryReceiver.kt +++ b/mobile/android/app/src/main/kotlin/app/alextran/immich/widget/MemoryReceiver.kt @@ -11,7 +11,7 @@ import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.launch -class MemoryReceiver : GlanceAppWidgetReceiver() { +open class MemoryReceiver : GlanceAppWidgetReceiver() { override val glanceAppWidget = PhotoWidget() override fun onUpdate( @@ -28,7 +28,7 @@ class MemoryReceiver : GlanceAppWidgetReceiver() { override fun onReceive(context: Context, intent: Intent) { val fromMainApp = intent.getBooleanExtra(HomeWidgetPlugin.TRIGGERED_FROM_HOME_WIDGET, false) - val provider = ComponentName(context, MemoryReceiver::class.java) + val provider = ComponentName(context, javaClass) val glanceIds = AppWidgetManager.getInstance(context).getAppWidgetIds(provider) // Launch coroutine to setup a single shot if the app requested the update diff --git a/mobile/android/app/src/main/kotlin/app/alextran/immich/widget/RandomReceiver.kt b/mobile/android/app/src/main/kotlin/app/alextran/immich/widget/RandomReceiver.kt index a7662181bc..3d4c581e52 100644 --- a/mobile/android/app/src/main/kotlin/app/alextran/immich/widget/RandomReceiver.kt +++ b/mobile/android/app/src/main/kotlin/app/alextran/immich/widget/RandomReceiver.kt @@ -11,7 +11,7 @@ import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.launch -class RandomReceiver : GlanceAppWidgetReceiver() { +open class RandomReceiver : GlanceAppWidgetReceiver() { override val glanceAppWidget = PhotoWidget() override fun onUpdate( @@ -28,7 +28,7 @@ class RandomReceiver : GlanceAppWidgetReceiver() { override fun onReceive(context: Context, intent: Intent) { val fromMainApp = intent.getBooleanExtra(HomeWidgetPlugin.TRIGGERED_FROM_HOME_WIDGET, false) - val provider = ComponentName(context, RandomReceiver::class.java) + val provider = ComponentName(context, javaClass) val glanceIds = AppWidgetManager.getInstance(context).getAppWidgetIds(provider) // Launch coroutine to setup a single shot if the app requested the update diff --git a/mobile/android/app/src/main/res/values/attrs_samsung_widget.xml b/mobile/android/app/src/main/res/values/attrs_samsung_widget.xml new file mode 100644 index 0000000000..27254c3866 --- /dev/null +++ b/mobile/android/app/src/main/res/values/attrs_samsung_widget.xml @@ -0,0 +1,9 @@ + + + + + + diff --git a/mobile/android/app/src/main/res/values/strings.xml b/mobile/android/app/src/main/res/values/strings.xml index d543e33116..89b6384ae4 100644 --- a/mobile/android/app/src/main/res/values/strings.xml +++ b/mobile/android/app/src/main/res/values/strings.xml @@ -2,6 +2,11 @@ Memories Random + + Memories (2x2) + Memories (4x2) + Random (2x2) + Random (4x2) See memories from Immich. View a random image from your library or a specific album. diff --git a/mobile/android/app/src/main/res/xml/memory_widget_flex_2x2.xml b/mobile/android/app/src/main/res/xml/memory_widget_flex_2x2.xml new file mode 100644 index 0000000000..8e0379e14f --- /dev/null +++ b/mobile/android/app/src/main/res/xml/memory_widget_flex_2x2.xml @@ -0,0 +1,19 @@ + + + diff --git a/mobile/android/app/src/main/res/xml/memory_widget_flex_4x2.xml b/mobile/android/app/src/main/res/xml/memory_widget_flex_4x2.xml new file mode 100644 index 0000000000..40d2faff9c --- /dev/null +++ b/mobile/android/app/src/main/res/xml/memory_widget_flex_4x2.xml @@ -0,0 +1,19 @@ + + + diff --git a/mobile/android/app/src/main/res/xml/random_widget_flex_2x2.xml b/mobile/android/app/src/main/res/xml/random_widget_flex_2x2.xml new file mode 100644 index 0000000000..791bc03c66 --- /dev/null +++ b/mobile/android/app/src/main/res/xml/random_widget_flex_2x2.xml @@ -0,0 +1,21 @@ + + + diff --git a/mobile/android/app/src/main/res/xml/random_widget_flex_4x2.xml b/mobile/android/app/src/main/res/xml/random_widget_flex_4x2.xml new file mode 100644 index 0000000000..5baa4e01c0 --- /dev/null +++ b/mobile/android/app/src/main/res/xml/random_widget_flex_4x2.xml @@ -0,0 +1,21 @@ + + + diff --git a/mobile/android/app/src/main/res/xml/samsung_appwidget_sub_screen.xml b/mobile/android/app/src/main/res/xml/samsung_appwidget_sub_screen.xml new file mode 100644 index 0000000000..3e7c6a0f27 --- /dev/null +++ b/mobile/android/app/src/main/res/xml/samsung_appwidget_sub_screen.xml @@ -0,0 +1,3 @@ + + + diff --git a/mobile/lib/constants/constants.dart b/mobile/lib/constants/constants.dart index c2a13c3ec2..cadb896c42 100644 --- a/mobile/lib/constants/constants.dart +++ b/mobile/lib/constants/constants.dart @@ -37,9 +37,14 @@ const String kWidgetCustomHeaders = "widget_custom_headers"; // add widget identifiers here for new widgets // these are used to force a widget refresh // (iOSName, androidFQDN) +// Android-only providers reuse the iOS name of their counterpart, updateWidget rejects a null one. const List<(String, String)> kWidgetNames = [ ('com.immich.widget.random', 'app.alextran.immich.widget.RandomReceiver'), ('com.immich.widget.memory', 'app.alextran.immich.widget.MemoryReceiver'), + ('com.immich.widget.memory', 'app.alextran.immich.widget.MemoryReceiverFlex2x2'), + ('com.immich.widget.memory', 'app.alextran.immich.widget.MemoryReceiverFlex4x2'), + ('com.immich.widget.random', 'app.alextran.immich.widget.RandomReceiverFlex2x2'), + ('com.immich.widget.random', 'app.alextran.immich.widget.RandomReceiverFlex4x2'), ]; const int kMinMonthsToEnableScrubberSnap = 12;