Android Q beta 4 support

This commit is contained in:
Mygod
2019-06-10 21:34:37 +08:00
parent 98246ec6d8
commit 0cb28477e4
9 changed files with 23 additions and 31 deletions

View File

@@ -12,7 +12,7 @@ buildscript {
} }
} }
dependencies { dependencies {
classpath 'com.android.tools.build:gradle:3.5.0-beta02' classpath 'com.android.tools.build:gradle:3.5.0-beta04'
classpath 'com.github.ben-manes:gradle-versions-plugin:0.21.0' classpath 'com.github.ben-manes:gradle-versions-plugin:0.21.0'
classpath 'com.google.gms:google-services:4.2.0' classpath 'com.google.gms:google-services:4.2.0'
classpath 'io.fabric.tools:gradle:1.29.0' classpath 'io.fabric.tools:gradle:1.29.0'

View File

@@ -9,7 +9,7 @@ if (!getGradle().getStartParameter().getTaskRequests().toString().contains("Fdro
} }
android { android {
compileSdkVersion 'android-Q' compileSdkVersion 29
compileOptions { compileOptions {
sourceCompatibility 1.8 sourceCompatibility 1.8
targetCompatibility 1.8 targetCompatibility 1.8
@@ -17,7 +17,7 @@ android {
defaultConfig { defaultConfig {
applicationId "be.mygod.vpnhotspot" applicationId "be.mygod.vpnhotspot"
minSdkVersion 21 minSdkVersion 21
targetSdkVersion 28 targetSdkVersion 29
resConfigs "ru", "zh-rCN" resConfigs "ru", "zh-rCN"
versionCode 204 versionCode 204
versionName '2.4.4' versionName '2.4.4'
@@ -73,15 +73,15 @@ dependencies {
kapt "androidx.room:room-compiler:$roomVersion" kapt "androidx.room:room-compiler:$roomVersion"
implementation fileTree(dir: 'libs', include: ['*.jar']) implementation fileTree(dir: 'libs', include: ['*.jar'])
implementation 'androidx.browser:browser:1.0.0' implementation 'androidx.browser:browser:1.0.0'
implementation 'androidx.core:core-ktx:1.1.0-beta01' implementation 'androidx.core:core-ktx:1.1.0-rc01'
implementation 'androidx.emoji:emoji:1.0.0' implementation 'androidx.emoji:emoji:1.0.0'
implementation "androidx.lifecycle:lifecycle-common-java8:$lifecycleVersion" implementation "androidx.lifecycle:lifecycle-common-java8:$lifecycleVersion"
implementation "androidx.lifecycle:lifecycle-extensions:$lifecycleVersion" implementation "androidx.lifecycle:lifecycle-extensions:$lifecycleVersion"
implementation "androidx.lifecycle:lifecycle-livedata-ktx:$lifecycleVersion" implementation "androidx.lifecycle:lifecycle-livedata-ktx:$lifecycleVersion"
implementation "androidx.lifecycle:lifecycle-viewmodel-ktx:$lifecycleVersion" implementation "androidx.lifecycle:lifecycle-viewmodel-ktx:$lifecycleVersion"
implementation 'androidx.preference:preference:1.1.0-alpha05' implementation 'androidx.preference:preference:1.1.0-beta01'
implementation "androidx.room:room-ktx:$roomVersion" implementation "androidx.room:room-ktx:$roomVersion"
implementation 'com.android.billingclient:billing:2.0.0' implementation 'com.android.billingclient:billing:2.0.1'
implementation 'com.github.topjohnwu.libsu:core:2.5.0' implementation 'com.github.topjohnwu.libsu:core:2.5.0'
implementation 'com.google.android.material:material:1.1.0-alpha07' implementation 'com.google.android.material:material:1.1.0-alpha07'
implementation 'com.jakewharton.timber:timber:4.7.1' implementation 'com.jakewharton.timber:timber:4.7.1'

View File

@@ -13,7 +13,6 @@ import android.os.Looper
import androidx.annotation.StringRes import androidx.annotation.StringRes
import androidx.core.content.edit import androidx.core.content.edit
import androidx.core.content.getSystemService import androidx.core.content.getSystemService
import androidx.core.os.BuildCompat
import be.mygod.vpnhotspot.App.Companion.app import be.mygod.vpnhotspot.App.Companion.app
import be.mygod.vpnhotspot.net.wifi.WifiP2pManagerHelper import be.mygod.vpnhotspot.net.wifi.WifiP2pManagerHelper
import be.mygod.vpnhotspot.net.wifi.WifiP2pManagerHelper.deletePersistentGroup import be.mygod.vpnhotspot.net.wifi.WifiP2pManagerHelper.deletePersistentGroup
@@ -161,7 +160,7 @@ class RepeaterService : Service(), WifiP2pManager.ChannelListener, SharedPrefere
override fun onCreate() { override fun onCreate() {
super.onCreate() super.onCreate()
onChannelDisconnected() onChannelDisconnected()
if (!BuildCompat.isAtLeastQ()) @Suppress("DEPRECATION") { if (Build.VERSION.SDK_INT < 29) @Suppress("DEPRECATION") {
registerReceiver(deviceListener, intentFilter(WifiP2pManager.WIFI_P2P_THIS_DEVICE_CHANGED_ACTION, registerReceiver(deviceListener, intentFilter(WifiP2pManager.WIFI_P2P_THIS_DEVICE_CHANGED_ACTION,
WifiP2pManagerHelper.WIFI_P2P_PERSISTENT_GROUPS_CHANGED_ACTION)) WifiP2pManagerHelper.WIFI_P2P_PERSISTENT_GROUPS_CHANGED_ACTION))
app.pref.registerOnSharedPreferenceChangeListener(this) app.pref.registerOnSharedPreferenceChangeListener(this)
@@ -194,7 +193,7 @@ class RepeaterService : Service(), WifiP2pManager.ChannelListener, SharedPrefere
channel = null channel = null
if (status != Status.DESTROYED) try { if (status != Status.DESTROYED) try {
channel = p2pManager.initialize(this, Looper.getMainLooper(), this) channel = p2pManager.initialize(this, Looper.getMainLooper(), this)
if (!BuildCompat.isAtLeastQ()) @Suppress("DEPRECATION") setOperatingChannel() if (Build.VERSION.SDK_INT < 29) @Suppress("DEPRECATION") setOperatingChannel()
} catch (e: RuntimeException) { } catch (e: RuntimeException) {
Timber.w(e) Timber.w(e)
handler.postDelayed(this::onChannelDisconnected, 1000) handler.postDelayed(this::onChannelDisconnected, 1000)
@@ -282,7 +281,7 @@ class RepeaterService : Service(), WifiP2pManager.ChannelListener, SharedPrefere
val networkName = networkName val networkName = networkName
val passphrase = passphrase val passphrase = passphrase
try { try {
if (!BuildCompat.isAtLeastQ() || networkName == null || passphrase == null) { if (Build.VERSION.SDK_INT < 29 || networkName == null || passphrase == null) {
persistNextGroup = true persistNextGroup = true
p2pManager.createGroup(channel, listener) p2pManager.createGroup(channel, listener)
} else p2pManager.createGroup(channel, WifiP2pConfig.Builder().apply { } else p2pManager.createGroup(channel, WifiP2pConfig.Builder().apply {
@@ -392,7 +391,7 @@ class RepeaterService : Service(), WifiP2pManager.ChannelListener, SharedPrefere
handler.removeCallbacksAndMessages(null) handler.removeCallbacksAndMessages(null)
if (status != Status.IDLE) binder.shutdown() if (status != Status.IDLE) binder.shutdown()
clean() // force clean to prevent leakage clean() // force clean to prevent leakage
if (!BuildCompat.isAtLeastQ()) @Suppress("DEPRECATION") { if (Build.VERSION.SDK_INT < 29) @Suppress("DEPRECATION") {
app.pref.unregisterOnSharedPreferenceChangeListener(this) app.pref.unregisterOnSharedPreferenceChangeListener(this)
unregisterReceiver(deviceListener) unregisterReceiver(deviceListener)
} }

View File

@@ -14,7 +14,6 @@ import android.provider.Settings
import android.view.View import android.view.View
import android.widget.Toast import android.widget.Toast
import androidx.core.content.getSystemService import androidx.core.content.getSystemService
import androidx.core.os.BuildCompat
import androidx.core.os.bundleOf import androidx.core.os.bundleOf
import androidx.recyclerview.widget.RecyclerView import androidx.recyclerview.widget.RecyclerView
import be.mygod.vpnhotspot.DebugHelper import be.mygod.vpnhotspot.DebugHelper
@@ -29,7 +28,7 @@ import java.net.NetworkInterface
@TargetApi(26) @TargetApi(26)
class LocalOnlyHotspotManager(private val parent: TetheringFragment) : Manager(), ServiceConnection { class LocalOnlyHotspotManager(private val parent: TetheringFragment) : Manager(), ServiceConnection {
companion object { companion object {
val permission = if (BuildCompat.isAtLeastQ()) val permission = if (Build.VERSION.SDK_INT >= 29)
Manifest.permission.ACCESS_FINE_LOCATION else Manifest.permission.ACCESS_COARSE_LOCATION Manifest.permission.ACCESS_FINE_LOCATION else Manifest.permission.ACCESS_COARSE_LOCATION
} }

View File

@@ -18,7 +18,6 @@ import android.view.WindowManager
import android.widget.EditText import android.widget.EditText
import androidx.appcompat.app.AlertDialog import androidx.appcompat.app.AlertDialog
import androidx.core.content.ContextCompat import androidx.core.content.ContextCompat
import androidx.core.os.BuildCompat
import androidx.databinding.BaseObservable import androidx.databinding.BaseObservable
import androidx.databinding.Bindable import androidx.databinding.Bindable
import androidx.lifecycle.ViewModel import androidx.lifecycle.ViewModel
@@ -33,7 +32,6 @@ import be.mygod.vpnhotspot.util.formatAddresses
import be.mygod.vpnhotspot.widget.SmartSnackbar import be.mygod.vpnhotspot.widget.SmartSnackbar
import kotlinx.android.parcel.Parcelize import kotlinx.android.parcel.Parcelize
import timber.log.Timber import timber.log.Timber
import java.lang.IllegalArgumentException
import java.net.NetworkInterface import java.net.NetworkInterface
import java.net.SocketException import java.net.SocketException
@@ -56,7 +54,7 @@ class RepeaterManager(private val parent: TetheringFragment) : Manager(), Servic
} }
val title: CharSequence @Bindable get() { val title: CharSequence @Bindable get() {
if (BuildCompat.isAtLeastQ()) binder?.group?.frequency?.let { if (Build.VERSION.SDK_INT >= 29) binder?.group?.frequency?.let {
return parent.getString(R.string.repeater_channel, it, frequencyToChannel(it)) return parent.getString(R.string.repeater_channel, it, frequencyToChannel(it))
} }
return parent.getString(R.string.title_repeater) return parent.getString(R.string.title_repeater)
@@ -76,7 +74,7 @@ class RepeaterManager(private val parent: TetheringFragment) : Manager(), Servic
} }
fun onGroupChanged(group: WifiP2pGroup? = null) { fun onGroupChanged(group: WifiP2pGroup? = null) {
p2pInterface = group?.`interface` p2pInterface = group?.`interface`
if (BuildCompat.isAtLeastQ()) notifyPropertyChanged(BR.title) if (Build.VERSION.SDK_INT >= 29) notifyPropertyChanged(BR.title)
notifyPropertyChanged(BR.addresses) notifyPropertyChanged(BR.addresses)
} }
@@ -85,7 +83,7 @@ class RepeaterManager(private val parent: TetheringFragment) : Manager(), Servic
when (binder?.service?.status) { when (binder?.service?.status) {
RepeaterService.Status.IDLE -> { RepeaterService.Status.IDLE -> {
val context = parent.requireContext() val context = parent.requireContext()
if (BuildCompat.isAtLeastQ() && context.checkSelfPermission( if (Build.VERSION.SDK_INT >= 29 && context.checkSelfPermission(
Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED) { Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
parent.requestPermissions(arrayOf(Manifest.permission.ACCESS_FINE_LOCATION), parent.requestPermissions(arrayOf(Manifest.permission.ACCESS_FINE_LOCATION),
TetheringFragment.START_REPEATER) TetheringFragment.START_REPEATER)
@@ -165,7 +163,7 @@ class RepeaterManager(private val parent: TetheringFragment) : Manager(), Servic
} }
val configuration: WifiConfiguration? get() { val configuration: WifiConfiguration? get() {
if (BuildCompat.isAtLeastQ()) { if (Build.VERSION.SDK_INT >= 29) {
val networkName = RepeaterService.networkName val networkName = RepeaterService.networkName
val passphrase = RepeaterService.passphrase val passphrase = RepeaterService.passphrase
if (networkName != null && passphrase != null) { if (networkName != null && passphrase != null) {
@@ -200,7 +198,7 @@ class RepeaterManager(private val parent: TetheringFragment) : Manager(), Servic
return null return null
} }
fun updateConfiguration(config: WifiConfiguration) { fun updateConfiguration(config: WifiConfiguration) {
if (BuildCompat.isAtLeastQ()) { if (Build.VERSION.SDK_INT >= 29) {
RepeaterService.networkName = config.SSID RepeaterService.networkName = config.SSID
RepeaterService.passphrase = config.preSharedKey RepeaterService.passphrase = config.preSharedKey
RepeaterService.operatingBand = when (config.apBand) { RepeaterService.operatingBand = when (config.apBand) {

View File

@@ -1,15 +1,14 @@
package be.mygod.vpnhotspot.net package be.mygod.vpnhotspot.net
import android.os.Build
import android.system.ErrnoException import android.system.ErrnoException
import android.system.OsConstants import android.system.OsConstants
import androidx.core.os.BuildCompat
import be.mygod.vpnhotspot.room.macToLong import be.mygod.vpnhotspot.room.macToLong
import be.mygod.vpnhotspot.util.parseNumericAddress import be.mygod.vpnhotspot.util.parseNumericAddress
import timber.log.Timber import timber.log.Timber
import java.io.File import java.io.File
import java.io.FileNotFoundException import java.io.FileNotFoundException
import java.io.IOException import java.io.IOException
import java.lang.NumberFormatException
import java.net.InetAddress import java.net.InetAddress
import java.net.NetworkInterface import java.net.NetworkInterface
import java.net.SocketException import java.net.SocketException
@@ -98,7 +97,7 @@ data class IpNeighbour(val ip: InetAddress, val dev: String, val lladdr: Long, v
.filter { it.size >= 6 && mac.matcher(it[ARP_HW_ADDRESS]).matches() } .filter { it.size >= 6 && mac.matcher(it[ARP_HW_ADDRESS]).matches() }
.toList() .toList()
} catch (e: IOException) { } catch (e: IOException) {
if (e !is FileNotFoundException || !BuildCompat.isAtLeastQ() || if (e !is FileNotFoundException || Build.VERSION.SDK_INT < 29 ||
(e.cause as? ErrnoException)?.errno != OsConstants.EACCES) Timber.w(e) (e.cause as? ErrnoException)?.errno != OsConstants.EACCES) Timber.w(e)
} }
return arpCache return arpCache

View File

@@ -3,13 +3,13 @@ package be.mygod.vpnhotspot.net.wifi
import android.annotation.SuppressLint import android.annotation.SuppressLint
import android.content.SharedPreferences import android.content.SharedPreferences
import android.net.wifi.WifiManager import android.net.wifi.WifiManager
import android.os.Build
import android.os.PowerManager import android.os.PowerManager
import android.view.WindowManager import android.view.WindowManager
import androidx.activity.ComponentActivity import androidx.activity.ComponentActivity
import androidx.annotation.RequiresApi import androidx.annotation.RequiresApi
import androidx.core.content.edit import androidx.core.content.edit
import androidx.core.content.getSystemService import androidx.core.content.getSystemService
import androidx.core.os.BuildCompat
import androidx.lifecycle.DefaultLifecycleObserver import androidx.lifecycle.DefaultLifecycleObserver
import androidx.lifecycle.LifecycleOwner import androidx.lifecycle.LifecycleOwner
import be.mygod.vpnhotspot.App.Companion.app import be.mygod.vpnhotspot.App.Companion.app
@@ -23,7 +23,7 @@ class WifiDoubleLock(lockType: Int) : AutoCloseable {
var mode: Mode var mode: Mode
@Suppress("DEPRECATION") @Suppress("DEPRECATION")
get() = Mode.valueOf(app.pref.getString(KEY, Mode.Full.toString()) ?: "").let { get() = Mode.valueOf(app.pref.getString(KEY, Mode.Full.toString()) ?: "").let {
if (it == Mode.Full && BuildCompat.isAtLeastQ()) Mode.None else it if (it == Mode.Full && Build.VERSION.SDK_INT >= 29) Mode.None else it
} }
set(value) = app.pref.edit { putString(KEY, value.toString()) } set(value) = app.pref.edit { putString(KEY, value.toString()) }
private val service by lazy { app.getSystemService<PowerManager>()!! } private val service by lazy { app.getSystemService<PowerManager>()!! }

View File

@@ -15,7 +15,6 @@ import android.widget.AdapterView
import android.widget.ArrayAdapter import android.widget.ArrayAdapter
import androidx.appcompat.app.AlertDialog import androidx.appcompat.app.AlertDialog
import androidx.appcompat.widget.Toolbar import androidx.appcompat.widget.Toolbar
import androidx.core.os.BuildCompat
import androidx.core.view.isGone import androidx.core.view.isGone
import be.mygod.vpnhotspot.AlertDialogFragment import be.mygod.vpnhotspot.AlertDialogFragment
import be.mygod.vpnhotspot.App.Companion.app import be.mygod.vpnhotspot.App.Companion.app
@@ -27,7 +26,6 @@ import be.mygod.vpnhotspot.util.toParcelable
import be.mygod.vpnhotspot.widget.SmartSnackbar import be.mygod.vpnhotspot.widget.SmartSnackbar
import kotlinx.android.parcel.Parcelize import kotlinx.android.parcel.Parcelize
import kotlinx.android.synthetic.main.dialog_wifi_ap.view.* import kotlinx.android.synthetic.main.dialog_wifi_ap.view.*
import java.lang.IllegalStateException
import java.nio.charset.Charset import java.nio.charset.Charset
/** /**
@@ -117,7 +115,7 @@ class WifiApDialogFragment : AlertDialogFragment<WifiApDialogFragment.Arg, WifiA
bandOptions = mutableListOf<BandOption>().apply { bandOptions = mutableListOf<BandOption>().apply {
if (arg.p2pMode) { if (arg.p2pMode) {
add(BandOption.BandAny) add(BandOption.BandAny)
if (BuildCompat.isAtLeastQ()) { if (Build.VERSION.SDK_INT >= 29) {
add(BandOption.Band2GHz) add(BandOption.Band2GHz)
add(BandOption.Band5GHz) add(BandOption.Band5GHz)
} }

View File

@@ -14,7 +14,6 @@ import android.view.View
import android.widget.ImageView import android.widget.ImageView
import androidx.annotation.DrawableRes import androidx.annotation.DrawableRes
import androidx.core.net.toUri import androidx.core.net.toUri
import androidx.core.os.BuildCompat
import androidx.core.view.isVisible import androidx.core.view.isVisible
import androidx.databinding.BindingAdapter import androidx.databinding.BindingAdapter
import be.mygod.vpnhotspot.App.Companion.app import be.mygod.vpnhotspot.App.Companion.app
@@ -95,12 +94,12 @@ fun NetworkInterface.formatAddresses(macOnly: Boolean = false) = SpannableString
} }
}.trimEnd() }.trimEnd()
private val parseNumericAddress by lazy { private val parseNumericAddress by lazy @SuppressLint("SoonBlockedPrivateApi") {
InetAddress::class.java.getDeclaredMethod("parseNumericAddress", String::class.java).apply { InetAddress::class.java.getDeclaredMethod("parseNumericAddress", String::class.java).apply {
isAccessible = true isAccessible = true
} }
} }
fun parseNumericAddress(address: String) = if (BuildCompat.isAtLeastQ()) fun parseNumericAddress(address: String) = if (Build.VERSION.SDK_INT >= 29)
InetAddresses.parseNumericAddress(address) else parseNumericAddress.invoke(null, address) as InetAddress InetAddresses.parseNumericAddress(address) else parseNumericAddress.invoke(null, address) as InetAddress
fun Context.launchUrl(url: String) { fun Context.launchUrl(url: String) {