autoconnect on fly mode (does not work yet)

This commit is contained in:
Constantin Leue
2026-08-02 08:25:23 +02:00
parent 5e9ef43f2f
commit 607dbb6584
13 changed files with 430 additions and 29 deletions
@@ -6,6 +6,7 @@ import android.net.LinkProperties
import android.net.Network
import android.net.NetworkCapabilities
import android.net.NetworkRequest
import android.net.wifi.WifiInfo
import android.net.wifi.WifiManager
import android.net.wifi.WifiNetworkSpecifier
import android.os.Build
@@ -101,7 +102,8 @@ class MlrsNetworkPlugin(
result.error("invalid_argument", "ssidPrefix darf nicht leer sein", null)
return
}
requestNetwork(ssidPrefix)
val exactSsid = call.argument<String>("exactSsid")
requestNetwork(ssidPrefix, exactSsid)
result.success(null)
}
"releaseNetwork" -> {
@@ -133,14 +135,24 @@ class MlrsNetworkPlugin(
}
}
private fun requestNetwork(ssidPrefix: String) {
private fun requestNetwork(ssidPrefix: String, exactSsid: String?) {
// Vorherigen Callback zuerst abmelden - sonst haeuften sich bei
// mehrfachem Connect-Versuch mehrere registrierte Callbacks an.
releaseNetwork()
val specifier = WifiNetworkSpecifier.Builder()
.setSsidPattern(PatternMatcher(ssidPrefix, PatternMatcher.PATTERN_PREFIX))
.build()
// Ist eine zuvor erfolgreich verbundene SSID bekannt, exakt statt per
// Praefix anfragen: Android merkt sich die Nutzerzustimmung nur fuer
// exakte WifiNetworkSpecifier-Treffer und kann dann kuenftig ohne
// erneuten Systemdialog automatisch verbinden. Praefix-Anfragen
// zeigen dagegen praktisch immer den Dialog, weil die aufgeloeste
// SSID (zufaellige Endung) sich aendern koennte.
val specifierBuilder = WifiNetworkSpecifier.Builder()
if (!exactSsid.isNullOrEmpty()) {
specifierBuilder.setSsid(exactSsid)
} else {
specifierBuilder.setSsidPattern(PatternMatcher(ssidPrefix, PatternMatcher.PATTERN_PREFIX))
}
val specifier = specifierBuilder.build()
val request = NetworkRequest.Builder()
.addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
@@ -152,8 +164,9 @@ class MlrsNetworkPlugin(
override fun onAvailable(network: Network) {
currentNetwork = network
val gateway = gatewayAddressOf(connectivityManager.getLinkProperties(network))
val ssid = ssidOf(connectivityManager.getNetworkCapabilities(network))
eventSink?.success(
mapOf("type" to "available", "gatewayAddress" to gateway),
mapOf("type" to "available", "gatewayAddress" to gateway, "ssid" to ssid),
)
}
@@ -189,6 +202,20 @@ class MlrsNetworkPlugin(
return route?.gateway?.hostAddress
}
/**
* Ermittelt die tatsaechliche SSID des verbundenen Netzes. Erfordert
* normalerweise ACCESS_FINE_LOCATION, ausser fuer die anfragende App
* selbst bei einem ueber WifiNetworkSpecifier bewilligten Netz - genau
* unser Fall, siehe `WifiInfo.getSSID()`-Dokumentation.
*/
private fun ssidOf(capabilities: NetworkCapabilities?): String? {
val wifiInfo = capabilities?.transportInfo as? WifiInfo ?: return null
val ssid = wifiInfo.ssid
if (ssid.isNullOrEmpty() || ssid == WifiManager.UNKNOWN_SSID) return null
// WifiInfo.getSSID() liefert UTF-8-SSIDs in Anfuehrungszeichen.
return ssid.removeSurrounding("\"")
}
private fun isStaConcurrencySupported(): Boolean? {
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.R) return null
val wifiManager =