Merge pull request #25 from Iamlooker/root-installation

Root installation
This commit is contained in:
LooKeR 2021-10-13 00:35:41 +05:30 committed by GitHub
commit a2bb4632fb
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
59 changed files with 923 additions and 1198 deletions

View File

@ -1,7 +1,5 @@
--- ---
name: Bug report name: Bug report about: Create a report to help us improve title: ''
about: Create a report to help us improve
title: ''
labels: '' labels: ''
assignees: '' assignees: ''
@ -12,6 +10,7 @@ A clear and concise description of what the bug is.
**To Reproduce** **To Reproduce**
Steps to reproduce the behavior: Steps to reproduce the behavior:
1. Go to '...' 1. Go to '...'
2. Click on '....' 2. Click on '....'
3. Scroll down to '....' 3. Scroll down to '....'
@ -24,15 +23,17 @@ A clear and concise description of what you expected to happen.
If applicable, add screenshots to help explain your problem. If applicable, add screenshots to help explain your problem.
**Desktop (please complete the following information):** **Desktop (please complete the following information):**
- OS: [e.g. iOS]
- Browser [e.g. chrome, safari] - OS: [e.g. iOS]
- Version [e.g. 22] - Browser [e.g. chrome, safari]
- Version [e.g. 22]
**Smartphone (please complete the following information):** **Smartphone (please complete the following information):**
- Device: [e.g. iPhone6]
- OS: [e.g. iOS8.1] - Device: [e.g. iPhone6]
- Browser [e.g. stock browser, safari] - OS: [e.g. iOS8.1]
- Version [e.g. 22] - Browser [e.g. stock browser, safari]
- Version [e.g. 22]
**Additional context** **Additional context**
Add any other context about the problem here. Add any other context about the problem here.

View File

@ -1,7 +1,5 @@
--- ---
name: Custom issue template name: Custom issue template about: Describe this issue template's purpose here. title: ''
about: Describe this issue template's purpose here.
title: ''
labels: '' labels: ''
assignees: '' assignees: ''

View File

@ -1,7 +1,5 @@
--- ---
name: Feature request name: Feature request about: Suggest an idea for this project title: ''
about: Suggest an idea for this project
title: ''
labels: '' labels: ''
assignees: '' assignees: ''

View File

@ -6,7 +6,8 @@ Material-ify with Droid-ify.
Unofficial F-Droid client with Material UI. Unofficial F-Droid client with Material UI.
This app is an Direct Adaptation/Modification of [Foxy-Droid](https://github.com/kitsunyan/foxy-droid/) This app is an Direct Adaptation/Modification
of [Foxy-Droid](https://github.com/kitsunyan/foxy-droid/)
### Features ### Features
@ -21,7 +22,8 @@ This app is an Direct Adaptation/Modification of [Foxy-Droid](https://github.com
## Building and Installing ## Building and Installing
Specify your Android SDK path either using the `ANDROID_HOME` environment variable, or by filling out the `sdk.dir` Specify your Android SDK path either using the `ANDROID_HOME` environment variable, or by filling
out the `sdk.dir`
property in `local.properties`. property in `local.properties`.
Signing can be done automatically using `keystore.properties` as follows: Signing can be done automatically using `keystore.properties` as follows:
@ -33,8 +35,10 @@ key.alias=key-alias
key.password=key-password key.password=key-password
``` ```
Run `./gradlew assembleRelease` to build the package, which can be installed using the Android package manager. Run `./gradlew assembleRelease` to build the package, which can be installed using the Android
package manager.
## License ## License
Droid-ify is available under the terms of the GNU General Public License v3 or later. Copyright © 2020 Iamlooker. Droid-ify is available under the terms of the GNU General Public License v3 or later. Copyright ©
2020 Iamlooker.

View File

@ -1,27 +0,0 @@
#!/bin/bash
set -e
cd "`dirname "$0"`"
dimensions=(mdpi:1 hdpi:1.5 xhdpi:2 xxhdpi:3 xxxhdpi:4)
res='../src/main/res'
cp 'launcher.svg' 'launcher-foreground.svg'
inkscape --select circle --verb EditDelete --verb=FileSave --verb=FileQuit \
'launcher-foreground.svg'
for dimension in ${dimensions[@]}; do
resource="${dimension%:*}"
scale="${dimension#*:}"
mkdir -p "$res/mipmap-$resource" "$res/drawable-$resource"
size="`bc <<< "48 * $scale"`"
inkscape 'launcher.svg' -a 15:15:93:93 -w "$size" -h "$size" \
-e "$res/mipmap-$resource/ic_launcher.png"
optipng "$res/mipmap-$resource/ic_launcher.png"
size="`bc <<< "108 * $scale"`"
inkscape 'launcher-foreground.svg' -w "$size" -h "$size" \
-e "$res/drawable-$resource/ic_launcher_foreground.png"
optipng "$res/drawable-$resource/ic_launcher_foreground.png"
done
rm 'launcher-foreground.svg'

View File

@ -1,273 +0,0 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
style="enable-background:new"
id="svg3"
version="1.1"
viewBox="0 0 108 108"
height="108"
width="108">
<metadata
id="metadata55">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<defs
id="defs17">
<clipPath
id="paper-clip"
clipPathUnits="userSpaceOnUse">
<path
id="paper-clip-path"
d="m 67.759585,28.469613 -18.355472,18.146485 -21.453125,-4.732422 9.087891,24.064453 25.894536,12.974609 12.37695,-23.86914 -1.93359,-0.66211 z" />
</clipPath>
<filter
id="paper-inner-shadow">
<feFlood
id="feFlood6"
result="flood"
flood-color="rgb(0,0,0)"
flood-opacity="0.2" />
<feComposite
id="feComposite8"
result="composite1"
operator="in"
in2="SourceGraphic"
in="flood" />
<feGaussianBlur
id="feGaussianBlur10"
result="blur"
stdDeviation="2"
in="composite1" />
<feOffset
id="feOffset12"
result="offset"
dy="0"
dx="0" />
<feComposite
id="feComposite14"
result="composite2"
operator="over"
in2="offset"
in="SourceGraphic" />
</filter>
<filter
id="paper-edge-1"
style="color-interpolation-filters:sRGB">
<feFlood
id="feFlood958"
result="flood"
flood-color="rgb(0,0,0)"
flood-opacity="0.2" />
<feComposite
id="feComposite960"
result="composite1"
operator="out"
in2="SourceGraphic"
in="flood" />
<feGaussianBlur
id="feGaussianBlur962"
result="blur"
stdDeviation="0"
in="composite1" />
<feOffset
id="feOffset964"
result="offset"
dy="0.2"
dx="0.2" />
<feComposite
id="feComposite966"
result="composite2"
operator="atop"
in2="SourceGraphic"
in="offset" />
</filter>
<filter
id="paper-edge-2"
style="color-interpolation-filters:sRGB">
<feFlood
id="feFlood1388"
result="flood"
flood-color="rgb(255,255,255)"
flood-opacity="0.2" />
<feComposite
id="feComposite1390"
result="composite1"
operator="out"
in2="SourceGraphic"
in="flood" />
<feGaussianBlur
id="feGaussianBlur1392"
result="blur"
stdDeviation="0"
in="composite1" />
<feOffset
id="feOffset1394"
result="offset"
dy="-0.1"
dx="0.3" />
<feComposite
id="feComposite1396"
result="composite2"
operator="atop"
in2="SourceGraphic"
in="offset" />
</filter>
<filter
id="paper-shadow"
style="color-interpolation-filters:sRGB">
<feFlood
id="feFlood1506"
result="flood"
flood-color="rgb(0,0,0)"
flood-opacity="0.4" />
<feComposite
id="feComposite1508"
result="composite1"
operator="in"
in2="SourceGraphic"
in="flood" />
<feGaussianBlur
id="feGaussianBlur1510"
result="blur"
stdDeviation="2"
in="composite1" />
<feOffset
id="feOffset1512"
result="offset"
dy="0"
dx="0" />
<feComposite
id="feComposite1514"
result="composite2"
operator="over"
in2="offset"
in="SourceGraphic" />
</filter>
<filter
id="circle-shadow"
style="color-interpolation-filters:sRGB">
<feFlood
id="feFlood1626"
result="flood"
flood-color="rgb(255,255,255)"
flood-opacity="0.2" />
<feComposite
id="feComposite1628"
result="composite1"
operator="out"
in2="SourceGraphic"
in="flood" />
<feGaussianBlur
id="feGaussianBlur1630"
result="blur"
stdDeviation="0"
in="composite1" />
<feOffset
id="feOffset1632"
result="offset"
dy="0.5"
dx="0" />
<feComposite
id="feComposite1634"
result="fbSourceGraphic"
operator="atop"
in2="SourceGraphic"
in="offset" />
<feFlood
in="fbSourceGraphic"
result="flood"
flood-color="rgb(0,0,0)"
flood-opacity="0.2"
id="feFlood1640" />
<feComposite
result="composite1"
operator="out"
in="flood"
id="feComposite1642"
in2="fbSourceGraphic" />
<feGaussianBlur
result="blur"
stdDeviation="0"
in="composite1"
id="feGaussianBlur1644" />
<feOffset
result="offset"
dy="-0.5"
dx="0"
id="feOffset1646" />
<feComposite
result="fbSourceGraphic"
operator="atop"
in="offset"
id="feComposite1648"
in2="fbSourceGraphic" />
<feFlood
in="fbSourceGraphic"
result="flood"
flood-color="rgb(0,0,0)"
flood-opacity="0.2"
id="feFlood1664" />
<feComposite
result="composite1"
operator="in"
in="flood"
id="feComposite1666"
in2="fbSourceGraphic" />
<feGaussianBlur
result="blur"
stdDeviation="1"
in="composite1"
id="feGaussianBlur1668" />
<feOffset
result="offset"
dy="1"
dx="0"
id="feOffset1670" />
<feComposite
result="composite2"
operator="over"
in="fbSourceGraphic"
id="feComposite1672"
in2="offset" />
</filter>
</defs>
<circle
r="36"
cy="54"
cx="54"
id="circle"
style="fill:#262c38;filter:url(#circle-shadow)" />
<g
style="filter:url(#paper-shadow)"
id="paper-group">
<path
d="m 67.75836,28.470764 -23.382292,23.115602 -0.0887,1.254642 29.189963,2.017946 z"
style="fill:#1976d2"
id="paper-4" />
<path
style="fill:#47a2fc;filter:url(#paper-inner-shadow)"
d="m 27.949219,41.884766 9.08789,24.064453 25.894532,12.974609 12.376953,-23.86914 -22.298828,-7.638672 v -0.002 z"
clip-path="url(#paper-clip)"
id="paper-3" />
<path
d="m 53.009473,47.414648 -15.970174,18.53113 25.894116,12.97696 z"
style="fill:#1976d2;filter:url(#paper-edge-1)"
id="paper-2" />
<path
style="fill:#47a2fc;filter:url(#paper-edge-2)"
d="m 53.009766,47.414016 9.923828,31.503906 12.375,-23.865234 z"
id="paper-1" />
</g>
</svg>

Before

Width:  |  Height:  |  Size: 7.1 KiB

View File

@ -5,21 +5,17 @@ import android.app.Application
import android.app.job.JobInfo import android.app.job.JobInfo
import android.app.job.JobScheduler import android.app.job.JobScheduler
import android.content.* import android.content.*
import android.content.pm.PackageInfo
import com.looker.droidify.content.Cache import com.looker.droidify.content.Cache
import com.looker.droidify.content.Preferences import com.looker.droidify.content.Preferences
import com.looker.droidify.content.ProductPreferences import com.looker.droidify.content.ProductPreferences
import com.looker.droidify.database.Database import com.looker.droidify.database.Database
import com.looker.droidify.entity.InstalledItem
import com.looker.droidify.index.RepositoryUpdater import com.looker.droidify.index.RepositoryUpdater
import com.looker.droidify.network.Downloader import com.looker.droidify.network.Downloader
import com.looker.droidify.network.PicassoDownloader import com.looker.droidify.network.PicassoDownloader
import com.looker.droidify.service.Connection import com.looker.droidify.service.Connection
import com.looker.droidify.service.SyncService import com.looker.droidify.service.SyncService
import com.looker.droidify.utility.Utils import com.looker.droidify.utility.Utils.toInstalledItem
import com.looker.droidify.utility.extension.android.Android import com.looker.droidify.utility.extension.android.Android
import com.looker.droidify.utility.extension.android.singleSignature
import com.looker.droidify.utility.extension.android.versionCodeCompat
import com.squareup.picasso.OkHttp3Downloader import com.squareup.picasso.OkHttp3Downloader
import com.squareup.picasso.Picasso import com.squareup.picasso.Picasso
import java.net.InetSocketAddress import java.net.InetSocketAddress
@ -27,10 +23,6 @@ import java.net.Proxy
@Suppress("unused") @Suppress("unused")
class MainApplication : Application() { class MainApplication : Application() {
private fun PackageInfo.toInstalledItem(): InstalledItem {
val signatureString = singleSignature?.let(Utils::calculateHash).orEmpty()
return InstalledItem(packageName, versionName.orEmpty(), versionCodeCompat, signatureString)
}
override fun onCreate() { override fun onCreate() {
super.onCreate() super.onCreate()

View File

@ -26,6 +26,8 @@ import com.looker.droidify.service.Connection
import com.looker.droidify.service.DownloadService import com.looker.droidify.service.DownloadService
import com.looker.droidify.utility.RxUtils import com.looker.droidify.utility.RxUtils
import com.looker.droidify.utility.Utils import com.looker.droidify.utility.Utils
import com.looker.droidify.utility.Utils.startPackageInstaller
import com.looker.droidify.utility.Utils.startUpdate
import com.looker.droidify.utility.extension.android.* import com.looker.droidify.utility.extension.android.*
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
import io.reactivex.rxjava3.core.Observable import io.reactivex.rxjava3.core.Observable
@ -134,7 +136,6 @@ class ProductFragment() : ScreenFragment(), ProductAdapter.Callbacks {
} }
addOnScrollListener(scrollListener) addOnScrollListener(scrollListener)
addItemDecoration(adapter.gridItemDecoration) addItemDecoration(adapter.gridItemDecoration)
// addItemDecoration(DividerItemDecoration(context, adapter::configureDivider))
savedInstanceState?.getParcelable<ProductAdapter.SavedState>(STATE_ADAPTER) savedInstanceState?.getParcelable<ProductAdapter.SavedState>(STATE_ADAPTER)
?.let(adapter::restoreState) ?.let(adapter::restoreState)
layoutManagerState = savedInstanceState?.getParcelable(STATE_LAYOUT_MANAGER) layoutManagerState = savedInstanceState?.getParcelable(STATE_LAYOUT_MANAGER)
@ -385,27 +386,7 @@ class ProductFragment() : ScreenFragment(), ProductAdapter.Callbacks {
ProductAdapter.Action.INSTALL, ProductAdapter.Action.INSTALL,
ProductAdapter.Action.UPDATE -> { ProductAdapter.Action.UPDATE -> {
val installedItem = installed?.installedItem val installedItem = installed?.installedItem
val productRepository = Product.findSuggested(products, installedItem) { it.first } startUpdate(packageName, installedItem, products, downloadConnection)
val compatibleReleases = productRepository?.first?.selectedReleases.orEmpty()
.filter { installedItem == null || installedItem.signature == it.signature }
val release = if (compatibleReleases.size >= 2) {
compatibleReleases
.filter { it.platforms.contains(Android.primaryPlatform) }
.minByOrNull { it.platforms.size }
?: compatibleReleases.minByOrNull { it.platforms.size }
?: compatibleReleases.firstOrNull()
} else {
compatibleReleases.firstOrNull()
}
val binder = downloadConnection.binder
if (productRepository != null && release != null && binder != null) {
binder.enqueue(
packageName,
productRepository.first.name,
productRepository.second,
release
)
} else Unit
} }
ProductAdapter.Action.LAUNCH -> { ProductAdapter.Action.LAUNCH -> {
val launcherActivities = installed?.launcherActivities.orEmpty() val launcherActivities = installed?.launcherActivities.orEmpty()

View File

@ -1,7 +1,6 @@
package com.looker.droidify.screen package com.looker.droidify.screen
import android.content.Intent import android.content.Intent
import android.net.Uri
import android.os.Bundle import android.os.Bundle
import android.os.Parcel import android.os.Parcel
import android.view.ViewGroup import android.view.ViewGroup
@ -11,11 +10,10 @@ import android.widget.Toolbar
import androidx.fragment.app.Fragment import androidx.fragment.app.Fragment
import androidx.fragment.app.FragmentActivity import androidx.fragment.app.FragmentActivity
import com.looker.droidify.R import com.looker.droidify.R
import com.looker.droidify.content.Cache
import com.looker.droidify.content.Preferences import com.looker.droidify.content.Preferences
import com.looker.droidify.database.CursorOwner import com.looker.droidify.database.CursorOwner
import com.looker.droidify.utility.KParcelable import com.looker.droidify.utility.KParcelable
import com.looker.droidify.utility.extension.android.Android import com.looker.droidify.utility.Utils.startPackageInstaller
import com.looker.droidify.utility.extension.resources.getDrawableFromAttr import com.looker.droidify.utility.extension.resources.getDrawableFromAttr
import com.looker.droidify.utility.extension.text.nullIfEmpty import com.looker.droidify.utility.extension.text.nullIfEmpty
@ -217,11 +215,7 @@ abstract class ScreenActivity : FragmentActivity() {
is SpecialIntent.Install -> { is SpecialIntent.Install -> {
val packageName = specialIntent.packageName val packageName = specialIntent.packageName
if (!packageName.isNullOrEmpty()) { if (!packageName.isNullOrEmpty()) {
val fragment = currentFragment specialIntent.cacheFileName?.let { startPackageInstaller(it) }
if (fragment !is ProductFragment || fragment.packageName != packageName) {
pushFragment(ProductFragment(packageName))
}
specialIntent.cacheFileName?.let(::startPackageInstaller)
} }
Unit Unit
} }
@ -242,20 +236,6 @@ abstract class ScreenActivity : FragmentActivity() {
} }
} }
internal fun startPackageInstaller(cacheFileName: String) {
val (uri, flags) = if (Android.sdk(24)) {
Pair(Cache.getReleaseUri(this, cacheFileName), Intent.FLAG_GRANT_READ_URI_PERMISSION)
} else {
Pair(Uri.fromFile(Cache.getReleaseFile(this, cacheFileName)), 0)
}
// TODO Handle deprecation
@Suppress("DEPRECATION")
startActivity(
Intent(Intent.ACTION_INSTALL_PACKAGE)
.setDataAndType(uri, "application/vnd.android.package-archive").setFlags(flags)
)
}
internal fun navigateProduct(packageName: String) = pushFragment(ProductFragment(packageName)) internal fun navigateProduct(packageName: String) = pushFragment(ProductFragment(packageName))
internal fun navigateRepositories() = pushFragment(RepositoriesFragment()) internal fun navigateRepositories() = pushFragment(RepositoriesFragment())
internal fun navigatePreferences() = pushFragment(SettingsFragment()) internal fun navigatePreferences() = pushFragment(SettingsFragment())

View File

@ -19,6 +19,7 @@ import com.looker.droidify.BuildConfig
import com.looker.droidify.R import com.looker.droidify.R
import com.looker.droidify.content.Preferences import com.looker.droidify.content.Preferences
import com.looker.droidify.utility.extension.resources.* import com.looker.droidify.utility.extension.resources.*
import com.topjohnwu.superuser.Shell
import io.reactivex.rxjava3.disposables.Disposable import io.reactivex.rxjava3.disposables.Disposable
@ -125,7 +126,7 @@ class SettingsFragment : ScreenFragment() {
} }
} }
addText( addText(
title = "Droid-ify", title = getString(R.string.application_name),
summary = "v ${BuildConfig.VERSION_NAME}" summary = "v ${BuildConfig.VERSION_NAME}"
) )
} }
@ -181,6 +182,9 @@ class SettingsFragment : ScreenFragment() {
preferences[Preferences.Key.ProxyHost]?.setEnabled(enabled) preferences[Preferences.Key.ProxyHost]?.setEnabled(enabled)
preferences[Preferences.Key.ProxyPort]?.setEnabled(enabled) preferences[Preferences.Key.ProxyPort]?.setEnabled(enabled)
} }
preferences[Preferences.Key.RootPermission]?.setEnabled(
Shell.getCachedShell()?.isRoot ?: Shell.getShell().isRoot
)
if (key == Preferences.Key.Theme) { if (key == Preferences.Key.Theme) {
requireActivity().recreate() requireActivity().recreate()
} }

View File

@ -14,6 +14,7 @@ import com.looker.droidify.Common
import com.looker.droidify.MainActivity import com.looker.droidify.MainActivity
import com.looker.droidify.R import com.looker.droidify.R
import com.looker.droidify.content.Cache import com.looker.droidify.content.Cache
import com.looker.droidify.content.Preferences
import com.looker.droidify.entity.Release import com.looker.droidify.entity.Release
import com.looker.droidify.entity.Repository import com.looker.droidify.entity.Repository
import com.looker.droidify.network.Downloader import com.looker.droidify.network.Downloader
@ -300,9 +301,17 @@ class DownloadService : ConnectionService<DownloadService.Binder>() {
stateSubject.onNext(State.Success(task.packageName, task.name, task.release) { stateSubject.onNext(State.Success(task.packageName, task.name, task.release) {
consumed = true consumed = true
}) })
if (!consumed) { if (consumed || (Preferences[Preferences.Key.RootPermission])) {
showNotificationInstall(task) PendingIntent.getBroadcast(
} this,
0,
Intent(this, Receiver::class.java)
.setAction("$ACTION_INSTALL.${task.packageName}")
.putExtra(EXTRA_CACHE_FILE_NAME, task.release.cacheFileName),
PendingIntent.FLAG_UPDATE_CURRENT
)
.send()
} else showNotificationInstall(task)
} }
private fun validatePackage(task: Task, file: File): ValidationError? { private fun validatePackage(task: Task, file: File): ValidationError? {
@ -436,7 +445,7 @@ class DownloadService : ConnectionService<DownloadService.Binder>() {
.observeOn(AndroidSchedulers.mainThread()) .observeOn(AndroidSchedulers.mainThread())
.subscribe { result, throwable -> .subscribe { result, throwable ->
currentTask = null currentTask = null
throwable?.printStackTrace() throwable.printStackTrace()
if (result == null || !result.success) { if (result == null || !result.success) {
showNotificationError( showNotificationError(
task, task,

View File

@ -1,15 +1,31 @@
package com.looker.droidify.utility package com.looker.droidify.utility
import android.animation.ValueAnimator import android.animation.ValueAnimator
import android.app.Activity
import android.content.Context import android.content.Context
import android.content.Intent
import android.content.pm.PackageInfo
import android.content.pm.Signature import android.content.pm.Signature
import android.graphics.drawable.Drawable import android.graphics.drawable.Drawable
import android.net.Uri
import android.provider.Settings import android.provider.Settings
import android.util.Log
import com.looker.droidify.R import com.looker.droidify.R
import com.looker.droidify.content.Cache
import com.looker.droidify.content.Preferences
import com.looker.droidify.entity.InstalledItem
import com.looker.droidify.entity.Product
import com.looker.droidify.entity.Repository
import com.looker.droidify.service.Connection
import com.looker.droidify.service.DownloadService
import com.looker.droidify.utility.extension.android.Android import com.looker.droidify.utility.extension.android.Android
import com.looker.droidify.utility.extension.android.singleSignature
import com.looker.droidify.utility.extension.android.versionCodeCompat
import com.looker.droidify.utility.extension.resources.getColorFromAttr import com.looker.droidify.utility.extension.resources.getColorFromAttr
import com.looker.droidify.utility.extension.resources.getDrawableCompat import com.looker.droidify.utility.extension.resources.getDrawableCompat
import com.looker.droidify.utility.extension.text.hex import com.looker.droidify.utility.extension.text.hex
import com.topjohnwu.superuser.Shell
import java.io.File
import java.security.MessageDigest import java.security.MessageDigest
import java.security.cert.Certificate import java.security.cert.Certificate
import java.security.cert.CertificateEncodingException import java.security.cert.CertificateEncodingException
@ -21,6 +37,11 @@ object Utils {
.apply { setTintList(context.getColorFromAttr(tintAttrResId)) } .apply { setTintList(context.getColorFromAttr(tintAttrResId)) }
} }
fun PackageInfo.toInstalledItem(): InstalledItem {
val signatureString = singleSignature?.let(Utils::calculateHash).orEmpty()
return InstalledItem(packageName, versionName.orEmpty(), versionCodeCompat, signatureString)
}
fun getDefaultApplicationIcons(context: Context): Pair<Drawable, Drawable> { fun getDefaultApplicationIcons(context: Context): Pair<Drawable, Drawable> {
val progressIcon: Drawable = val progressIcon: Drawable =
createDefaultApplicationIcon(context, android.R.attr.textColorSecondary) createDefaultApplicationIcon(context, android.R.attr.textColorSecondary)
@ -78,4 +99,92 @@ object Utils {
) != 0f ) != 0f
} }
} }
internal fun Activity.startPackageInstaller(cacheFileName: String) {
val file = Cache.getReleaseFile(this, cacheFileName)
if (Preferences[Preferences.Key.RootPermission]) {
val commandBuilder = StringBuilder()
val verifyState = getVerifyState()
if (verifyState == "1") commandBuilder.append("settings put global verifier_verify_adb_installs 0 ; ")
commandBuilder.append(getPackageInstallCommand(file))
commandBuilder.append(" ; settings put global verifier_verify_adb_installs $verifyState")
val result = Shell.su(commandBuilder.toString()).exec()
if (result.isSuccess) Shell.su("${getUtilBoxPath()} rm ${quote(file.absolutePath)}")
} else {
val (uri, flags) = if (Android.sdk(24)) {
Pair(
Cache.getReleaseUri(this, cacheFileName),
Intent.FLAG_GRANT_READ_URI_PERMISSION
)
} else {
Pair(Uri.fromFile(file), 0)
}
// TODO Handle deprecation
@Suppress("DEPRECATION")
startActivity(
Intent(Intent.ACTION_INSTALL_PACKAGE)
.setDataAndType(uri, "application/vnd.android.package-archive").setFlags(flags)
)
}
}
fun startUpdate(
packageName: String,
installedItem: InstalledItem?,
products: List<Pair<Product, Repository>>,
downloadConnection: Connection<DownloadService.Binder, DownloadService>
) {
val productRepository = Product.findSuggested(products, installedItem) { it.first }
val compatibleReleases = productRepository?.first?.selectedReleases.orEmpty()
.filter { installedItem == null || installedItem.signature == it.signature }
val release = if (compatibleReleases.size >= 2) {
compatibleReleases
.filter { it.platforms.contains(Android.primaryPlatform) }
.minByOrNull { it.platforms.size }
?: compatibleReleases.minByOrNull { it.platforms.size }
?: compatibleReleases.firstOrNull()
} else {
compatibleReleases.firstOrNull()
}
val binder = downloadConnection.binder
if (productRepository != null && release != null && binder != null) {
binder.enqueue(
packageName,
productRepository.first.name,
productRepository.second,
release
)
} else Unit
}
private fun getPackageInstallCommand(cacheFile: File): String =
"cat \"${cacheFile.absolutePath}\" | pm install -t -r -S ${cacheFile.length()}"
private fun getVerifyState(): String =
Shell.sh("settings get global verifier_verify_adb_installs").exec().out[0]
private fun quote(string: String) =
"\"${string.replace(Regex("""[\\$"`]""")) { c -> "\\${c.value}" }}\""
private fun getUtilBoxPath(): String {
listOf("toybox", "busybox").forEach {
var shellResult = Shell.su("which $it").exec()
if (shellResult.out.isNotEmpty()) {
val utilBoxPath = shellResult.out.joinToString("")
if (utilBoxPath.isNotEmpty()) {
val utilBoxQuoted = quote(utilBoxPath)
shellResult = Shell.su("$utilBoxQuoted --version").exec()
if (shellResult.out.isNotEmpty()) {
val utilBoxVersion = shellResult.out.joinToString("")
Log.i(
this.javaClass.canonicalName,
"Using Utilbox $it : $utilBoxQuoted $utilBoxVersion"
)
}
return utilBoxQuoted
}
}
}
return ""
}
} }

View File

@ -1,19 +1,18 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<set <set xmlns:android="http://schemas.android.com/apk/res/android">
xmlns:android="http://schemas.android.com/apk/res/android">
<objectAnimator <objectAnimator
android:duration="100"
android:interpolator="@android:interpolator/decelerate_quad"
android:propertyName="alpha" android:propertyName="alpha"
android:valueFrom="0" android:valueFrom="0"
android:valueTo="1" android:valueTo="1" />
android:duration="100"
android:interpolator="@android:interpolator/decelerate_quad" />
<objectAnimator <objectAnimator
android:duration="175"
android:interpolator="@android:interpolator/decelerate_quad"
android:propertyName="percentTranslationY" android:propertyName="percentTranslationY"
android:valueFrom="0.08" android:valueFrom="0.08"
android:valueTo="0" android:valueTo="0" />
android:duration="175"
android:interpolator="@android:interpolator/decelerate_quad" />
</set> </set>

View File

@ -1,4 +1,3 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<objectAnimator <objectAnimator xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:duration="175" /> android:duration="175" />

View File

@ -1,20 +1,19 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<set <set xmlns:android="http://schemas.android.com/apk/res/android">
xmlns:android="http://schemas.android.com/apk/res/android">
<objectAnimator <objectAnimator
android:propertyName="alpha"
android:valueFrom="1"
android:valueTo="0"
android:startOffset="50"
android:duration="75" android:duration="75"
android:interpolator="@android:interpolator/linear" /> android:interpolator="@android:interpolator/linear"
android:propertyName="alpha"
android:startOffset="50"
android:valueFrom="1"
android:valueTo="0" />
<objectAnimator <objectAnimator
android:duration="125"
android:interpolator="@android:interpolator/accelerate_quad"
android:propertyName="percentTranslationY" android:propertyName="percentTranslationY"
android:valueFrom="0" android:valueFrom="0"
android:valueTo="0.08" android:valueTo="0.08" />
android:duration="125"
android:interpolator="@android:interpolator/accelerate_quad" />
</set> </set>

View File

@ -1,13 +1,8 @@
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<selector <selector xmlns:android="http://schemas.android.com/apk/res/android">
xmlns:android="http://schemas.android.com/apk/res/android">
<item <item android:alpha="0.3" android:color="@color/accent_default_dark" android:state_enabled="false" />
android:state_enabled="false"
android:color="@color/accent_default_dark"
android:alpha="0.3" />
<item <item android:color="@color/accent_default_dark" />
android:color="@color/accent_default_dark" />
</selector> </selector>

View File

@ -1,13 +1,8 @@
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<selector <selector xmlns:android="http://schemas.android.com/apk/res/android">
xmlns:android="http://schemas.android.com/apk/res/android">
<item <item android:alpha="0.26" android:color="@color/accent_default_light" android:state_enabled="false" />
android:state_enabled="false"
android:color="@color/accent_default_light"
android:alpha="0.26" />
<item <item android:color="@color/accent_default_light" />
android:color="@color/accent_default_light" />
</selector> </selector>

View File

@ -1,13 +1,8 @@
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<selector <selector xmlns:android="http://schemas.android.com/apk/res/android">
xmlns:android="http://schemas.android.com/apk/res/android">
<item <item android:alpha="0.3" android:color="@color/error_default_dark" android:state_enabled="false" />
android:state_enabled="false"
android:color="@color/error_default_dark"
android:alpha="0.3" />
<item <item android:color="@color/error_default_dark" />
android:color="@color/error_default_dark" />
</selector> </selector>

View File

@ -1,13 +1,8 @@
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<selector <selector xmlns:android="http://schemas.android.com/apk/res/android">
xmlns:android="http://schemas.android.com/apk/res/android">
<item <item android:alpha="0.26" android:color="@color/error_default_light" android:state_enabled="false" />
android:state_enabled="false"
android:color="@color/error_default_light"
android:alpha="0.26" />
<item <item android:color="@color/error_default_light" />
android:color="@color/error_default_light" />
</selector> </selector>

View File

@ -1,5 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"> <shape xmlns:android="http://schemas.android.com/apk/res/android">
<solid android:color="?attr/colorOnBackground" /> <solid android:color="?attr/colorOnBackground" />
<corners android:radius="10dp"/> <corners android:radius="10dp" />
</shape> </shape>

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="96dp" android:width="96dp"
android:height="96dp" android:height="96dp"
android:viewportWidth="96" android:viewportWidth="96"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,6 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<vector <vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
android:width="24dp" android:width="24dp"
android:height="24dp" android:height="24dp"
android:viewportWidth="24" android:viewportWidth="24"

View File

@ -1,9 +1,9 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android" > <shape xmlns:android="http://schemas.android.com/apk/res/android">
<solid <solid
android:angle="0" android:angle="0"
android:color="@null"/> android:color="@null" />
<corners android:radius="6dp" /> <corners android:radius="6dp" />

View File

@ -31,9 +31,9 @@
android:id="@+id/fragment_content" android:id="@+id/fragment_content"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="0dp" android:layout_height="0dp"
android:paddingHorizontal="10dp"
android:paddingTop="10dp"
android:layout_weight="1" android:layout_weight="1"
android:background="?android:attr/colorBackground" /> android:background="?android:attr/colorBackground"
android:paddingHorizontal="10dp"
android:paddingTop="10dp" />
</com.looker.droidify.widget.FragmentLinearLayout> </com.looker.droidify.widget.FragmentLinearLayout>

View File

@ -1,20 +1,19 @@
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<LinearLayout <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools" xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:background="?android:attr/selectableItemBackground"
android:orientation="horizontal" android:orientation="horizontal"
android:paddingStart="16dp" android:paddingStart="16dp"
android:paddingEnd="16dp" android:paddingEnd="16dp">
android:background="?android:attr/selectableItemBackground">
<ImageView <ImageView
android:id="@+id/icon" android:id="@+id/icon"
android:layout_width="24dp" android:layout_width="24dp"
android:layout_height="24dp" android:layout_height="24dp"
android:scaleType="centerInside"
android:layout_gravity="center" android:layout_gravity="center"
android:scaleType="centerInside"
android:tint="?android:attr/textColorSecondary" android:tint="?android:attr/textColorSecondary"
android:tintMode="src_in" android:tintMode="src_in"
tools:ignore="ContentDescription" /> tools:ignore="ContentDescription" />
@ -23,8 +22,8 @@
android:id="@+id/text" android:id="@+id/text"
android:layout_width="0dp" android:layout_width="0dp"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_weight="1"
android:layout_marginStart="32dp" android:layout_marginStart="32dp"
android:layout_weight="1"
android:paddingTop="16dp" android:paddingTop="16dp"
android:paddingBottom="16dp" android:paddingBottom="16dp"
android:textColor="?android:attr/textColor" android:textColor="?android:attr/textColor"

View File

@ -3,8 +3,8 @@
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:orientation="vertical" android:orientation="vertical"
android:paddingVertical="8dp" android:paddingHorizontal="16dp"
android:paddingHorizontal="16dp"> android:paddingVertical="8dp">
<TextView <TextView
android:id="@+id/title" android:id="@+id/title"

View File

@ -1,5 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<adaptive-icon xmlns:android="http://schemas.android.com/apk/res/android"> <adaptive-icon xmlns:android="http://schemas.android.com/apk/res/android">
<background android:drawable="@color/ic_launcher_background"/> <background android:drawable="@color/ic_launcher_background" />
<foreground android:drawable="@mipmap/ic_launcher_foreground"/> <foreground android:drawable="@mipmap/ic_launcher_foreground" />
</adaptive-icon> </adaptive-icon>

View File

@ -1,5 +1,5 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<adaptive-icon xmlns:android="http://schemas.android.com/apk/res/android"> <adaptive-icon xmlns:android="http://schemas.android.com/apk/res/android">
<background android:drawable="@color/ic_launcher_background"/> <background android:drawable="@color/ic_launcher_background" />
<foreground android:drawable="@mipmap/ic_launcher_foreground"/> <foreground android:drawable="@mipmap/ic_launcher_foreground" />
</adaptive-icon> </adaptive-icon>

View File

@ -1,11 +1,11 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<resources> <resources>
<item type="id" name="sections_list" /> <item name="sections_list" type="id" />
<item type="id" name="divider_configuration" /> <item name="divider_configuration" type="id" />
<item type="id" name="fragment_pager" /> <item name="fragment_pager" type="id" />
<item type="id" name="main_content" /> <item name="main_content" type="id" />
<item type="id" name="preferences_list" /> <item name="preferences_list" type="id" />
<item type="id" name="toolbar_search" /> <item name="toolbar_search" type="id" />
</resources> </resources>