メインコンテンツまでスキップ

iOS Application の実装

サンプルコードを例に、idfaなどの受け渡し、そのほか実装上の注意事項に関して説明します。

  1. JavaScriptとの連携方法
    1. IDFAの取得
    2. Webページにデータ取得用のインターフェース作成
    3. Webページからidfa, appbundle, platformvを受け取る
  2. 広告リダイレクトの対応
  3. 動画の再生

JavaScriptとの連携方法

各種パラメーターの取得については公式リファレンスなどをご参照ください。

IDFAの取得

AppTrackingTransparency.framework(*1) および、AdSupport.framework(*2) を追加する必要があります。

(*1)iOS14以降で有効なIDFAが取得可能であるか判定するために必要です。
(*2)IDFAの取得のために必要です。

また、下記で後述しているサンプルコードでは、ATTrackingManagerAuthorizationStatusAuthorized のステータスにてIDFAを取得するように記述しております。

// IDFAを取得するためのサンプルコード
import AppTrackingTransparency
import AdSupport

~~省略~~

if #available(iOS 14, *) {
// iOS14以降ではAppTrackingTransparencyを利用してIDFA取得に関する判定をする
switch ATTrackingManager.trackingAuthorizationStatus {
case .authorized:
// IDFAの取得がユーザーにより許可されている
idfa = ASIdentifierManager.shared().advertisingIdentifier.uuidString
case .denied:
// IDFAの取得がユーザーにより拒否されている
print("denied")
case .restricted:
// IDFAの取得がユーザーの設定により制限されている
print("restricted")
case .notDetermined:
// IDFAの取得に関するリクエストをまだユーザーが受け取っていない
print("notDetermined")
@unknown default:
fatalError()
}
} else {
// iOS13以前ではAppTrackingTransparencyを利用せずIDFA取得に関する判定をする
if (ASIdentifierManager.shared().isAdvertisingTrackingEnabled) {
idfa = ASIdentifierManager.shared().advertisingIdentifier.uuidString
}
}

Webページにデータ取得用のインターフェース作成

JavaScriptの雛形を準備し、Web画面に読み込ませる。 そのJavaScriptを介して、データを受け渡します。

func webView(_ webView: WKWebView, didStartProvisionalNavigation navigation: WKNavigation!) {
// ページの読み込み準備開始
updateUserScript()
}

// MARK: - HTMLの読み込み前に動作するスクリプトの作成

func updateUserScript() {
let script = createUserScript()

// 登録されているスクリプトを削除
userContentController.removeAllUserScripts()

// 新規のスクリプトを登録
userContentController.addUserScript(script)
}

func createUserScript() -> WKUserScript {
// bundleId
let bundleId = Bundle.main.bundleIdentifier ?? ""
// IDFA, ATTダイアログの表示は別に行う必要があります
let idfa = ASIdentifierManager.shared().advertisingIdentifier.uuidString

// iOSバージョンを取得
let platformv = UIDevice.current.systemVersion

// js
let jsString = "window.adgAdParams = {idfa:'\(idfa)', appbundle:'\(bundleId)', platformv:'\(platformv)'};"

let userScript = WKUserScript(source: jsString, injectionTime: .atDocumentStart, forMainFrameOnly: true)
return userScript
}

Webページからidfa, appbundle, platformvを受け取る

const idfa = window?.adgAdParams?.idfa;
const appbundle = window?.adgAdParams?.appbundle;
const platformv = window?.adgAdParams?.platformv;

取得したadid,packageNameを利用し 広告タグにパラメータを生成してください。 下記サンプルでは、iOS又はAndroidからパラメータを受け取り、広告タグのパラメータに含めています。

<div id="adg_area"></div>
<script>
/*
idfa : iOSの場合この変数にidfaがセットされているとする(オプトアウト時除く)
aaid : Androidの場合この変数にAdvertising IDがセットされているとする(オプトアウト時除く)
appbundle : 実際にはこの変数にBundle IDかPackage Nameがセットされているとする。
platformv : iOS/Androidのバージョンがセットされているとする。
*/
(function() {
const div = document.getElementById("adg_area");
const script = document.createElement('script');
script.type = 'text/javascript';

let idfa = window?.adgAdParams?.idfa ?? "";
let advertising_id = window?.Android?.getAdvertisingId?.() ?? "";
let appbundle = window?.adgAdParams?.appbundle ?? window?.Android?.getAppBundle?.() ?? "";
let platformv = window?.adgAdParams?.platformv ?? window?.Android?.getPlatformV?.() ?? "";


// scriptのsrcにセットするテキストは実際に管理画面から取得されるタグのsrcと合わせてください。ただし、asyncは必ずtrueにしてください。
let srcText ='https://i.socdm.com/sdk/js/adg-script-loader.js?id=48547&targetID=adg_48547&displayid=1&adType=SP&async=true&tagver=2.0.0';
if(idfa.length > 0){
srcText += '&idfa=' + encodeURIComponent(idfa);
}
else if(advertising_id.length > 0){
srcText += '&advertising_id=' +encodeURIComponent(advertising_id);
}
if(appbundle.length > 0){
srcText += '&appbundle=' + encodeURIComponent(appbundle);
}
if(platformv.length > 0){
srcText += '&platformv=' + encodeURIComponent(platformv);
}
script.src =srcText;
if(div != null){
div.appendChild(script);
}
})();
</script>

広告リダイレクトの対応

配信される広告のタップ動作によって、外部のサイトへ移動したり AppleStoreのリンクなどを開けるようにする。 サンプルではドメインによって、外部サイトを判定しています。

func configureWebView() {
let configuration = WKWebViewConfiguration()
...(中略)...

// jsのコンテンツを差し込むことで、idfaやappbundleをjsから取得できるようにする
userContentController = WKUserContentController()
configuration.userContentController = userContentController

...(中略)...
}
func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction, decisionHandler: @escaping (WKNavigationActionPolicy) -> Void) {
// URL遷移時に呼ばれる
guard let url = navigationAction.request.url else {
decisionHandler(.allow)
return
}

let currentDomain = webView.url?.host
let targetDomain = url.host

if handleClick(url: url, currentDomain: currentDomain, targetDomain: targetDomain, navigationAction: navigationAction) {
decisionHandler(.cancel)
} else {
decisionHandler(.allow)
}
}

func webView(_ webView: WKWebView, createWebViewWith configuration: WKWebViewConfiguration, for navigationAction: WKNavigationAction, windowFeatures: WKWindowFeatures) -> WKWebView? {
// window.openの時などに呼ばれる
print("createWebViewWithConfiguration")
guard let url = navigationAction.request.url else {
return nil
}
let currentDomain = webView.url?.host
let targetDomain = url.host

if handleClick(url: url, currentDomain: currentDomain, targetDomain: targetDomain, navigationAction: navigationAction) {
print("URL opened in SFSafariViewController.")
}
return nil
}

func handleClick(url: URL, currentDomain: String?, targetDomain: String?, navigationAction: WKNavigationAction) -> Bool {
// http(s) 以外のプロトコル: 他のアプリへ移動する場合
if !url.absoluteString.hasPrefix("http://") && !url.absoluteString.hasPrefix("https://") && UIApplication.shared.canOpenURL(url) {
print("NOT HTTP/HTTPS : \(url.absoluteString)")
UIApplication.shared.open(url, options: [:], completionHandler: nil)
return true
}

guard let currentDomain = currentDomain, let targetDomain = targetDomain else {
return false
}

// hrefが指定された場合、新しいwindowで開こうとしている場合
// 現在のドメインとは別のドメインのページを開こうとしている場合
// 外部サイトへの遷移としてSFSafariViewで表示する。
if (navigationAction.navigationType == .linkActivated || navigationAction.targetFrame == nil) && currentDomain != targetDomain {
// SFSafariView
let safariViewController = SFSafariViewController(url: url)
present(safariViewController, animated: true, completion: nil)
return true
}
return false
}

動画の再生

広告内に動画が流れることがあります。インライン・自動再生を許可してください。

let configuration = WKWebViewConfiguration()

// インライン再生を許可
configuration.allowsInlineMediaPlayback = true
// すべてのメディアについてユーザインタラクションなしの自動再生を許可
configuration.mediaTypesRequiringUserActionForPlayback = []