From 6e28fbfea522af73d6bae2d674414b16aa43a4fa Mon Sep 17 00:00:00 2001 From: Josia Pietsch Date: Wed, 11 Sep 2024 21:07:18 +0200 Subject: [PATCH] chore: refactored code --- app/src/main/AndroidManifest.xml | 8 +- .../de/jrpie/android/launcher/Application.kt | 3 +- .../de/jrpie/android/launcher/Functions.kt | 255 +++--------- .../java/de/jrpie/android/launcher/Gesture.kt | 155 ------- .../jrpie/android/launcher/actions/Action.kt | 100 +++++ .../android/launcher/actions/AppAction.kt | 85 ++++ .../jrpie/android/launcher/actions/AppInfo.kt | 49 +++ .../jrpie/android/launcher/actions/Gesture.kt | 222 ++++++++++ .../launcher/actions/LauncherAction.kt | 185 +++++++++ .../android/launcher/list/apps/AppInfo.kt | 16 - .../launcher/list/other/LauncherAction.kt | 43 -- .../LauncherPreferences$Config.java | 76 ++-- .../launcher/preferences/Preferences.kt | 386 +++++++++++++++--- .../android/launcher/{ => ui}/HomeActivity.kt | 84 ++-- .../android/launcher/{ => ui}/UIObject.kt | 8 +- .../launcher/{ => ui}/list/ListActivity.kt | 22 +- .../{ => ui}/list/apps/AppsRecyclerAdapter.kt | 92 +++-- .../{ => ui}/list/apps/ListFragmentApps.kt | 15 +- .../{ => ui}/list/other/ListFragmentOther.kt | 3 +- .../list/other/OtherRecyclerAdapter.kt | 23 +- .../{ => ui}/settings/SettingsActivity.kt | 48 ++- .../actions/SettingsFragmentActions.kt | 16 +- .../SettingsFragmentActionsRecycler.kt | 92 ++--- .../launcher/SettingsFragmentLauncher.kt | 15 +- .../settings/meta/SettingsFragmentMeta.kt | 12 +- .../{ => ui}/tutorial/TutorialActivity.kt | 35 +- .../tutorial/tabs/TutorialFragmentConcept.kt | 7 +- .../tutorial/tabs/TutorialFragmentFinish.kt | 11 +- .../tutorial/tabs/TutorialFragmentSetup.kt | 6 +- .../tutorial/tabs/TutorialFragmentStart.kt | 9 +- .../tutorial/tabs/TutorialFragmentUsage.kt | 6 +- app/src/main/res/layout/home.xml | 2 +- app/src/main/res/layout/list.xml | 2 +- app/src/main/res/layout/settings.xml | 2 +- app/src/main/res/layout/settings_actions.xml | 2 +- app/src/main/res/layout/settings_meta.xml | 2 +- app/src/main/res/layout/tutorial.xml | 2 +- app/src/main/res/layout/tutorial_concept.xml | 2 +- app/src/main/res/layout/tutorial_finish.xml | 2 +- app/src/main/res/layout/tutorial_setup.xml | 4 +- app/src/main/res/layout/tutorial_start.xml | 2 +- app/src/main/res/layout/tutorial_usage.xml | 2 +- app/src/main/res/values/strings.xml | 2 +- 43 files changed, 1367 insertions(+), 746 deletions(-) delete mode 100644 app/src/main/java/de/jrpie/android/launcher/Gesture.kt create mode 100644 app/src/main/java/de/jrpie/android/launcher/actions/Action.kt create mode 100644 app/src/main/java/de/jrpie/android/launcher/actions/AppAction.kt create mode 100644 app/src/main/java/de/jrpie/android/launcher/actions/AppInfo.kt create mode 100644 app/src/main/java/de/jrpie/android/launcher/actions/Gesture.kt create mode 100644 app/src/main/java/de/jrpie/android/launcher/actions/LauncherAction.kt delete mode 100644 app/src/main/java/de/jrpie/android/launcher/list/apps/AppInfo.kt delete mode 100644 app/src/main/java/de/jrpie/android/launcher/list/other/LauncherAction.kt rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/HomeActivity.kt (80%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/UIObject.kt (94%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/list/ListActivity.kt (91%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/list/apps/AppsRecyclerAdapter.kt (71%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/list/apps/ListFragmentApps.kt (87%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/list/other/ListFragmentOther.kt (94%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/list/other/OtherRecyclerAdapter.kt (77%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/settings/SettingsActivity.kt (71%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/settings/actions/SettingsFragmentActions.kt (82%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/settings/actions/SettingsFragmentActionsRecycler.kt (69%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/settings/launcher/SettingsFragmentLauncher.kt (84%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/settings/meta/SettingsFragmentMeta.kt (93%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/tutorial/TutorialActivity.kt (74%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/tutorial/tabs/TutorialFragmentConcept.kt (88%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/tutorial/tabs/TutorialFragmentFinish.kt (82%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/tutorial/tabs/TutorialFragmentSetup.kt (84%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/tutorial/tabs/TutorialFragmentStart.kt (83%) rename app/src/main/java/de/jrpie/android/launcher/{ => ui}/tutorial/tabs/TutorialFragmentUsage.kt (84%) diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index 5ccea00..b3b266f 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -19,7 +19,7 @@ android:theme="@style/launcherBaseTheme"> diff --git a/app/src/main/java/de/jrpie/android/launcher/Application.kt b/app/src/main/java/de/jrpie/android/launcher/Application.kt index 49a9014..6f0aaad 100644 --- a/app/src/main/java/de/jrpie/android/launcher/Application.kt +++ b/app/src/main/java/de/jrpie/android/launcher/Application.kt @@ -1,10 +1,9 @@ package de.jrpie.android.launcher -import android.content.Context import androidx.preference.PreferenceManager import de.jrpie.android.launcher.preferences.LauncherPreferences -class Application: android.app.Application() { +class Application : android.app.Application() { override fun onCreate() { super.onCreate() diff --git a/app/src/main/java/de/jrpie/android/launcher/Functions.kt b/app/src/main/java/de/jrpie/android/launcher/Functions.kt index 3358909..cf6a511 100644 --- a/app/src/main/java/de/jrpie/android/launcher/Functions.kt +++ b/app/src/main/java/de/jrpie/android/launcher/Functions.kt @@ -1,7 +1,6 @@ package de.jrpie.android.launcher import android.app.Activity -import android.app.AlertDialog import android.app.Service import android.app.role.RoleManager import android.content.Context @@ -10,42 +9,27 @@ import android.content.pm.ApplicationInfo import android.content.pm.LauncherActivityInfo import android.content.pm.LauncherApps import android.content.pm.PackageManager -import android.graphics.BlendMode -import android.graphics.BlendModeColorFilter import android.graphics.ColorMatrix import android.graphics.ColorMatrixColorFilter -import android.graphics.PorterDuff -import android.graphics.PorterDuffColorFilter import android.graphics.Rect -import android.graphics.drawable.Drawable -import android.media.AudioManager import android.net.Uri import android.os.Build import android.os.Bundle -import android.os.SystemClock import android.os.UserHandle import android.os.UserManager import android.provider.Settings import android.util.DisplayMetrics import android.util.Log -import android.view.KeyEvent import android.view.View -import android.view.Window -import android.view.WindowManager import android.view.animation.AlphaAnimation import android.view.animation.Animation import android.view.inputmethod.InputMethodManager -import android.widget.Button import android.widget.ImageView -import android.widget.Switch -import android.widget.Toast -import androidx.annotation.RequiresApi -import de.jrpie.android.launcher.list.ListActivity -import de.jrpie.android.launcher.list.apps.AppInfo -import de.jrpie.android.launcher.list.apps.AppsRecyclerAdapter -import de.jrpie.android.launcher.list.other.LauncherAction -import de.jrpie.android.launcher.settings.SettingsActivity -import de.jrpie.android.launcher.tutorial.TutorialActivity +import de.jrpie.android.launcher.actions.Action +import de.jrpie.android.launcher.actions.AppInfo +import de.jrpie.android.launcher.actions.Gesture +import de.jrpie.android.launcher.ui.list.apps.AppsRecyclerAdapter +import de.jrpie.android.launcher.ui.tutorial.TutorialActivity const val INVALID_USER = -1 @@ -87,19 +71,23 @@ fun setDefaultHomeScreen(context: Context, checkDefault: Boolean = false) { if (checkDefault && Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q - && context is Activity) { + && context is Activity + ) { val roleManager = context.getSystemService(RoleManager::class.java) - if(!roleManager.isRoleHeld(RoleManager.ROLE_HOME)) { - context.startActivityForResult(roleManager.createRequestRoleIntent(RoleManager.ROLE_HOME), REQUEST_SET_DEFAULT_HOME) + if (!roleManager.isRoleHeld(RoleManager.ROLE_HOME)) { + context.startActivityForResult( + roleManager.createRequestRoleIntent(RoleManager.ROLE_HOME), + REQUEST_SET_DEFAULT_HOME + ) } return } - if(checkDefault) { + if (checkDefault) { val testIntent = Intent(Intent.ACTION_MAIN) testIntent.addCategory(Intent.CATEGORY_HOME) val defaultHome = testIntent.resolveActivity(context.packageManager)?.packageName - if(defaultHome == context.packageName){ + if (defaultHome == context.packageName) { // Launcher is already the default home app return } @@ -108,170 +96,48 @@ fun setDefaultHomeScreen(context: Context, checkDefault: Boolean = false) { context.startActivity(intent) } -/* Activity related */ -fun isInstalled(uri: String, context: Context): Boolean { - if (uri.startsWith("launcher:")) return true // All internal actions - - try { - context.packageManager.getPackageInfo(uri, PackageManager.GET_ACTIVITIES) - return true - } catch (_: PackageManager.NameNotFoundException) { } - return false -} - -private fun getIntent(packageName: String, context: Context): Intent? { +fun getIntent(packageName: String, context: Context): Intent? { val intent: Intent? = context.packageManager.getLaunchIntentForPackage(packageName) intent?.addCategory(Intent.CATEGORY_LAUNCHER) return intent } - -fun launch( - data: String, user: Int?, - activity: Activity, - animationIn: Int = android.R.anim.fade_in, animationOut: Int = android.R.anim.fade_out -) { - - if (LauncherAction.isOtherAction(data)) { // [type]:[info] - LauncherAction.byId(data)?.let {it.launch(activity) } - } - else launchApp(data, user, activity) // app - - activity.overridePendingTransition(animationIn, animationOut) -} - -/* Media player actions */ - -fun audioNextTrack(activity: Activity) { - - val mAudioManager = activity.getSystemService(Context.AUDIO_SERVICE) as AudioManager - - val eventTime: Long = SystemClock.uptimeMillis() - - val downEvent = KeyEvent(eventTime, eventTime, KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_MEDIA_NEXT, 0) - mAudioManager.dispatchMediaKeyEvent(downEvent) - - val upEvent = KeyEvent(eventTime, eventTime, KeyEvent.ACTION_UP, KeyEvent.KEYCODE_MEDIA_NEXT, 0) - mAudioManager.dispatchMediaKeyEvent(upEvent) -} - -fun audioPreviousTrack(activity: Activity) { - val mAudioManager = activity.getSystemService(Context.AUDIO_SERVICE) as AudioManager - - val eventTime: Long = SystemClock.uptimeMillis() - - val downEvent = - KeyEvent(eventTime, eventTime, KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_MEDIA_PREVIOUS, 0) - mAudioManager.dispatchMediaKeyEvent(downEvent) - - val upEvent = KeyEvent(eventTime, eventTime, KeyEvent.ACTION_UP, KeyEvent.KEYCODE_MEDIA_PREVIOUS, 0) - mAudioManager.dispatchMediaKeyEvent(upEvent) -} - -fun audioVolumeUp(activity: Activity) { - val audioManager = - activity.getSystemService(Context.AUDIO_SERVICE) as AudioManager - - audioManager.adjustStreamVolume( - AudioManager.STREAM_MUSIC, - AudioManager.ADJUST_RAISE, - AudioManager.FLAG_SHOW_UI - ) -} - -fun audioVolumeDown(activity: Activity) { - val audioManager = - activity.getSystemService(Context.AUDIO_SERVICE) as AudioManager - - audioManager.adjustStreamVolume( - AudioManager.STREAM_MUSIC, - AudioManager.ADJUST_LOWER, - AudioManager.FLAG_SHOW_UI - ) -} - -fun expandNotificationsPanel(context: Context) { - /* https://stackoverflow.com/a/15582509 */ - try { - @Suppress("SpellCheckingInspection") - val statusBarService: Any? = context.getSystemService("statusbar") - val statusBarManager = Class.forName("android.app.StatusBarManager") - val showStatusBar = statusBarManager.getMethod("expandNotificationsPanel") - showStatusBar.invoke(statusBarService) - } catch (e: Exception) { - Toast.makeText(context, context.getString(R.string.alert_cant_expand_notifications_panel), Toast.LENGTH_LONG).show() - } -} - /* --- */ fun getUserFromId(user: Int?, context: Context): UserHandle? { val userManager = context.getSystemService(Service.USER_SERVICE) as UserManager return userManager.userProfiles.firstOrNull { it.hashCode() == user } } -fun getLauncherActivityInfo(packageName: String, user: Int?, context: Context): LauncherActivityInfo? { + +fun getLauncherActivityInfo( + packageName: String, + user: Int?, + context: Context +): LauncherActivityInfo? { val launcherApps = context.getSystemService(Service.LAUNCHER_APPS_SERVICE) as LauncherApps - return getUserFromId(user,context)?.let { - userHandle -> launcherApps.getActivityList(packageName, userHandle).firstOrNull() + return getUserFromId(user, context)?.let { userHandle -> + launcherApps.getActivityList(packageName, userHandle).firstOrNull() } } -fun uninstallApp(packageName: String, user: Int?, activity: Activity) { + +fun uninstallApp(appInfo: AppInfo, activity: Activity) { + val packageName = appInfo.packageName.toString() + val user = appInfo.user + Log.i("Launcher", "uninstalling $packageName ($user)") val intent = Intent(Intent.ACTION_UNINSTALL_PACKAGE) intent.data = Uri.parse("package:$packageName") - getUserFromId(user, activity)?.let { - user -> intent.putExtra(Intent.EXTRA_USER, user) + getUserFromId(user, activity)?.let { user -> + intent.putExtra(Intent.EXTRA_USER, user) } intent.putExtra(Intent.EXTRA_RETURN_RESULT, true) - activity.startActivityForResult(intent, + activity.startActivityForResult( + intent, REQUEST_UNINSTALL ) } -fun launchApp(packageName: String, user: Int?, context: Context, rect: Rect? = null) { - if (user != null && user != INVALID_USER) { - val launcherApps = context.getSystemService(Service.LAUNCHER_APPS_SERVICE) as LauncherApps - getLauncherActivityInfo(packageName,user,context)?.let { - app -> launcherApps.startMainActivity(app.componentName, app.user, rect, null) - return - } - } - - val intent = getIntent(packageName, context) - - if (intent != null) { - context.startActivity(intent) - } else { - if (isInstalled(packageName, context)){ - - AlertDialog.Builder( - context, - R.style.AlertDialogCustom - ) - .setTitle(context.getString(R.string.alert_cant_open_title)) - .setMessage(context.getString(R.string.alert_cant_open_message)) - .setPositiveButton(android.R.string.ok - ) { _, _ -> - openAppSettings( - packageName, - user, - context - ) - } - .setNegativeButton(android.R.string.cancel, null) - .setIcon(android.R.drawable.ic_dialog_info) - .show() - } else { - Toast.makeText( - context, - context.getString(R.string.toast_cant_open_message), - Toast.LENGTH_SHORT - ).show() - } - } -} - fun openNewTabWindow(urls: String, context: Context) { val uris = Uri.parse(urls) val intents = Intent(Intent.ACTION_VIEW, uris) @@ -281,39 +147,22 @@ fun openNewTabWindow(urls: String, context: Context) { context.startActivity(intents) } - -fun openAppSettings(packageName: String, user: Int?, context: Context, sourceBounds: Rect? = null, opts: Bundle? = null) { +fun openAppSettings( + appInfo: AppInfo, + context: Context, + sourceBounds: Rect? = null, + opts: Bundle? = null +) { val launcherApps = context.getSystemService(Service.LAUNCHER_APPS_SERVICE) as LauncherApps - getLauncherActivityInfo(packageName, user, context)?.let { - app -> launcherApps.startAppDetailsActivity(app.componentName, app.user, sourceBounds, opts) + getLauncherActivityInfo(appInfo.packageName.toString(), appInfo.user, context)?.let { app -> + launcherApps.startAppDetailsActivity(app.componentName, app.user, sourceBounds, opts) } } -fun openSettings(activity: Activity) { - activity.startActivity(Intent(activity, SettingsActivity::class.java)) +fun openTutorial(context: Context) { + context.startActivity(Intent(context, TutorialActivity::class.java)) } -fun openTutorial(activity: Activity){ - activity.startActivity(Intent(activity, TutorialActivity::class.java)) -} - -fun openAppsList(activity: Activity){ - val intent = Intent(activity, ListActivity::class.java) - intent.putExtra("intention", ListActivity.ListActivityIntention.VIEW.toString()) - activity.startActivity(intent) -} - -fun getAppIcon(context: Context, packageName: String, user: Int?): Drawable { - if (user != null) { - val launcherApps = context.getSystemService(Service.LAUNCHER_APPS_SERVICE) as LauncherApps - getUserFromId(user,context)?.let { - userHandle -> launcherApps.getActivityList(packageName, userHandle).firstOrNull()?.let { - app -> return app.getBadgedIcon(0) - } - } - } - return context.packageManager.getApplicationIcon(packageName) -} /** * [loadApps] is used to speed up the [AppsRecyclerAdapter] loading time, @@ -327,21 +176,22 @@ fun loadApps(packageManager: PackageManager, context: Context) { // TODO: shortcuts - launcherApps.getShortcuts() val users = userManager.userProfiles - for(user in users) { - for (activityInfo in launcherApps.getActivityList(null,user)) { + for (user in users) { + for (activityInfo in launcherApps.getActivityList(null, user)) { val app = AppInfo() app.label = activityInfo.label app.packageName = activityInfo.applicationInfo.packageName app.icon = activityInfo.getBadgedIcon(0) app.user = user.hashCode() - app.isSystemApp = activityInfo.applicationInfo.flags.and(ApplicationInfo.FLAG_SYSTEM) != 0 + app.isSystemApp = + activityInfo.applicationInfo.flags.and(ApplicationInfo.FLAG_SYSTEM) != 0 loadList.add(app) } } // fallback option - if(loadList.isEmpty()){ + if (loadList.isEmpty()) { Log.i("Launcher", "using fallback option to load packages") val i = Intent(Intent.ACTION_MAIN, null) i.addCategory(Intent.CATEGORY_LAUNCHER) @@ -361,14 +211,9 @@ fun loadApps(packageManager: PackageManager, context: Context) { // Used in Tutorial and Settings `ActivityOnResult` -fun saveListActivityChoice(context: Context, data: Intent?) { - val value = data?.getStringExtra("value") - var user = data?.getIntExtra("user", INVALID_USER) - user = user?.let{ if(it == INVALID_USER) null else it } - +fun saveListActivityChoice(data: Intent?) { val forGesture = data?.getStringExtra("forGesture") ?: return - - Gesture.byId(forGesture)?.setApp(context, value.toString(), user) + Gesture.byId(forGesture)?.let { Action.setActionForGesture(it, Action.fromIntent(data)) } } // Taken from https://stackoverflow.com/a/50743764/12787264 @@ -380,7 +225,7 @@ fun openSoftKeyboard(context: Context, view: View) { } // Taken from: https://stackoverflow.com/a/30340794/12787264 -fun transformGrayscale(imageView: ImageView){ +fun transformGrayscale(imageView: ImageView) { val matrix = ColorMatrix() matrix.setSaturation(0f) diff --git a/app/src/main/java/de/jrpie/android/launcher/Gesture.kt b/app/src/main/java/de/jrpie/android/launcher/Gesture.kt deleted file mode 100644 index 53745b5..0000000 --- a/app/src/main/java/de/jrpie/android/launcher/Gesture.kt +++ /dev/null @@ -1,155 +0,0 @@ -package de.jrpie.android.launcher - -import android.app.Activity -import android.content.Context -import de.jrpie.android.launcher.preferences.LauncherPreferences - -/** - * @param id internal id to serialize the action. Used as a key in shared preferences. - * @param defaultsResource res id of array of default actions for the gesture. - * @param labelResource res id of the name of the gesture. - * @param animationIn res id of transition animation (in) when using the gesture to launch an app. - * @param animationOut res id of transition animation (out) when using the gesture to launch an app. - */ -enum class Gesture (val id: String, private val labelResource: Int, - private val defaultsResource: Int, - private val animationIn: Int = android.R.anim.fade_in, - private val animationOut: Int = android.R.anim.fade_out){ - VOLUME_UP("action.volume_up", R.string.settings_gesture_vol_up, R.array.default_volume_up, 0,0), - VOLUME_DOWN("action.volume_down", R.string.settings_gesture_vol_down, R.array.default_volume_down,0,0), - TIME("action.time", R.string.settings_gesture_time, R.array.default_time), - DATE("action.date", R.string.settings_gesture_date, R.array.default_date), - LONG_CLICK("action.long_click", R.string.settings_gesture_long_click, R.array.default_long_click, 0,0), - DOUBLE_CLICK("action.double_click", R.string.settings_gesture_double_click, R.array.default_double_click,0,0), - SWIPE_UP("action.up", R.string.settings_gesture_up, R.array.default_up, R.anim.bottom_up), - SWIPE_UP_LEFT_EDGE("action.up_left", R.string.settings_gesture_up_left_edge, R.array.default_up_left, R.anim.bottom_up), - SWIPE_UP_RIGHT_EDGE("action.up_right", R.string.settings_gesture_up_right_edge, R.array.default_up_right, R.anim.bottom_up), - SWIPE_UP_DOUBLE( "action.double_up", R.string.settings_gesture_double_up, R.array.default_double_up, R.anim.bottom_up), - SWIPE_DOWN("action.down", R.string.settings_gesture_down, R.array.default_down, R.anim.top_down), - SWIPE_DOWN_LEFT_EDGE("action.down_left", R.string.settings_gesture_down_left_edge, R.array.default_down_left, R.anim.top_down), - SWIPE_DOWN_RIGHT_EDGE("action.down_right", R.string.settings_gesture_down_right_edge, R.array.default_down_right, R.anim.top_down), - SWIPE_DOWN_DOUBLE("action.double_down", R.string.settings_gesture_double_down, R.array.default_double_down, R.anim.top_down), - SWIPE_LEFT("action.left", R.string.settings_gesture_left, R.array.default_left, R.anim.right_left), - SWIPE_LEFT_TOP_EDGE("action.left_top", R.string.settings_gesture_left_top_edge, R.array.default_left_top, R.anim.right_left), - SWIPE_LEFT_BOTTOM_EDGE("action.left_bottom", R.string.settings_gesture_left_bottom_edge, R.array.default_left_bottom, R.anim.right_left), - SWIPE_LEFT_DOUBLE("action.double_left", R.string.settings_gesture_double_left, R.array.default_double_left, R.anim.right_left), - SWIPE_RIGHT("action.right", R.string.settings_gesture_right, R.array.default_right, R.anim.left_right), - SWIPE_RIGHT_TOP_EDGE("action.right_top", R.string.settings_gesture_right_top_edge, R.array.default_right_top, R.anim.left_right), - SWIPE_RIGHT_BOTTOM_EDGE("action.right_bottom", R.string.settings_gesture_right_bottom_edge, R.array.default_right_bottom, R.anim.left_right), - SWIPE_RIGHT_DOUBLE("action.double_right", R.string.settings_gesture_double_right, R.array.default_double_right, R.anim.left_right); - - enum class Edge{ - TOP, BOTTOM, LEFT, RIGHT - } - - fun getApp(context: Context): Pair { - val preferences = LauncherPreferences.getSharedPreferences() - var packageName = preferences.getString(this.id + ".app", "")!! - var u: Int? = preferences.getInt(this.id + ".user", INVALID_USER) - u = if(u == INVALID_USER) null else u - return Pair(packageName,u) - } - - fun removeApp(context: Context) { - LauncherPreferences.getSharedPreferences().edit() - .putString(this.id + ".app", "") // clear it - .apply() - } - - fun setApp(context: Context, app: String, user: Int?) { - LauncherPreferences.getSharedPreferences().edit() - .putString(this.id + ".app", app) - .apply() - - val u = user?: INVALID_USER - LauncherPreferences.getSharedPreferences().edit() - .putInt(this.id + ".user", u) - .apply() - } - - fun getLabel(context: Context): String { - return context.resources.getString(this.labelResource) - } - - fun pickDefaultApp(context: Context) : String { - return context.resources - .getStringArray(this.defaultsResource) - .firstOrNull { isInstalled(it, context) } - ?: "" - } - - fun getDoubleVariant(): Gesture { - return when(this) { - SWIPE_UP -> SWIPE_UP_DOUBLE - SWIPE_DOWN -> SWIPE_DOWN_DOUBLE - SWIPE_LEFT -> SWIPE_LEFT_DOUBLE - SWIPE_RIGHT -> SWIPE_RIGHT_DOUBLE - else -> this - } - } - - fun getEdgeVariant(edge: Edge): Gesture { - return when(edge) { - Edge.TOP -> - when(this) { - SWIPE_LEFT -> SWIPE_LEFT_TOP_EDGE - SWIPE_RIGHT -> SWIPE_RIGHT_TOP_EDGE - else -> this - } - Edge.BOTTOM -> - when(this) { - SWIPE_LEFT -> SWIPE_LEFT_BOTTOM_EDGE - SWIPE_RIGHT -> SWIPE_RIGHT_BOTTOM_EDGE - else -> this - } - Edge.LEFT -> - when(this) { - SWIPE_UP -> SWIPE_UP_LEFT_EDGE - SWIPE_DOWN -> SWIPE_DOWN_LEFT_EDGE - else -> this - } - Edge.RIGHT -> - when(this) { - SWIPE_UP -> SWIPE_UP_RIGHT_EDGE - SWIPE_DOWN -> SWIPE_DOWN_RIGHT_EDGE - else -> this - } - } - } - - fun isDoubleVariant(): Boolean { - return when(this){ - SWIPE_UP_DOUBLE, - SWIPE_DOWN_DOUBLE, - SWIPE_LEFT_DOUBLE, - SWIPE_RIGHT_DOUBLE -> true - else -> false - } - } - - fun isEdgeVariant(): Boolean { - return when(this){ - SWIPE_UP_RIGHT_EDGE, - SWIPE_UP_LEFT_EDGE, - SWIPE_DOWN_LEFT_EDGE, - SWIPE_DOWN_RIGHT_EDGE, - SWIPE_LEFT_TOP_EDGE, - SWIPE_LEFT_BOTTOM_EDGE, - SWIPE_RIGHT_TOP_EDGE, - SWIPE_RIGHT_BOTTOM_EDGE -> true - else -> false - } - } - - operator fun invoke(activity: Activity) { - val app = this.getApp(activity) - launch(app.first, app.second, activity, this.animationIn, this.animationOut) - } - - companion object { - fun byId(id: String): Gesture? { - return Gesture.values().firstOrNull {it.id == id } - } - } - -} diff --git a/app/src/main/java/de/jrpie/android/launcher/actions/Action.kt b/app/src/main/java/de/jrpie/android/launcher/actions/Action.kt new file mode 100644 index 0000000..d35a157 --- /dev/null +++ b/app/src/main/java/de/jrpie/android/launcher/actions/Action.kt @@ -0,0 +1,100 @@ +package de.jrpie.android.launcher.actions + +import android.app.Activity +import android.content.Context +import android.content.Intent +import android.content.SharedPreferences.Editor +import android.graphics.Rect +import android.graphics.drawable.Drawable +import android.widget.Toast +import de.jrpie.android.launcher.INVALID_USER +import de.jrpie.android.launcher.R +import de.jrpie.android.launcher.preferences.LauncherPreferences + +interface Action { + fun invoke(context: Context, rect: Rect? = null): Boolean + fun bindToGesture(prefEditor: Editor, id: String) + fun label(context: Context): String + fun getIcon(context: Context): Drawable? + fun isAvailable(context: Context): Boolean + + fun writeToIntent(intent: Intent) + + companion object { + private fun fromId(id: String, user: Int?): Action? { + if (id.isEmpty()) { + return null + } + if (LauncherAction.isOtherAction(id)) { + return LauncherAction.byId(id) + } + + return AppAction(AppInfo(id, user)) + } + + fun forGesture(gesture: Gesture): Action? { + val id = gesture.id + + val preferences = LauncherPreferences.getSharedPreferences() + var actionId = preferences.getString("$id.app", "")!! + var u: Int? = preferences.getInt("$id.user", INVALID_USER) + u = if (u == INVALID_USER) null else u + + return fromId(actionId, u) + } + + fun resetToDefaultActions(context: Context) { + val editor = LauncherPreferences.getSharedPreferences().edit() + Gesture.values().forEach { gesture -> + context.resources + .getStringArray(gesture.defaultsResource) + .map { fromId(it, null) } + .firstOrNull { it?.isAvailable(context) ?: false } + ?.bindToGesture(editor, gesture.id) + } + editor.apply() + } + + fun setActionForGesture(gesture: Gesture, action: Action?) { + if (action == null) { + clearActionForGesture(gesture) + return + } + val editor = LauncherPreferences.getSharedPreferences().edit() + action.bindToGesture(editor, gesture.id) + editor.apply() + } + + fun clearActionForGesture(gesture: Gesture) { + LauncherPreferences.getSharedPreferences().edit() + .putString(gesture.id + ".app", "") + .putInt(gesture.id + ".user", INVALID_USER) + .apply() + } + + fun launch( + action: Action?, + context: Context, + animationIn: Int = android.R.anim.fade_in, + animationOut: Int = android.R.anim.fade_out + ) { + if (action != null && action.invoke(context)) { + if (context is Activity) { + context.overridePendingTransition(animationIn, animationOut) + } + } else { + Toast.makeText( + context, + context.getString(R.string.toast_cant_open_message), + Toast.LENGTH_SHORT + ).show() + } + } + + fun fromIntent(data: Intent): Action? { + val value = data.getStringExtra("action_id") ?: return null + var user = data.getIntExtra("user", INVALID_USER) + return fromId(value, user) + } + } +} \ No newline at end of file diff --git a/app/src/main/java/de/jrpie/android/launcher/actions/AppAction.kt b/app/src/main/java/de/jrpie/android/launcher/actions/AppAction.kt new file mode 100644 index 0000000..f1a377a --- /dev/null +++ b/app/src/main/java/de/jrpie/android/launcher/actions/AppAction.kt @@ -0,0 +1,85 @@ +package de.jrpie.android.launcher.actions + +import android.app.AlertDialog +import android.app.Service +import android.content.Context +import android.content.Intent +import android.content.SharedPreferences +import android.content.pm.LauncherApps +import android.graphics.Rect +import android.graphics.drawable.Drawable +import de.jrpie.android.launcher.INVALID_USER +import de.jrpie.android.launcher.R +import de.jrpie.android.launcher.getIntent +import de.jrpie.android.launcher.getLauncherActivityInfo +import de.jrpie.android.launcher.openAppSettings + +class AppAction(private var appInfo: AppInfo) : Action { + + override fun invoke(context: Context, rect: Rect?): Boolean { + val packageName = appInfo.packageName.toString() + val user = appInfo.user + if (user != null && user != INVALID_USER) { + val launcherApps = + context.getSystemService(Service.LAUNCHER_APPS_SERVICE) as LauncherApps + getLauncherActivityInfo(packageName, user, context)?.let { app -> + launcherApps.startMainActivity(app.componentName, app.user, rect, null) + return true + } + } + + val intent = getIntent(packageName, context) + + if (intent != null) { + context.startActivity(intent) + return true + } + + if (AppInfo(packageName).isInstalled(context)) { + AlertDialog.Builder( + context, + R.style.AlertDialogCustom + ) + .setTitle(context.getString(R.string.alert_cant_open_title)) + .setMessage(context.getString(R.string.alert_cant_open_message)) + .setPositiveButton(android.R.string.ok) { _, _ -> + openAppSettings(appInfo, context) + } + .setNegativeButton(android.R.string.cancel, null) + .setIcon(android.R.drawable.ic_dialog_info) + .show() + return true + } + return false + } + + override fun label(context: Context): String { + return appInfo.label.toString() + } + + override fun getIcon(context: Context): Drawable? { + var icon: Drawable? = null + try { + icon = appInfo.getAppIcon(context) + } catch (e: Exception) { + // probably the app was uninstalled + } + return icon + } + + override fun isAvailable(context: Context): Boolean { + return appInfo.isInstalled(context) + } + + override fun bindToGesture(editor: SharedPreferences.Editor, id: String) { + val u = appInfo.user ?: INVALID_USER + editor + .putString("$id.app", appInfo.packageName.toString()) + .putInt("$id.user", u) + } + + override fun writeToIntent(intent: Intent) { + intent.putExtra("action_id", appInfo.packageName) + appInfo.user?.let { intent.putExtra("user", it) } + } +} \ No newline at end of file diff --git a/app/src/main/java/de/jrpie/android/launcher/actions/AppInfo.kt b/app/src/main/java/de/jrpie/android/launcher/actions/AppInfo.kt new file mode 100644 index 0000000..8e1e7f1 --- /dev/null +++ b/app/src/main/java/de/jrpie/android/launcher/actions/AppInfo.kt @@ -0,0 +1,49 @@ +package de.jrpie.android.launcher.actions + +import android.app.Service +import android.content.Context +import android.content.pm.LauncherApps +import android.content.pm.PackageManager +import android.graphics.drawable.Drawable +import de.jrpie.android.launcher.INVALID_USER +import de.jrpie.android.launcher.getUserFromId + +/** + * Stores information used to create [AppsRecyclerAdapter] rows. + * + * Represents an app installed on the users device. + */ +class AppInfo(var packageName: CharSequence? = null, var user: Int? = null) { + var label: CharSequence? = null + var icon: Drawable? = null + var isSystemApp: Boolean = false + + fun getAppIcon(context: Context): Drawable { + if (user != null && user != INVALID_USER) { + val launcherApps = + context.getSystemService(Service.LAUNCHER_APPS_SERVICE) as LauncherApps + getUserFromId(user, context)?.let { userHandle -> + launcherApps.getActivityList(packageName.toString(), userHandle).firstOrNull() + ?.let { app -> + return app.getBadgedIcon(0) + } + } + } + return context.packageManager.getApplicationIcon(packageName.toString()) + } + + fun isInstalled(context: Context): Boolean { + /* TODO: this should also check the user */ + try { + context.packageManager.getPackageInfo( + packageName.toString(), + PackageManager.GET_ACTIVITIES + ) + return true + } catch (_: PackageManager.NameNotFoundException) { + } + return false + } + + +} \ No newline at end of file diff --git a/app/src/main/java/de/jrpie/android/launcher/actions/Gesture.kt b/app/src/main/java/de/jrpie/android/launcher/actions/Gesture.kt new file mode 100644 index 0000000..6725e27 --- /dev/null +++ b/app/src/main/java/de/jrpie/android/launcher/actions/Gesture.kt @@ -0,0 +1,222 @@ +package de.jrpie.android.launcher.actions + +import android.content.Context +import de.jrpie.android.launcher.R + +/** + * @param id internal id to serialize the action. Used as a key in shared preferences. + * @param defaultsResource res id of array of default actions for the gesture. + * @param labelResource res id of the name of the gesture. + * @param animationIn res id of transition animation (in) when using the gesture to launch an app. + * @param animationOut res id of transition animation (out) when using the gesture to launch an app. + */ +enum class Gesture( + val id: String, private val labelResource: Int, + internal val defaultsResource: Int, + private val animationIn: Int = android.R.anim.fade_in, + private val animationOut: Int = android.R.anim.fade_out +) { + VOLUME_UP( + "action.volume_up", + R.string.settings_gesture_vol_up, + R.array.default_volume_up, + 0, + 0 + ), + VOLUME_DOWN( + "action.volume_down", + R.string.settings_gesture_vol_down, + R.array.default_volume_down, 0, 0 + ), + TIME("action.time", R.string.settings_gesture_time, R.array.default_time), + DATE("action.date", R.string.settings_gesture_date, R.array.default_date), + LONG_CLICK( + "action.long_click", + R.string.settings_gesture_long_click, + R.array.default_long_click, 0, 0 + ), + DOUBLE_CLICK( + "action.double_click", + R.string.settings_gesture_double_click, + R.array.default_double_click, 0, 0 + ), + SWIPE_UP("action.up", R.string.settings_gesture_up, R.array.default_up, R.anim.bottom_up), + SWIPE_UP_LEFT_EDGE( + "action.up_left", + R.string.settings_gesture_up_left_edge, + R.array.default_up_left, + R.anim.bottom_up + ), + SWIPE_UP_RIGHT_EDGE( + "action.up_right", + R.string.settings_gesture_up_right_edge, + R.array.default_up_right, + R.anim.bottom_up + ), + SWIPE_UP_DOUBLE( + "action.double_up", + R.string.settings_gesture_double_up, + R.array.default_double_up, + R.anim.bottom_up + ), + SWIPE_DOWN( + "action.down", + R.string.settings_gesture_down, + R.array.default_down, + R.anim.top_down + ), + SWIPE_DOWN_LEFT_EDGE( + "action.down_left", + R.string.settings_gesture_down_left_edge, + R.array.default_down_left, + R.anim.top_down + ), + SWIPE_DOWN_RIGHT_EDGE( + "action.down_right", + R.string.settings_gesture_down_right_edge, + R.array.default_down_right, + R.anim.top_down + ), + SWIPE_DOWN_DOUBLE( + "action.double_down", + R.string.settings_gesture_double_down, + R.array.default_double_down, + R.anim.top_down + ), + SWIPE_LEFT( + "action.left", + R.string.settings_gesture_left, + R.array.default_left, + R.anim.right_left + ), + SWIPE_LEFT_TOP_EDGE( + "action.left_top", + R.string.settings_gesture_left_top_edge, + R.array.default_left_top, + R.anim.right_left + ), + SWIPE_LEFT_BOTTOM_EDGE( + "action.left_bottom", + R.string.settings_gesture_left_bottom_edge, + R.array.default_left_bottom, + R.anim.right_left + ), + SWIPE_LEFT_DOUBLE( + "action.double_left", + R.string.settings_gesture_double_left, + R.array.default_double_left, + R.anim.right_left + ), + SWIPE_RIGHT( + "action.right", + R.string.settings_gesture_right, + R.array.default_right, + R.anim.left_right + ), + SWIPE_RIGHT_TOP_EDGE( + "action.right_top", + R.string.settings_gesture_right_top_edge, + R.array.default_right_top, + R.anim.left_right + ), + SWIPE_RIGHT_BOTTOM_EDGE( + "action.right_bottom", + R.string.settings_gesture_right_bottom_edge, + R.array.default_right_bottom, + R.anim.left_right + ), + SWIPE_RIGHT_DOUBLE( + "action.double_right", + R.string.settings_gesture_double_right, + R.array.default_double_right, + R.anim.left_right + ); + + enum class Edge { + TOP, BOTTOM, LEFT, RIGHT + } + + fun getLabel(context: Context): String { + return context.resources.getString(this.labelResource) + } + + fun getDoubleVariant(): Gesture { + return when (this) { + SWIPE_UP -> SWIPE_UP_DOUBLE + SWIPE_DOWN -> SWIPE_DOWN_DOUBLE + SWIPE_LEFT -> SWIPE_LEFT_DOUBLE + SWIPE_RIGHT -> SWIPE_RIGHT_DOUBLE + else -> this + } + } + + fun getEdgeVariant(edge: Edge): Gesture { + return when (edge) { + Edge.TOP -> + when (this) { + SWIPE_LEFT -> SWIPE_LEFT_TOP_EDGE + SWIPE_RIGHT -> SWIPE_RIGHT_TOP_EDGE + else -> this + } + + Edge.BOTTOM -> + when (this) { + SWIPE_LEFT -> SWIPE_LEFT_BOTTOM_EDGE + SWIPE_RIGHT -> SWIPE_RIGHT_BOTTOM_EDGE + else -> this + } + + Edge.LEFT -> + when (this) { + SWIPE_UP -> SWIPE_UP_LEFT_EDGE + SWIPE_DOWN -> SWIPE_DOWN_LEFT_EDGE + else -> this + } + + Edge.RIGHT -> + when (this) { + SWIPE_UP -> SWIPE_UP_RIGHT_EDGE + SWIPE_DOWN -> SWIPE_DOWN_RIGHT_EDGE + else -> this + } + } + } + + fun isDoubleVariant(): Boolean { + return when (this) { + SWIPE_UP_DOUBLE, + SWIPE_DOWN_DOUBLE, + SWIPE_LEFT_DOUBLE, + SWIPE_RIGHT_DOUBLE -> true + + else -> false + } + } + + fun isEdgeVariant(): Boolean { + return when (this) { + SWIPE_UP_RIGHT_EDGE, + SWIPE_UP_LEFT_EDGE, + SWIPE_DOWN_LEFT_EDGE, + SWIPE_DOWN_RIGHT_EDGE, + SWIPE_LEFT_TOP_EDGE, + SWIPE_LEFT_BOTTOM_EDGE, + SWIPE_RIGHT_TOP_EDGE, + SWIPE_RIGHT_BOTTOM_EDGE -> true + + else -> false + } + } + + operator fun invoke(context: Context) { + val action = Action.forGesture(this) + Action.launch(action, context, this.animationIn, this.animationOut) + } + + companion object { + fun byId(id: String): Gesture? { + return Gesture.values().firstOrNull { it.id == id } + } + } + +} diff --git a/app/src/main/java/de/jrpie/android/launcher/actions/LauncherAction.kt b/app/src/main/java/de/jrpie/android/launcher/actions/LauncherAction.kt new file mode 100644 index 0000000..6d455eb --- /dev/null +++ b/app/src/main/java/de/jrpie/android/launcher/actions/LauncherAction.kt @@ -0,0 +1,185 @@ +package de.jrpie.android.launcher.actions + +import android.content.Context +import android.content.Intent +import android.content.SharedPreferences.Editor +import android.graphics.Rect +import android.graphics.drawable.Drawable +import android.media.AudioManager +import android.os.SystemClock +import android.view.KeyEvent +import android.widget.Toast +import de.jrpie.android.launcher.INVALID_USER +import de.jrpie.android.launcher.R +import de.jrpie.android.launcher.ui.list.ListActivity +import de.jrpie.android.launcher.ui.settings.SettingsActivity + +enum class LauncherAction( + val id: String, + val label: Int, + val icon: Int, + val launch: (Context) -> Unit +) : Action { + SETTINGS( + "launcher:settings", + R.string.list_other_settings, + R.drawable.baseline_settings_24, + ::openSettings + ), + CHOOSE( + "launcher:choose", + R.string.list_other_list, + R.drawable.baseline_menu_24, + ::openAppsList + ), + VOLUME_UP( + "launcher:volumeUp", + R.string.list_other_volume_up, + R.drawable.baseline_volume_up_24, ::audioVolumeUp + ), + VOLUME_DOWN( + "launcher:volumeDown", + R.string.list_other_volume_down, + R.drawable.baseline_volume_down_24, ::audioVolumeDown + ), + TRACK_NEXT( + "launcher:nextTrack", + R.string.list_other_track_next, + R.drawable.baseline_skip_next_24, ::audioNextTrack + ), + TRACK_PREV( + "launcher:previousTrack", + R.string.list_other_track_previous, + R.drawable.baseline_skip_previous_24, ::audioPreviousTrack + ), + EXPAND_NOTIFICATIONS_PANEL( + "launcher:expandNotificationsPanel", + R.string.list_other_expand_notifications_panel, + R.drawable.baseline_notifications_24, + ::expandNotificationsPanel + ), + NOP("launcher:nop", R.string.list_other_nop, R.drawable.baseline_not_interested_24, {}); + + override fun invoke(context: Context, rect: Rect?): Boolean { + launch(context) + return true + } + + override fun label(context: Context): String { + return context.getString(label) + } + + override fun getIcon(context: Context): Drawable? { + return context.getDrawable(icon) + } + + override fun bindToGesture(editor: Editor, id: String) { + editor + .putString("$id.app", this.id) + .putInt("$id.user", INVALID_USER) + } + + override fun writeToIntent(intent: Intent) { + intent.putExtra("action_id", id) + } + + override fun isAvailable(context: Context): Boolean { + return true + } + + companion object { + fun byId(id: String): LauncherAction? { + return LauncherAction.values().singleOrNull { it.id == id } + } + + fun isOtherAction(id: String): Boolean { + return id.startsWith("launcher") + } + } +} + + +/* Media player actions */ + +private fun audioNextTrack(context: Context) { + + val mAudioManager = context.getSystemService(Context.AUDIO_SERVICE) as AudioManager + + val eventTime: Long = SystemClock.uptimeMillis() + + val downEvent = + KeyEvent(eventTime, eventTime, KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_MEDIA_NEXT, 0) + mAudioManager.dispatchMediaKeyEvent(downEvent) + + val upEvent = KeyEvent(eventTime, eventTime, KeyEvent.ACTION_UP, KeyEvent.KEYCODE_MEDIA_NEXT, 0) + mAudioManager.dispatchMediaKeyEvent(upEvent) +} + +private fun audioPreviousTrack(context: Context) { + val mAudioManager = context.getSystemService(Context.AUDIO_SERVICE) as AudioManager + + val eventTime: Long = SystemClock.uptimeMillis() + + val downEvent = + KeyEvent(eventTime, eventTime, KeyEvent.ACTION_DOWN, KeyEvent.KEYCODE_MEDIA_PREVIOUS, 0) + mAudioManager.dispatchMediaKeyEvent(downEvent) + + val upEvent = + KeyEvent(eventTime, eventTime, KeyEvent.ACTION_UP, KeyEvent.KEYCODE_MEDIA_PREVIOUS, 0) + mAudioManager.dispatchMediaKeyEvent(upEvent) +} + +private fun audioVolumeUp(context: Context) { + val audioManager = + context.getSystemService(Context.AUDIO_SERVICE) as AudioManager + + audioManager.adjustStreamVolume( + AudioManager.STREAM_MUSIC, + AudioManager.ADJUST_RAISE, + AudioManager.FLAG_SHOW_UI + ) +} + +private fun audioVolumeDown(context: Context) { + val audioManager = + context.getSystemService(Context.AUDIO_SERVICE) as AudioManager + + audioManager.adjustStreamVolume( + AudioManager.STREAM_MUSIC, + AudioManager.ADJUST_LOWER, + AudioManager.FLAG_SHOW_UI + ) +} +/* End media player actions */ + +private fun expandNotificationsPanel(context: Context) { + /* https://stackoverflow.com/a/15582509 */ + try { + @Suppress("SpellCheckingInspection") + val statusBarService: Any? = context.getSystemService("statusbar") + val statusBarManager = Class.forName("android.app.StatusBarManager") + val showStatusBar = statusBarManager.getMethod("expandNotificationsPanel") + showStatusBar.invoke(statusBarService) + } catch (e: Exception) { + Toast.makeText( + context, + context.getString(R.string.alert_cant_expand_notifications_panel), + Toast.LENGTH_LONG + ).show() + } +} + + +private fun openSettings(context: Context) { + context.startActivity(Intent(context, SettingsActivity::class.java)) +} + +private fun openAppsList(context: Context) { + val intent = Intent(context, ListActivity::class.java) + intent.putExtra("intention", ListActivity.ListActivityIntention.VIEW.toString()) + context.startActivity(intent) +} + + + + diff --git a/app/src/main/java/de/jrpie/android/launcher/list/apps/AppInfo.kt b/app/src/main/java/de/jrpie/android/launcher/list/apps/AppInfo.kt deleted file mode 100644 index f19fd0e..0000000 --- a/app/src/main/java/de/jrpie/android/launcher/list/apps/AppInfo.kt +++ /dev/null @@ -1,16 +0,0 @@ -package de.jrpie.android.launcher.list.apps - -import android.graphics.drawable.Drawable - -/** - * Stores information used to create [AppsRecyclerAdapter] rows. - * - * Represents an app installed on the users device. - */ -class AppInfo { - var user: Int? = null - var label: CharSequence? = null - var packageName: CharSequence? = null - var icon: Drawable? = null - var isSystemApp: Boolean = false -} \ No newline at end of file diff --git a/app/src/main/java/de/jrpie/android/launcher/list/other/LauncherAction.kt b/app/src/main/java/de/jrpie/android/launcher/list/other/LauncherAction.kt deleted file mode 100644 index b1137f3..0000000 --- a/app/src/main/java/de/jrpie/android/launcher/list/other/LauncherAction.kt +++ /dev/null @@ -1,43 +0,0 @@ -package de.jrpie.android.launcher.list.other - -import android.app.Activity -import de.jrpie.android.launcher.R -import de.jrpie.android.launcher.audioNextTrack -import de.jrpie.android.launcher.audioPreviousTrack -import de.jrpie.android.launcher.audioVolumeDown -import de.jrpie.android.launcher.audioVolumeUp -import de.jrpie.android.launcher.expandNotificationsPanel -import de.jrpie.android.launcher.openAppsList -import de.jrpie.android.launcher.openSettings - -enum class LauncherAction(val id: String, val label: Int, val icon: Int, val launch: (Activity) -> Unit) { - SETTINGS("launcher:settings", R.string.list_other_settings, R.drawable.baseline_settings_24, ::openSettings), - CHOOSE("launcher:choose", R.string.list_other_list, R.drawable.baseline_menu_24, ::openAppsList), - VOLUME_UP("launcher:volumeUp", - R.string.list_other_volume_up, - R.drawable.baseline_volume_up_24, ::audioVolumeUp), - VOLUME_DOWN("launcher:volumeDown", - R.string.list_other_volume_down, - R.drawable.baseline_volume_down_24, ::audioVolumeDown), - TRACK_NEXT("launcher:nextTrack", - R.string.list_other_track_next, - R.drawable.baseline_skip_next_24, ::audioNextTrack), - TRACK_PREV("launcher:previousTrack", - R.string.list_other_track_previous, - R.drawable.baseline_skip_previous_24, ::audioPreviousTrack), - EXPAND_NOTIFICATIONS_PANEL("launcher:expandNotificationsPanel", - R.string.list_other_expand_notifications_panel, - R.drawable.baseline_notifications_24, - ::expandNotificationsPanel), - NOP("launcher:nop", R.string.list_other_nop, R.drawable.baseline_not_interested_24, {}); - - companion object { - fun byId(id: String): LauncherAction? { - return LauncherAction.values().singleOrNull { it.id == id } - } - - fun isOtherAction(id: String): Boolean { - return id.startsWith("launcher") - } - } -} diff --git a/app/src/main/java/de/jrpie/android/launcher/preferences/LauncherPreferences$Config.java b/app/src/main/java/de/jrpie/android/launcher/preferences/LauncherPreferences$Config.java index b63b06f..dde600f 100644 --- a/app/src/main/java/de/jrpie/android/launcher/preferences/LauncherPreferences$Config.java +++ b/app/src/main/java/de/jrpie/android/launcher/preferences/LauncherPreferences$Config.java @@ -13,44 +13,44 @@ import eu.jonahbauer.android.preference.annotations.Preferences; makeFile = true, r = R.class, value = { - @PreferenceGroup(name = "internal", prefix = "settings_internal_", suffix = "_key", value = { - @Preference(name = "started", type = boolean.class, defaultValue = "false"), - @Preference(name = "started_time", type = long.class), - @Preference(name = "version_code", type = int.class, defaultValue = "-1"), - }), - @PreferenceGroup( name = "gestures", prefix = "settings_gesture_", suffix = "_key", value = { - }), - @PreferenceGroup(name = "general", prefix = "settings_general_", suffix = "_key", value = { - @Preference(name = "choose_home_screen", type = void.class) - }), - @PreferenceGroup(name = "theme", prefix = "settings_theme_", suffix = "_key", value = { - @Preference(name = "wallpaper", type = void.class), - @Preference(name = "color_theme", type = ColorTheme.class, defaultValue = "DEFAULT"), - @Preference(name = "background", type = Background.class, defaultValue = "BLUR"), - @Preference(name = "font", type = Font.class, defaultValue = "HACK"), - @Preference(name = "monochrome_icons", type = boolean.class, defaultValue = "false"), - }), - @PreferenceGroup(name = "clock", prefix = "settings_clock_", suffix = "_key", value = { - @Preference(name = "font", type = Font.class, defaultValue = "HACK"), - @Preference(name = "date_visible", type = boolean.class, defaultValue = "true"), - @Preference(name = "time_visible", type = boolean.class, defaultValue = "true"), - @Preference(name = "flip_date_time", type = boolean.class, defaultValue = "false"), - @Preference(name = "localized", type = boolean.class, defaultValue = "false"), - @Preference(name = "show_seconds", type = boolean.class, defaultValue = "true"), - }), - @PreferenceGroup(name = "display", prefix = "settings_display_", suffix = "_key", value = { - @Preference(name = "screen_timeout_disabled", type = boolean.class, defaultValue = "false"), - @Preference(name = "full_screen", type = boolean.class, defaultValue = "true"), - @Preference(name = "rotate_screen", type = boolean.class, defaultValue = "false"), - }), - @PreferenceGroup( name = "functionality", prefix = "settings_functionality_", suffix = "_key", value = { - @Preference(name = "search_auto_launch", type = boolean.class, defaultValue = "true"), - @Preference(name = "search_auto_open_keyboard", type = boolean.class, defaultValue = "true"), - }), - @PreferenceGroup(name = "enabled_gestures", prefix = "settings_enabled_gestures_", suffix = "_key", value = { - @Preference(name = "double_swipe", type = boolean.class, defaultValue = "true"), - @Preference(name = "edge_swipe", type = boolean.class, defaultValue = "true"), - }), + @PreferenceGroup(name = "internal", prefix = "settings_internal_", suffix = "_key", value = { + @Preference(name = "started", type = boolean.class, defaultValue = "false"), + @Preference(name = "started_time", type = long.class), + @Preference(name = "version_code", type = int.class, defaultValue = "-1"), + }), + @PreferenceGroup(name = "gestures", prefix = "settings_gesture_", suffix = "_key", value = { + }), + @PreferenceGroup(name = "general", prefix = "settings_general_", suffix = "_key", value = { + @Preference(name = "choose_home_screen", type = void.class) + }), + @PreferenceGroup(name = "theme", prefix = "settings_theme_", suffix = "_key", value = { + @Preference(name = "wallpaper", type = void.class), + @Preference(name = "color_theme", type = ColorTheme.class, defaultValue = "DEFAULT"), + @Preference(name = "background", type = Background.class, defaultValue = "BLUR"), + @Preference(name = "font", type = Font.class, defaultValue = "HACK"), + @Preference(name = "monochrome_icons", type = boolean.class, defaultValue = "false"), + }), + @PreferenceGroup(name = "clock", prefix = "settings_clock_", suffix = "_key", value = { + @Preference(name = "font", type = Font.class, defaultValue = "HACK"), + @Preference(name = "date_visible", type = boolean.class, defaultValue = "true"), + @Preference(name = "time_visible", type = boolean.class, defaultValue = "true"), + @Preference(name = "flip_date_time", type = boolean.class, defaultValue = "false"), + @Preference(name = "localized", type = boolean.class, defaultValue = "false"), + @Preference(name = "show_seconds", type = boolean.class, defaultValue = "true"), + }), + @PreferenceGroup(name = "display", prefix = "settings_display_", suffix = "_key", value = { + @Preference(name = "screen_timeout_disabled", type = boolean.class, defaultValue = "false"), + @Preference(name = "full_screen", type = boolean.class, defaultValue = "true"), + @Preference(name = "rotate_screen", type = boolean.class, defaultValue = "false"), + }), + @PreferenceGroup(name = "functionality", prefix = "settings_functionality_", suffix = "_key", value = { + @Preference(name = "search_auto_launch", type = boolean.class, defaultValue = "true"), + @Preference(name = "search_auto_open_keyboard", type = boolean.class, defaultValue = "true"), + }), + @PreferenceGroup(name = "enabled_gestures", prefix = "settings_enabled_gestures_", suffix = "_key", value = { + @Preference(name = "double_swipe", type = boolean.class, defaultValue = "true"), + @Preference(name = "edge_swipe", type = boolean.class, defaultValue = "true"), + }), }) public final class LauncherPreferences$Config { } diff --git a/app/src/main/java/de/jrpie/android/launcher/preferences/Preferences.kt b/app/src/main/java/de/jrpie/android/launcher/preferences/Preferences.kt index 1115ee8..df847ec 100644 --- a/app/src/main/java/de/jrpie/android/launcher/preferences/Preferences.kt +++ b/app/src/main/java/de/jrpie/android/launcher/preferences/Preferences.kt @@ -3,8 +3,7 @@ package de.jrpie.android.launcher.preferences import android.content.Context import android.content.SharedPreferences import android.util.Log -import android.widget.Toast -import de.jrpie.android.launcher.Gesture +import de.jrpie.android.launcher.actions.Action import de.jrpie.android.launcher.preferences.theme.Background import de.jrpie.android.launcher.preferences.theme.ColorTheme @@ -17,15 +16,35 @@ const val UNKNOWN_PREFERENCE_VERSION = -1 private const val TAG = "Launcher - Preferences" -private fun migrateStringPreference(oldPrefs: SharedPreferences, newPreferences: SharedPreferences.Editor, oldKey: String, newKey: String, default: String) { +private fun migrateStringPreference( + oldPrefs: SharedPreferences, + newPreferences: SharedPreferences.Editor, + oldKey: String, + newKey: String, + default: String +) { val s = oldPrefs.getString(oldKey, default) newPreferences.putString(newKey, s) } -private fun migrateIntPreference(oldPrefs: SharedPreferences, newPreferences: SharedPreferences.Editor, oldKey: String, newKey: String, default: Int) { + +private fun migrateIntPreference( + oldPrefs: SharedPreferences, + newPreferences: SharedPreferences.Editor, + oldKey: String, + newKey: String, + default: Int +) { val s = oldPrefs.getInt(oldKey, default) newPreferences.putInt(newKey, s) } -private fun migrateBooleanPreference(oldPrefs: SharedPreferences, newPreferences: SharedPreferences.Editor, oldKey: String, newKey: String, default: Boolean) { + +private fun migrateBooleanPreference( + oldPrefs: SharedPreferences, + newPreferences: SharedPreferences.Editor, + oldKey: String, + newKey: String, + default: Boolean +) { val s = oldPrefs.getBoolean(oldKey, default) newPreferences.putBoolean(newKey, s) } @@ -33,86 +52,344 @@ private fun migrateBooleanPreference(oldPrefs: SharedPreferences, newPreferences fun migratePreferencesToNewVersion(context: Context) { when (LauncherPreferences.internal().versionCode()) { // Check versions, make sure transitions between versions go well - PREFERENCE_VERSION -> { /* the version installed and used previously are the same */ } + PREFERENCE_VERSION -> { /* the version installed and used previously are the same */ + } + UNKNOWN_PREFERENCE_VERSION -> { /* still using the old preferences file */ - Log.i(TAG, "Unknown preference version, trying to restore preferences from old version.") + Log.i( + TAG, + "Unknown preference version, trying to restore preferences from old version." + ) val oldPrefs = context.getSharedPreferences( "V3RYR4ND0MK3YCR4P", Context.MODE_PRIVATE ) - if(!oldPrefs.contains("startedBefore")) { + if (!oldPrefs.contains("startedBefore")) { Log.i(TAG, "No old preferences found.") return } val newPrefs = LauncherPreferences.getSharedPreferences().edit() - migrateBooleanPreference(oldPrefs, newPrefs, "startedBefore", "internal.started_before", false) + migrateBooleanPreference( + oldPrefs, + newPrefs, + "startedBefore", + "internal.started_before", + false + ) - migrateStringPreference(oldPrefs, newPrefs, "action_volumeUpApp", "action.volume_up.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_volumeUpApp_user", "action.volume_up.user", -1) - migrateStringPreference(oldPrefs, newPrefs, "action_volumeDownApp", "action.volume_down.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_volumeDownApp_user", "action.volume_down.user", -1) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_volumeUpApp", + "action.volume_up.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_volumeUpApp_user", + "action.volume_up.user", + -1 + ) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_volumeDownApp", + "action.volume_down.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_volumeDownApp_user", + "action.volume_down.user", + -1 + ) migrateStringPreference(oldPrefs, newPrefs, "action_timeApp", "action.time.app", "") migrateIntPreference(oldPrefs, newPrefs, "action_timeApp_user", "action.time.user", -1) migrateStringPreference(oldPrefs, newPrefs, "action_dateApp", "action.date.app", "") migrateIntPreference(oldPrefs, newPrefs, "action_dateApp_user", "action.date.user", -1) - migrateStringPreference(oldPrefs, newPrefs, "action_longClickApp", "action.long_click.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_longClickApp_user", "action.long_click.user", -1) - migrateStringPreference(oldPrefs, newPrefs, "action_doubleClickApp", "action.double_click.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_doubleClickApp_user", "action.double_click.user", -1) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_longClickApp", + "action.long_click.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_longClickApp_user", + "action.long_click.user", + -1 + ) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_doubleClickApp", + "action.double_click.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_doubleClickApp_user", + "action.double_click.user", + -1 + ) migrateStringPreference(oldPrefs, newPrefs, "action_upApp", "action.up.app", "") migrateIntPreference(oldPrefs, newPrefs, "action_upApp_user", "action.up.user", -1) - migrateStringPreference(oldPrefs, newPrefs, "action_up_leftApp", "action.up_left.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_up_leftApp_user", "action.up_left.user", -1) - migrateStringPreference(oldPrefs, newPrefs, "action_up_rightApp", "action.up_right.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_up_rightApp_user", "action.up_right.user", -1) - migrateStringPreference(oldPrefs, newPrefs, "action_doubleUpApp", "action.double_up.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_doubleUpApp_user", "action.double_up.user", -1) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_up_leftApp", + "action.up_left.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_up_leftApp_user", + "action.up_left.user", + -1 + ) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_up_rightApp", + "action.up_right.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_up_rightApp_user", + "action.up_right.user", + -1 + ) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_doubleUpApp", + "action.double_up.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_doubleUpApp_user", + "action.double_up.user", + -1 + ) migrateStringPreference(oldPrefs, newPrefs, "action_downApp", "action.down.app", "") migrateIntPreference(oldPrefs, newPrefs, "action_downApp_user", "action.down.user", -1) - migrateStringPreference(oldPrefs, newPrefs, "action_down_leftApp", "action.down_left.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_down_leftApp_user", "action.down_left.user", -1) - migrateStringPreference(oldPrefs, newPrefs, "action_down_rightApp", "action.down_right.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_down_rightApp_user", "action.down_right.user", -1) - migrateStringPreference(oldPrefs, newPrefs, "action_doubleDownApp", "action.double_down.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_doubleDownApp_user", "action.double_down.user", -1) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_down_leftApp", + "action.down_left.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_down_leftApp_user", + "action.down_left.user", + -1 + ) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_down_rightApp", + "action.down_right.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_down_rightApp_user", + "action.down_right.user", + -1 + ) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_doubleDownApp", + "action.double_down.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_doubleDownApp_user", + "action.double_down.user", + -1 + ) migrateStringPreference(oldPrefs, newPrefs, "action_leftApp", "action.left.app", "") migrateIntPreference(oldPrefs, newPrefs, "action_leftApp_user", "action.left.user", -1) - migrateStringPreference(oldPrefs, newPrefs, "action_left_topApp", "action.left_top.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_left_topApp_user", "action.left_top.user", -1) - migrateStringPreference(oldPrefs, newPrefs, "action_left_bottomApp", "action.left_bottom.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_left_bottomApp_user", "action.left_bottom.user", -1) - migrateStringPreference(oldPrefs, newPrefs, "action_doubleLeftApp", "action.double_left.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_doubleLeftApp_user", "action.double_left.user", -1) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_left_topApp", + "action.left_top.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_left_topApp_user", + "action.left_top.user", + -1 + ) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_left_bottomApp", + "action.left_bottom.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_left_bottomApp_user", + "action.left_bottom.user", + -1 + ) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_doubleLeftApp", + "action.double_left.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_doubleLeftApp_user", + "action.double_left.user", + -1 + ) migrateStringPreference(oldPrefs, newPrefs, "action_rightApp", "action.right.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_rightApp_user", "action.right.user", -1) - migrateStringPreference(oldPrefs, newPrefs, "action_right_topApp", "action.right_top.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_right_topApp_user", "action.right_top.user", -1) - migrateStringPreference(oldPrefs, newPrefs, "action_right_bottomApp", "action.right_bottom.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_right_bottomApp_user", "action.right_bottom.user", -1) - migrateStringPreference(oldPrefs, newPrefs, "action_doubleRightApp", "action.double_right.app", "") - migrateIntPreference(oldPrefs, newPrefs, "action_doubleRightApp_user", "action.double_right.user", -1) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_rightApp_user", + "action.right.user", + -1 + ) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_right_topApp", + "action.right_top.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_right_topApp_user", + "action.right_top.user", + -1 + ) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_right_bottomApp", + "action.right_bottom.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_right_bottomApp_user", + "action.right_bottom.user", + -1 + ) + migrateStringPreference( + oldPrefs, + newPrefs, + "action_doubleRightApp", + "action.double_right.app", + "" + ) + migrateIntPreference( + oldPrefs, + newPrefs, + "action_doubleRightApp_user", + "action.double_right.user", + -1 + ) migrateBooleanPreference(oldPrefs, newPrefs, "timeVisible", "clock.time_visible", true) migrateBooleanPreference(oldPrefs, newPrefs, "dateVisible", "clock.date_visible", true) - migrateBooleanPreference(oldPrefs, newPrefs, "dateLocalized", "clock.date_localized", false) - migrateBooleanPreference(oldPrefs, newPrefs, "dateTimeFlip", "clock.date_time_flip", false) - migrateBooleanPreference(oldPrefs, newPrefs, "disableTimeout", "display.disable_timeout", false) - migrateBooleanPreference(oldPrefs, newPrefs, "useFullScreen", "display.use_full_screen", true) - migrateBooleanPreference(oldPrefs, newPrefs, "enableDoubleActions", "enabled_gestures.double_actions", true) - migrateBooleanPreference(oldPrefs, newPrefs, "enableEdgeActions", "enabled_gestures.edge_actions", true) - migrateBooleanPreference(oldPrefs, newPrefs, "searchAutoLaunch", "functionality.search_auto_launch", true) - migrateBooleanPreference(oldPrefs, newPrefs, "searchAutoKeyboard", "functionality.search_auto_keyboard", true) + migrateBooleanPreference( + oldPrefs, + newPrefs, + "dateLocalized", + "clock.date_localized", + false + ) + migrateBooleanPreference( + oldPrefs, + newPrefs, + "dateTimeFlip", + "clock.date_time_flip", + false + ) + migrateBooleanPreference( + oldPrefs, + newPrefs, + "disableTimeout", + "display.disable_timeout", + false + ) + migrateBooleanPreference( + oldPrefs, + newPrefs, + "useFullScreen", + "display.use_full_screen", + true + ) + migrateBooleanPreference( + oldPrefs, + newPrefs, + "enableDoubleActions", + "enabled_gestures.double_actions", + true + ) + migrateBooleanPreference( + oldPrefs, + newPrefs, + "enableEdgeActions", + "enabled_gestures.edge_actions", + true + ) + migrateBooleanPreference( + oldPrefs, + newPrefs, + "searchAutoLaunch", + "functionality.search_auto_launch", + true + ) + migrateBooleanPreference( + oldPrefs, + newPrefs, + "searchAutoKeyboard", + "functionality.search_auto_keyboard", + true + ) newPrefs.apply() - when(oldPrefs.getString("theme", "finn")) { + when (oldPrefs.getString("theme", "finn")) { "finn" -> { LauncherPreferences.theme().colorTheme(ColorTheme.DEFAULT) LauncherPreferences.theme().monochromeIcons(false) LauncherPreferences.theme().background(Background.BLUR) } + "dark" -> { LauncherPreferences.theme().colorTheme(ColorTheme.DARK) LauncherPreferences.theme().monochromeIcons(true) @@ -127,6 +404,7 @@ fun migratePreferencesToNewVersion(context: Context) { // show the new tutorial // context.startActivity(Intent(context, TutorialActivity::class.java)) } + else -> {} } } @@ -135,8 +413,6 @@ fun resetPreferences(context: Context) { Log.i(TAG, "resetting preferences") LauncherPreferences.clear() LauncherPreferences.internal().versionCode(PREFERENCE_VERSION) - val editor = LauncherPreferences.getSharedPreferences().edit() - Gesture.values().forEach { editor.putString(it.id + ".app", it.pickDefaultApp(context)) } - Gesture.values().forEach { editor.putInt(it.id + ".user", -1) } - editor.apply() + + Action.resetToDefaultActions(context) } diff --git a/app/src/main/java/de/jrpie/android/launcher/HomeActivity.kt b/app/src/main/java/de/jrpie/android/launcher/ui/HomeActivity.kt similarity index 80% rename from app/src/main/java/de/jrpie/android/launcher/HomeActivity.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/HomeActivity.kt index fd02fa4..f2fe06e 100644 --- a/app/src/main/java/de/jrpie/android/launcher/HomeActivity.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/HomeActivity.kt @@ -1,29 +1,32 @@ -package de.jrpie.android.launcher +package de.jrpie.android.launcher.ui -import android.content.Intent import android.content.SharedPreferences import android.content.res.Resources import android.os.AsyncTask import android.os.Bundle +import android.util.DisplayMetrics import android.view.GestureDetector import android.view.KeyEvent import android.view.MotionEvent import androidx.appcompat.app.AppCompatActivity import androidx.core.view.GestureDetectorCompat import androidx.core.view.isVisible +import de.jrpie.android.launcher.R +import de.jrpie.android.launcher.actions.Gesture +import de.jrpie.android.launcher.actions.LauncherAction import de.jrpie.android.launcher.databinding.HomeBinding -import de.jrpie.android.launcher.list.other.LauncherAction +import de.jrpie.android.launcher.loadApps +import de.jrpie.android.launcher.openTutorial import de.jrpie.android.launcher.preferences.LauncherPreferences -import de.jrpie.android.launcher.tutorial.TutorialActivity +import de.jrpie.android.launcher.preferences.migratePreferencesToNewVersion +import de.jrpie.android.launcher.preferences.resetPreferences +import de.jrpie.android.launcher.ui.tutorial.TutorialActivity import java.text.SimpleDateFormat import java.util.* import kotlin.concurrent.fixedRateTimer import kotlin.math.abs import kotlin.math.max import kotlin.math.min -import android.util.DisplayMetrics -import de.jrpie.android.launcher.preferences.migratePreferencesToNewVersion -import de.jrpie.android.launcher.preferences.resetPreferences /** @@ -38,15 +41,16 @@ import de.jrpie.android.launcher.preferences.resetPreferences * - Setting global variables (preferences etc.) * - Opening the [TutorialActivity] on new installations */ -class HomeActivity: UIObject, AppCompatActivity(), +class HomeActivity : UIObject, AppCompatActivity(), GestureDetector.OnGestureListener, GestureDetector.OnDoubleTapListener { private lateinit var binding: HomeBinding private var sharedPreferencesListener = SharedPreferences.OnSharedPreferenceChangeListener { _, prefKey -> - if(prefKey?.startsWith("clock.") == true || - prefKey?.startsWith("display.") == true) { + if (prefKey?.startsWith("clock.") == true || + prefKey?.startsWith("display.") == true + ) { recreate() } } @@ -70,7 +74,7 @@ class HomeActivity: UIObject, AppCompatActivity(), resetPreferences(this) LauncherPreferences.internal().started(true) - startActivity(Intent(this, TutorialActivity::class.java)) + openTutorial(this) } // Preload apps to speed up the Apps Recycler @@ -82,7 +86,7 @@ class HomeActivity: UIObject, AppCompatActivity(), } - override fun onStart(){ + override fun onStart() { super.onStart() mDetector = GestureDetectorCompat(this, this) @@ -90,7 +94,8 @@ class HomeActivity: UIObject, AppCompatActivity(), super.onStart() - LauncherPreferences.getSharedPreferences().registerOnSharedPreferenceChangeListener(sharedPreferencesListener) + LauncherPreferences.getSharedPreferences() + .registerOnSharedPreferenceChangeListener(sharedPreferencesListener) } private fun updateClock() { @@ -120,7 +125,7 @@ class HomeActivity: UIObject, AppCompatActivity(), var upperVisible = dateVisible var lowerVisible = timeVisible - if(LauncherPreferences.clock().flipDateTime()) { + if (LauncherPreferences.clock().flipDateTime()) { upperFormat = lowerFormat.also { lowerFormat = upperFormat } upperVisible = lowerVisible.also { lowerVisible = upperVisible } } @@ -162,7 +167,8 @@ class HomeActivity: UIObject, AppCompatActivity(), } override fun onDestroy() { - LauncherPreferences.getSharedPreferences().unregisterOnSharedPreferenceChangeListener(sharedPreferencesListener) + LauncherPreferences.getSharedPreferences() + .unregisterOnSharedPreferenceChangeListener(sharedPreferencesListener) super.onDestroy() } @@ -180,7 +186,6 @@ class HomeActivity: UIObject, AppCompatActivity(), if (e1 == null) return false - val displayMetrics: DisplayMetrics? = DisplayMetrics() windowManager.defaultDisplay.getMetrics(displayMetrics) @@ -194,7 +199,7 @@ class HomeActivity: UIObject, AppCompatActivity(), val edgeActions = LauncherPreferences.enabled_gestures().edgeSwipe() val edgeStrictness = 0.15 - var gesture = if(abs(diffX) > abs(diffY)) { // horizontal swipe + var gesture = if (abs(diffX) > abs(diffY)) { // horizontal swipe if (diffX > width / 4) Gesture.SWIPE_LEFT else if (diffX < -width / 4) @@ -214,16 +219,16 @@ class HomeActivity: UIObject, AppCompatActivity(), } if (edgeActions) { - if(max(e1.x, e2.x) < edgeStrictness * width){ - gesture = gesture?.let{it.getEdgeVariant(Gesture.Edge.LEFT)} - } else if (min(e1.x, e2.x) > (1-edgeStrictness) * width){ - gesture = gesture?.let{it.getEdgeVariant(Gesture.Edge.RIGHT)} + if (max(e1.x, e2.x) < edgeStrictness * width) { + gesture = gesture?.let { it.getEdgeVariant(Gesture.Edge.LEFT) } + } else if (min(e1.x, e2.x) > (1 - edgeStrictness) * width) { + gesture = gesture?.let { it.getEdgeVariant(Gesture.Edge.RIGHT) } } - if(max(e1.y, e2.y) < edgeStrictness * height){ - gesture = gesture?.let{it.getEdgeVariant(Gesture.Edge.TOP)} - } else if (min(e1.y, e2.y) > (1-edgeStrictness) * height){ - gesture = gesture?.let{it.getEdgeVariant(Gesture.Edge.BOTTOM)} + if (max(e1.y, e2.y) < edgeStrictness * height) { + gesture = gesture?.let { it.getEdgeVariant(Gesture.Edge.TOP) } + } else if (min(e1.y, e2.y) > (1 - edgeStrictness) * height) { + gesture = gesture?.let { it.getEdgeVariant(Gesture.Edge.BOTTOM) } } } gesture?.invoke(this) @@ -257,13 +262,17 @@ class HomeActivity: UIObject, AppCompatActivity(), } } - return if (mDetector.onTouchEvent(event)) { false } else { super.onTouchEvent(event) } + return if (mDetector.onTouchEvent(event)) { + false + } else { + super.onTouchEvent(event) + } } override fun setOnClicks() { binding.homeUpperView.setOnClickListener { - if(LauncherPreferences.clock().flipDateTime()) { + if (LauncherPreferences.clock().flipDateTime()) { Gesture.TIME(this) } else { Gesture.DATE(this) @@ -271,7 +280,7 @@ class HomeActivity: UIObject, AppCompatActivity(), } binding.homeLowerView.setOnClickListener { - if(LauncherPreferences.clock().flipDateTime()) { + if (LauncherPreferences.clock().flipDateTime()) { Gesture.DATE(this) } else { Gesture.TIME(this) @@ -281,11 +290,22 @@ class HomeActivity: UIObject, AppCompatActivity(), /* TODO: Remove those. For now they are necessary * because this inherits from GestureDetector.OnGestureListener */ - override fun onDoubleTapEvent(event: MotionEvent): Boolean { return false } - override fun onDown(event: MotionEvent): Boolean { return false } - override fun onScroll(e1: MotionEvent?, e2: MotionEvent, dX: Float, dY: Float): Boolean { return false } + override fun onDoubleTapEvent(event: MotionEvent): Boolean { + return false + } + + override fun onDown(event: MotionEvent): Boolean { + return false + } + + override fun onScroll(e1: MotionEvent?, e2: MotionEvent, dX: Float, dY: Float): Boolean { + return false + } + override fun onShowPress(event: MotionEvent) {} - override fun onSingleTapUp(event: MotionEvent): Boolean { return false } + override fun onSingleTapUp(event: MotionEvent): Boolean { + return false + } override fun isHomeScreen(): Boolean { return true diff --git a/app/src/main/java/de/jrpie/android/launcher/UIObject.kt b/app/src/main/java/de/jrpie/android/launcher/ui/UIObject.kt similarity index 94% rename from app/src/main/java/de/jrpie/android/launcher/UIObject.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/UIObject.kt index f661572..94bf347 100644 --- a/app/src/main/java/de/jrpie/android/launcher/UIObject.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/UIObject.kt @@ -1,9 +1,8 @@ -package de.jrpie.android.launcher +package de.jrpie.android.launcher.ui import android.app.Activity import android.content.pm.ActivityInfo import android.content.res.Resources -import android.os.Build import android.view.Window import android.view.WindowManager import de.jrpie.android.launcher.preferences.LauncherPreferences @@ -51,6 +50,7 @@ interface UIObject { setOnClicks() adjustLayout() } + fun modifyTheme(theme: Resources.Theme): Resources.Theme { LauncherPreferences.theme().colorTheme().applyToTheme(theme) LauncherPreferences.theme().background().applyToTheme(theme) @@ -60,8 +60,8 @@ interface UIObject { } // fun applyTheme() { } - fun setOnClicks() { } - fun adjustLayout() { } + fun setOnClicks() {} + fun adjustLayout() {} fun isHomeScreen(): Boolean { return false diff --git a/app/src/main/java/de/jrpie/android/launcher/list/ListActivity.kt b/app/src/main/java/de/jrpie/android/launcher/ui/list/ListActivity.kt similarity index 91% rename from app/src/main/java/de/jrpie/android/launcher/list/ListActivity.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/list/ListActivity.kt index 1bc304e..fbe9e28 100644 --- a/app/src/main/java/de/jrpie/android/launcher/list/ListActivity.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/list/ListActivity.kt @@ -1,4 +1,4 @@ -package de.jrpie.android.launcher.list +package de.jrpie.android.launcher.ui.list import android.app.Activity import android.content.Context @@ -17,12 +17,12 @@ import androidx.viewpager.widget.ViewPager import com.google.android.material.tabs.TabLayout import de.jrpie.android.launcher.R import de.jrpie.android.launcher.REQUEST_UNINSTALL -import de.jrpie.android.launcher.UIObject +import de.jrpie.android.launcher.actions.LauncherAction import de.jrpie.android.launcher.databinding.ListBinding -import de.jrpie.android.launcher.list.apps.ListFragmentApps -import de.jrpie.android.launcher.list.other.LauncherAction -import de.jrpie.android.launcher.list.other.ListFragmentOther import de.jrpie.android.launcher.preferences.LauncherPreferences +import de.jrpie.android.launcher.ui.UIObject +import de.jrpie.android.launcher.ui.list.apps.ListFragmentApps +import de.jrpie.android.launcher.ui.list.other.ListFragmentOther // TODO: Better solution for this intercommunication functionality (used in list-fragments) @@ -44,6 +44,7 @@ class ListActivity : AppCompatActivity(), UIObject { VIEW(R.string.list_title_view), /* view list of apps */ PICK(R.string.list_title_pick) /* choose app or action to associate to a gesture */ } + override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) @@ -66,7 +67,8 @@ class ListActivity : AppCompatActivity(), UIObject { binding.listContainer.context.resources.displayMetrics.heightPixels val diff = height - r.bottom if (diff != 0 && - LauncherPreferences.display().fullScreen()) { + LauncherPreferences.display().fullScreen() + ) { if (binding.listContainer.paddingBottom !== diff) { binding.listContainer.setPadding(0, 0, 0, diff) } @@ -80,7 +82,7 @@ class ListActivity : AppCompatActivity(), UIObject { } - override fun onStart(){ + override fun onStart() { super.onStart() super.onStart() } @@ -146,11 +148,11 @@ private val TAB_TITLES = arrayOf( * The [ListSectionsPagerAdapter] returns the fragment, * which corresponds to the selected tab in [ListActivity]. */ -class ListSectionsPagerAdapter(private val context: Context, fm: FragmentManager) - : FragmentPagerAdapter(fm, BEHAVIOR_RESUME_ONLY_CURRENT_FRAGMENT) { +class ListSectionsPagerAdapter(private val context: Context, fm: FragmentManager) : + FragmentPagerAdapter(fm, BEHAVIOR_RESUME_ONLY_CURRENT_FRAGMENT) { override fun getItem(position: Int): Fragment { - return when (position){ + return when (position) { 0 -> ListFragmentApps() 1 -> ListFragmentOther() else -> Fragment() diff --git a/app/src/main/java/de/jrpie/android/launcher/list/apps/AppsRecyclerAdapter.kt b/app/src/main/java/de/jrpie/android/launcher/ui/list/apps/AppsRecyclerAdapter.kt similarity index 71% rename from app/src/main/java/de/jrpie/android/launcher/list/apps/AppsRecyclerAdapter.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/list/apps/AppsRecyclerAdapter.kt index 86fdb6f..5c1cc9a 100644 --- a/app/src/main/java/de/jrpie/android/launcher/list/apps/AppsRecyclerAdapter.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/list/apps/AppsRecyclerAdapter.kt @@ -1,4 +1,4 @@ -package de.jrpie.android.launcher.list.apps +package de.jrpie.android.launcher.ui.list.apps import android.app.Activity import android.content.Intent @@ -14,14 +14,14 @@ import android.widget.TextView import androidx.recyclerview.widget.RecyclerView import de.jrpie.android.launcher.R import de.jrpie.android.launcher.REQUEST_CHOOSE_APP +import de.jrpie.android.launcher.actions.AppAction +import de.jrpie.android.launcher.actions.AppInfo import de.jrpie.android.launcher.appsList -import de.jrpie.android.launcher.launch -import de.jrpie.android.launcher.launchApp -import de.jrpie.android.launcher.list.ListActivity import de.jrpie.android.launcher.loadApps import de.jrpie.android.launcher.openAppSettings import de.jrpie.android.launcher.preferences.LauncherPreferences import de.jrpie.android.launcher.transformGrayscale +import de.jrpie.android.launcher.ui.list.ListActivity import de.jrpie.android.launcher.uninstallApp import java.util.* import kotlin.text.Regex.Companion.escapeReplacement @@ -34,10 +34,12 @@ import kotlin.text.Regex.Companion.escapeReplacement * @param intention - why the list is displayed ("view", "pick") * @param forGesture - the action which an app is chosen for (when the intention is "pick") */ -class AppsRecyclerAdapter(val activity: Activity, - private val intention: ListActivity.ListActivityIntention - = ListActivity.ListActivityIntention.VIEW, - private val forGesture: String? = ""): +class AppsRecyclerAdapter( + val activity: Activity, + private val intention: ListActivity.ListActivityIntention + = ListActivity.ListActivityIntention.VIEW, + private val forGesture: String? = "" +) : RecyclerView.Adapter() { private val appsListDisplayed: MutableList @@ -53,7 +55,9 @@ class AppsRecyclerAdapter(val activity: Activity, selectItem(adapterPosition, rect) } - init { itemView.setOnClickListener(this) } + init { + itemView.setOnClickListener(this) + } } override fun onBindViewHolder(viewHolder: ViewHolder, i: Int) { @@ -72,16 +76,35 @@ class AppsRecyclerAdapter(val activity: Activity, // decide when to show the options popup menu about if (intention == ListActivity.ListActivityIntention.VIEW) { - viewHolder.textView.setOnLongClickListener{ showOptionsPopup(viewHolder, appPackageName, appUser, isSystemApp) } - viewHolder.img.setOnLongClickListener{ showOptionsPopup(viewHolder, appPackageName, appUser, isSystemApp) } + viewHolder.textView.setOnLongClickListener { + showOptionsPopup( + viewHolder, + appPackageName, + appUser, + isSystemApp + ) + } + viewHolder.img.setOnLongClickListener { + showOptionsPopup( + viewHolder, + appPackageName, + appUser, + isSystemApp + ) + } // ensure onClicks are actually caught - viewHolder.textView.setOnClickListener{ viewHolder.onClick(viewHolder.textView) } - viewHolder.img.setOnClickListener{ viewHolder.onClick(viewHolder.img) } + viewHolder.textView.setOnClickListener { viewHolder.onClick(viewHolder.textView) } + viewHolder.img.setOnClickListener { viewHolder.onClick(viewHolder.img) } } } @Suppress("SameReturnValue") - private fun showOptionsPopup(viewHolder: ViewHolder, appPackageName: String, user: Int?, isSystemApp: Boolean): Boolean { + private fun showOptionsPopup( + viewHolder: ViewHolder, + appPackageName: String, + user: Int?, + isSystemApp: Boolean + ): Boolean { //create the popup menu val popup = PopupMenu(activity, viewHolder.img) @@ -94,13 +117,15 @@ class AppsRecyclerAdapter(val activity: Activity, popup.setOnMenuItemClickListener { when (it.itemId) { R.id.app_menu_delete -> { - uninstallApp(appPackageName, user, activity) + uninstallApp(AppInfo(appPackageName, user), activity) true } + R.id.app_menu_info -> { - openAppSettings(appPackageName, user, activity) + openAppSettings(AppInfo(appPackageName, user), activity) true } + else -> false } } @@ -109,7 +134,9 @@ class AppsRecyclerAdapter(val activity: Activity, return true } - override fun getItemCount(): Int { return appsListDisplayed.size } + override fun getItemCount(): Int { + return appsListDisplayed.size + } override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder { val inflater = LayoutInflater.from(parent.context) @@ -131,19 +158,18 @@ class AppsRecyclerAdapter(val activity: Activity, } fun selectItem(pos: Int, rect: Rect = Rect()) { - if(pos >= appsListDisplayed.size) { + if (pos >= appsListDisplayed.size) { return } - val appPackageName = appsListDisplayed[pos].packageName.toString() - val appUser = appsListDisplayed[pos].user - when (intention){ + val appInfo = appsListDisplayed[pos] + when (intention) { ListActivity.ListActivityIntention.VIEW -> { - launchApp(appPackageName, appUser, activity, rect) + AppAction(appInfo).invoke(activity, rect) } + ListActivity.ListActivityIntention.PICK -> { val returnIntent = Intent() - returnIntent.putExtra("value", appPackageName) - appUser?.let{ returnIntent.putExtra("user", it) } + AppAction(appInfo).writeToIntent(returnIntent) returnIntent.putExtra("forGesture", forGesture) activity.setResult(REQUEST_CHOOSE_APP, returnIntent) activity.finish() @@ -160,12 +186,12 @@ class AppsRecyclerAdapter(val activity: Activity, .lowercase(Locale.ROOT) .toCharArray() .distinct() - .filter { c -> ! ((c in 'a'..'z') || (c in '0'..'9')) } - .map { c -> escapeReplacement(c.toString())} - .fold("") { x,y -> x+y } + .filter { c -> !((c in 'a'..'z') || (c in '0'..'9')) } + .map { c -> escapeReplacement(c.toString()) } + .fold("") { x, y -> x + y } var disallowedCharsRegex = "[^a-z0-9$allowedSpecialCharacters]".toRegex() - fun normalize(text: String): String{ + fun normalize(text: String): String { return text.lowercase(Locale.ROOT).replace(disallowedCharsRegex, "") } appsListDisplayed.clear() @@ -179,7 +205,7 @@ class AppsRecyclerAdapter(val activity: Activity, if (itemLabel.startsWith(normalizedText)) { appsListDisplayed.add(item) - }else if(itemLabel.contains(normalizedText)){ + } else if (itemLabel.contains(normalizedText)) { appsSecondary.add(item) } } @@ -187,11 +213,13 @@ class AppsRecyclerAdapter(val activity: Activity, } if (appsListDisplayed.size == 1 && intention == ListActivity.ListActivityIntention.VIEW - && LauncherPreferences.functionality().searchAutoLaunch()) { + && LauncherPreferences.functionality().searchAutoLaunch() + ) { val info = appsListDisplayed[0] - launch(info.packageName.toString(), info.user, activity) + AppAction(info).invoke(activity) - val inputMethodManager = activity.getSystemService(Activity.INPUT_METHOD_SERVICE) as InputMethodManager + val inputMethodManager = + activity.getSystemService(Activity.INPUT_METHOD_SERVICE) as InputMethodManager inputMethodManager.hideSoftInputFromWindow(View(activity).windowToken, 0) } diff --git a/app/src/main/java/de/jrpie/android/launcher/list/apps/ListFragmentApps.kt b/app/src/main/java/de/jrpie/android/launcher/ui/list/apps/ListFragmentApps.kt similarity index 87% rename from app/src/main/java/de/jrpie/android/launcher/list/apps/ListFragmentApps.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/list/apps/ListFragmentApps.kt index 72f3f48..6712e2c 100644 --- a/app/src/main/java/de/jrpie/android/launcher/list/apps/ListFragmentApps.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/list/apps/ListFragmentApps.kt @@ -1,4 +1,4 @@ -package de.jrpie.android.launcher.list.apps +package de.jrpie.android.launcher.ui.list.apps import android.os.Bundle import android.view.LayoutInflater @@ -6,13 +6,13 @@ import android.view.View import android.view.ViewGroup import androidx.fragment.app.Fragment import androidx.recyclerview.widget.LinearLayoutManager -import de.jrpie.android.launcher.UIObject import de.jrpie.android.launcher.databinding.ListAppsBinding -import de.jrpie.android.launcher.list.ListActivity -import de.jrpie.android.launcher.list.forGesture -import de.jrpie.android.launcher.list.intention import de.jrpie.android.launcher.openSoftKeyboard import de.jrpie.android.launcher.preferences.LauncherPreferences +import de.jrpie.android.launcher.ui.UIObject +import de.jrpie.android.launcher.ui.list.ListActivity +import de.jrpie.android.launcher.ui.list.forGesture +import de.jrpie.android.launcher.ui.list.intention /** @@ -36,7 +36,7 @@ class ListFragmentApps : Fragment(), UIObject { super.onStart() } - override fun setOnClicks() { } + override fun setOnClicks() {} override fun adjustLayout() { @@ -66,7 +66,8 @@ class ListFragmentApps : Fragment(), UIObject { }) if (intention == ListActivity.ListActivityIntention.VIEW - && LauncherPreferences.functionality().searchAutoOpenKeyboard()){ + && LauncherPreferences.functionality().searchAutoOpenKeyboard() + ) { openSoftKeyboard(requireContext(), binding.listAppsSearchview) } } diff --git a/app/src/main/java/de/jrpie/android/launcher/list/other/ListFragmentOther.kt b/app/src/main/java/de/jrpie/android/launcher/ui/list/other/ListFragmentOther.kt similarity index 94% rename from app/src/main/java/de/jrpie/android/launcher/list/other/ListFragmentOther.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/list/other/ListFragmentOther.kt index 2c73aea..097f9c5 100644 --- a/app/src/main/java/de/jrpie/android/launcher/list/other/ListFragmentOther.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/list/other/ListFragmentOther.kt @@ -1,4 +1,4 @@ -package de.jrpie.android.launcher.list.other +package de.jrpie.android.launcher.ui.list.other import android.os.Bundle import android.view.LayoutInflater @@ -6,7 +6,6 @@ import android.view.View import android.view.ViewGroup import androidx.fragment.app.Fragment import androidx.recyclerview.widget.LinearLayoutManager -import de.jrpie.android.launcher.R import de.jrpie.android.launcher.databinding.ListOtherBinding /** diff --git a/app/src/main/java/de/jrpie/android/launcher/list/other/OtherRecyclerAdapter.kt b/app/src/main/java/de/jrpie/android/launcher/ui/list/other/OtherRecyclerAdapter.kt similarity index 77% rename from app/src/main/java/de/jrpie/android/launcher/list/other/OtherRecyclerAdapter.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/list/other/OtherRecyclerAdapter.kt index 0b54fa6..ddfcfd1 100644 --- a/app/src/main/java/de/jrpie/android/launcher/list/other/OtherRecyclerAdapter.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/list/other/OtherRecyclerAdapter.kt @@ -1,4 +1,4 @@ -package de.jrpie.android.launcher.list.other +package de.jrpie.android.launcher.ui.list.other import android.app.Activity import android.content.Intent @@ -8,10 +8,10 @@ import android.view.ViewGroup import android.widget.ImageView import android.widget.TextView import androidx.recyclerview.widget.RecyclerView -import de.jrpie.android.launcher.INVALID_USER import de.jrpie.android.launcher.R import de.jrpie.android.launcher.REQUEST_CHOOSE_APP -import de.jrpie.android.launcher.list.forGesture +import de.jrpie.android.launcher.actions.LauncherAction +import de.jrpie.android.launcher.ui.list.forGesture /** * The [OtherRecyclerAdapter] will only be displayed in the ListActivity, @@ -20,7 +20,7 @@ import de.jrpie.android.launcher.list.forGesture * It lists `other` things to be launched that are not really represented by a URI, * rather by Launcher- internal conventions. */ -class OtherRecyclerAdapter(val activity: Activity): +class OtherRecyclerAdapter(val activity: Activity) : RecyclerView.Adapter() { private val othersList: Array = LauncherAction.values() @@ -35,10 +35,12 @@ class OtherRecyclerAdapter(val activity: Activity): val pos = adapterPosition val content = othersList[pos] - forGesture?.let { returnChoiceIntent(it, content.id) } + forGesture?.let { returnChoiceIntent(it, content) } } - init { itemView.setOnClickListener(this) } + init { + itemView.setOnClickListener(this) + } } override fun onBindViewHolder(viewHolder: ViewHolder, i: Int) { @@ -49,7 +51,9 @@ class OtherRecyclerAdapter(val activity: Activity): viewHolder.iconView.setImageResource(icon) } - override fun getItemCount(): Int { return othersList.size } + override fun getItemCount(): Int { + return othersList.size + } override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder { val inflater = LayoutInflater.from(parent.context) @@ -57,11 +61,10 @@ class OtherRecyclerAdapter(val activity: Activity): return ViewHolder(view) } - private fun returnChoiceIntent(forGesture: String, value: String) { + private fun returnChoiceIntent(forGesture: String, action: LauncherAction) { val returnIntent = Intent() - returnIntent.putExtra("value", value) returnIntent.putExtra("forGesture", forGesture) - returnIntent.putExtra("user", INVALID_USER) + action.writeToIntent(returnIntent) activity.setResult(REQUEST_CHOOSE_APP, returnIntent) activity.finish() } diff --git a/app/src/main/java/de/jrpie/android/launcher/settings/SettingsActivity.kt b/app/src/main/java/de/jrpie/android/launcher/ui/settings/SettingsActivity.kt similarity index 71% rename from app/src/main/java/de/jrpie/android/launcher/settings/SettingsActivity.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/settings/SettingsActivity.kt index 54938fd..f509235 100644 --- a/app/src/main/java/de/jrpie/android/launcher/settings/SettingsActivity.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/settings/SettingsActivity.kt @@ -1,4 +1,4 @@ -package de.jrpie.android.launcher.settings +package de.jrpie.android.launcher.ui.settings import android.content.Context import android.content.Intent @@ -7,17 +7,20 @@ import android.content.res.Resources import android.os.Bundle import android.provider.Settings import androidx.appcompat.app.AppCompatActivity -import androidx.viewpager.widget.ViewPager -import de.jrpie.android.launcher.* -import com.google.android.material.tabs.TabLayout -import de.jrpie.android.launcher.databinding.SettingsBinding import androidx.fragment.app.Fragment import androidx.fragment.app.FragmentManager import androidx.fragment.app.FragmentPagerAdapter +import androidx.viewpager.widget.ViewPager +import com.google.android.material.tabs.TabLayout +import de.jrpie.android.launcher.R +import de.jrpie.android.launcher.REQUEST_CHOOSE_APP +import de.jrpie.android.launcher.databinding.SettingsBinding import de.jrpie.android.launcher.preferences.LauncherPreferences -import de.jrpie.android.launcher.settings.actions.SettingsFragmentActions -import de.jrpie.android.launcher.settings.launcher.SettingsFragmentLauncher -import de.jrpie.android.launcher.settings.meta.SettingsFragmentMeta +import de.jrpie.android.launcher.saveListActivityChoice +import de.jrpie.android.launcher.ui.UIObject +import de.jrpie.android.launcher.ui.settings.actions.SettingsFragmentActions +import de.jrpie.android.launcher.ui.settings.launcher.SettingsFragmentLauncher +import de.jrpie.android.launcher.ui.settings.meta.SettingsFragmentMeta /** * The [SettingsActivity] is a tabbed activity: @@ -28,12 +31,13 @@ import de.jrpie.android.launcher.settings.meta.SettingsFragmentMeta * * Settings are closed automatically if the activity goes `onPause` unexpectedly. */ -class SettingsActivity: AppCompatActivity(), UIObject { +class SettingsActivity : AppCompatActivity(), UIObject { private var sharedPreferencesListener = - SharedPreferences.OnSharedPreferenceChangeListener { _,prefKey -> - if(prefKey?.startsWith("theme.") == true || - prefKey?.startsWith("display.") == true) { + SharedPreferences.OnSharedPreferenceChangeListener { _, prefKey -> + if (prefKey?.startsWith("theme.") == true || + prefKey?.startsWith("display.") == true + ) { recreate() } } @@ -58,11 +62,13 @@ class SettingsActivity: AppCompatActivity(), UIObject { override fun onStart() { super.onStart() super.onStart() - LauncherPreferences.getSharedPreferences().registerOnSharedPreferenceChangeListener(sharedPreferencesListener) + LauncherPreferences.getSharedPreferences() + .registerOnSharedPreferenceChangeListener(sharedPreferencesListener) } override fun onPause() { - LauncherPreferences.getSharedPreferences().unregisterOnSharedPreferenceChangeListener(sharedPreferencesListener) + LauncherPreferences.getSharedPreferences() + .unregisterOnSharedPreferenceChangeListener(sharedPreferencesListener) super.onPause() } @@ -70,7 +76,7 @@ class SettingsActivity: AppCompatActivity(), UIObject { return modifyTheme(super.getTheme()) } - override fun setOnClicks(){ + override fun setOnClicks() { // As older APIs somehow do not recognize the xml defined onClick binding.settingsClose.setOnClickListener { finish() } // open device settings (see https://stackoverflow.com/a/62092663/12787264) @@ -81,7 +87,7 @@ class SettingsActivity: AppCompatActivity(), UIObject { override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) { when (requestCode) { - REQUEST_CHOOSE_APP -> saveListActivityChoice(this, data) + REQUEST_CHOOSE_APP -> saveListActivityChoice(data) else -> super.onActivityResult(requestCode, resultCode, data) } } @@ -93,11 +99,11 @@ private val TAB_TITLES = arrayOf( R.string.settings_tab_meta ) -class SettingsSectionsPagerAdapter(private val context: Context, fm: FragmentManager) - : FragmentPagerAdapter(fm, BEHAVIOR_RESUME_ONLY_CURRENT_FRAGMENT) { +class SettingsSectionsPagerAdapter(private val context: Context, fm: FragmentManager) : + FragmentPagerAdapter(fm, BEHAVIOR_RESUME_ONLY_CURRENT_FRAGMENT) { override fun getItem(position: Int): Fragment { - return when (position){ + return when (position) { 0 -> SettingsFragmentActions() 1 -> SettingsFragmentLauncher() 2 -> SettingsFragmentMeta() @@ -109,5 +115,7 @@ class SettingsSectionsPagerAdapter(private val context: Context, fm: FragmentMan return context.resources.getString(TAB_TITLES[position]) } - override fun getCount(): Int { return 3 } + override fun getCount(): Int { + return 3 + } } diff --git a/app/src/main/java/de/jrpie/android/launcher/settings/actions/SettingsFragmentActions.kt b/app/src/main/java/de/jrpie/android/launcher/ui/settings/actions/SettingsFragmentActions.kt similarity index 82% rename from app/src/main/java/de/jrpie/android/launcher/settings/actions/SettingsFragmentActions.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/settings/actions/SettingsFragmentActions.kt index bd0fa19..976e08e 100644 --- a/app/src/main/java/de/jrpie/android/launcher/settings/actions/SettingsFragmentActions.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/settings/actions/SettingsFragmentActions.kt @@ -1,4 +1,4 @@ -package de.jrpie.android.launcher.settings.actions +package de.jrpie.android.launcher.ui.settings.actions import android.content.ActivityNotFoundException import android.content.Intent @@ -9,9 +9,9 @@ import android.view.ViewGroup import android.widget.Toast import androidx.fragment.app.Fragment import de.jrpie.android.launcher.R -import de.jrpie.android.launcher.UIObject import de.jrpie.android.launcher.databinding.SettingsActionsBinding -import de.jrpie.android.launcher.list.ListActivity +import de.jrpie.android.launcher.ui.UIObject +import de.jrpie.android.launcher.ui.list.ListActivity /** @@ -44,18 +44,22 @@ SettingsFragmentActions : Fragment(), UIObject { override fun setOnClicks() { // App management buttons - binding!!.settingsActionsButtonViewApps.setOnClickListener{ + binding!!.settingsActionsButtonViewApps.setOnClickListener { val intent = Intent(this.context, ListActivity::class.java) intent.putExtra("intention", ListActivity.ListActivityIntention.VIEW.toString()) startActivity(intent) } - binding!!.settingsActionsButtonInstallApps.setOnClickListener{ + binding!!.settingsActionsButtonInstallApps.setOnClickListener { try { val intent = Intent(Intent.ACTION_MAIN) intent.addCategory(Intent.CATEGORY_APP_MARKET) startActivity(intent) } catch (e: ActivityNotFoundException) { - Toast.makeText(context, getString(R.string.settings_apps_toast_store_not_found), Toast.LENGTH_SHORT).show() + Toast.makeText( + context, + getString(R.string.settings_apps_toast_store_not_found), + Toast.LENGTH_SHORT + ).show() } } } diff --git a/app/src/main/java/de/jrpie/android/launcher/settings/actions/SettingsFragmentActionsRecycler.kt b/app/src/main/java/de/jrpie/android/launcher/ui/settings/actions/SettingsFragmentActionsRecycler.kt similarity index 69% rename from app/src/main/java/de/jrpie/android/launcher/settings/actions/SettingsFragmentActionsRecycler.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/settings/actions/SettingsFragmentActionsRecycler.kt index 898f6f7..9d9685f 100644 --- a/app/src/main/java/de/jrpie/android/launcher/settings/actions/SettingsFragmentActionsRecycler.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/settings/actions/SettingsFragmentActionsRecycler.kt @@ -1,24 +1,27 @@ -package de.jrpie.android.launcher.settings.actions +package de.jrpie.android.launcher.ui.settings.actions +import android.app.Activity +import android.content.Intent +import android.content.SharedPreferences import android.os.Bundle import android.view.LayoutInflater import android.view.View import android.view.ViewGroup -import androidx.fragment.app.Fragment -import androidx.recyclerview.widget.LinearLayoutManager -import de.jrpie.android.launcher.* -import de.jrpie.android.launcher.list.ListActivity -import android.app.Activity -import android.content.Intent -import android.content.SharedPreferences import android.widget.Button import android.widget.ImageView import android.widget.TextView +import androidx.fragment.app.Fragment +import androidx.recyclerview.widget.LinearLayoutManager import androidx.recyclerview.widget.RecyclerView -import de.jrpie.android.launcher.list.other.LauncherAction +import de.jrpie.android.launcher.R +import de.jrpie.android.launcher.REQUEST_CHOOSE_APP +import de.jrpie.android.launcher.actions.Action +import de.jrpie.android.launcher.actions.Gesture import de.jrpie.android.launcher.databinding.SettingsActionsRecyclerBinding import de.jrpie.android.launcher.preferences.LauncherPreferences -import java.lang.Exception +import de.jrpie.android.launcher.transformGrayscale +import de.jrpie.android.launcher.ui.UIObject +import de.jrpie.android.launcher.ui.list.ListActivity /** * The [SettingsFragmentActionsRecycler] is a fragment containing the [ActionsRecyclerAdapter], @@ -48,7 +51,7 @@ class SettingsFragmentActionsRecycler : Fragment(), UIObject { // set up the list / recycler val actionViewManager = LinearLayoutManager(context) - actionViewAdapter = ActionsRecyclerAdapter( requireActivity() ) + actionViewAdapter = ActionsRecyclerAdapter(requireActivity()) binding.settingsActionsRview.apply { // improve performance (since content changes don't change the layout size) @@ -56,19 +59,21 @@ class SettingsFragmentActionsRecycler : Fragment(), UIObject { layoutManager = actionViewManager adapter = actionViewAdapter } - LauncherPreferences.getSharedPreferences().registerOnSharedPreferenceChangeListener(sharedPreferencesListener) + LauncherPreferences.getSharedPreferences() + .registerOnSharedPreferenceChangeListener(sharedPreferencesListener) super.onStart() } override fun onDestroy() { - LauncherPreferences.getSharedPreferences().unregisterOnSharedPreferenceChangeListener(sharedPreferencesListener) + LauncherPreferences.getSharedPreferences() + .unregisterOnSharedPreferenceChangeListener(sharedPreferencesListener) super.onDestroy() } } -class ActionsRecyclerAdapter(val activity: Activity): +class ActionsRecyclerAdapter(val activity: Activity) : RecyclerView.Adapter() { private val gesturesList: ArrayList @@ -80,52 +85,44 @@ class ActionsRecyclerAdapter(val activity: Activity): var chooseButton: Button = itemView.findViewById(R.id.settings_actions_row_button_choose) var removeAction: ImageView = itemView.findViewById(R.id.settings_actions_row_remove) - override fun onClick(v: View) { } + override fun onClick(v: View) {} - init { itemView.setOnClickListener(this) } + init { + itemView.setOnClickListener(this) + } } private fun updateViewHolder(gesture: Gesture, viewHolder: ViewHolder) { - val app = gesture.getApp(activity) - val content = app.first - viewHolder.img.visibility = View.VISIBLE - viewHolder.removeAction.visibility = View.VISIBLE - viewHolder.chooseButton.visibility = View.INVISIBLE - if (content.isEmpty()){ + val action = Action.forGesture(gesture) + val drawable = action?.getIcon(activity) + + if (action == null || drawable == null) { viewHolder.img.visibility = View.INVISIBLE viewHolder.removeAction.visibility = View.GONE viewHolder.chooseButton.visibility = View.VISIBLE + return } - else if (LauncherAction.isOtherAction(content)) { - LauncherAction.byId(content)?.let { - viewHolder.img.setImageResource(it.icon) - } - } else { - // Set image icon (by packageName) - try { - viewHolder.img.setImageDrawable(getAppIcon(activity, content, app.second)) - } catch (e : Exception) { - // Probably the app was uninstalled - // the button is shown, user asked to select an action - viewHolder.img.visibility = View.INVISIBLE - viewHolder.removeAction.visibility = View.GONE - viewHolder.chooseButton.visibility = View.VISIBLE - } - } + + viewHolder.img.visibility = View.VISIBLE + viewHolder.removeAction.visibility = View.VISIBLE + viewHolder.chooseButton.visibility = View.INVISIBLE + viewHolder.img.setImageDrawable(drawable) } override fun onBindViewHolder(viewHolder: ViewHolder, i: Int) { val gesture = gesturesList[i] viewHolder.textView.text = gesture.getLabel(activity) if (LauncherPreferences.theme().monochromeIcons()) - transformGrayscale( viewHolder.img ) + transformGrayscale(viewHolder.img) updateViewHolder(gesture, viewHolder) - viewHolder.img.setOnClickListener{ chooseApp(gesture) } - viewHolder.chooseButton.setOnClickListener{ chooseApp(gesture) } - viewHolder.removeAction.setOnClickListener{ gesture.removeApp(activity) } + viewHolder.img.setOnClickListener { chooseApp(gesture) } + viewHolder.chooseButton.setOnClickListener { chooseApp(gesture) } + viewHolder.removeAction.setOnClickListener { Action.clearActionForGesture(gesture) } } - override fun getItemCount(): Int { return gesturesList.size } + override fun getItemCount(): Int { + return gesturesList.size + } override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder { val inflater = LayoutInflater.from(parent.context) @@ -138,7 +135,8 @@ class ActionsRecyclerAdapter(val activity: Activity): val edgeActions = LauncherPreferences.enabled_gestures().edgeSwipe() gesturesList = Gesture.values().filter { (doubleActions || !it.isDoubleVariant()) - && (edgeActions || !it.isEdgeVariant())} as ArrayList + && (edgeActions || !it.isEdgeVariant()) + } as ArrayList } fun updateActions() { @@ -147,7 +145,8 @@ class ActionsRecyclerAdapter(val activity: Activity): this.gesturesList.clear() gesturesList.addAll(Gesture.values().filter { (doubleActions || !it.isDoubleVariant()) - && (edgeActions || !it.isEdgeVariant())}) + && (edgeActions || !it.isEdgeVariant()) + }) notifyDataSetChanged() } @@ -157,7 +156,8 @@ class ActionsRecyclerAdapter(val activity: Activity): val intent = Intent(activity, ListActivity::class.java) intent.putExtra("intention", ListActivity.ListActivityIntention.PICK.toString()) intent.putExtra("forGesture", gesture.id) // for which action we choose the app - activity.startActivityForResult(intent, + activity.startActivityForResult( + intent, REQUEST_CHOOSE_APP ) } diff --git a/app/src/main/java/de/jrpie/android/launcher/settings/launcher/SettingsFragmentLauncher.kt b/app/src/main/java/de/jrpie/android/launcher/ui/settings/launcher/SettingsFragmentLauncher.kt similarity index 84% rename from app/src/main/java/de/jrpie/android/launcher/settings/launcher/SettingsFragmentLauncher.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/settings/launcher/SettingsFragmentLauncher.kt index adfc67b..d436ca3 100644 --- a/app/src/main/java/de/jrpie/android/launcher/settings/launcher/SettingsFragmentLauncher.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/settings/launcher/SettingsFragmentLauncher.kt @@ -1,12 +1,11 @@ -package de.jrpie.android.launcher.settings.launcher +package de.jrpie.android.launcher.ui.settings.launcher -import android.content.Context import android.content.Intent import android.content.SharedPreferences import android.os.Bundle import androidx.preference.PreferenceFragmentCompat -import de.jrpie.android.launcher.preferences.LauncherPreferences import de.jrpie.android.launcher.R +import de.jrpie.android.launcher.preferences.LauncherPreferences import de.jrpie.android.launcher.setDefaultHomeScreen @@ -20,12 +19,12 @@ class SettingsFragmentLauncher : PreferenceFragmentCompat() { private var sharedPreferencesListener = SharedPreferences.OnSharedPreferenceChangeListener { _, prefKey -> - if(prefKey?.startsWith("clock.") == true) { + if (prefKey?.startsWith("clock.") == true) { updateVisibility() } } - private fun updateVisibility(){ + private fun updateVisibility() { val showSeconds = findPreference( LauncherPreferences.clock().keys().showSeconds() ) @@ -35,11 +34,13 @@ class SettingsFragmentLauncher : PreferenceFragmentCompat() { override fun onStart() { super.onStart() - LauncherPreferences.getSharedPreferences().registerOnSharedPreferenceChangeListener(sharedPreferencesListener) + LauncherPreferences.getSharedPreferences() + .registerOnSharedPreferenceChangeListener(sharedPreferencesListener) } override fun onPause() { - LauncherPreferences.getSharedPreferences().unregisterOnSharedPreferenceChangeListener(sharedPreferencesListener) + LauncherPreferences.getSharedPreferences() + .unregisterOnSharedPreferenceChangeListener(sharedPreferencesListener) super.onPause() } diff --git a/app/src/main/java/de/jrpie/android/launcher/settings/meta/SettingsFragmentMeta.kt b/app/src/main/java/de/jrpie/android/launcher/ui/settings/meta/SettingsFragmentMeta.kt similarity index 93% rename from app/src/main/java/de/jrpie/android/launcher/settings/meta/SettingsFragmentMeta.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/settings/meta/SettingsFragmentMeta.kt index 2a19c13..a1e0eba 100644 --- a/app/src/main/java/de/jrpie/android/launcher/settings/meta/SettingsFragmentMeta.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/settings/meta/SettingsFragmentMeta.kt @@ -1,4 +1,4 @@ -package de.jrpie.android.launcher.settings.meta +package de.jrpie.android.launcher.ui.settings.meta import android.app.AlertDialog import android.content.Intent @@ -9,11 +9,11 @@ import android.view.View import android.view.ViewGroup import androidx.fragment.app.Fragment import de.jrpie.android.launcher.R -import de.jrpie.android.launcher.UIObject -import de.jrpie.android.launcher.openNewTabWindow -import de.jrpie.android.launcher.tutorial.TutorialActivity import de.jrpie.android.launcher.databinding.SettingsMetaBinding +import de.jrpie.android.launcher.openNewTabWindow import de.jrpie.android.launcher.preferences.resetPreferences +import de.jrpie.android.launcher.ui.UIObject +import de.jrpie.android.launcher.ui.tutorial.TutorialActivity /** * The [SettingsFragmentMeta] is a used as a tab in the SettingsActivity. @@ -65,7 +65,8 @@ class SettingsFragmentMeta : Fragment(), UIObject { AlertDialog.Builder(this.requireContext(), R.style.AlertDialogCustom) .setTitle(getString(R.string.settings_meta_reset)) .setMessage(getString(R.string.settings_meta_reset_confirm)) - .setPositiveButton(android.R.string.ok + .setPositiveButton( + android.R.string.ok ) { _, _ -> resetPreferences(this.requireContext()) requireActivity().finish() @@ -85,7 +86,6 @@ class SettingsFragmentMeta : Fragment(), UIObject { } - // contact developer binding.settingsMetaButtonContact.setOnClickListener { openNewTabWindow( diff --git a/app/src/main/java/de/jrpie/android/launcher/tutorial/TutorialActivity.kt b/app/src/main/java/de/jrpie/android/launcher/ui/tutorial/TutorialActivity.kt similarity index 74% rename from app/src/main/java/de/jrpie/android/launcher/tutorial/TutorialActivity.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/tutorial/TutorialActivity.kt index a9e0478..490f42d 100644 --- a/app/src/main/java/de/jrpie/android/launcher/tutorial/TutorialActivity.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/tutorial/TutorialActivity.kt @@ -1,4 +1,4 @@ -package de.jrpie.android.launcher.tutorial +package de.jrpie.android.launcher.ui.tutorial import android.content.Intent import android.content.res.Resources @@ -9,16 +9,16 @@ import androidx.fragment.app.FragmentManager import androidx.fragment.app.FragmentPagerAdapter import androidx.viewpager.widget.ViewPager import com.google.android.material.tabs.TabLayout -import de.jrpie.android.launcher.preferences.LauncherPreferences import de.jrpie.android.launcher.R import de.jrpie.android.launcher.REQUEST_CHOOSE_APP -import de.jrpie.android.launcher.UIObject +import de.jrpie.android.launcher.preferences.LauncherPreferences import de.jrpie.android.launcher.saveListActivityChoice -import de.jrpie.android.launcher.tutorial.tabs.TutorialFragmentConcept -import de.jrpie.android.launcher.tutorial.tabs.TutorialFragmentFinish -import de.jrpie.android.launcher.tutorial.tabs.TutorialFragmentSetup -import de.jrpie.android.launcher.tutorial.tabs.TutorialFragmentStart -import de.jrpie.android.launcher.tutorial.tabs.TutorialFragmentUsage +import de.jrpie.android.launcher.ui.UIObject +import de.jrpie.android.launcher.ui.tutorial.tabs.TutorialFragmentConcept +import de.jrpie.android.launcher.ui.tutorial.tabs.TutorialFragmentFinish +import de.jrpie.android.launcher.ui.tutorial.tabs.TutorialFragmentSetup +import de.jrpie.android.launcher.ui.tutorial.tabs.TutorialFragmentStart +import de.jrpie.android.launcher.ui.tutorial.tabs.TutorialFragmentUsage /** * The [TutorialActivity] is displayed automatically on new installations. @@ -27,7 +27,7 @@ import de.jrpie.android.launcher.tutorial.tabs.TutorialFragmentUsage * It tells the user about the concept behind launcher * and helps with the setup process (on new installations) */ -class TutorialActivity: AppCompatActivity(), UIObject { +class TutorialActivity : AppCompatActivity(), UIObject { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) @@ -54,7 +54,7 @@ class TutorialActivity: AppCompatActivity(), UIObject { override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) { when (requestCode) { - REQUEST_CHOOSE_APP -> saveListActivityChoice(this,data) + REQUEST_CHOOSE_APP -> saveListActivityChoice(data) else -> super.onActivityResult(requestCode, resultCode, data) } } @@ -73,11 +73,11 @@ class TutorialActivity: AppCompatActivity(), UIObject { * * Tabs: (Start | Concept | Usage | Setup | Finish) */ -class TutorialSectionsPagerAdapter(fm: FragmentManager) - : FragmentPagerAdapter(fm, BEHAVIOR_RESUME_ONLY_CURRENT_FRAGMENT) { +class TutorialSectionsPagerAdapter(fm: FragmentManager) : + FragmentPagerAdapter(fm, BEHAVIOR_RESUME_ONLY_CURRENT_FRAGMENT) { override fun getItem(position: Int): Fragment { - return when (position){ + return when (position) { 0 -> TutorialFragmentStart() 1 -> TutorialFragmentConcept() 2 -> TutorialFragmentUsage() @@ -88,6 +88,11 @@ class TutorialSectionsPagerAdapter(fm: FragmentManager) } /* We don't use titles here, as we have the dots */ - override fun getPageTitle(position: Int): CharSequence { return "" } - override fun getCount(): Int { return 5 } + override fun getPageTitle(position: Int): CharSequence { + return "" + } + + override fun getCount(): Int { + return 5 + } } diff --git a/app/src/main/java/de/jrpie/android/launcher/tutorial/tabs/TutorialFragmentConcept.kt b/app/src/main/java/de/jrpie/android/launcher/ui/tutorial/tabs/TutorialFragmentConcept.kt similarity index 88% rename from app/src/main/java/de/jrpie/android/launcher/tutorial/tabs/TutorialFragmentConcept.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/tutorial/tabs/TutorialFragmentConcept.kt index ffeb464..26d4141 100644 --- a/app/src/main/java/de/jrpie/android/launcher/tutorial/tabs/TutorialFragmentConcept.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/tutorial/tabs/TutorialFragmentConcept.kt @@ -1,4 +1,4 @@ -package de.jrpie.android.launcher.tutorial.tabs +package de.jrpie.android.launcher.ui.tutorial.tabs import android.os.Bundle import android.view.LayoutInflater @@ -6,8 +6,9 @@ import android.view.View import android.view.ViewGroup import androidx.fragment.app.Fragment import de.jrpie.android.launcher.BuildConfig -import de.jrpie.android.launcher.UIObject import de.jrpie.android.launcher.databinding.TutorialConceptBinding +import de.jrpie.android.launcher.ui.UIObject + /** * The [TutorialFragmentConcept] is a used as a tab in the TutorialActivity. * @@ -25,7 +26,7 @@ class TutorialFragmentConcept : Fragment(), UIObject { return binding.root } - override fun onStart(){ + override fun onStart() { super.onStart() super.onStart() } diff --git a/app/src/main/java/de/jrpie/android/launcher/tutorial/tabs/TutorialFragmentFinish.kt b/app/src/main/java/de/jrpie/android/launcher/ui/tutorial/tabs/TutorialFragmentFinish.kt similarity index 82% rename from app/src/main/java/de/jrpie/android/launcher/tutorial/tabs/TutorialFragmentFinish.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/tutorial/tabs/TutorialFragmentFinish.kt index f4598b1..2d01d0a 100644 --- a/app/src/main/java/de/jrpie/android/launcher/tutorial/tabs/TutorialFragmentFinish.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/tutorial/tabs/TutorialFragmentFinish.kt @@ -1,14 +1,15 @@ -package de.jrpie.android.launcher.tutorial.tabs +package de.jrpie.android.launcher.ui.tutorial.tabs import android.os.Bundle -import androidx.fragment.app.Fragment import android.view.LayoutInflater import android.view.View import android.view.ViewGroup -import de.jrpie.android.launcher.* +import androidx.fragment.app.Fragment import de.jrpie.android.launcher.BuildConfig.VERSION_CODE import de.jrpie.android.launcher.databinding.TutorialFinishBinding import de.jrpie.android.launcher.preferences.LauncherPreferences +import de.jrpie.android.launcher.setDefaultHomeScreen +import de.jrpie.android.launcher.ui.UIObject /** * The [TutorialFragmentFinish] is a used as a tab in the TutorialActivity. @@ -34,11 +35,11 @@ class TutorialFragmentFinish : Fragment(), UIObject { override fun setOnClicks() { super.setOnClicks() - binding.tutorialFinishButtonStart.setOnClickListener{ finishTutorial() } + binding.tutorialFinishButtonStart.setOnClickListener { finishTutorial() } } private fun finishTutorial() { - if(!LauncherPreferences.internal().started()) { + if (!LauncherPreferences.internal().started()) { LauncherPreferences.internal().started(true) LauncherPreferences.internal().startedTime(System.currentTimeMillis() / 1000L) LauncherPreferences.internal().versionCode(VERSION_CODE) diff --git a/app/src/main/java/de/jrpie/android/launcher/tutorial/tabs/TutorialFragmentSetup.kt b/app/src/main/java/de/jrpie/android/launcher/ui/tutorial/tabs/TutorialFragmentSetup.kt similarity index 84% rename from app/src/main/java/de/jrpie/android/launcher/tutorial/tabs/TutorialFragmentSetup.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/tutorial/tabs/TutorialFragmentSetup.kt index a71088d..09ef4c9 100644 --- a/app/src/main/java/de/jrpie/android/launcher/tutorial/tabs/TutorialFragmentSetup.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/tutorial/tabs/TutorialFragmentSetup.kt @@ -1,4 +1,4 @@ -package de.jrpie.android.launcher.tutorial.tabs +package de.jrpie.android.launcher.ui.tutorial.tabs import android.os.Bundle import android.view.LayoutInflater @@ -6,7 +6,7 @@ import android.view.View import android.view.ViewGroup import androidx.fragment.app.Fragment import de.jrpie.android.launcher.R -import de.jrpie.android.launcher.UIObject +import de.jrpie.android.launcher.ui.UIObject /** * The [TutorialFragmentSetup] is a used as a tab in the TutorialActivity. @@ -22,7 +22,7 @@ class TutorialFragmentSetup : Fragment(), UIObject { return inflater.inflate(R.layout.tutorial_setup, container, false) } - override fun onStart(){ + override fun onStart() { super.onStart() super.onStart() } diff --git a/app/src/main/java/de/jrpie/android/launcher/tutorial/tabs/TutorialFragmentStart.kt b/app/src/main/java/de/jrpie/android/launcher/ui/tutorial/tabs/TutorialFragmentStart.kt similarity index 83% rename from app/src/main/java/de/jrpie/android/launcher/tutorial/tabs/TutorialFragmentStart.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/tutorial/tabs/TutorialFragmentStart.kt index 433da9b..160a1d4 100644 --- a/app/src/main/java/de/jrpie/android/launcher/tutorial/tabs/TutorialFragmentStart.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/tutorial/tabs/TutorialFragmentStart.kt @@ -1,12 +1,13 @@ -package de.jrpie.android.launcher.tutorial.tabs +package de.jrpie.android.launcher.ui.tutorial.tabs import android.os.Bundle -import androidx.fragment.app.Fragment import android.view.LayoutInflater import android.view.View import android.view.ViewGroup -import de.jrpie.android.launcher.* +import androidx.fragment.app.Fragment +import de.jrpie.android.launcher.blink import de.jrpie.android.launcher.databinding.TutorialStartBinding +import de.jrpie.android.launcher.ui.UIObject /** * The [TutorialFragmentStart] is a used as a tab in the TutorialActivity. @@ -25,7 +26,7 @@ class TutorialFragmentStart : Fragment(), UIObject { return binding.root } - override fun onStart(){ + override fun onStart() { super.onStart() super.onStart() } diff --git a/app/src/main/java/de/jrpie/android/launcher/tutorial/tabs/TutorialFragmentUsage.kt b/app/src/main/java/de/jrpie/android/launcher/ui/tutorial/tabs/TutorialFragmentUsage.kt similarity index 84% rename from app/src/main/java/de/jrpie/android/launcher/tutorial/tabs/TutorialFragmentUsage.kt rename to app/src/main/java/de/jrpie/android/launcher/ui/tutorial/tabs/TutorialFragmentUsage.kt index 00cd9d3..90db232 100644 --- a/app/src/main/java/de/jrpie/android/launcher/tutorial/tabs/TutorialFragmentUsage.kt +++ b/app/src/main/java/de/jrpie/android/launcher/ui/tutorial/tabs/TutorialFragmentUsage.kt @@ -1,4 +1,4 @@ -package de.jrpie.android.launcher.tutorial.tabs +package de.jrpie.android.launcher.ui.tutorial.tabs import android.os.Bundle import android.view.LayoutInflater @@ -6,7 +6,7 @@ import android.view.View import android.view.ViewGroup import androidx.fragment.app.Fragment import de.jrpie.android.launcher.R -import de.jrpie.android.launcher.UIObject +import de.jrpie.android.launcher.ui.UIObject /** * The [TutorialFragmentUsage] is a used as a tab in the TutorialActivity. @@ -22,7 +22,7 @@ class TutorialFragmentUsage : Fragment(), UIObject { return inflater.inflate(R.layout.tutorial_usage, container, false) } - override fun onStart(){ + override fun onStart() { super.onStart() super.onStart() } diff --git a/app/src/main/res/layout/home.xml b/app/src/main/res/layout/home.xml index d61c201..a99dcae 100644 --- a/app/src/main/res/layout/home.xml +++ b/app/src/main/res/layout/home.xml @@ -7,7 +7,7 @@ android:layout_width="match_parent" android:layout_height="match_parent" android:longClickable="false" - tools:context=".HomeActivity"> + tools:context=".ui.HomeActivity"> + tools:context=".ui.list.ListActivity"> + tools:context=".ui.settings.SettingsActivity"> + tools:context=".ui.settings.meta.SettingsFragmentMeta">