เพิ่มประสิทธิภาพพฤติกรรมการคลิก WKWebView

หากแอปใช้ WKWebView เพื่อแสดงเนื้อหาเว็บ คุณอาจต้องพิจารณา เพิ่มประสิทธิภาพลักษณะการคลิกด้วยเหตุผลต่อไปนี้

  • WKWebView ไม่รองรับการท่องเว็บแบบเปิดได้หลายแท็บในวินโดว์เดียวของเบราว์เซอร์ การคลิกโฆษณาที่พยายามเปิดแท็บใหม่จะไม่ทําอะไรโดยค่าเริ่มต้น

  • การคลิกโฆษณาที่เปิดในแท็บเดียวกันจะโหลดหน้าเว็บซ้ำ คุณอาจต้องการบังคับให้ การคลิกโฆษณาเปิดภายนอก WKWebView เช่น หากคุณโฮสต์เกม H5 และต้องการ รักษาสถานะของแต่ละเกม

  • การป้อนข้อความอัตโนมัติไม่รองรับข้อมูลบัตรเครดิตใน WKWebView ซึ่งอาจส่งผลให้ผู้ลงโฆษณาได้รับ Conversion จากอีคอมเมิร์ซน้อยลง และส่งผลเสียต่อการสร้างรายได้จากเนื้อหาเว็บ

คู่มือนี้จะแสดงขั้นตอนที่แนะนำในการเพิ่มประสิทธิภาพลักษณะการคลิกในมุมมองเว็บบนอุปกรณ์เคลื่อนที่ ขณะที่ยังคงเนื้อหาของมุมมองเว็บไว้

ข้อกำหนดเบื้องต้น

การใช้งาน

ลิงก์โฆษณาสามารถมีแอตทริบิวต์เป้าหมาย href ที่ตั้งค่าเป็น _blank, _top, _self หรือ _parent Ad Manager ช่วยให้คุณควบคุมแอตทริบิวต์เป้าหมายให้เป็น _blank หรือ _top โดยตั้งค่าให้โฆษณาเปิดในแท็บหรือ หน้าต่างใหม่ ลิงก์โฆษณายังมีฟังก์ชัน JavaScript เช่น window.open(url, "_blank") ได้ด้วย

ตารางต่อไปนี้จะอธิบายลักษณะการทำงานของลิงก์แต่ละรายการในมุมมองเว็บ

href แอตทริบิวต์เป้าหมาย ลักษณะการทำงานเริ่มต้นของการคลิก WKWebView
target="_blank" ลิงก์ที่ WebView ไม่ได้จัดการ
target="_top" โหลดลิงก์ซ้ำใน WebView ที่มีอยู่
target="_self" โหลดลิงก์ซ้ำใน WebView ที่มีอยู่
target="_parent" โหลดลิงก์ซ้ำใน WebView ที่มีอยู่
ฟังก์ชัน JavaScript ลักษณะการทำงานเริ่มต้นของการคลิก WKWebView
window.open(url, "_blank") ลิงก์ที่ WebView ไม่ได้จัดการ

ทําตามขั้นตอนต่อไปนี้เพื่อเพิ่มประสิทธิภาพลักษณะการคลิกในWKWebView อินสแตนซ์

  1. ตั้งค่า WKUIDelegate ในอินสแตนซ์ WKWebView

  2. ตั้งค่า WKNavigationDelegate ในอินสแตนซ์ WKWebView

  3. พิจารณาว่าจะเพิ่มประสิทธิภาพลักษณะการทำงานของ URL การคลิกหรือไม่

    • ตรวจสอบว่าพร็อพเพอร์ตี้ navigationType ในออบเจ็กต์ WKNavigationAction เป็นประเภทคลิกที่คุณต้องการเพิ่มประสิทธิภาพหรือไม่ ตัวอย่างโค้ดจะตรวจสอบ .linkActivated ซึ่งใช้กับการคลิกลิงก์ที่มีแอตทริบิวต์ href เท่านั้น

    • ตรวจสอบพร็อพเพอร์ตี้ targetFrame ในออบเจ็กต์ WKNavigationAction หากแสดงผลเป็น nil แสดงว่า เป้าหมายของการนำทางคือหน้าต่างใหม่ เนื่องจาก WKWebView จัดการคลิกดังกล่าวไม่ได้ คุณจึงต้องจัดการคลิกเหล่านี้ด้วยตนเอง

  4. เลือกว่าจะเปิด URL ในเบราว์เซอร์ภายนอก SFSafariViewController หรือ WebView ที่มีอยู่ ข้อมูลโค้ดแสดงวิธีเปิด URL ที่นำทางออกจากเว็บไซต์โดยการแสดง SFSafariViewController

ตัวอย่างโค้ด

ข้อมูลโค้ดต่อไปนี้แสดงวิธีเพิ่มประสิทธิภาพลักษณะการทำงานของการคลิก WebView เช่น ตรวจสอบว่าโดเมนปัจจุบันแตกต่างจากโดเมนเป้าหมายหรือไม่ นี่เป็นเพียงแนวทางหนึ่ง เนื่องจากเกณฑ์ที่คุณใช้จะแตกต่างกันไป

Swift

import GoogleMobileAds
import SafariServices
import WebKit

class ViewController: UIViewController, WKNavigationDelegate, WKUIDelegate {

  override func viewDidLoad() {
    super.viewDidLoad()

    // ... Register the WKWebView.

    // 1. Set the WKUIDelegate on your WKWebView instance.
    webView.uiDelegate = self;
    // 2. Set the WKNavigationDelegate on your WKWebView instance.
    webView.navigationDelegate = self
  }

  // Implement the WKUIDelegate method.
  func webView(
      _ webView: WKWebView,
      createWebViewWith configuration: WKWebViewConfiguration,
      for navigationAction: WKNavigationAction,
      windowFeatures: WKWindowFeatures) -> WKWebView? {
    // 3. Determine whether to optimize the behavior of the click URL.
    if didHandleClickBehavior(
        currentURL: webView.url,
        navigationAction: navigationAction) {
      print("URL opened in SFSafariViewController.")
    }

    return nil
  }

  // Implement the WKNavigationDelegate method.
  func webView(
      _ webView: WKWebView,
      decidePolicyFor navigationAction: WKNavigationAction,
      decisionHandler: @escaping (WKNavigationActionPolicy) -> Void)
  {
    // 3. Determine whether to optimize the behavior of the click URL.
    if didHandleClickBehavior(
        currentURL: webView.url,
        navigationAction: navigationAction) {
      return decisionHandler(.cancel)
    }

    decisionHandler(.allow)
  }

  // Implement a helper method to handle click behavior.
  func didHandleClickBehavior(
      currentURL: URL,
      navigationAction: WKNavigationAction) -> Bool {
    guard let targetURL = navigationAction.request.url else {
      return false
    }

    // Handle custom URL schemes such as itms-apps:// by attempting to
    // launch the corresponding application.
    if navigationAction.navigationType == .linkActivated {
      if let scheme = targetURL.scheme, !["http", "https"].contains(scheme) {
        UIApplication.shared.open(targetURL, options: [:], completionHandler: nil)
        return true
      }
    }

    guard let currentDomain = currentURL.host,
      let targetDomain = targetURL.host else {
      return false
    }

    // Check if the navigationType is a link with an href attribute or
    // if the target of the navigation is a new window.
    if (navigationAction.navigationType == .linkActivated ||
      navigationAction.targetFrame == nil) &&
      // If the current domain does not equal the target domain,
      // the assumption is the user is navigating away from the site.
      currentDomain != targetDomain {
      // 4. Open the URL in a SFSafariViewController.
      let safariViewController = SFSafariViewController(url: targetURL)
      present(safariViewController, animated: true)
      return true
    }

    return false
  }
}

Objective-C

@import GoogleMobileAds;
@import SafariServices;
@import WebKit;

@interface ViewController () <WKNavigationDelegate, WKUIDelegate>

@property(nonatomic, strong) WKWebView *webView;

@end

@implementation ViewController

- (void)viewDidLoad {
  [super viewDidLoad];

  // ... Register the WKWebView.

  // 1. Set the WKUIDelegate on your WKWebView instance.
  self.webView.uiDelegate = self;
  // 2. Set the WKNavigationDelegate on your WKWebView instance.
  self.webView.navigationDelegate = self;
}

// Implement the WKUIDelegate method.
- (WKWebView *)webView:(WKWebView *)webView
  createWebViewWithConfiguration:(WKWebViewConfiguration *)configuration
             forNavigationAction:(WKNavigationAction *)navigationAction
                  windowFeatures:(WKWindowFeatures *)windowFeatures {
  // 3. Determine whether to optimize the behavior of the click URL.
  if ([self didHandleClickBehaviorForCurrentURL: webView.URL
      navigationAction: navigationAction]) {
    NSLog(@"URL opened in SFSafariViewController.");
  }

  return nil;
}

// Implement the WKNavigationDelegate method.
- (void)webView:(WKWebView *)webView
    decidePolicyForNavigationAction:(WKNavigationAction *)navigationAction
                    decisionHandler:
                        (void (^)(WKNavigationActionPolicy))decisionHandler {
  // 3. Determine whether to optimize the behavior of the click URL.
  if ([self didHandleClickBehaviorForCurrentURL: webView.URL
      navigationAction: navigationAction]) {
    decisionHandler(WKNavigationActionPolicyCancel);
    return;
  }

  decisionHandler(WKNavigationActionPolicyAllow);
}

// Implement a helper method to handle click behavior.
- (BOOL)didHandleClickBehaviorForCurrentURL:(NSURL *)currentURL
                    navigationAction:(WKNavigationAction *)navigationAction {
  NSURL *targetURL = navigationAction.request.URL;

  // Handle custom URL schemes such as itms-apps:// by attempting to
  // launch the corresponding application.
  if (navigationAction.navigationType == WKNavigationTypeLinkActivated) {
    NSString *scheme = targetURL.scheme;
    if (![scheme isEqualToString:@"http"] && ![scheme isEqualToString:@"https"]) {
      [UIApplication.sharedApplication openURL:targetURL options:@{} completionHandler:nil];
      return YES;
    }
  }

  NSString *currentDomain = currentURL.host;
  NSString *targetDomain = targetURL.host;

  if (!currentDomain || !targetDomain) {
    return NO;
  }

  // Check if the navigationType is a link with an href attribute or
  // if the target of the navigation is a new window.
  if ((navigationAction.navigationType == WKNavigationTypeLinkActivated
      || !navigationAction.targetFrame)
      // If the current domain does not equal the target domain,
      // the assumption is the user is navigating away from the site.
      && ![currentDomain isEqualToString: targetDomain]) {
     // 4. Open the URL in a SFSafariViewController.
    SFSafariViewController *safariViewController =
        [[SFSafariViewController alloc] initWithURL:targetURL];
    [self presentViewController:safariViewController animated:YES
        completion:nil];
    return YES;
  }

  return NO;
}

ทดสอบการนำทางหน้าเว็บ

หากต้องการทดสอบการเปลี่ยนแปลงการนำทางในหน้าเว็บ ให้โหลด

https://google.github.io/webview-ads/test/#click-behavior-tests

ลงในข้อมูลพร็อพเพอร์ตี้เว็บ คลิกลิงก์แต่ละประเภทเพื่อดูว่าลิงก์เหล่านั้น ทำงานอย่างไรในแอป

โปรดตรวจสอบสิ่งต่อไปนี้

  • แต่ละลิงก์จะเปิด URL ที่ต้องการ
  • เมื่อกลับไปที่แอป ตัวนับของหน้าทดสอบจะไม่รีเซ็ตเป็น 0 เพื่อตรวจสอบว่าระบบยังคงรักษาสถานะของหน้าไว้