본문 바로가기
Android

<Kotlin 코틀린> 안드로이드 WebView(웹뷰) window.open 새창 처리하기 (옆에 짤림 해결)

by 일용직 코딩노동자 2021. 11. 10.
728x90
반응형

자바가 필요하신 분께서는

https://onedaycodeing.tistory.com/62

 

안드로이드 하이브리드앱 새창 Popup(팝업)창 띄우기 및 닫기

하이브리드 앱을 진행하면서 Webview를 통해 페이지를 띄웁니다. 진행을 하다보면 스크립트(Javascript)딴에서 window.open으로 새창(팝업)을 띄웁니다. 이걸 안드로이드(네이티브)딴에서 뒤로가기나 다

onedaycodeing.tistory.com

이쪽 게시글로 가주세요!

 

lateinit var mContainer : FrameLayout
lateinit var mWebView : WebView
lateinit var mWebViewPop : WebView
lateinit var mWebSettings : WebSettings

우선 이렇게 선언을 해주었습니다.

 

XML은 

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity"
    android:orientation="vertical"
    android:id="@+id/rootview">

    <FrameLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:id="@+id/webview_frame">

        <WebView
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:id="@+id/webView">
        </WebView>

    </FrameLayout>

</androidx.constraintlayout.widget.ConstraintLayout>

이렇게 설정해줬습니다.

 

제가 기본적으로 사용하는 웹뷰 셋팅입니다.

 

fun layoutInit() : Unit {
        mContainer = findViewById(R.id.webview_frame)
        mWebView = findViewById(R.id.webView)
        mWebViewPop = findViewById(R.id.webView)

        mWebView.dispatchWindowFocusChanged(true)
        mWebView.webViewClient = WebViewClient()
        mWebView.isScrollbarFadingEnabled = true
        mWebView.scrollBarStyle = WebView.SCROLLBARS_OUTSIDE_OVERLAY
        mWebView.webViewClient = WebViewClientClass()
        mWebView.webChromeClient = WebChromeClient()
        mWebView.addJavascriptInterface(AndroidBridge(),"GIFT")

        mWebSettings = mWebView.settings
        mWebSettings.javaScriptEnabled = true
        mWebSettings.setSupportMultipleWindows(true)
        mWebSettings.javaScriptCanOpenWindowsAutomatically = true
        mWebSettings.domStorageEnabled = true
        mWebSettings.setSupportZoom(true)
        mWebSettings.displayZoomControls = true
        mWebSettings.loadsImagesAutomatically = true
        mWebSettings.useWideViewPort = true
        mWebSettings.mixedContentMode = WebSettings.MIXED_CONTENT_NEVER_ALLOW
        mWebSettings.allowFileAccess = true
        mWebSettings.textZoom = 100
        mWebSettings.cacheMode = WebSettings.LOAD_DEFAULT
        mWebSettings.setRenderPriority(WebSettings.RenderPriority.HIGH)
        mWebSettings.layoutAlgorithm = WebSettings.LayoutAlgorithm.SINGLE_COLUMN
        mWebSettings.setEnableSmoothTransition(true)
        mWebSettings.loadWithOverviewMode = true
        mWebSettings.builtInZoomControls = true

        if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP){
            WebView.setWebContentsDebuggingEnabled(true)
            mWebView.setLayerType(View.LAYER_TYPE_HARDWARE, null)
        }
        else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
            WebView.setWebContentsDebuggingEnabled(true)
            mWebView.setLayerType(View.LAYER_TYPE_HARDWARE, null)
        }
        else if (Build.VERSION.SDK_INT < Build.VERSION_CODES.KITKAT) {
            mWebView.setLayerType(View.LAYER_TYPE_SOFTWARE, null)
        }
    }

결정적으로 새창을 처리하는데는

 

mWebSettings.javaScriptEnabled = true
mWebSettings.setSupportMultipleWindows(true)
mWebSettings.javaScriptCanOpenWindowsAutomatically = true

해당 3줄이 제일 중요한 역할입니다.

 

이렇게까지 하신 후에 이제 onCreate 로 돌아오세요.

 

mWebView.webChromeClient = object : WebChromeClient(){
      override fun onCreateWindow(view: WebView?, isDialog: Boolean, isUserGesture: Boolean, resultMsg: Message?): Boolean {
        Log.d("로그 ","onCreateWindow")
        mWebViewPop = WebView(this@MainActivity).apply {
          webViewClient = WebViewClient()
          settings.javaScriptEnabled = true
        }
        mContainer.addView(mWebViewPop)
        
        mWebViewPop.webChromeClient = object : WebChromeClient() {
        override fun onCloseWindow(window: WebView?) {
          Log.d("로그 ","onCloseWindow")
          mContainer!!.removeView(window)
          window!!.destroy()
      	}
  }
      (resultMsg?.obj as WebView.WebViewTransport).webView = mWebViewPop
      resultMsg.sendToTarget()
      return true
      }
 }

웹딴에서 widow.open 을 호출하면 네이티브에 있는 onCreateWindow 가 호출됩니다.

 

처음에 만들어둔 mWebViewPop 에 새창에 대한 정보를 담아주고 

프레임레이아웃에 addView 해주는 방식으로 전체화면에 새창이 뜬것 같은 효과를 보입니다.

 

다이얼로그로 해봤으나 양쪽 화면이 짤리는 증상이 있어서 다른 방식으로 개선 해보았습니다.

 

웹에서 window.close 를 호출하면 네이티브의 onCloseWindow가 호출됩니다.

프레임 레이아웃을 remove해준 다음 

window!!.destroy 해줍니다. (안해주면 이후에 팝업이 앱을 재시동 걸기 전까지 안열리는 증상이 있었습니다.)

 

할때는 삽질했는데 완성하고 보니 몇줄 없네요..

 

 

728x90
반응형

댓글