From b436f75f17beb668e4fdc7fed756641210555c14 Mon Sep 17 00:00:00 2001 From: MM20 <15646950+MM2-0@users.noreply.github.com> Date: Sun, 12 Jun 2022 15:48:43 +0200 Subject: [PATCH] Sort chinese apps by their pinyin transliteration Close #61 --- applications/build.gradle.kts | 2 -- .../launcher2/applications/AppRepository.kt | 12 +++--------- appshortcuts/build.gradle.kts | 1 - .../appshortcuts/AppShortcutRepository.kt | 11 ++++------- ktx/build.gradle.kts | 1 + .../main/java/de/mm20/launcher2/ktx/String.kt | 18 ++++++++++++++++++ .../mm20/launcher2/search/data/Searchable.kt | 19 ++++++++++++++----- 7 files changed, 40 insertions(+), 24 deletions(-) diff --git a/applications/build.gradle.kts b/applications/build.gradle.kts index 1450c223..6d5c5b13 100644 --- a/applications/build.gradle.kts +++ b/applications/build.gradle.kts @@ -45,8 +45,6 @@ dependencies { implementation(libs.commons.text) - implementation(libs.tinypinyin) - implementation(project(":search")) implementation(project(":base")) implementation(project(":preferences")) diff --git a/applications/src/main/java/de/mm20/launcher2/applications/AppRepository.kt b/applications/src/main/java/de/mm20/launcher2/applications/AppRepository.kt index 9253995a..ba266cd0 100644 --- a/applications/src/main/java/de/mm20/launcher2/applications/AppRepository.kt +++ b/applications/src/main/java/de/mm20/launcher2/applications/AppRepository.kt @@ -5,15 +5,13 @@ import android.content.Context import android.content.Intent import android.content.pm.LauncherActivityInfo import android.content.pm.LauncherApps -import android.content.pm.PackageInstaller import android.content.pm.ShortcutInfo import android.os.Handler import android.os.Looper import android.os.Process import android.os.UserHandle import android.util.Log -import com.github.promeg.pinyinhelper.Pinyin -import de.mm20.launcher2.search.data.AppInstallation +import de.mm20.launcher2.ktx.normalize import de.mm20.launcher2.search.data.Application import de.mm20.launcher2.search.data.LauncherApp import kotlinx.coroutines.Dispatchers @@ -170,14 +168,10 @@ internal class AppRepositoryImpl( } private fun matches(label: String, query: String): Boolean { - val labelLatin = romanize(label) + val normalizedLabel = label.normalize() val fuzzyScore = FuzzyScore(Locale.getDefault()) return fuzzyScore.fuzzyScore(label, query) >= query.length * 1.5 || - fuzzyScore.fuzzyScore(labelLatin, query) >= query.length * 1.5 - } - - private fun romanize(label: String): String { - return Pinyin.toPinyin(label, "").lowercase(Locale.getDefault()) + fuzzyScore.fuzzyScore(normalizedLabel, query.normalize()) >= query.length * 1.5 } private fun getActivityByComponentName(componentName: ComponentName?): Application? { diff --git a/appshortcuts/build.gradle.kts b/appshortcuts/build.gradle.kts index 274b44dd..4fd77504 100644 --- a/appshortcuts/build.gradle.kts +++ b/appshortcuts/build.gradle.kts @@ -42,7 +42,6 @@ dependencies { implementation(libs.koin.android) implementation(libs.commons.text) - implementation(libs.tinypinyin) implementation(project(":search")) implementation(project(":permissions")) diff --git a/appshortcuts/src/main/java/de/mm20/launcher2/appshortcuts/AppShortcutRepository.kt b/appshortcuts/src/main/java/de/mm20/launcher2/appshortcuts/AppShortcutRepository.kt index f704c8ec..7f61be3e 100644 --- a/appshortcuts/src/main/java/de/mm20/launcher2/appshortcuts/AppShortcutRepository.kt +++ b/appshortcuts/src/main/java/de/mm20/launcher2/appshortcuts/AppShortcutRepository.kt @@ -6,7 +6,8 @@ import android.content.pm.LauncherApps import android.content.pm.PackageManager import android.os.Process import androidx.core.content.getSystemService -import com.github.promeg.pinyinhelper.Pinyin +import de.mm20.launcher2.ktx.normalize +import de.mm20.launcher2.ktx.romanize import de.mm20.launcher2.permissions.PermissionGroup import de.mm20.launcher2.permissions.PermissionsManager import de.mm20.launcher2.preferences.LauncherDataStore @@ -128,13 +129,9 @@ internal class AppShortcutRepositoryImpl( private fun matches(label: String, query: String): Boolean { - val labelLatin = romanize(label) + val labelLatin = label.normalize() val fuzzyScore = FuzzyScore(Locale.getDefault()) return fuzzyScore.fuzzyScore(label, query) >= query.length * 1.5 || - fuzzyScore.fuzzyScore(labelLatin, query) >= query.length * 1.5 - } - - private fun romanize(label: String): String { - return Pinyin.toPinyin(label, "").lowercase(Locale.getDefault()) + fuzzyScore.fuzzyScore(labelLatin, query.normalize()) >= query.length * 1.5 } } \ No newline at end of file diff --git a/ktx/build.gradle.kts b/ktx/build.gradle.kts index 3ae57c9b..ca8c35f4 100644 --- a/ktx/build.gradle.kts +++ b/ktx/build.gradle.kts @@ -38,6 +38,7 @@ dependencies { implementation(libs.bundles.kotlin) implementation(libs.androidx.core) + implementation(libs.tinypinyin) implementation(libs.androidx.appcompat) implementation(libs.bundles.androidx.lifecycle) diff --git a/ktx/src/main/java/de/mm20/launcher2/ktx/String.kt b/ktx/src/main/java/de/mm20/launcher2/ktx/String.kt index d1fd1d1f..a6653847 100644 --- a/ktx/src/main/java/de/mm20/launcher2/ktx/String.kt +++ b/ktx/src/main/java/de/mm20/launcher2/ktx/String.kt @@ -1,7 +1,25 @@ package de.mm20.launcher2.ktx +import com.github.promeg.pinyinhelper.Pinyin import java.net.URLDecoder +import java.util.* fun String.decodeUrl(charset: String): String? { return URLDecoder.decode(this, charset) +} + +/** + * Normalize a string to lowercase ASCII + * TODO: Only supports Chinese/Pinyin at the moment + */ +fun String.normalize(): String { + return this.romanize().lowercase(Locale.getDefault()) +} + +/** + * Romanize a string, transliterate non-latin characters into latin + * TODO: Only supports Chinese/Pinyin at the moment + */ +fun String.romanize(): String { + return Pinyin.toPinyin(this, "") } \ No newline at end of file diff --git a/search/src/main/java/de/mm20/launcher2/search/data/Searchable.kt b/search/src/main/java/de/mm20/launcher2/search/data/Searchable.kt index 2dabef8f..1d1a40d3 100644 --- a/search/src/main/java/de/mm20/launcher2/search/data/Searchable.kt +++ b/search/src/main/java/de/mm20/launcher2/search/data/Searchable.kt @@ -1,13 +1,12 @@ package de.mm20.launcher2.search.data -import android.content.ActivityNotFoundException import android.content.Context import android.content.Intent import android.os.Bundle import android.widget.Toast import de.mm20.launcher2.icons.LauncherIcon +import de.mm20.launcher2.ktx.romanize import de.mm20.launcher2.ktx.tryStartActivity -import de.mm20.launcher2.preferences.Settings import de.mm20.launcher2.preferences.Settings.IconSettings.LegacyIconBackground import de.mm20.launcher2.search.R import java.text.Collator @@ -26,16 +25,26 @@ abstract class Searchable : Comparable { return if (context.tryStartActivity(intent, options)) { true } else { - Toast.makeText(context, context.getString(R.string.error_activity_not_found, label), Toast.LENGTH_SHORT).show() + Toast.makeText( + context, + context.getString(R.string.error_activity_not_found, label), + Toast.LENGTH_SHORT + ).show() false } } - open suspend fun loadIcon(context: Context, size: Int, legacyIconBackground: LegacyIconBackground): LauncherIcon? = null + open suspend fun loadIcon( + context: Context, + size: Int, + legacyIconBackground: LegacyIconBackground + ): LauncherIcon? = null + abstract fun getPlaceholderIcon(context: Context): LauncherIcon override fun compareTo(other: Searchable): Int { - return Collator.getInstance().apply { strength = Collator.SECONDARY }.compare(label, other.label) + return Collator.getInstance().apply { strength = Collator.SECONDARY } + .compare(label.romanize(), other.label.romanize()) } override fun equals(other: Any?): Boolean {