Intereting Posts
Вызов Twilio не работает в iOS и Android в режиме реагирования Макет, такой как PInterest «Open Declaration» в Eclipse переходит к файлам классов вместо исходных файлов для Android-библиотек Ошибка «EGL_BAD_MATCH» в эмуляторе Android Studio Студия Android – развертывание apk версии вместо отладки Как использовать @ ActivityInfo.ScreenOrientation Как исправить «Пропустите перетаскивание, поскольку мы ждем ответа WebCore на прикосновение» Отправьте ссылку на группу whatsapp непосредственно из браузера (или из приложения) Уменьшить буферизацию видео Android HTTPUrlConnection: как установить почтовые данные в теле http? Возможно ли сосредоточить макет / представление внутри CoordinatorLayout? Сбой приложения с защитой Proguard Можно добавить кнопку Voice action рядом с edittext в android Получение токена авторизации Google oauth с Android-return с invalid_scope / Неизвестная ошибка Как предоставить root-доступ к конкретному приложению из исходного кода вместо укоренения ROM?

Как работает JavaScriptJavascript?

Я пытаюсь использовать новый метод оценки JavaScript в Android 4.4, но все, что я когда-либо получал, – это нулевой результат:

webView1.evaluateJavascript("return \"test\";", new ValueCallback<String>() { @Override public void onReceiveValue(String s) { Log.d("LogName", s); // Log is written, but s is always null } }); 

Как вернуть результат этому методу?

Обновление: Немного больше информации:

  1. У меня есть набор разрешений INTERNET
  2. У меня есть setJavascriptEnabled(true);
  3. Пробовал строку апострофа: return 'test'; ,
  4. Tried JS object: return { test: 'this' }
  5. console.log('test'); Выполняется отлично.
  6. Установите targetSdkVersion на 19: Если ваше приложение использует WebView

Устройства: как Nexus 7, так и Nexus 5 (Stock)

Solutions Collecting From Web of "Как работает JavaScriptJavascript?"

В этом примере используется пример метода JavaScript с оценкой:

https://github.com/GoogleChrome/chromium-webview-samples/tree/master/jsinterface-example

По сути, если javascript, который вы выполняете в WebView, возвращает значение, которое будет передано в обратном вызове.

Главное отметить, что строка, возвращаемая в OnReceiveValue, представляет собой значение JSON Value, JSON Object или JSON Array в зависимости от того, что вы возвращаете.

Следует отметить, что если вы вернете одно значение, вам нужно использовать setLenient (true) в считывателе JSON для его работы.

  if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) { // In KitKat+ you should use the evaluateJavascript method mWebView.evaluateJavascript(javascript, new ValueCallback<String>() { @TargetApi(Build.VERSION_CODES.HONEYCOMB) @Override public void onReceiveValue(String s) { JsonReader reader = new JsonReader(new StringReader(s)); // Must set lenient to parse single values reader.setLenient(true); try { if(reader.peek() != JsonToken.NULL) { if(reader.peek() == JsonToken.STRING) { String msg = reader.nextString(); if(msg != null) { Toast.makeText(getApplicationContext(), msg, Toast.LENGTH_LONG).show(); } } } } catch (IOException e) { Log.e("TAG", "MainActivity: IOException", e); } finally { try { reader.close(); } catch (IOException e) { // NOOP } } } }); } 

Причина, по которой вы все еще можете использовать синтаксический анализатор для строкового ответа, преобразуется в значение JSON, что означает, что он будет заключен в кавычки.

Например, если вы пошли:

 mWebView.evaluateJavascript("(function() { return 'this'; })();", new ValueCallback<String>() { @Override public void onReceiveValue(String s) { Log.d("LogName", s); // Prints: "this" } }); 

Он напечатает эту строку, заключенную в двойные кавычки: «this».

Другие примеры, которые стоит отметить:

 mWebView.evaluateJavascript("(function() { return null; })();", new ValueCallback<String>() { @Override public void onReceiveValue(String s) { Log.d("LogName", s); // Prints the string 'null' NOT Java null } }); mWebView.evaluateJavascript("(function() { })();", new ValueCallback<String>() { @Override public void onReceiveValue(String s) { Log.d("LogName", s); //s is Java null } }); 

ОК, поэтому получается, что resultрезультат вызова Javascript – как если бы кто-то вводил команду в консоль Javascript.

Поэтому, чтобы получить результат, он должен быть завернут в функцию:

 webView1.evaluateJavascript("(function() { return \"this\"; })();", new ValueCallback<String>() { @Override public void onReceiveValue(String s) { Log.d("LogName", s); // Prints 'this' } }); 

Это также будет работать:

 webView1.evaluateJavascript("window.variable = \"asd\";", new ValueCallback<String>() { @Override public void onReceiveValue(String s) { Log.d("LogName", s); // Prints asd } }); 

Метод также обрабатывает объекты Javascript:

 webView1.evaluateJavascript("(function() { return { var1: \"variable1\", var2: \"variable2\" }; })();", new ValueCallback<String>() { @Override public void onReceiveValue(String s) { Log.d("LogName", s); // Prints: {"var1":"variable1","var2":"variable2"} } }); 

AndroidDAore – хорошая альтернатива для оценки JavaScript, который не использует WebView.

Если вы хотите придерживаться WebView и вам нужно оценить JavaScript в более ранних версиях Android (4+), вот небольшая библиотека:

https://github.com/evgenyneu/js-evaluator-for-android

 jsEvaluator.evaluate("put your JavaScript code", new JsCallback() { @Override public void onResult(final String result) { // get result here (optional) } }); 

Чтобы обобщить ответ @GauntFace и предоставить альтернативное решение без использования анализатора JSON:

Если ваша функция JS возвращает только String и вам интересно, почему строка искажается на Java, это потому, что она скрыта от JSON.

 mWebView.evaluateJavascript("(function() { return 'Earvin \"Magic\" Johnson'; })();", new ValueCallback<String>() { @Override public void onReceiveValue(String s) { Log.d("LogName", s); // expected: s == Earvin "Magic" Johnson // actual: s == "Earvin \"Magic\" Johnson" } }); 

(Обратите внимание, что onReceiveValue всегда предоставляет String то время как функция JS может возвращать null , литерал номера и т. Д.)

Чтобы получить строковое значение так же, как в JS, если вы на 100% уверены, что ожидаете возвращения правильной String , вам нужно будет JSON-unescape, например:

 String unescaped = s.substring(1, s.length() - 1) // remove wrapping quotes .replace("\\\\", "\\") // unescape \\ -> \ .replace("\\\"", "\""); // unescape \" -> " 

Однако обратите внимание, что s может быть строкой "null" если JS возвращает правильный null , поэтому вам, очевидно, необходимо проверить это как самый первый шаг.

 if ("null".equals(s)) { ... } else { // unescape JSON }