Search code examples
androidkotlinandroid-webviewandroid-jetpack-compose

Trigger event on state change, in android jetpack compose


I have a web view and a TextField. I want to trigger web view reload when textField triggers the onGo action or its value change.

Below is mutable string:

var urlValue: MutableState<String> = mutableStateOf(DefaultUrl)

the textField looks like this

var textFieldValue by remember { mutableStateOf(DefaultUrl) }

val textStyle = androidx.compose.ui.text.TextStyle(
    fontSize = ToolbarUrlFontSize.sp
)

BasicTextField(
    value = textFieldValue,
    onValueChange = { text ->
        textFieldValue = text
    },
   
    keyboardOptions = KeyboardOptions(imeAction = ImeAction.Go),
    keyboardActions = KeyboardActions(
        onGo = {
            urlValue.value = textFieldValue
        }
    )
) { innerTextField ->
    innerTextField()
}

And below is the code for web view:

AndroidView({ context ->
    WebView(context).apply {
        if(urlValue.value.isNotEmpty()) {
            Log.i("TAG", "MainComposable: ${urlValue.value}")
            loadUrl(urlValue.value)
        }

        webViewClient = object : WebViewClient() {
            override fun shouldOverrideUrlLoading(
                view: WebView,
                url: String
            ): Boolean {
                view.loadUrl(url)
                return false
            }
        }
    }
}

But the web view doesn't reload the new URL. How can I do the new URL load on the go action trigger?


Solution

  • Check the below code to render in WebView:

    @SuppressLint("SetJavaScriptEnabled")
    @Composable
    fun WebPageScreen(urlToRender: String) {
        AndroidView(factory = {
            WebView(it).apply {
                webViewClient = object : WebViewClient() {
                    override fun shouldOverrideUrlLoading(
                        view: WebView?,
                        request: WebResourceRequest?
                    ): Boolean {
                        return false
                    }
                }
            }
        }, update = {
            it.loadUrl(urlToRender)
        })
    }
    

    AndroidView() composable function's update block is invoked after the layout is inflated.