13
10

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

Ionic3でInAppBrowserを使ってみる

Last updated at Posted at 2018-12-12

はじめに

最近ionic3を触る機会があり、その中でWebViewを実装することがありました。
が、基本的にionicのドキュメントは英語のみ、問題が起こってもほとんどstackoverflowとかgithubのissueを見て解決しなければならない…といった具合になかなか思うように進まず苦しい思いをしました:sob:
そこで今回は、実際にionicでWebViewを実装する際に調べたことを共有していこうと思います。

注意事項

ionicがどういったもの?、Cordova、WebViewって?といったことは省略させていただきます💦
またNode.js, ionic, cordova等のインストールが済んでいる前提で進めていきます。

InAppBrowserとは

Launches in app Browser

ionicのアプリ内でwebページを開くための機能になります。(そのまんま)

インストール

$ ionic cordova plugin add cordova-plugin-inappbrowser
$ npm install --save @ionic-native/in-app-browser

プラグインとモジュール両方のインストールが必要です!
ちなみに僕は上記コマンドのどちらかでいいんだろうなと勝手に判断してnpm install npm install --save @ionic-native/in-app-browserのほうだけやったら一応webページが表示されるのですが、後に出てくるtarget_blankを設定しても意図した動きをしてくれませんでした:sweat:
後にプラグインのインストールが必要とわかり入れたところ、うまく動くようになりました。
(cordovaがベースとあるんですから当然ですね…:dizzy_face:)

初期設定

以下のようにapp.module.tsに追加していきます。

app.module.ts
import { InAppBrowser } from "@ionic-native/in-app-browser"; // ← 追加!

@NgModule({
    (省略)
    providers: [
        StatusBar,
        SplashScreen,
        { provide: ErrorHandler, useClass: IonicErrorHandler },
        InAppBrowser // ← 追加!
    ]
})

使い方

表示させたいコンポーネントファイルに以下のように実装していきます。
※今回の例ではngOnInitに実装してますが、イベント発火時でも実装できます。そこはよしなに:v:

hoge.ts

import { Component, OnInit } from '@angular/core';
import { IonicPage, NavController, NavParams } from 'ionic-angular';
import { InAppBrowser } from "@ionic-native/in-app-browser"; // ← 追加!

@IonicPage()
@Component({
    selector: 'page-hoge',
    templateUrl: 'hoge.html',
})
export class hogePage implements OnInit {

    constructor(
        public navCtrl: NavController,
        public navParams: NavParams,
        private inAppBrowser: InAppBrowser // ← 追加!
    ) { }

    ngOnInit() {
        const browser = this.inAppBrowser.create('https://hogehoge.com', '_blank', { location: "no", zoom: "no"});
    }
}

では順に実際に処理を見ていきましょう:kissing_closed_eyes:

InAppBrowser.create( url, target, options)

このメソッドで実際にInAppBrowserのインスタンスを生成し同時にwebページの表示まで行います
引数は以下の通り

引数 詳細
url string 表示するページのURL
target string URLを表示させるブラウザを指定できる。ターゲットに関しては後述。デフォルトでは_self
options InAppBrowserOptions InAppBrowserのオプション。デフォルトはlocation= "yes"
optionsInAppBrowserOptions型に関して、オプションを直接引数に渡すのであれば例のように{location: "yes"}で問題ないのですが、例えば変数に切り出して実装したいというときに型の指定で必要になります。
hoge.ts
// InAppBrowserOptionsを追加!
import { InAppBrowser, InAppBrowserOptions } from "@ionic-native/in-app-browser";

(省略)

const url: string = 'https://hogehoge.com';
const target: string = '_blank';
const options: object = { ... }; // ← コンパイルエラー
const options: InAppBrowserOptions = { ... }; // ← OK

const browser = this.inAppBrowser.create(url, target, options);

targetについて

webページを表示するターゲットは3種類あります。

ターゲット 詳細
_self URLがホワイトリストに追加されている場合はcordova browserで、それ以外ではInAppBrowserのブラウザで開く
_blank InAppBrowserのブラウザで開く
_system システム標準のブラウザを開く(chrome, safari等)

例えばAndroidでwebページをchromeを立ち上げずにアプリ内で開きたいという場合には_blankを使用します。
また後で説明しますがexecuteScript()は**_blankでしか実行することができません。
_selfでもできました💦
(すみません、insertCSSは未確認です…。💦確認次第反映させます。)

InAppBrowserのメソッド

create(url , target, options)

先ほども説明しましたが、URLtargetoptionsを設定して実際にwebページを表示させます。

show()

InAppBrowserウィンドウを表示させます。既に表示されている場合は表示されません。

close()

現在表示されているInAppBrowserを非表示にします。既に非表示の場合は何もしません。

executeScript(script)

戻り値:Promise< any >

InAppBrowserに実行するJavascriptのコードを注入します。
引数はobject型で渡します。コードを直接書けますし、外部ファイルを読み込ませることも可能です。
executeScript()を使用する場合はcreate(url, target, options)target_blankである必要があります。
_selfでもできました💦

executeScript({code: "alert('Hello Ionic!');"});

insertCSS(css)

戻り値:Promise< any >

InAppBrowserウィンドウにCSSを注入します。
executeScriptのCSS版と思っていただいて大丈夫です。こちらも同じようにコードまたは外部ファイルを使用することができます。

on(event)

戻り値:Observable< InAppBrowserEvent >

InAppBrowserのイベントによって処理のタイミングを設定します。
イベントは4種類用意されています。

Param Details
loadstart ページの読み込みが始まったら
loadstop ページの読み込みが終わったら
loaderror ページの読み込み中にエラーが起きたら
exit ブラウザを閉じたら

InAppBrowserOptions

InAppBrowser.createのoptionsに設定できるプロパティです。
が、長いのでゆっくり更新していきます:sob:
Ionic InAppBrowser Options
※一部は直訳していたり適当に書いている部分もありますが許してください!なんでもしますから!

Param Type Details OS
location 'yes' or 'no' InAppBrowserのロケーションバーの表示、非表示を設定する。(任意設定)
hidden 'yes' or 'no' (任意設定)
clearcache 'yes' yesを設定すると新しいウィンドウを開くときにクッキーとキャッシュをクリアする。
clearsessioncache 'yes' (任意設定)
closebuttoncaption string (任意設定)
closebuttoncolor string (任意設定)
zoom 'yes' or 'no' ブラウザのズームコントロールの表示非表示を設定する。デフォルトはyes Android
hardwareback 'yes' or 'no' (任意設定)
mediaPlaybackRequiresUserAction 'yes' or 'no' yesに設定するとHTML5オーディオまたはビデオが自動再生されなくなる。デフォルトはno
hidenavigationbuttons 'yes' or 'no' (任意設定)
hideurlbar 'yes' or 'no' (任意設定)
navigationbuttoncolor string (任意設定)
toolbarcolor string (任意設定)
shouldPauseOnSuspend 'yes' or 'no' InAppBrowser WebViewでバックグラウンドオーディオを停止するためにアプリを一時停止/再開させるにはyesに設定する。 ※GooglePlayで利用規約違反になる問題があるため。 Android
footer 'yes' or 'no' yesに設定すると、iOSの完了ボタンと同様にフッターに閉じるボタンが表示される。そのためclosebuttoncaptionclosebuttoncolorを使用してプロパティを設定する。 Android
footercolor 'string' # 00ff00などの有効な16進数の文字列に設定するとフッターの色がデフォルトから変更される。footeryesに設定している場合のみ適用される。 Android
disallowoverscroll 'yes' or 'no' UIWebViewBounce(rubber-band)を使用するか設定する。 iOS
toolbar 'yes' or 'no' InAppBrowserのツールバーの表示、非表示を設定する。デフォルトはyes iOS
toolvartranslucent 'yes' or 'no' ツールバーを半透明にするかしないかを設定する。ツールバーが設定されているときのみ。デフォルトはyes iOS
enableViewportScale 'yes' or 'no' メタタグによるビューポートの拡大縮小を防止する。 iOS
allowInlineMediaPlayback 'yes' or 'no' (任意設定) -
keyboardDisplayRequiresUserAction 'yes' or 'no' Javascriptのfocus()呼び出しでフォーカスが当たったときにキーボードを開くにはyesを設定する。 iOS
suppressesIncrementalRendering 'yes' or 'no' レンダリングする前に全ての表示内容が受信されるまで待機する。デフォルトはno iOS
presntationstyle 'pagesheet' or 'formsheet' or 'fullscreen' プレゼンテーションスタイルを設定する。デフォルトはフルスクリーン iOS
transitionstyle 'fliphorizontal' or 'crossdissolve' or 'coververtical' トランジションスタイルを設定する。デフォルトはcoververtical ここわかりやすい iOS
toolbarposition 'top' or 'bottom' ツールバーの位置を設定する。デフォルトは下 iOS
hidespinner 'yes' or 'no' ローディングインジケーターの表示、非表示を設定する。 iOS
fullscreen 'yes' (任意設定)
useWideViewPort 'yes' or 'no' viewportHTMLメタタグのサポートの有効無効を設定する。yesでページにビューポートメタタグが含まれる場合、指定された幅の値が適用される。ページにメタタグが無いか、幅が指定されていない場合はワイドビューポートが適用される。デフォルトはyes Android

ユースケース

ネイティブ側でCognitoを利用しサインインまでを行い、サインイン完了後以降はCloudFrontにあるページをWebviewで表示したい。

この時、サインインで取得したトークンをWebViewのページに渡すにはどうしたらよいでしょうか?
このケースのようにネイティブからWebviewへ値を渡したいときは**executeScript()**を利用します:laughing:

実装例はこちら

hoge.ts

const browser = this.inAppbrowser.create(url, target, options);
browser.on('loadstop').subscribe(event => {
    browser.executeScript({ code: "sessionStorage.setItem('hoge', 'piyopiyo');"});
});

まず基本であるcreateをします。繰り返しますがtarget_blankで設定してください。
次にイベントを設定します。表示先webページの読み込みが完了したら指定したJavascript、ここではSessionStorageに値を入れる処理をしていますが、これを実行します。
こうすることで、ネイティブ側で保持している値をWebview側に渡すことが出来ます。
※ちなみにon().subscribe()は**Android端末またはiOS端末でしか動作しません。**ブラウザで動作を確認しようとするとエラーが出ます。

余談ですが僕は実装当初

browser.executeScript({ code: `SessionStorage.setItem('hoge, ${this.hoge}');`});

このようなことをしていましたがうまく値渡しができませんでした。いろいろ調べてはみたのですがどれも解決に至らず…。
約1日ほど悩みました。が、なんと

browser.executeScript({ code: `SessionStorage.setItem('hoge', '${this.hoge}');`});

このように${}をシングルクォーテーション囲んでいなかったのが原因でした。
こんなのにハマって1日無駄にしたのが情けない情けない…。
もしかしたら僕以外にハマる方がいらっしゃるかもしれないので一応これも共有しておきます…。

さいごに

エンジニアが学ぶべき言語は英語(確信)

参考リンク

Ionic native InAppBrowser
apache/cordova-plugin-inappbrowser github
※あとから追記していきます。

13
10
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
13
10

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?