VWebView
An embedded web view component for displaying web content. Maps to WKWebView on iOS and macOS, and android.webkit.WebView on Android.
Usage
<VWebView
:source="{ uri: 'https://example.com' }"
:style="{ flex: 1 }"
@load="onLoad"
/>
Props
| Prop | Type | Default | Description |
|---|---|---|---|
source | WebViewSource | required | The content to display (URL or inline HTML) |
javaScriptEnabled | boolean | true | Enable JavaScript execution in the web view |
allowedOrigins | string[] | origin of source | Origins allowed to navigate the web view and post messages into the app. A non-empty list replaces the default, so include the source origin if it still needs access. An empty list restores the default. Navigation to file:, javascript: and data: sources is refused. |
style | StyleProp | — | Layout + appearance styles |
WebViewSource
interface WebViewSource {
uri?: string // URL to load
html?: string // Inline HTML string to render
}
Provide either uri or html, not both.
Events
| Event | Payload | Description |
|---|---|---|
@load | { url: string } | Fired when the page finishes loading |
@error | { message: string, url?: string } | Fired when navigation fails; Android includes the failing URL |
@message | { data: any } | Fired when the web page posts a message through the platform's vueNative bridge |
Example
Loading a URL
<script setup>
const loading = ref(true)
function onLoad(e) {
loading.value = false
console.log('Loaded:', e.url)
}
function onError(e) {
loading.value = false
console.log('Error:', e.message)
}
</script>
<template>
<VView :style="styles.container">
<VActivityIndicator v-if="loading" :style="styles.loader" />
<VWebView
:source="{ uri: 'https://vuejs.org' }"
:style="styles.webview"
@load="onLoad"
@error="onError"
/>
</VView>
</template>
<script>
import { ref, createStyleSheet } from '@thelacanians/vue-native-runtime'
const styles = createStyleSheet({
container: {
flex: 1,
},
webview: {
flex: 1,
},
loader: {
position: 'absolute',
top: 100,
alignSelf: 'center',
},
})
</script>
Loading inline HTML
<template>
<VWebView
:source="{ html: '<h1>Hello from Vue Native!</h1><p>This is inline HTML.</p>' }"
:style="{ flex: 1 }"
/>
</template>
Receiving messages from web content
The web page can send messages to your Vue Native app using the platform's vueNative message handler.
On iOS and macOS, use WebKit's script message handler. The payload may be any value supported by WKScriptMessage:
window.webkit.messageHandlers.vueNative.postMessage({ type: 'ready', count: 42 })
On Android, use the injected window.vueNative interface. Android receives a string, so serialize structured data explicitly:
window.vueNative.postMessage(JSON.stringify({ type: 'ready', count: 42 }))
On Android, each message is checked against the origin of the frame that sent it. Where WebView's message listener is available, that check uses the listener. On outdated WebViews without it, the older JavaScript interface is used as a fallback. Messages from origins outside allowedOrigins are dropped.
<template>
<VWebView
:source="{ uri: 'https://example.com' }"
:style="{ flex: 1 }"
@message="onMessage"
/>
</template>
<script setup>
function onMessage(e) {
const data = typeof e.data === 'string' ? JSON.parse(e.data) : e.data
console.log('Received from web:', data)
}
</script>
Notes
VWebViewshould typically be givenflex: 1or explicit dimensions, as it has no intrinsic content size.- The
javaScriptEnabledprop istrueby default and can be toggled at runtime. On iOS and macOS, changes useWKWebpagePreferencesand apply to future navigations; they do not reload the current page. - On iOS and macOS, the
@messageevent usesWKScriptMessageHandlerwith the channel name"vueNative". - Android blocks mixed HTTP content inside HTTPS pages by default.