반응형
private void onWebViewSet() {
wvMainWebview.addJavascriptInterface(new AndroidBridge(), Common.ANDROID_BRIDGE_NAME);
wvMainWebview.setWebViewClient(new mMainWebviewClient());
wvMainWebview.setWebChromeClient(new mMainWebChromeClient());
}
JavascriptInterface
AndroidBridge이름으로 웹과 통신하는 클래스를 만들어줍니다.
이녀석의 역할은 웹에서 앱으로 문자열을 전달합니다. (문자열을 이용해 원하는 기능을 구현할수있습니다.)
private class AndroidBridge {
@JavascriptInterface
public void executeMobile(final String arg) {
mAndroidBridgeHandler.post(new Runnable() {
@Override
public void run() {
//arg를 string type으로 받아와 데이터 처리한다.
}
}
}
}
WebViewClient
페이지가 로드를 시작했을때 , 오류가 났을때, 로드가 완료 했을때 등 ... 현 페이지에 load상태를 알수있다.
private class mMainWebviewClient extends WebViewClient {
private static final String TAG ="mMainWebviewClient";
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
L.i("shouldOverrideUrlLoading(), url : " + url);
setUrlNameAndSetLogListener(url);
if( url.startsWith("http:") || url.startsWith("https:") ) {
return false;
}
if (url.startsWith("tel:")) {
Intent tel = new Intent(Intent.ACTION_DIAL, Uri.parse(url));
startActivity(tel);
return true;
}
else if (url.startsWith("mailto:")) {
String body = "Enter your Question, Enquiry or Feedback below:\n\n";
Intent mail = new Intent(Intent.ACTION_SEND);
mail.setType("application/octet-stream");
mail.putExtra(Intent.EXTRA_EMAIL, new String[]{"email address"});
mail.putExtra(Intent.EXTRA_SUBJECT, "Subject");
mail.putExtra(Intent.EXTRA_TEXT, body);
startActivity(mail);
return true;
}
else if (url.startsWith("intent:")) {
try {
Intent intent = Intent.parseUri(url, Intent.URI_INTENT_SCHEME);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
Intent existPackage = getPackageManager().getLaunchIntentForPackage(intent.getPackage());
if (existPackage != null) {
startActivity(intent);
} else {
Intent marketIntent = new Intent(Intent.ACTION_VIEW);
marketIntent.setData(Uri.parse("market://details?id=" + intent.getPackage()));
startActivity(marketIntent);
}
return true;
} catch (Exception e) {
e.printStackTrace();
}
}
return true;
}
@TargetApi(Build.VERSION_CODES.M)
@Override
public void onReceivedError(WebView view, WebResourceRequest request, WebResourceError error) {
onReceivedError(view, error.getErrorCode(), error.getDescription().toString(), request.getUrl().toString());
}
@SuppressWarnings("deprecation")
@Override
public void onReceivedError(WebView view, int errorCode, String description, String failingUrl) {
String message = getResources().getString(R.string.webview_error_unkown);
switch(errorCode) {
case ERROR_AUTHENTICATION: // 서버에서 사용자 인증 실패
message = getResources().getString(R.string.webview_error_authentication);
break;
case ERROR_BAD_URL: // 잘못된 URL
message = getResources().getString(R.string.webview_error_bad_url);
break;
case ERROR_CONNECT: // 서버로 연결 실패
message = getResources().getString(R.string.webview_error_connect);
break;
case ERROR_FAILED_SSL_HANDSHAKE: // SSL handshake 수행 실패
message = getResources().getString(R.string.webview_error_failed_ssl_handshake);
break;
case ERROR_FILE: // 일반 파일 오류
message = getResources().getString(R.string.webview_error_file);
break;
case ERROR_FILE_NOT_FOUND: // 파일을 찾을 수 없습니다
message = getResources().getString(R.string.webview_error_file_not_found);
break;
case ERROR_HOST_LOOKUP: // 서버 또는 프록시 호스트 이름 조회 실패
message = getResources().getString(R.string.webview_error_host_lookup);
break;
case ERROR_IO: // 서버에서 읽거나 서버로 쓰기 실패
message = getResources().getString(R.string.webview_error_io);
break;
case ERROR_PROXY_AUTHENTICATION: // 프록시에서 사용자 인증 실패
message = getResources().getString(R.string.webview_error_proxy_auttentication);
break;
case ERROR_REDIRECT_LOOP: // 너무 많은 리디렉션
message = getResources().getString(R.string.webview_error_redirect_loop);
break;
case ERROR_TIMEOUT: // 연결 시간 초과
message = getResources().getString(R.string.webview_error_timeout);
break;
case ERROR_TOO_MANY_REQUESTS: // 페이지 로드중 너무 많은 요청 발생
message = getResources().getString(R.string.webview_error_too_many_requests);
break;
case ERROR_UNKNOWN: // 일반 오류
message = getResources().getString(R.string.webview_error_unkown);
break;
case ERROR_UNSUPPORTED_AUTH_SCHEME: // 지원되지 않는 인증 체계
message = getResources().getString(R.string.webview_error_unsupported_auth_scheme);
break;
case ERROR_UNSUPPORTED_SCHEME: // URI가 지원되지 않는 방식
message = getResources().getString(R.string.webview_error_unsupported_scheme);
break;
}
}
@Override
public void onPageStarted(WebView view, String url, Bitmap favicon) {
super.onPageStarted(view, url, favicon);
}
@Override
public void onPageFinished(WebView view, String url) {
super.onPageFinished(view, url);
}
}
string.xml
<string name="webview_error_authentication">서버에서 사용자 인증 실패</string>
<string name="webview_error_bad_url">잘못된 URL</string>
<string name="webview_error_connect">서버로 연결 실패</string>
<string name="webview_error_failed_ssl_handshake">SSL handshake 수행 실패</string>
<string name="webview_error_file">일반 파일 오류</string>
<string name="webview_error_file_not_found">파일을 찾을 수 없습니다</string>
<string name="webview_error_host_lookup">서버 또는 프록시 호스트 이름 조회 실패</string>
<string name="webview_error_io">서버에서 읽거나 서버로 쓰기 실패</string>
<string name="webview_error_proxy_auttentication">프록시에서 사용자 인증 실패</string>
<string name="webview_error_redirect_loop">너무 많은 리디렉션</string>
<string name="webview_error_timeout">연결 시간 초과</string>
<string name="webview_error_too_many_requests">페이지 로드중 너무 많은 요청 발생</string>
<string name="webview_error_unkown">일반 오류</string>
<string name="webview_error_unsupported_auth_scheme">지원되지 않는 인증 체계</string>
<string name="webview_error_unsupported_scheme">URI가 지원되지 않는 방식</string>
WebChromeClient
javascript의 기본적인기능인 alert이나 confirm등을 제어해 ui를 입혀줄수있는 녀석이다.
public class mMainWebChromeClient extends WebChromeClient {
@Override
public void onGeolocationPermissionsShowPrompt(String origin, GeolocationPermissions.Callback callback) {
callback.invoke(origin, true, false);
}
@Override
public void onProgressChanged(WebView view, int progress) {
L.d("onProgressChanged, progress : " + progress);
if ( progress == 100 ) {
showLoading( false );
mEventHandler.removeMessages( Common.HANDLER_WEBVIEW_CONNECTION_CANCEL );
}
}
@Override
public boolean onJsAlert(WebView view, String url, String message, final android.webkit.JsResult result) {
new AlertDialog.Builder(view.getContext())
.setTitle(getText(R.string.notice))
.setTitle("")
.setMessage(message)
.setPositiveButton(android.R.string.ok,
new AlertDialog.OnClickListener() {
public void onClick(DialogInterface dialog, int which) {
result.confirm();
}
})
.setCancelable(false)
.create()
.show();
return true;
}
@Override
public boolean onJsConfirm(WebView view, String url, String message, final JsResult result) {
new AlertDialog.Builder(view.getContext())
.setTitle(getText(R.string.notice))
.setTitle("")
.setMessage(message)
.setPositiveButton(android.R.string.ok,
new AlertDialog.OnClickListener(){
public void onClick(DialogInterface dialog, int which) {
result.confirm();
}
})
.setNegativeButton(android.R.string.cancel,
new AlertDialog.OnClickListener(){
public void onClick(DialogInterface dialog, int which) {
result.cancel();
}
})
.setCancelable(false)
.create()
.show();
return true;
}
}
// 자바 스크립트 사용
webSettings.setjavaScriptEnabled(true);
// mixed content 처리 여부
webSettings.setMixedContentMode(int)
MIXED_CONTENT_ALWAYS_ALLOW
MIXED_CONTENT_COMPATIBILITY_MODE
MIXED_CONTENT_NEVER_ALLOW
// DOM Storage Api 허용 여부
webSettings.setDomStorageEnabled(true);
이 부분이 중요한게 특정 사이트의 경우 메뉴 버튼을 이 API 를 사용하는 경우가 있어 이것을 허용해주지 않으면 버튼을 눌렀는데 반응이 없는 경우가 있다.
예시 > rakuten.co.jp
// 기본 인코딩 설정
webSettings.setDefaultTextEncodingName("UTF-8");
// 웹 뷰에 맞게 출력
webSettings.setLoadWithOverviewMode(true);
webSettings.setUseWideViewPort(true);
// 플러그인 사용
webSettings.setPluginState(PluginState.ON);
// 화면 줌 컨트롤과 제스처를 사용하여 확대
webSettings.setSupportZoom(true);
// 내장 줌 컨트롤 사용
webSettings.setBuildInZoomControls(true);
// 내장 줌 컨트롤 표시 여부
webSettings.setDisplayZoomControls(false);
// 앱 캐시 사용 여부 설정
webSettings.setAppCacheEnabled(true);
// 앱 캐시 크기 설정
webSettings.setAppCacheMaxsize(1024*1024*8);
// 캐시 파일 경로 설정
webSettings.setAppCachePath(path);
// 캐시 방식 설정
webSettings.setCacheMode(WebSettings.LOAD_DEFAULT);
// 암호 저장
webSettings.setSavepassword(true);
// 양식 데이터 저장
webSettings.setSaveFormData(true);
// 웹 뷰 내에서 파일 액세스 활성화
webSettings.setAllowFileAccess(true); API 3
파일에 접근하는 것을 허용
webSettings.getAllowFileAccessFromFileURLs(true); API 16
파일 구성표 URL의 컨텍스트에서 실행중인 JavaScript가 다른 파일 구성표 URL의 콘텐츠에 액세스 할 수 있는지 여부를 가져옵니다.
webSettings.getAllowUniversalAccessFromFileURLS(true); API 16
파일 구성표 URL의 컨텍스트에서 실행되는 JavaScript가 모든 출처의 콘텐츠에 액세스 할 수 있는지 여부를 가져옵니다. 여기에는 다른 파일 구성표 URL의 내용에 대한 액세스가 포함됩니다.
// 마우스 오버를 활성화 하기 위해 Light Touch를 사용 여부 설정
webSettings.setLighttouchEnabled(true);
반응형
'AOS' 카테고리의 다른 글
(안드로이드)오류 - IllegalBlockSizeException DATA_TOO_LARGE_FOR_KEY_SIZE (0) | 2020.03.11 |
---|---|
(안드로이드)recycleview 만들기 1편 (기본) (0) | 2020.02.27 |
(안드로이드) interface를 이용한 ADID 가저오기 (0) | 2020.02.03 |
(공통) 외부에서 앱실행(계속수정중) (0) | 2020.02.03 |
(안드로이드)공유하기 (0) | 2020.01.20 |