Stories

Detail Return Return

HarmonyOS 5.0應用開發——Web組件的使用 - Stories Detail

【高心星出品】

Web組件的使用

ArkWeb(方舟Web)提供了Web組件,用於在應用程序中顯示Web頁面內容。常見使用場景包括:

  • 應用集成Web頁面:應用可以在頁面中使用Web組件,嵌入Web頁面內容,以降低開發成本,提升開發、運營效率。
  • 瀏覽器網頁瀏覽場景:瀏覽器類應用可以使用Web組件,打開三方網頁,使用無痕模式瀏覽Web頁面,設置廣告攔截等。
  • 小程序:小程序類宿主應用可以使用Web組件,渲染小程序的頁面。

加載網頁資源

private webcontroller:WebviewController=new webview.WebviewController()//控制器
....
Web({src:'https://www.sohu.com/',controller:this.webcontroller})
  .margin(20)
名稱 類型 必填 説明
src string \ Resource 網頁資源地址。如果訪問本地資源文件,請使用$rawfile或者resource協議。如果加載應用包外沙箱路徑的本地資源文件(文件支持html和txt類型),請使用file://沙箱文件路徑。src不能通過狀態變量(例如:@State)動態更改地址,如需更改,請通過loadUrl()重新加載。
controller WebviewController9+ 控制器。從API Version 9開始,WebController不再維護,建議使用WebviewController替代。

這裏的src可以提供網絡地址,也可以提供項目中本地網頁代碼資源。

項目結構

在這裏插入圖片描述

項目代碼
import { webview } from '@kit.ArkWeb';

@Entry
@Component
struct Index {
  @State message: string = 'Hello World';
  private webcontroller:WebviewController=new webview.WebviewController()
  build() {
    Column(){
      Button('重新加載')
        .onClick(()=>{
          //重新加載本地資源
         this.webcontroller.loadUrl($rawfile('test.html'))
        })
        //加載網絡地址
      Web({src:'https://www.sohu.com/',controller:this.webcontroller})
        .margin(20)
    }
    .width('100%')
    .height('100%')
  }
}

在這裏插入圖片描述

Web組件的生命週期方法

Web組件提供了豐富的組件生命週期回調接口,通過這些回調接口,開發者可以感知Web組件的生命週期狀態變化,進行相關的業務處理。

Web組件的狀態主要包括:Controller綁定到Web組件、網頁加載開始、網頁加載進度、網頁加載結束、頁面即將可見等。

img

  • onControllerAttached事件:當Controller成功綁定到Web組件時觸發該回調,且禁止在該事件回調前調用Web組件相關的接口,否則會拋出js-error異常。推薦在此事件中注入JS對象registerJavaScriptProxy、設置自定義用户代理setCustomUserAgent,可以在回調中使用loadUrl,getWebId等操作網頁不相關的接口。但因該回調調用時網頁還未加載,因此無法在回調中使用有關操作網頁的接口,例如zoomIn、zoomOut等。
  • onLoadIntercept事件:當Web組件加載url之前觸發該回調,用於判斷是否阻止此次訪問。默認允許加載。
  • onOverrideUrlLoading事件:當URL將要加載到當前Web中時,讓宿主應用程序有機會獲得控制權,回調函數返回true將導致當前Web中止加載URL,而返回false則會導致Web繼續照常加載URL。onLoadIntercept接口和onOverrideUrlLoading接口行為不一致,觸發時機也不同,所以在應用場景上存在一定區別。主要是在LoadUrl和iframe(HTML標籤,表示HTML內聯框架元素,用於將另一個頁面嵌入到當前頁面中)加載時,onLoadIntercept事件會正常回調到,但onOverrideUrlLoading事件在LoadUrl加載時不會觸發,在iframe加載HTTP(s)協議或about:blank時也不會觸發。詳細介紹請見onLoadIntercept和onOverrideUrlLoading的説明。
  • onInterceptRequest事件:當Web組件加載url之前觸發該回調,用於攔截url並返回響應數據。
  • onPageBegin事件:網頁開始加載時觸發該回調,且只在主frame(表示一個HTML元素,用於展示HTML頁面的HTML元素)觸發。如果是iframe或者frameset(用於包含frame的HTML標籤)的內容加載時則不會觸發此回調。多frame頁面有可能同時開始加載,即使主frame已經加載結束,子frame也有可能才開始或者繼續加載中。同一頁面導航(片段、歷史狀態等)或者在提交前失敗、被取消的導航等也不會觸發該回調。
  • onProgressChange事件:告知開發者當前頁面加載的進度。多frame頁面或者子frame有可能還在繼續加載而主frame可能已經加載結束,所以在onPageEnd事件後依然有可能收到該事件。
  • onPageEnd事件:網頁加載完成時觸發該回調,且只在主frame觸發。多frame頁面有可能同時開始加載,即使主frame已經加載結束,子frame也有可能才開始或者繼續加載中。同一頁面導航(片段、歷史狀態等)或者在提交前失敗、被取消的導航等也不會觸發該回調。推薦在此回調中執行JavaScript腳本loadUrl等。需要注意的是收到該回調並不能保證Web繪製的下一幀將反映此時DOM的狀態。
  • onPageVisible事件:Web回調事件。渲染流程中當HTTP響應的主體開始加載,新頁面即將可見時觸發該回調。此時文檔加載還處於早期,因此鏈接的資源比如在線CSS、在線圖片等可能尚不可用。
  • onRenderExited事件:應用渲染進程異常退出時觸發該回調,可以在此回調中進行系統資源的釋放、數據的保存等操作。如果應用希望異常恢復,需要調用loadUrl接口重新加載頁面。
  • onDisAppear事件:組件卸載消失時觸發此回調。該事件為通用事件,指組件從組件樹上卸載時觸發的事件。
項目結構

在這裏插入圖片描述

import { webview } from '@kit.ArkWeb';
import { buffer } from '@kit.ArkTS';

@Entry
@Component
struct Index {
  @State message: string = 'Hello World';
  private webcontroller: WebviewController = new webview.WebviewController()

  build() {
    Column() {
      Button('重新加載')
        .onClick(() => {
          this.webcontroller.loadUrl($rawfile('test.html'))
        })
      Web({ src: 'https://www.sohu.com/', controller: this.webcontroller })
        .onControllerAttached(() => {
          //此時controller可以使用,一番設置或者注入js對象
          console.log('gxxt ', 'controller綁定web的時候調用')
        })
        .onLoadIntercept((event) => {
          // 獲取請求地址  請求方法
          console.log('gxxt ', '即將加載倆  url= ' + event.data.getRequestUrl())
          // 返回true則攔截此次請求,false表示不攔截
          return false
        })
        .onInterceptRequest((event) => {
          console.log('gxxt 根據url 即將發起請求: ' + event.request.getRequestUrl())
          // 如果請求地址有https
          if (event.request.getRequestUrl().indexOf('https') >= 0) {
            //自己定義一個響應
            let webreqres = new WebResourceResponse()
            webreqres.setResponseEncoding('UTF-8')
            webreqres.setResponseMimeType('text/html')
            webreqres.setResponseCode(200)
            webreqres.setResponseData(this.getrawstr())
            return webreqres
          }
          // 否則 繼續返回
          return null
        })
        .onPageBegin((event) => {
          //頁面開始加載的時候調用
          console.log('gxxt  頁面開始加載:' + event.url)
        })
        .onProgressChange((event) => {
          console.log('gxxt 加載進度: ' + event.newProgress)
        })
        .onPageEnd((event) => {
          console.log('gxxt 頁面加載完畢: ' + event.url)
        })
        .margin(20)
    }
    .width('100%')
    .height('100%')
  }

  getrawstr() {
      //讀取網頁內容轉換成字符串
    let buffer1 = getContext(this).resourceManager.getRawFileContentSync('intercept.html').buffer
    return buffer.from(buffer1).toString()
  }
}

在這裏插入圖片描述

網頁導航

在前端頁面點擊網頁中的鏈接時,Web組件默認會自動打開並加載目標網址。當前端頁面替換為新的加載鏈接時,會自動記錄已經訪問的網頁地址。可以通過forward()和backward()接口向前/向後瀏覽上一個/下一個歷史記錄。

例如點擊後退鍵的時候,我們不再推出應用而是回到上一頁,如果沒有上一頁再退出應用。

在這裏插入圖片描述

import { webview } from '@kit.ArkWeb';
import { buffer } from '@kit.ArkTS';

@Entry
@Component
struct Index {
  @State message: string = 'Hello World';
  private webcontroller: WebviewController = new webview.WebviewController()

  build() {
    Column() {
      Button('重新加載')
        .onClick(() => {
          this.webcontroller.loadUrl($rawfile('test.html'))
        })
      Web({ src: 'https://www.sohu.com/', controller: this.webcontroller })
        .margin(20)
    }
    .width('100%')
    .height('100%')
  }

  // getrawstr() {
  //   let buffer1 = getContext(this).resourceManager.getRawFileContentSync('intercept.html').buffer
  //   return buffer.from(buffer1).toString()
  // }
  onBackPress(): boolean | void {
  //   如果能後退就退到上一頁
  if(this.webcontroller.accessBackward())
  {
    this.webcontroller.backward()
    // 攔截默認的back鍵操作
    return true

  }else{
    // 否則不攔截
    return false
  }
  }
}
user avatar jingmingdewudongmian_dscnyw Avatar finally-vince Avatar wodekouwei Avatar hongmengbaixiaosheng Avatar waylau521 Avatar
Favorites 5 users favorite the story!
Favorites

Add a new Comments

Some HTML is okay.