鸿蒙Next开发日记 Day13 - Web组件的使用与避坑

unnamed.png

程序中经常会用到使用H5展示内容的情况,更何况Hybrid的情况。

鸿蒙NEXT也提供了方便的网页展示容器--Web组件,是Web,不是WebView,鸿蒙没有WebView。

下面是一个示例代码

import { webview } from '@kit.ArkWeb';
import StringUtil from '../../utils/StringUtil';
import LoadingDialogView from '../../view/Dialog/LoadingDialogView'

@Builder
export function WebViewPageBuilder(name: string, param: Object) {
  WebViewPage({ param: param as Record<string, Object> })
}

@Component
struct WebViewPage {
  @Builder
  WebView() {
    Web({ src: this.url, controller: this.controller })
      .javaScriptAccess(true)
      .geolocationAccess(true)
      .imageAccess(true)
      .onlineImageAccess(true)
      .domStorageAccess(true)
      .fileAccess(true)
      .mediaPlayGestureAccess(true)
      .mixedMode(MixedMode.Compatible)
      .onTitleReceive((event) => {
        if (event) {
          this.title = event.title
        }
      })
      .onProgressChange((event) => {
        if (event) {
          this.progressPercentage = event.newProgress
        }
      })
      .onHttpErrorReceive((event) => {
        if (event) {
          console.log('url:' + event.request.getRequestUrl());
          console.log('isMainFrame:' + event.request.isMainFrame());
          console.log('isRedirect:' + event.request.isRedirect());
          console.log('isRequestGesture:' + event.request.isRequestGesture());
          console.log('getResponseData:' + event.response.getResponseData());
          console.log('getResponseEncoding:' + event.response.getResponseEncoding());
          console.log('getResponseMimeType:' + event.response.getResponseMimeType());
          console.log('getResponseCode:' + event.response.getResponseCode());
          console.log('getReasonMessage:' + event.response.getReasonMessage());
          let result = event.request.getRequestHeader();
          console.log('The request header result size is ' + result.length);
          for (let i of result) {
            console.log('The request header key is : ' + i.headerKey + ' , value is : ' + i.headerValue);
          }
          let resph = event.response.getResponseHeader();
          console.log('The response header result size is ' + resph.length);
          for (let i of resph) {
            console.log('The response header key is : ' + i.headerKey + ' , value is : ' + i.headerValue);
          }
        }
      })
      // .onControllerAttached(() => {
      //   this.controller.loadUrl(this.url)
      // })
      .width("100%")
      .flexGrow(1)
      .layoutWeight(1)
  }

  build() {
    NavDestination() {
      Column() {
        if (!StringUtil.isNullStr(this.url)) {
          if (this.progressPercentage > 0 && this.progressPercentage < 100) {
            Progress({ value: this.progressPercentage, total: 100, type: ProgressType.Linear })
              .width("100%").height(2).backgroundColor($r('app.color.background_main'))
              .style({ strokeWidth: 2 })
          }
          this.WebView()
        }
      }
      .backgroundColor("#FFAAFF")
      .width("100%").height("100%")
    }.title(this.title)
    .onWillAppear(() => {
      this.url = this.param.url as string
    })
    .onAppear(() => {

    })
    .onShown(() => {

    })
  }

  param: Record<string, Object> = {}
  @State url: string = ""
  @State title: string = ""
  controller: webview.WebviewController = new webview.WebviewController()
  @State avoidMode: WebKeyboardAvoidMode = WebKeyboardAvoidMode.RESIZE_VISUAL;
  @Consume('navPathStack') navPathStack: NavPathStack;
  @State progressPercentage: number = 0
  loadingController: CustomDialogController = new CustomDialogController({
    builder: LoadingDialogView(),
    autoCancel: true,
    customStyle: true,
  })
}

通过以上代码就可以实现一个带进度条的简易浏览器。

Screenshot_2024-09-04T184945.png

这里有几个坑需要注意一下。

1. 多给Web组件添加一些权限,有些网页使用了本地存储等技术,权限未开的情况下会出现加载不出内容的情况,然后还定位不出原因。具体权限添加如下:

.javaScriptAccess(true)
.geolocationAccess(true)
.imageAccess(true)
.onlineImageAccess(true)
.domStorageAccess(true)
.fileAccess(true)
.mediaPlayGestureAccess(true)

.mixedMode(MixedMode.Compatible)


2. 是我在使用模拟器调试Web组件时出现的问题,模拟器是可以设置http代理的,当你开启模拟器代理时,会出现Web组件在加载域名地址失败情况,DNS解析失败了。现象就是内容是空白。

Screenshot_2024-09-04T184919.png

为了避免不必要的麻烦,调试Web组件时,就把代理关了吧。

关键词:鸿蒙NEXT

网友留言(0 条)

发表评论

验证码