3

I'm using NativeScript-vue.

I want to use WebView to display an HTML file in a local asset.

src/components/App.vue:

<template>
  <Frame>
    <Page>
      <GridLayout columns="*" rows="*">
        <WebView row="0" col="0" src="~/assets/index.html" />
      </GridLayout>
    </Page>
  </Frame>
</template>

src/main.ts:

import Vue from 'nativescript-vue';
import App from './components/App.vue';

new Vue({
  render: h => h(App)
}).$start();

src/assets/index.html:

<html>
  <body>
    <div>test</div>
  </body>
</html>

App_Resources/Android/src/main/AndroidManifest.xml:

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="__PACKAGE__"
    android:versionCode="10000"
    android:versionName="1.0">

    <supports-screens
        android:smallScreens="true"
        android:normalScreens="true"
        android:largeScreens="true"
        android:xlargeScreens="true"/>

    <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
    <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
    <uses-permission android:name="android.permission.INTERNET"/>

    <application
        android:name="com.tns.NativeScriptApplication"
        android:allowBackup="true"
        android:icon="@drawable/icon"
        android:label="@string/app_name"
        android:theme="@style/AppTheme"
        android:usesCleartextTraffic="true">

        <activity
            android:name="com.tns.NativeScriptActivity"
            android:label="@string/title_activity_kimera"
            android:configChanges="keyboard|keyboardHidden|orientation|screenSize|smallestScreenSize|screenLayout|locale|uiMode"
            android:theme="@style/LaunchScreenTheme">

            <meta-data android:name="SET_THEME_ON_LAUNCH" android:resource="@style/AppTheme" />

            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
        <activity android:name="com.tns.ErrorReportActivity"/>
    </application>
</manifest>

Now, I get the error "ERR_ACCESS_DENIED" when I run this application on Android Emulator.

enter image description here

This situation is the same with the actual device instead of the emulator.

Is there any possible cause?

Environment:

  • npm:
    • @nativescript/core: 7.0.3
    • nativescript-socketio: 3.3.1
    • nativescript-vue: 2.8.1
  • Emulator: API 30, Android 11.0, x86

Curiously, it works fine with the Android 10.0 (API 29, x86) emulator.

2
  • maybe you can check this answer stackoverflow.com/a/63535281/10772133 Commented Nov 9, 2020 at 10:10
  • Thanks for your comment. Probably my webpack settings are correct. HTML file is located in the "assets" directory, and the CopyWebpackPlugin setting in webpack is correct. -----> ` { from: 'assets/**', noErrorOnMissing: true, globOptions: { dot: false, ...copyIgnore } }, ` Commented Nov 9, 2020 at 11:49

1 Answer 1

5

It turns out that in Android 11.0 and later, file access is not allowed by default!

Android Developers Reference: WebSettings

The default value is true for apps targeting Build.VERSION_CODES.Q and below, and false when targeting Build.VERSION_CODES.R and above.

resolved code

src/components/App.vue:

<template>
  <Frame>
    <Page>
      <GridLayout columns="*" rows="*">
        <WebView row="0" col="0" @loaded="webViewLoaded" />
      </GridLayout>
    </Page>
  </Frame>
</template>

<script lang="ts">
export default {
  methods: {
    webViewLoaded(args) {
      if (args.object.android) {
        args.object.android.getSettings().setAllowFileAccess(true); // IMPORTANT!!
        args.object.src = "~/assets/map/index.html"; // Load local HTML.
      }
    },
  },
};
</script>
Sign up to request clarification or add additional context in comments.

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.