4

I am trying to set up a simple Android app that displays a webview and has some extra functionality available via the Javascript Interface.

I am testing on a HTC One S running Kitkat (via Cyanogenmod). When I inspect the webview the object inserted (Android) is empty "Object {}". I cannot use the functions in the interface via the loaded page.

I had built a more complicated activity but could not get the interface working, so I've created this new app for testing which contains the only the code from the webview guides. Still not inserting the methods into the exposed object.

MyActivity

import android.app.Activity;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;
import android.webkit.WebSettings;
import android.webkit.WebView;


public class MyActivity extends Activity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_my);

        WebView myWebView = (WebView) findViewById(R.id.webview);
        myWebView.addJavascriptInterface(new WebAppInterface(this), "Android");
        WebSettings webSettings = myWebView.getSettings();
        webSettings.setJavaScriptEnabled(true);
        myWebView.loadUrl("http://47e148ba.ngrok.com");
    }


    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.my, menu);
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        // Handle action bar item clicks here. The action bar will
        // automatically handle clicks on the Home/Up button, so long
        // as you specify a parent activity in AndroidManifest.xml.
        int id = item.getItemId();
        if (id == R.id.action_settings) {
            return true;
        }
        return super.onOptionsItemSelected(item);
    }
}

WebAppInterface

import android.content.Context;
import android.webkit.JavascriptInterface;
import android.widget.Toast;

/**
 * Created by graeme on 28/08/2014.
 */
public class WebAppInterface {
    Context mContext;

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

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

Layout

<?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"
    />

build.gradle

apply plugin: 'com.android.application'

android {
    compileSdkVersion 19
    buildToolsVersion "20.0.0"

    defaultConfig {
        applicationId "com.mydomain.jswebview"
        minSdkVersion 17
        targetSdkVersion 19
        versionCode 1
        versionName "1.0"
    }
    buildTypes {
        release {
            runProguard false
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
    }
}

dependencies {
    compile fileTree(dir: 'libs', include: ['*.jar'])
}

You can see I'm using the decorator required for the methods, which most questions seem to have as the solution. I'm developing in Android Studio if any of the presets in there might be interfering?

Edit:

In The JS file, or via the console if I'm inspecting the webview via chrome if I call Android or window.Android i get an empty objected returned "Object {}". Or if I try to use the methods defined in the interface above I'll receive a method undefined error.

2
  • What's issue? showToast is not working? Have you called it from js file? Commented Aug 28, 2014 at 12:20
  • I've edited the question with some more information on the issue, thanks Commented Aug 28, 2014 at 12:28

2 Answers 2

2

I was having the same problem. Turned out to be a Proguard problem. Try adding the following to your Proguard rules:

-keepclassmembers class ** {
    @android.webkit.JavascriptInterface <methods>;
}
Sign up to request clarification or add additional context in comments.

Comments

0

I don't know how are you trying to call to your Java methods from inside of your WebView. I think that the correct way is:

javascript:window.Android.showToast('Hi!');

you could also test your JS interface from your Java code using:

myWebView.loadUrl("javascript:window.Android.showToast('Hi!');");

I hope this help you!

1 Comment

the javascript: label is redundant and a more proper way to evaluate javascript from java is webView.evaluateJavascript("console.log(123)", callback);

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.