Warning: include(/home/users/2/lolipop.jp-a-virtual/web/dhmo/dhmo/wp-content/advanced-cache.php): failed to open stream: No such file or directory in /home/users/2/lolipop.jp-a-virtual/web/dhmo/dhmo/wp-settings.php on line 74

Warning: include(/home/users/2/lolipop.jp-a-virtual/web/dhmo/dhmo/wp-content/advanced-cache.php): failed to open stream: No such file or directory in /home/users/2/lolipop.jp-a-virtual/web/dhmo/dhmo/wp-settings.php on line 74

Warning: include(): Failed opening '/home/users/2/lolipop.jp-a-virtual/web/dhmo/dhmo/wp-content/advanced-cache.php' for inclusion (include_path='.:/usr/local/php/5.4/lib/php') in /home/users/2/lolipop.jp-a-virtual/web/dhmo/dhmo/wp-settings.php on line 74
android webview実装方法のまとめ – Androidアプリつくったった

android webview実装方法のまとめ

html share

◇Webviewを使いこなそう

Webviewについては、ディベロッパーとして一番最初にリリースした
Webcaptureをはじめ、何度か取り組んだ課題なので
今回も使い方の紹介・ソースの公開を行っていきます。

◇Webview基本的な使い方

1>>最初のゴールは特定のwebページ(Google)の表示とします。

まずは基本からといいつつ結構忘れる人がいるのがパーミッションです。
ソースは以上がないのに動かない』と言われたら『マニフェストファイル』を見てあげましょう。

Androidで開発、実装する際は次の手順で制作するとミスが少なくなります。
① manifestファイルの設定
② XMLファイルでレイアウト(idの設定)(+res/asset/lib内のファイルの準備)
③ Javaでの実装

ソースの実装方法に話を戻します。
いまはWebページが見られれば良いので必要なのはINTERNETだけなので追加するのは一行です。
>>Manifest.permissionのINTERNETの公式ドキュメントはコチラ

・Manifestファイル

<uses-permission android:name="android.permission.INTERNET"/>

・XMLファイル
setContentView(webview); でもいいのですが
ここは今後の汎用性も考えてレイアウトファイルを用いて
setContentView(R.layout.main);
といった指定で作成していくことにします。

<!--?xml version="1.0" encoding="utf-8"?-->

<?xml version="1.0" encoding="utf-8"?>
<WebView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/webview"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
/>

◎webViewを素早く表示するためには
いかにサイズ計算の負荷を少なくするかがポイントになってきます。
下記のような書き方にすると、ボタンなどを配置した後の余ったスペースを
がwebviewのサイズとなり計算がシンプルになります。
広告などが入れる時にも手間いらずなのでオススメです。

    <WebView
        android:id="@+id/webView1"
        android:layout_width="match_parent"
        android:layout_height="0dip"
        android:layout_weight="1" />

・Javaファイル
webviewを指定して読ませるだけです。
以下のようになります。

	WebView web= (WebView) findViewById(R.id.webview);
        web.loadUrl("http://www.google.com");

応用:ローカルファイルの表示

    web.loadUrl("file:///android_asset/hoge.html");

まずはここまでで実行してみましょう。

ページが表示された・・・アレっとなりませんでしたか?

そうです。Googleのロゴが表示されません。
なぜかというとGoogleのロゴ部分は現在javascriptで表示されているからです。

javascriptを有効にする方法は次の通りです。
有効化の設定をweb.loadUrl(“http://www.google.com”);の前に入れます。
ページ読み込んでから設定しても動作しません。

ページの表示に関してはここが初めのゴールです。

ソースは以下のようになります。

WebView web= (WebView) findViewById(R.id.webview);
               //対象のWebivewを取得して設定を有効化
	    web.getSettings().setJavaScriptEnabled(true);
               //その後、ページをロードします。
web.loadUrl("http://www.google.com");

応用:javascriptを使ってandroidとwebページとの連携する
①HTML側にjavascriptで関数を作っておいてjavaファイルから呼び出す方法
javaファイルから直接、javascriptに定義された関数を呼び出します。
・html側

<script type="text/javascript">// <![CDATA[
function showMessage(msg)
{
 document.write('メッセージは'+msg+'です');
}
// ]]></script>

・javaファイル側
javascriptを有効にしてから目的の関数を呼び出します。

WebView web= (WebView) findViewById(R.id.webview);
	    web.getSettings().setJavaScriptEnabled(true);
web.loadUrl("javascript:showMessage('Hello HTML!');");

② javaファイルでjavascriptの関数を実行する方法
javaファイル上に関数を書いて実行
・javaファイル

WebView web= (WebView) findViewById(R.id.webview);
	    web.getSettings().setJavaScriptEnabled(true);
webView.loadUrl("javascript:alert('javaファイルからの実行です');");

③ HTMLからandroid上の関数を呼び出す方法
自分の所有するwebサービスとの連携させる応用も可能となります。
特定のページでandroidアプリだけ別動作といったことも可能です。

コチラの公式ページ(Building Web Apps in WebView)からの引用ですが、
JavaScriptInterfaceを利用することで、HTMLファイルからandroidを呼び出すことが可能です。
具体的には以下のように実装します。

・javaファイル①(引用)
JavaScriptInterfaceのインターフェースで呼び出す関数を定義します。

public class JavaScriptInterface {
Context mContext;

/** Instantiate the interface and set the context */
JavaScriptInterface(Context c) {
mContext = c;
}

/** Show a toast from the web page */
public void showToast(String toast) {
Toast.makeText(mContext, toast, Toast.LENGTH_SHORT).show();
}
}

・javaファイル②(引用)

    WebView web = (WebView) findViewById(R.id.webview);
            web.addJavascriptInterface(new JavaScriptInterface(this), "Android");

・HTMLファイル(引用)
ボタンを押すとToastがふわっとでる仕様にします。

<input onclick="showAndroidToast('Hello Android!')" type="button" value="Say hello" />
<script type="text/javascript">// <![CDATA[
function showAndroidToast(toast) {
 Android.showToast(toast);
}
// ]]></script>

とりあえず指定のURLの表示ができましたのでどんどん便利な機能をつけていきましょう。

◇拡大/縮小したい

現在、HPの新規の製作では当たり前のようにスマホ対応を頂きますが、
まだまだ対応していないが多数派です。

そうなるとスマホでは小さくて見えなくなります。
拡大があったら便利だなと思うわけです。

・拡大コントローラの実装
拡大の実装はただの既存の関数に設定通知するだけでOKです。
実装はこんな感じです。

・javaファイル

     WebView web = (WebView) findViewById(R.id.webView1);
             web.getSettings().setJavaScriptEnabled(true);
             web.getSettings().setBuiltInZoomControls(true);

◎応用オリジナルの拡大・縮小をつけたくなった。
WebViewクラスには、zoomIn(),zoomOut(),resetZoom()というメソッドが
用意されているのでこれを利用してみる。

まず、レイアウトXMLでボタンを3つ作って、idをふる
(わかりやすくzoom_in,zoom_out,resetとした)
javaファイル側は以下のようにするとボタンタップで
拡大・縮小が別々のボタンとして実装できる。
※クラスにはimplements OnClickListenerを忘れずに

   public void onClick(View v) {
        if (v == zoom_in){
            webview.zoomIn();
        }else if (v == zoom_out){
            webview.zoomOut();
        }else if (v == reset){
            webview.resetZoom();
        }

◇進む・戻る・検索の実装

検索は
進む戻るは、これ以上戻れない場合と、これ以上進めない場合があるので
まず進む、戻るの可否を確認してから処理を実行させます。
ボタンで実装したソースは以下のようになります。
※クラスにはimplements OnClickListenerを忘れずに

・javaファイル

    if (v == b_go) {
        String url = urlbox.getText().toString();
        web.loadUrl(url);
    } else if (v == b_prev) {
       if(webView.canGoBack()){
           web.goBack();
       }
   } else if (v == b_next) {
       if(webView.canGoForward())
       web.goForward();
   }

・応用 戻れないケースへの対処
ここのサイトで詳しく書いてあるが
実は上記のような教科書通りの記述だともどれないケースがあります。
そんな時は下記のように記載することで問題は回避できます。

    if (webview.canGoBack()) {
        webview.goBackOrForward(-2);
    }

◇遷移しても標準ブラウザに行かないようにする設定

googleのトップページが表示されているので検索を押してみたひともいると思うが
今の状態でloadUrl で読み込んだページ内のリンクをクリックすると、
(検索すると)標準のブラウザ(初期はbrower:chromeLite)が起動して先のページはそっちで表示される。
自分の WebView で遷移先も表示させるには,以下のようにWebViewClientを設定する必要があります。
まとめると以下のようになります。

・javaファイル(onCreate()内)

        WebView	web = (WebView) findViewById(R.id.webView1);
		web.getSettings().setJavaScriptEnabled(true);
		web.getSettings().setBuiltInZoomControls(true);
		web.addJavascriptInterface(this, "activity");
		// そこでリンクしてもアプリ内で遷移する(アプリ内に閉じ込めておく)
		web.setWebViewClient(new WebViewClient());
		web.loadUrl("https://www.google.co.jp/");

◇ブラウザの回転対策と値の保持

androidでは、実記を傾けるとあら不思議、ブラウザの入力値が
いったん破棄されます。
傾かないようにレイアウトを固定してしまうのも手ですが
(android:screenOrientation=”portrait”とか)
ブラウザに関しては傾けて利用するのも便利なので回転にも対応できるようにしましょう。
ブラウザが傾いたときに値を保存する部分と、保存した値があるときに呼び出す部分があれば
よいことになります。今までのこともふまえると以下のようなソースになります。

回転対策①


	if (savedInstanceState != null){
		setContentView(R.layout.main);
		web = (WebView) findViewById(R.id.webView1);
		web.getSettings().setJavaScriptEnabled(true);
		web.getSettings().setBuiltInZoomControls(true);
		web.addJavascriptInterface(this, "activity");
		// そこでリンクしてもアプリ内で遷移する(アプリ内に閉じ込めておく)
		web.setWebViewClient(new WebViewClient());
		web.restoreState(savedInstanceState);
		return;
	}

回転対策②
その外側に以下を記載します。


	@Override
	protected void onSaveInstanceState(Bundle outState) {
		web.saveState(outState);
	}

◇検索窓にフォーカスを当てる

urlからの検索ができるようにwebviewとは別に検索ボックスをつけると
webview上の検索窓にフォーカスが行かなくなります。
それを回避するためには下記のように読み込み完了後に改めて
フォーカスを設定してあげます。

※私はonResume()にしましたが、
確実に読み込み完了後となっていればどこに記載してもかまいません

	protected void onResume() {
		super.onResume();
		// 入力フォーム選択時にフォーカスを当てる
		web.requestFocus(View.FOCUS_DOWN);
	}

だいたい基本的な所ではこんな感じでしょうか。

それでは、まとまったソースを紹介します。
これは、HTML SOUCEに実際に使われているソースです。
※バージョンアップにより現在のソースと異なる部分があります。
※今回の解説に関係ない入力補完やソース解析の部分は公開しておりません。
希望の方はお問い合わせくださいませ

<< メインのActivity >>

インポートの記述は省いています。
また今回の記事の内容とは関係ない部分のソース

public class HTMLActivity extends Activity implements OnClickListener {
	private Handler handler = new Handler();
	WebView web;
	private ImageButton b_prev;
	private ImageButton b_go;
	private ImageButton b_next;
	private MultiAutoCompleteTextView urlbox;

	@Override
	public void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		// タイトルバーにプログレスアイコンを表示可能にする
		requestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS);
		setContentView(R.layout.main);
		b_prev = (ImageButton) findViewById(R.id.imageButton1);
		b_next = (ImageButton) findViewById(R.id.imageButton3);
		b_go = (ImageButton) findViewById(R.id.imageButton2);
		b_prev.setOnClickListener(this);
		b_next.setOnClickListener(this);
		b_go.setOnClickListener(this);
		ArrayAdapter adapter = new ArrayAdapter(this,
				android.R.layout.simple_dropdown_item_1line, getResources()
						.getStringArray(R.array.sitenames));
		urlbox = (MultiAutoCompleteTextView) findViewById(R.id.multiAutoCompleteTextView1);
		urlbox.setAdapter(adapter);
		urlbox.setTokenizer(new UrlTokenizer());
		//回転対策①
		if (savedInstanceState != null){
			setContentView(R.layout.main);
			web = (WebView) findViewById(R.id.webView1);
			web.getSettings().setJavaScriptEnabled(true);
			web.getSettings().setBuiltInZoomControls(true);
			web.addJavascriptInterface(this, "activity");
			// そこでリンクしてもアプリ内で遷移する(アプリ内に閉じ込めておく)
			web.setWebViewClient(new WebViewClient());
			web.restoreState(savedInstanceState);
			return;
			}
		web = (WebView) findViewById(R.id.webView1);
		web.getSettings().setJavaScriptEnabled(true);
		web.getSettings().setBuiltInZoomControls(true);
		web.addJavascriptInterface(this, "activity");
		// そこでリンクしてもアプリ内で遷移する(アプリ内に閉じ込めておく)
		web.setWebViewClient(new WebViewClient());
		web.loadUrl("https://www.google.co.jp/");
		ImageButton button = (ImageButton) findViewById(R.id.share);
		button.setOnClickListener(this);
	}
	@Override
	protected void onResume() {
		super.onResume();
		// 入力フォーム選択時にフォーカスを当てる
		web.requestFocus(View.FOCUS_DOWN);
	}
	int i=0;
	public void viewSource(final String src) {

		handler.post(new Runnable() {
			@Override
			public void run() {
				if(i==0){
				Intent sendm1 = new Intent(Intent.ACTION_SEND);
				sendm1.setType("text/plain");
				sendm1.putExtra(Intent.EXTRA_TEXT, src);
				startActivity(Intent.createChooser(sendm1,
						getString(R.string.share_dialog_title)));
				i++;
				}
			}
		});
	}
	//回転対策②
	@Override
	protected void onSaveInstanceState(Bundle outState) {
		web.saveState(outState);
	}

	@Override
	public void onClick(View v) {
                if (v == b_go) {
			String url = urlbox.getText().toString();
			web.loadUrl(url);
		} else if (v == b_prev) {
			if(webView.canGoBack()){
			//web.goBack();
webview.goBackOrForward(-2);
                        }
		} else if (v == b_next) {
			if(webView.canGoForward())
			web.goForward();
		}
       }
}

レイアウトのXMLファイルです。
このページの解説に含まれていない部分は上記のjavaファイルでは
割愛されているため、その部分をのぞいて参考にしてください。

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:id="@+id/LinearLayout1"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical" >
	<LinearLayout
	android:id="@+id/linearLayout1"
	android:layout_width="match_parent"
	android:layout_height="wrap_content">
		<ImageButton
		android:id="@+id/imageButton1"
		android:layout_width="44dp"
        android:layout_height="44dp"
		android:src="@android:drawable/ic_media_previous">
		</ImageButton>
		<MultiAutoCompleteTextView
		android:id="@+id/multiAutoCompleteTextView1"
		android:layout_width="wrap_content"
		android:text="http://"
		android:layout_weight="1"
		android:layout_height="match_parent"
		android:inputType="textUri">
		</MultiAutoCompleteTextView>
		<ImageButton
        android:layout_width="44dp"
        android:layout_height="44dp"
		android:id="@+id/imageButton2"
		android:src="@android:drawable/ic_menu_search">
		</ImageButton>
		<ImageButton
        android:layout_width="44dp"
        android:layout_height="44dp"
		android:id="@+id/imageButton3"
		android:src="@android:drawable/ic_media_next">
		</ImageButton>
	</LinearLayout>
    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content" >
        <ImageButton
            android:id="@+id/setting"
            android:layout_width="44dp"
            android:layout_height="44dp"
            android:onClick="onClick"
            android:src="@android:drawable/ic_menu_preferences" />
        <ImageButton
            android:id="@+id/share"
            android:layout_width="44dp"
            android:layout_height="44dp"
            android:onClick="onClick"
            android:src="@android:drawable/ic_menu_share" />

        <ImageButton
            android:id="@+id/mail"
            android:layout_width="44dp"
            android:layout_height="44dp"
            android:onClick="onClick"
            android:src="@android:drawable/ic_dialog_email" />
        <ImageButton
            android:id="@+id/capture"
            android:layout_width="44dp"
            android:layout_height="44dp"
            android:onClick="onClick"
            android:src="@android:drawable/ic_menu_crop" />

        <ImageButton
            android:id="@+id/btn_help"
            android:layout_width="88dp"
            android:layout_height="44dp"
            android:onClick="onClick"
            android:src="@drawable/btn_help" />

    </LinearLayout>

    <WebView
        android:id="@+id/webView1"
        android:layout_width="match_parent"
        android:layout_height="0dip"
        android:layout_weight="1" />

</LinearLayout>

以上です。

まだ載せきれていない事項がたくさんあるので機会があれば
また書いて行きたいと思います。

参考になれば幸いです。


About the Author

dhmo
Author:DHMO(ディベロッパー名) 仕事では自社サービス・メディアの開発を行ってます。 趣味でAndroidアプリ製作を行っています。 カラオケではランキングバトルにはまっております。 Mail: dihydromooxide7@gmail.com 

Be the first to comment on "android webview実装方法のまとめ"

Leave a comment

Your email address will not be published.


*