Feat(ToolView): Add native api

Add native api to support clipboard operations
This commit is contained in:
2024-08-21 16:52:24 +08:00
parent 893131fe02
commit e0485ecc32
2 changed files with 67 additions and 0 deletions

View File

@@ -1,6 +1,8 @@
package top.fatweb.oxygen.toolbox.ui.view
import android.annotation.SuppressLint
import android.util.Log
import android.webkit.ConsoleMessage
import androidx.compose.animation.core.Ease
import androidx.compose.animation.core.animateFloat
import androidx.compose.animation.core.infiniteRepeatable
@@ -26,20 +28,25 @@ import androidx.compose.material3.Text
import androidx.compose.material3.TopAppBarDefaults
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.remember
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.graphicsLayer
import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.res.stringResource
import androidx.compose.ui.unit.dp
import androidx.hilt.navigation.compose.hiltViewModel
import androidx.lifecycle.compose.collectAsStateWithLifecycle
import com.kevinnzou.web.AccompanistWebChromeClient
import com.kevinnzou.web.WebView
import com.kevinnzou.web.rememberWebViewStateWithHTMLData
import timber.log.Timber
import top.fatweb.oxygen.toolbox.R
import top.fatweb.oxygen.toolbox.icon.Loading
import top.fatweb.oxygen.toolbox.icon.OxygenIcons
import top.fatweb.oxygen.toolbox.ui.component.OxygenTopAppBar
import top.fatweb.oxygen.toolbox.util.NativeWebApi
@Composable
internal fun ToolViewRoute(
@@ -67,6 +74,7 @@ internal fun ToolViewScreen(
isPreview: Boolean,
onBackClick: () -> Unit
) {
val context = LocalContext.current
val infiniteTransition = rememberInfiniteTransition(label = "infiniteTransition")
@@ -150,8 +158,33 @@ internal fun ToolViewScreen(
.fillMaxSize()
.imePadding(),
state = webViewState,
chromeClient = remember {
object : AccompanistWebChromeClient() {
override fun onConsoleMessage(consoleMessage: ConsoleMessage?): Boolean {
consoleMessage?.let {
Timber.tag("WebView").log(
priority = when (it.messageLevel()) {
ConsoleMessage.MessageLevel.TIP -> Log.VERBOSE
ConsoleMessage.MessageLevel.LOG -> Log.INFO
ConsoleMessage.MessageLevel.WARNING -> Log.WARN
ConsoleMessage.MessageLevel.ERROR -> Log.ERROR
else -> Log.DEBUG
},
message = "${it.message()} (${it.lineNumber()})"
)
return true
}
return false
}
}
},
onCreated = {
it.settings.javaScriptEnabled = true
it.settings.domStorageEnabled = true
it.addJavascriptInterface(
NativeWebApi(context = context, webView = it),
"NativeApi"
)
}
)
}

View File

@@ -0,0 +1,34 @@
package top.fatweb.oxygen.toolbox.util
import android.content.ClipData
import android.content.ClipboardManager
import android.content.Context
import android.content.Context.CLIPBOARD_SERVICE
import android.webkit.JavascriptInterface
import android.webkit.WebView
class NativeWebApi(
private val context: Context,
private val webView: WebView
) {
@JavascriptInterface
fun copyToClipboard(text: String): Boolean {
val clipboardManager = context.getSystemService(CLIPBOARD_SERVICE) as ClipboardManager?
return clipboardManager?.let {
it.setPrimaryClip(ClipData.newPlainText("copy", text))
true
} ?: false
}
@JavascriptInterface
fun readClipboard(): String {
val clipboardManager = context.getSystemService(CLIPBOARD_SERVICE) as ClipboardManager?
return clipboardManager?.primaryClip?.getItemAt(0)?.text?.toString() ?: ""
}
private fun callback(callback: String, vararg args: Any) {
val jsCode =
"$callback(${args.map { if (it is String) "'$it'" else it }.joinToString(", ")})"
webView.evaluateJavascript(jsCode, null)
}
}