Aynı iş parçacığı hatası üzerinde WebView yöntemleri


88

Bir android programım var (web görünümünde Java + html). Javascript'ten Java kodunu arayabilirim. Ancak diğer yol çalışmayı durdurdu (tutulmada güncelledikten sonra).

Yani yapmaya çalıştığım şey bu

  • Bir web görünümü oluşturun (çalıştı)
  • javascript'te AndroidFunction.test () çağrısı; (çalıştı)
  • java test () işlevi çağrısı webView.loadUrl ("javascript: helloBack ()"); (! artık çalışmıyor)

MainActivity'de WebView ile çalışmasına izin vermeye çalıştım ama işe yaramadı.

MainActivity.java

public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        final WebView webView = (WebView)findViewById(R.id.webView);
        webView.getSettings().setJavaScriptEnabled(true);
        webView.setWebChromeClient(new WebChromeClient());
        WebSettings webSettings = webView.getSettings();
        webSettings.setJavaScriptEnabled(true);

        javascr = new Javascript(this, webView);
        webView.addJavascriptInterface(javascr, "AndroidFunction");
        webView.loadUrl("file:///android_asset/www/index.html");

        ....
}

Javascript.java

public class Javascript {   
    Context cont;
    WebView webView;

    Javascript(Context c, WebView w) {
        cont = c;
        webView = w;
    }

    // function called in the javascript by AndroidFunction.test();
    public void test() {
          // Breaking point!!!
        webView.loadUrl("javascript:helloBack()");
    }

Hata:

03-24 11:47:50.103: W/WebView(21026):   at com.android.org.chromium.base.SystemMessageHandler.handleMessage(SystemMessageHandler.java:27)
03-24 11:47:50.103: W/WebView(21026):   java.lang.Throwable: A WebView method was called on thread 'JavaBridge'. All WebView methods must be called on the same thread. (Expected Looper Looper{41ab68f8} called on Looper{41bb70a8}, FYI main Looper is Looper{41ab68f8})

03-24 11:47:50.103: W/WebView(21026):   at android.webkit.WebView.checkThread(WebView.java:2063)
03-24 11:47:50.103: W/WebView(21026):   at android.webkit.WebView.loadUrl(WebView.java:794)
03-24 11:47:50.103: W/WebView(21026):   at com.example.hellobt.Javascript.test(Javascript.java:24)

03-24 11:47:50.103: W/WebView(21026):   at com.android.org.chromium.base.SystemMessageHandler.nativeDoRunLoopOnce(Native Method)
03-24 11:47:50.103: W/WebView(21026):   at com.android.org.chromium.base.SystemMessageHandler.handleMessage(SystemMessageHandler.java:27)
03-24 11:47:50.103: W/WebView(21026):   at android.os.Handler.dispatchMessage(Handler.java:102)

03-24 11:47:50.103: W/WebView(21026):   at android.os.Looper.loop(Looper.java:137)
03-24 11:47:50.103: W/WebView(21026):   at android.os.HandlerThread.run(HandlerThread.java:61)

Cevap için teşekkürler. Javascript dosyamdaki işlevi şu şekilde düzenledim:

private void test(final String s) {
        webView.post(new Runnable() {
            public void run() {
                webView.loadUrl("javascript:" + s + ";");
            }
        });
        System.out.println("javscript done..");
    }

Düzenlemenizde, kodunuzu yanıtlara (yanıtlardan birine) göre değiştirdiğinizi ve bunun hala sorununuzu çözmemiş gibi görünmesini sağladığınızı belirtiyorsunuz - ancak kabul edilmiş bir yanıt var. Bunun sorunu çözüp çözmediğini açıkça belirtmenizi (veya başka türlü düzenlemeyi geri almanızı) öneririm.
Tom

Yanıtlar:


214

JavaScript yöntemi bir arka planda (yani UI olmayan) iş parçacığında yürütülür. UI iş parçacığında Android View ile ilgili tüm yöntemleri çağırmanız gerekir. İhtiyacınız olanı şunlarla elde edebilirsiniz:

mWebView.post(new Runnable() {
    @Override
    public void run() {
        mWebView.loadUrl(...).
    }
});

Hangi görevi UI iş parçacığında çalıştıracak.


parçacığı (mWebView) orijinal kodunuza nereye eklediniz?
Bowie

Test () işlevinde yukarıdaki soruma bakın.
Johan Hoeksma

Ya bir değer döndürmeniz gerekirse? ör. webview.getUrl döndür? stackoverflow.com/questions/29748782/… @JohanHoeksma
Suresh Subedi

Bu sorunun nasıl ve ne zaman ortaya çıktığını biliyor musunuz? Nexus 5X'imde (Android 7.1.1) sorun yok, ancak bazı cihazlar çöktü.
Ellie Zou

bir değişken nasıl geçirilir? MWebView.loadUrl'de değişken eklemeye çalıştım ("javascript: test ('" + MyData + "');"); ancak değer javascript'e asla aktarılmaz!
user1788736

15

Benim durumumda bir WebView'da hiçbir şey gösterilmedi, bu yüzden başka bir yolu tercih ediyorum:

runOnUiThread(new Runnable() {
    @Override
    public void run() {
        final WebView webView = (WebView) findViewById(R.id.map);
        webView.loadDataWithBaseURL(...);
    }
});

3

Bu post yöntemi kullanılarak aşılabilir. Lütfen aşağıdaki kodu gözden geçirin.

 m_targetView.post(new Runnable() {
                        @Override
                        public void run() {
                            m_targetView.loadUrl(".....");
                        }
                    });

3

Java sürümü: Çalıştırılabilir arabirimi ve İşleyiciye Gönder'i kullanmanız gerekir .

webView.post(new Runnable() {
          @Override
          public void run() {
             webView.loadUrl("file:///android_asset/www/index.html");
          }
       });

Kotlin versiyonu:

webView.post(new Runnable {
   webView.loadUrl("file:///android_asset/www/index.html")
})
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.