Updated window.flutter_inappwebview.callHandler implementation: if there is an error/exception on Flutter/Dart side, the callHandler will reject the JavaScript promise with the error/exception message, so you can catch it also on JavaScript side, Fixed Android Web Storage Manager deleteAllData and deleteOrigin methods implementation, fix #1462, fix #1475

This commit is contained in:
Lorenzo Pichilli 2022-12-15 17:43:29 +01:00
parent 0f1c7e3029
commit ae199f1dc4
71 changed files with 1012 additions and 673 deletions

View File

@ -1,3 +1,24 @@
## 6.0.0-beta.23
- Updated `androidx.webkit:webkit` dependency to `1.6.1`
- Updated `androidx.browser:browser` dependency to `1.5.0`
- Updated `androidx.appcompat:appcompat` dependency to `1.6.1`
- Added support for Android `WebViewFeature.GET_COOKIE_INFO`
- Added `requestedWithHeaderOriginAllowList` WebView setting for Android
- Added `isInspectable`, `shouldPrintBackgrounds` WebView settings for iOS and macOS
- Removed `WebViewFeature.REQUESTED_WITH_HEADER_CONTROL`, `ServiceWorkerController.setRequestedWithHeaderMode()`, `ServiceWorkerController.getRequestedWithHeaderMode()`, `InAppWebViewSettings.requestedWithHeaderMode`
- Fixed "Build fail with AGP 8.0" [#1643](https://github.com/pichillilorenzo/flutter_inappwebview/issues/1643)
- Fixed "java.lang.RuntimeException: Unknown feature REQUESTED_WITH_HEADER_CONTROL" [#1611](https://github.com/pichillilorenzo/flutter_inappwebview/issues/1611)
- Fixed "iOS 16.4 WebDebugging WKWebView.isInspectable" [#1629](https://github.com/pichillilorenzo/flutter_inappwebview/issues/1629)
- Fixed some `@available` checks for macOS
## 6.0.0-beta.22
- Updated `window.flutter_inappwebview.callHandler` implementation: if there is an error/exception on Flutter/Dart side, the `callHandler` will reject the JavaScript promise with the error/exception message, so you can catch it also on JavaScript side
- Fixed Android Web Storage Manager `deleteAllData` and `deleteOrigin` methods implementation
- Fixed "Xiaomi store - Conflict of Privacy Permissions, android.permission.MY_READ_INSTALLED_PACKAGES" [#1462](https://github.com/pichillilorenzo/flutter_inappwebview/issues/1462)
- Fixed "Flutter 3.0.5 compilation issue" [#1475](https://github.com/pichillilorenzo/flutter_inappwebview/issues/1475)
## 6.0.0-beta.21
- Fixed "Android plugin version 6 - UserScripts not executing on new tabs." [#1455](https://github.com/pichillilorenzo/flutter_inappwebview/issues/1455)
@ -174,6 +195,10 @@
- Removed `URLProtectionSpace.iosIsProxy` property
- `historyUrl` and `baseUrl` of `InAppWebViewInitialData` can be `null`
## 5.7.2+3
- Fixed "Xiaomi store - Conflict of Privacy Permissions, android.permission.MY_READ_INSTALLED_PACKAGES" [#1462](https://github.com/pichillilorenzo/flutter_inappwebview/issues/1462)
## 5.7.2+2
- Fixed "Unexpected addWebMessageListener behaviour" [#1422](https://github.com/pichillilorenzo/flutter_inappwebview/issues/1422)

View File

@ -8,7 +8,7 @@ buildscript {
}
dependencies {
classpath 'com.android.tools.build:gradle:4.1.0'
classpath 'com.android.tools.build:gradle:8.0.1'
}
}
@ -22,6 +22,10 @@ rootProject.allprojects {
apply plugin: 'com.android.library'
android {
// Conditional for compatibility with AGP <4.2.
if (project.android.hasProperty("namespace")) {
namespace 'com.pichillilorenzo.flutter_inappwebview'
}
compileSdkVersion 33
defaultConfig {
@ -45,9 +49,9 @@ android {
}
}
dependencies {
implementation 'androidx.webkit:webkit:1.5.0'
implementation 'androidx.browser:browser:1.4.0'
implementation 'androidx.appcompat:appcompat:1.5.1'
implementation 'androidx.webkit:webkit:1.6.1'
implementation 'androidx.browser:browser:1.5.0'
implementation 'androidx.appcompat:appcompat:1.6.1'
implementation 'androidx.swiperefreshlayout:swiperefreshlayout:1.1.0'
}
}

View File

@ -1,17 +1,24 @@
package com.pichillilorenzo.flutter_inappwebview;
import android.os.Build;
import android.util.Log;
import android.webkit.CookieManager;
import android.webkit.CookieSyncManager;
import android.webkit.ValueCallback;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.webkit.CookieManagerCompat;
import androidx.webkit.WebViewFeature;
import com.pichillilorenzo.flutter_inappwebview.types.ChannelDelegateImpl;
import java.text.DateFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
@ -30,14 +37,21 @@ public class MyCookieManager extends ChannelDelegateImpl {
@Nullable
public InAppWebViewFlutterPlugin plugin;
public MyCookieManager(final InAppWebViewFlutterPlugin plugin) {
public MyCookieManager(@NonNull final InAppWebViewFlutterPlugin plugin) {
super(new MethodChannel(plugin.messenger, METHOD_CHANNEL_NAME));
this.plugin = plugin;
cookieManager = getCookieManager();
}
public static void init() {
if (cookieManager == null) {
cookieManager = getCookieManager();
}
}
@Override
public void onMethodCall(@NonNull MethodCall call, @NonNull MethodChannel.Result result) {
init();
switch (call.method) {
case "setCookie":
{
@ -192,28 +206,79 @@ public class MyCookieManager extends ChannelDelegateImpl {
cookieManager = getCookieManager();
if (cookieManager == null) return cookieListMap;
String cookiesString = cookieManager.getCookie(url);
if (cookiesString != null) {
String[] cookies = cookiesString.split(";");
for (String cookie : cookies) {
String[] nameValue = cookie.split("=", 2);
String name = nameValue[0].trim();
String value = (nameValue.length > 1) ? nameValue[1].trim() : "";
Map<String, Object> cookieMap = new HashMap<>();
cookieMap.put("name", name);
cookieMap.put("value", value);
cookieMap.put("expiresDate", null);
cookieMap.put("isSessionOnly", null);
cookieMap.put("domain", null);
cookieMap.put("sameSite", null);
cookieMap.put("isSecure", null);
cookieMap.put("isHttpOnly", null);
cookieMap.put("path", null);
cookieListMap.add(cookieMap);
List<String> cookies = new ArrayList<>();
if (WebViewFeature.isFeatureSupported(WebViewFeature.GET_COOKIE_INFO)) {
cookies = CookieManagerCompat.getCookieInfo(cookieManager, url);
} else {
String cookiesString = cookieManager.getCookie(url);
if (cookiesString != null) {
cookies = Arrays.asList(cookiesString.split(";"));
}
}
for (String cookie : cookies) {
String[] cookieParams = cookie.split(";");
if (cookieParams.length == 0) continue;
String[] nameValue = cookieParams[0].split("=", 2);
String name = nameValue[0].trim();
String value = (nameValue.length > 1) ? nameValue[1].trim() : "";
Map<String, Object> cookieMap = new HashMap<>();
cookieMap.put("name", name);
cookieMap.put("value", value);
cookieMap.put("expiresDate", null);
cookieMap.put("isSessionOnly", null);
cookieMap.put("domain", null);
cookieMap.put("sameSite", null);
cookieMap.put("isSecure", null);
cookieMap.put("isHttpOnly", null);
cookieMap.put("path", null);
if (WebViewFeature.isFeatureSupported(WebViewFeature.GET_COOKIE_INFO)) {
cookieMap.put("isSecure", false);
cookieMap.put("isHttpOnly", false);
for (int i = 1; i < cookieParams.length; i++) {
String[] cookieParamNameValue = cookieParams[i].split("=", 2);
String cookieParamName = cookieParamNameValue[0].trim();
String cookieParamValue = (cookieParamNameValue.length > 1) ? cookieParamNameValue[1].trim() : "";
if (cookieParamName.equalsIgnoreCase("Expires")) {
try {
final SimpleDateFormat sdf = new SimpleDateFormat("EEE, dd MMM yyyy hh:mm:ss z", Locale.US);
Date expiryDate = sdf.parse(cookieParamValue);
if (expiryDate != null) {
cookieMap.put("expiresDate", expiryDate.getTime());
}
} catch (ParseException e) {
e.printStackTrace();
Log.e(LOG_TAG, e.getMessage());
}
} else if (cookieParamName.equalsIgnoreCase("Max-Age")) {
try {
long maxAge = Long.parseLong(cookieParamValue);
cookieMap.put("expiresDate", System.currentTimeMillis() + maxAge);
} catch (NumberFormatException e) {
e.printStackTrace();
Log.e(LOG_TAG, e.getMessage());
}
} else if (cookieParamName.equalsIgnoreCase("Domain")) {
cookieMap.put("domain", cookieParamValue);
} else if (cookieParamName.equalsIgnoreCase("SameSite")) {
cookieMap.put("sameSite", cookieParamValue);
} else if (cookieParamName.equalsIgnoreCase("Secure")) {
cookieMap.put("isSecure", true);
} else if (cookieParamName.equalsIgnoreCase("HttpOnly")) {
cookieMap.put("isHttpOnly", true);
} else if (cookieParamName.equalsIgnoreCase("Path")) {
cookieMap.put("path", cookieParamValue);
}
}
}
cookieListMap.add(cookieMap);
}
return cookieListMap;
}

View File

@ -25,20 +25,27 @@ public class MyWebStorage extends ChannelDelegateImpl {
@Nullable
public InAppWebViewFlutterPlugin plugin;
public MyWebStorage(final InAppWebViewFlutterPlugin plugin) {
public MyWebStorage(@NonNull final InAppWebViewFlutterPlugin plugin) {
super(new MethodChannel(plugin.messenger, METHOD_CHANNEL_NAME));
this.plugin = plugin;
webStorageManager = WebStorage.getInstance();
}
public static void init() {
if (webStorageManager == null) {
webStorageManager = WebStorage.getInstance();
}
}
@Override
public void onMethodCall(@NonNull MethodCall call, @NonNull MethodChannel.Result result) {
init();
switch (call.method) {
case "getOrigins":
getOrigins(result);
break;
case "deleteAllData":
if (webStorageManager == null) {
if (webStorageManager != null) {
webStorageManager.deleteAllData();
result.success(true);
} else {
@ -47,7 +54,7 @@ public class MyWebStorage extends ChannelDelegateImpl {
break;
case "deleteOrigin":
{
if (webStorageManager == null) {
if (webStorageManager != null) {
String origin = (String) call.argument("origin");
webStorageManager.deleteOrigin(origin);
result.success(true);

View File

@ -16,7 +16,7 @@ public class WebViewFeatureManager extends ChannelDelegateImpl {
@Nullable
public InAppWebViewFlutterPlugin plugin;
public WebViewFeatureManager(final InAppWebViewFlutterPlugin plugin) {
public WebViewFeatureManager(@NonNull final InAppWebViewFlutterPlugin plugin) {
super(new MethodChannel(plugin.messenger, METHOD_CHANNEL_NAME));
this.plugin = plugin;
}

View File

@ -30,14 +30,23 @@ public class CredentialDatabaseHandler extends ChannelDelegateImpl {
@Nullable
public InAppWebViewFlutterPlugin plugin;
public CredentialDatabaseHandler(final InAppWebViewFlutterPlugin plugin) {
public CredentialDatabaseHandler(@NonNull final InAppWebViewFlutterPlugin plugin) {
super(new MethodChannel(plugin.messenger, METHOD_CHANNEL_NAME));
this.plugin = plugin;
credentialDatabase = CredentialDatabase.getInstance(plugin.applicationContext);
}
public static void init(@NonNull InAppWebViewFlutterPlugin plugin) {
if (credentialDatabase == null) {
credentialDatabase = CredentialDatabase.getInstance(plugin.applicationContext);
}
}
@Override
public void onMethodCall(@NonNull MethodCall call, @NonNull MethodChannel.Result result) {
if (plugin != null) {
init(plugin);
}
switch (call.method) {
case "getAllAuthCredentials":
{

View File

@ -220,7 +220,7 @@ public class JavaScriptBridgeJS {
" var _callHandlerID = setTimeout(function(){});" +
" window." + JAVASCRIPT_BRIDGE_NAME + "._callHandler(arguments[0], _callHandlerID, JSON.stringify(Array.prototype.slice.call(arguments, 1)));" +
" return new Promise(function(resolve, reject) {" +
" window." + JAVASCRIPT_BRIDGE_NAME + "[_callHandlerID] = resolve;" +
" window." + JAVASCRIPT_BRIDGE_NAME + "[_callHandlerID] = {resolve: resolve, reject: reject};" +
" });" +
" };" +
" }"+
@ -230,7 +230,7 @@ public class JavaScriptBridgeJS {
" var _callHandlerID = setTimeout(function(){});" +
" window.top." + JAVASCRIPT_BRIDGE_NAME + "._callHandler(arguments[0], _callHandlerID, JSON.stringify(Array.prototype.slice.call(arguments, 1)));" +
" return new Promise(function(resolve, reject) {" +
" window.top." + JAVASCRIPT_BRIDGE_NAME + "[_callHandlerID] = resolve;" +
" window.top." + JAVASCRIPT_BRIDGE_NAME + "[_callHandlerID] = {resolve: resolve, reject: reject};" +
" });" +
" };" +
"}" +

View File

@ -25,18 +25,22 @@ public class ProxyManager extends ChannelDelegateImpl {
@Nullable
public InAppWebViewFlutterPlugin plugin;
public ProxyManager(final InAppWebViewFlutterPlugin plugin) {
public ProxyManager(@NonNull final InAppWebViewFlutterPlugin plugin) {
super(new MethodChannel(plugin.messenger, METHOD_CHANNEL_NAME));
this.plugin = plugin;
if (WebViewFeature.isFeatureSupported(WebViewFeature.PROXY_OVERRIDE)) {
}
public static void init() {
if (proxyController == null &&
WebViewFeature.isFeatureSupported(WebViewFeature.PROXY_OVERRIDE)) {
proxyController = ProxyController.getInstance();
} else {
proxyController = null;
}
}
@Override
public void onMethodCall(@NonNull MethodCall call, @NonNull MethodChannel.Result result) {
init();
switch (call.method) {
case "setProxyOverride":
if (proxyController != null) {

View File

@ -1,6 +1,5 @@
package com.pichillilorenzo.flutter_inappwebview.service_worker;
import android.annotation.SuppressLint;
import android.os.Build;
import androidx.annotation.NonNull;
@ -16,7 +15,6 @@ import com.pichillilorenzo.flutter_inappwebview.types.ChannelDelegateImpl;
import com.pichillilorenzo.flutter_inappwebview.types.SyncBaseCallbackResultImpl;
import com.pichillilorenzo.flutter_inappwebview.types.WebResourceRequestExt;
import com.pichillilorenzo.flutter_inappwebview.types.WebResourceResponseExt;
import com.pichillilorenzo.flutter_inappwebview.webview.WebViewChannelDelegate;
import java.util.Map;
@ -33,9 +31,9 @@ public class ServiceWorkerChannelDelegate extends ChannelDelegateImpl {
this.serviceWorkerManager = serviceWorkerManager;
}
@SuppressLint("RestrictedApi")
@Override
public void onMethodCall(@NonNull MethodCall call, @NonNull MethodChannel.Result result) {
ServiceWorkerManager.init();
ServiceWorkerControllerCompat serviceWorkerController = ServiceWorkerManager.serviceWorkerController;
ServiceWorkerWebSettingsCompat serviceWorkerWebSettings = (serviceWorkerController != null) ?
serviceWorkerController.getServiceWorkerWebSettings() : null;
@ -71,13 +69,6 @@ public class ServiceWorkerChannelDelegate extends ChannelDelegateImpl {
result.success(false);
}
break;
case "getRequestedWithHeaderMode":
if (serviceWorkerWebSettings != null && WebViewFeature.isFeatureSupported(WebViewFeature.REQUESTED_WITH_HEADER_CONTROL)) {
result.success(serviceWorkerWebSettings.getRequestedWithHeaderMode());
} else {
result.success(null);
}
break;
case "getCacheMode":
if (serviceWorkerWebSettings != null && WebViewFeature.isFeatureSupported(WebViewFeature.SERVICE_WORKER_CACHE_MODE)) {
result.success(serviceWorkerWebSettings.getCacheMode());
@ -113,13 +104,6 @@ public class ServiceWorkerChannelDelegate extends ChannelDelegateImpl {
}
result.success(true);
break;
case "setRequestedWithHeaderMode":
if (serviceWorkerWebSettings != null && WebViewFeature.isFeatureSupported(WebViewFeature.REQUESTED_WITH_HEADER_CONTROL)) {
Integer mode = (Integer) call.argument("mode");
serviceWorkerWebSettings.setRequestedWithHeaderMode(mode);
}
result.success(true);
break;
default:
result.notImplemented();
}

View File

@ -33,14 +33,16 @@ public class ServiceWorkerManager implements Disposable {
@Nullable
public InAppWebViewFlutterPlugin plugin;
public ServiceWorkerManager(final InAppWebViewFlutterPlugin plugin) {
public ServiceWorkerManager(@NonNull final InAppWebViewFlutterPlugin plugin) {
this.plugin = plugin;
final MethodChannel channel = new MethodChannel(plugin.messenger, METHOD_CHANNEL_NAME);
this.channelDelegate = new ServiceWorkerChannelDelegate(this, channel);
if (WebViewFeature.isFeatureSupported(WebViewFeature.SERVICE_WORKER_BASIC_USAGE)) {
}
public static void init() {
if (serviceWorkerController == null &&
WebViewFeature.isFeatureSupported(WebViewFeature.SERVICE_WORKER_BASIC_USAGE)) {
serviceWorkerController = ServiceWorkerControllerCompat.getInstance();
} else {
serviceWorkerController = null;
}
}

View File

@ -27,6 +27,7 @@ public class TracingControllerChannelDelegate extends ChannelDelegateImpl {
@Override
public void onMethodCall(@NonNull MethodCall call, @NonNull MethodChannel.Result result) {
TracingControllerManager.init();
TracingController tracingController = TracingControllerManager.tracingController;
switch (call.method) {

View File

@ -1,6 +1,7 @@
package com.pichillilorenzo.flutter_inappwebview.tracing;
import androidx.annotation.Nullable;
import androidx.webkit.ProxyController;
import androidx.webkit.TracingConfig;
import androidx.webkit.TracingController;
import androidx.webkit.WebViewFeature;
@ -25,10 +26,12 @@ public class TracingControllerManager implements Disposable {
this.plugin = plugin;
final MethodChannel channel = new MethodChannel(plugin.messenger, METHOD_CHANNEL_NAME);
this.channelDelegate = new TracingControllerChannelDelegate(this, channel);
if (WebViewFeature.isFeatureSupported(WebViewFeature.TRACING_CONTROLLER_BASIC_USAGE)) {
}
public static void init() {
if (tracingController == null &&
WebViewFeature.isFeatureSupported(WebViewFeature.TRACING_CONTROLLER_BASIC_USAGE)) {
tracingController = TracingController.getInstance();
} else {
tracingController = null;
}
}

View File

@ -130,7 +130,7 @@ public class JavaScriptBridgeInterface {
return;
}
String sourceCode = "if (window." + JavaScriptBridgeJS.JAVASCRIPT_BRIDGE_NAME + "[" + _callHandlerID + "] != null) { " +
"window." + JavaScriptBridgeJS.JAVASCRIPT_BRIDGE_NAME + "[" + _callHandlerID + "](" + json + "); " +
"window." + JavaScriptBridgeJS.JAVASCRIPT_BRIDGE_NAME + "[" + _callHandlerID + "].resolve(" + json + "); " +
"delete window." + JavaScriptBridgeJS.JAVASCRIPT_BRIDGE_NAME + "[" + _callHandlerID + "]; " +
"}";
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
@ -143,7 +143,24 @@ public class JavaScriptBridgeInterface {
@Override
public void error(String errorCode, @Nullable String errorMessage, @Nullable Object errorDetails) {
Log.e(LOG_TAG, errorCode + ", " + ((errorMessage != null) ? errorMessage : ""));
String message = errorCode + ((errorMessage != null) ? ", " + errorMessage : "");
Log.e(LOG_TAG, message);
if (inAppWebView == null) {
// The webview has already been disposed, ignore.
return;
}
String sourceCode = "if (window." + JavaScriptBridgeJS.JAVASCRIPT_BRIDGE_NAME + "[" + _callHandlerID + "] != null) { " +
"window." + JavaScriptBridgeJS.JAVASCRIPT_BRIDGE_NAME + "[" + _callHandlerID + "].reject(new Error(" + JSONObject.quote(message) + ")); " +
"delete window." + JavaScriptBridgeJS.JAVASCRIPT_BRIDGE_NAME + "[" + _callHandlerID + "]; " +
"}";
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
inAppWebView.evaluateJavascript(sourceCode, (ValueCallback<String>) null);
}
else {
inAppWebView.loadUrl("javascript:" + sourceCode);
}
}
});
}

View File

@ -433,13 +433,13 @@ final public class InAppWebView extends InputAwareWebView implements InAppWebVie
if (WebViewFeature.isFeatureSupported(WebViewFeature.ALGORITHMIC_DARKENING) && Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
WebSettingsCompat.setAlgorithmicDarkeningAllowed(settings, customSettings.algorithmicDarkeningAllowed);
}
if (WebViewFeature.isFeatureSupported(WebViewFeature.REQUESTED_WITH_HEADER_CONTROL) &&
customSettings.requestedWithHeaderMode != null) {
WebSettingsCompat.setRequestedWithHeaderMode(settings, customSettings.requestedWithHeaderMode);
}
if (WebViewFeature.isFeatureSupported(WebViewFeature.ENTERPRISE_AUTHENTICATION_APP_LINK_POLICY)) {
WebSettingsCompat.setEnterpriseAuthenticationAppLinkPolicyEnabled(settings, customSettings.enterpriseAuthenticationAppLinkPolicyEnabled);
}
if (customSettings.requestedWithHeaderOriginAllowList != null &&
WebViewFeature.isFeatureSupported(WebViewFeature.REQUESTED_WITH_HEADER_ALLOW_LIST)) {
WebSettingsCompat.setRequestedWithHeaderOriginAllowList(settings, customSettings.requestedWithHeaderOriginAllowList);
}
contentBlockerHandler.getRuleList().clear();
for (Map<String, Map<String, Object>> contentBlocker : customSettings.contentBlockers) {
@ -1089,17 +1089,16 @@ final public class InAppWebView extends InputAwareWebView implements InAppWebVie
WebViewFeature.isFeatureSupported(WebViewFeature.ALGORITHMIC_DARKENING) && Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
WebSettingsCompat.setAlgorithmicDarkeningAllowed(settings, newCustomSettings.algorithmicDarkeningAllowed);
}
if (newSettingsMap.get("requestedWithHeaderMode") != null &&
!Util.objEquals(customSettings.requestedWithHeaderMode, newCustomSettings.requestedWithHeaderMode) &&
WebViewFeature.isFeatureSupported(WebViewFeature.REQUESTED_WITH_HEADER_CONTROL) &&
newCustomSettings.requestedWithHeaderMode != null) {
WebSettingsCompat.setRequestedWithHeaderMode(settings, newCustomSettings.requestedWithHeaderMode);
}
if (newSettingsMap.get("enterpriseAuthenticationAppLinkPolicyEnabled") != null &&
!Util.objEquals(customSettings.enterpriseAuthenticationAppLinkPolicyEnabled, newCustomSettings.enterpriseAuthenticationAppLinkPolicyEnabled) &&
WebViewFeature.isFeatureSupported(WebViewFeature.ENTERPRISE_AUTHENTICATION_APP_LINK_POLICY)) {
WebSettingsCompat.setEnterpriseAuthenticationAppLinkPolicyEnabled(settings, newCustomSettings.enterpriseAuthenticationAppLinkPolicyEnabled);
}
if (newSettingsMap.get("requestedWithHeaderOriginAllowList") != null &&
!Util.objEquals(customSettings.requestedWithHeaderOriginAllowList, newCustomSettings.requestedWithHeaderOriginAllowList) &&
WebViewFeature.isFeatureSupported(WebViewFeature.REQUESTED_WITH_HEADER_ALLOW_LIST)) {
WebSettingsCompat.setRequestedWithHeaderOriginAllowList(settings, newCustomSettings.requestedWithHeaderOriginAllowList);
}
if (plugin != null) {
if (webViewAssetLoaderExt != null) {

View File

@ -19,8 +19,10 @@ import com.pichillilorenzo.flutter_inappwebview.webview.InAppWebViewInterface;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
public class InAppWebViewSettings implements ISettings<InAppWebViewInterface> {
@ -115,13 +117,13 @@ public class InAppWebViewSettings implements ISettings<InAppWebViewInterface> {
@Nullable
public String horizontalScrollbarTrackColor;
public Boolean algorithmicDarkeningAllowed = false;
@Nullable
public Integer requestedWithHeaderMode;
public Boolean enterpriseAuthenticationAppLinkPolicyEnabled = true;
@Nullable
public Map<String, Object> webViewAssetLoader;
@Nullable
public byte[] defaultVideoPoster;
@Nullable
public Set<String> requestedWithHeaderOriginAllowList;
@NonNull
@Override
@ -383,9 +385,6 @@ public class InAppWebViewSettings implements ISettings<InAppWebViewInterface> {
case "algorithmicDarkeningAllowed":
algorithmicDarkeningAllowed = (Boolean) value;
break;
case "requestedWithHeaderMode":
requestedWithHeaderMode = (Integer) value;
break;
case "enterpriseAuthenticationAppLinkPolicyEnabled":
enterpriseAuthenticationAppLinkPolicyEnabled = (Boolean) value;
break;
@ -398,6 +397,9 @@ public class InAppWebViewSettings implements ISettings<InAppWebViewInterface> {
case "defaultVideoPoster":
defaultVideoPoster = (byte[]) value;
break;
case "requestedWithHeaderOriginAllowList":
requestedWithHeaderOriginAllowList = new HashSet<>((List<String>) value);
break;
}
}
@ -491,10 +493,11 @@ public class InAppWebViewSettings implements ISettings<InAppWebViewInterface> {
settings.put("horizontalScrollbarThumbColor", horizontalScrollbarThumbColor);
settings.put("horizontalScrollbarTrackColor", horizontalScrollbarTrackColor);
settings.put("algorithmicDarkeningAllowed", algorithmicDarkeningAllowed);
settings.put("requestedWithHeaderMode", requestedWithHeaderMode);
settings.put("enterpriseAuthenticationAppLinkPolicyEnabled", enterpriseAuthenticationAppLinkPolicyEnabled);
settings.put("allowBackgroundAudioPlaying", allowBackgroundAudioPlaying);
settings.put("defaultVideoPoster", defaultVideoPoster);
settings.put("requestedWithHeaderOriginAllowList",
requestedWithHeaderOriginAllowList != null ? new ArrayList<>(requestedWithHeaderOriginAllowList) : null);
return settings;
}
@ -586,12 +589,12 @@ public class InAppWebViewSettings implements ISettings<InAppWebViewInterface> {
if (WebViewFeature.isFeatureSupported(WebViewFeature.ALGORITHMIC_DARKENING) && Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
realSettings.put("algorithmicDarkeningAllowed", WebSettingsCompat.isAlgorithmicDarkeningAllowed(settings));
}
if (WebViewFeature.isFeatureSupported(WebViewFeature.REQUESTED_WITH_HEADER_CONTROL)) {
realSettings.put("requestedWithHeaderMode", WebSettingsCompat.getRequestedWithHeaderMode(settings));
}
if (WebViewFeature.isFeatureSupported(WebViewFeature.ENTERPRISE_AUTHENTICATION_APP_LINK_POLICY)) {
realSettings.put("enterpriseAuthenticationAppLinkPolicyEnabled", WebSettingsCompat.getEnterpriseAuthenticationAppLinkPolicyEnabled(settings));
}
if (WebViewFeature.isFeatureSupported(WebViewFeature.REQUESTED_WITH_HEADER_ALLOW_LIST)) {
realSettings.put("requestedWithHeaderOriginAllowList", new ArrayList<>(WebSettingsCompat.getRequestedWithHeaderOriginAllowList(settings)));
}
}
return realSettings;
}

View File

@ -23,25 +23,25 @@ class ExchangeableEnumGenerator
// Visits all the children of element in no particular order.
element.visitChildren(visitor);
final className = visitor.constructor.returnType.element2.name;
final className = visitor.constructor.returnType.element.name;
// remove "_" to generate the correct class name
final extClassName = className.replaceFirst("_", "");
final classBuffer = StringBuffer();
final classDocs =
visitor.constructor.returnType.element2.documentationComment;
visitor.constructor.returnType.element.documentationComment;
if (classDocs != null) {
classBuffer.writeln(classDocs);
}
final classSupportedDocs = Util.getSupportedDocs(
_coreCheckerEnumSupportedPlatforms,
visitor.constructor.returnType.element2);
visitor.constructor.returnType.element);
if (classSupportedDocs != null) {
classBuffer.writeln(classSupportedDocs);
}
if (visitor.constructor.returnType.element2.hasDeprecated) {
if (visitor.constructor.returnType.element.hasDeprecated) {
classBuffer.writeln(
"@Deprecated('${_coreCheckerDeprecated.firstAnnotationOfExact(visitor.constructor.returnType.element2)?.getField("message")?.toStringValue()}')");
"@Deprecated('${_coreCheckerDeprecated.firstAnnotationOfExact(visitor.constructor.returnType.element)?.getField("message")?.toStringValue()}')");
}
classBuffer.writeln('class $extClassName {');

View File

@ -29,35 +29,37 @@ class ExchangeableObjectGenerator
// Visits all the children of element in no particular order.
element.visitChildren(visitor);
final className = visitor.constructor.returnType.element2.name;
final className = visitor.constructor.returnType.element.name;
final superClass =
visitor.constructor.returnType.superclass?.element2.name != 'Object'
visitor.constructor.returnType.superclass?.element.name != 'Object'
? visitor.constructor.returnType.superclass
: null;
final interfaces = visitor.constructor.returnType.interfaces;
final superClassName = superClass?.element2.name.replaceFirst("_", "");
final superClassName = superClass?.element.name.replaceFirst("_", "");
// remove "_" to generate the correct class name
final extClassName = className.replaceFirst("_", "");
final classBuffer = StringBuffer();
final classDocs =
visitor.constructor.returnType.element2.documentationComment;
visitor.constructor.returnType.element.documentationComment;
if (classDocs != null) {
classBuffer.writeln(classDocs);
}
final classSupportedDocs = Util.getSupportedDocs(
_coreCheckerSupportedPlatforms, visitor.constructor.returnType.element2);
_coreCheckerSupportedPlatforms, visitor.constructor.returnType.element);
if (classSupportedDocs != null) {
classBuffer.writeln(classSupportedDocs);
}
if (visitor.constructor.returnType.element2.hasDeprecated) {
if (visitor.constructor.returnType.element.hasDeprecated) {
classBuffer.writeln(
"@Deprecated('${_coreCheckerDeprecated.firstAnnotationOfExact(visitor.constructor.returnType.element2)?.getField("message")?.toStringValue()}')");
"@Deprecated('${_coreCheckerDeprecated.firstAnnotationOfExact(visitor.constructor.returnType.element)?.getField("message")?.toStringValue()}')");
}
classBuffer.write('${(visitor.constructor.enclosingElement3 as ClassElement).isAbstract ? 'abstract ' : ''}class $extClassName');
classBuffer.write(
'${(visitor.constructor.enclosingElement as ClassElement).isAbstract ? 'abstract ' : ''}class $extClassName');
if (interfaces.isNotEmpty) {
classBuffer.writeln(' implements ${interfaces.map((i) => i.element2.name.replaceFirst("_", "")).join(', ')}');
classBuffer.writeln(
' implements ${interfaces.map((i) => i.element.name.replaceFirst("_", "")).join(', ')}');
}
if (superClass != null) {
classBuffer.writeln(' extends ${superClassName}');
@ -174,7 +176,7 @@ class ExchangeableObjectGenerator
if (constructorSupportedDocs == null) {
constructorSupportedDocs = Util.getSupportedDocs(
_coreCheckerSupportedPlatforms,
visitor.constructor.returnType.element2);
visitor.constructor.returnType.element);
}
if (constructorSupportedDocs != null) {
classBuffer.writeln(constructorSupportedDocs);
@ -233,11 +235,13 @@ class ExchangeableObjectGenerator
.trim();
final fieldElement = visitor.fields[fieldName];
if (fieldElement != null) {
final fieldTypeElement = fieldElement.type.element2;
final deprecatedFieldTypeElement = deprecatedField.type.element2;
final fieldTypeElement = fieldElement.type.element;
final deprecatedFieldTypeElement = deprecatedField.type.element;
final isNullable = Util.typeIsNullable(fieldElement.type);
var hasDefaultValue = (fieldElement is ParameterElement) ? (fieldElement as ParameterElement).hasDefaultValue : false;
var hasDefaultValue = (fieldElement is ParameterElement)
? (fieldElement as ParameterElement).hasDefaultValue
: false;
if (!isNullable && hasDefaultValue) {
continue;
}
@ -267,10 +271,14 @@ class ExchangeableObjectGenerator
} else if (hasFromValue && deprecatedHasToValue) {
classBuffer.write(fieldTypeElement.name!.replaceFirst("_", "") +
'.fromValue($deprecatedFieldName${deprecatedIsNullable ? '?' : ''}.toValue())${!isNullable ? '!' : ''}');
} else if (deprecatedField.type.getDisplayString(withNullability: false) == "Uri" &&
fieldElement.type.getDisplayString(withNullability: false) == "WebUri") {
} else if (deprecatedField.type
.getDisplayString(withNullability: false) ==
"Uri" &&
fieldElement.type.getDisplayString(withNullability: false) ==
"WebUri") {
if (deprecatedIsNullable) {
classBuffer.write("($deprecatedFieldName != null ? WebUri.uri($deprecatedFieldName!) : ${isNullable ? "null" : "WebUri('')"})");
classBuffer.write(
"($deprecatedFieldName != null ? WebUri.uri($deprecatedFieldName!) : ${isNullable ? "null" : "WebUri('')"})");
} else {
classBuffer.write("WebUri.uri($deprecatedFieldName)");
}
@ -288,8 +296,9 @@ class ExchangeableObjectGenerator
classBuffer.writeln(';');
}
if (annotation.read("fromMapFactory").boolValue && (!visitor.methods.containsKey("fromMap") ||
Util.methodHasIgnore(visitor.methods['fromMap']!))) {
if (annotation.read("fromMapFactory").boolValue &&
(!visitor.methods.containsKey("fromMap") ||
Util.methodHasIgnore(visitor.methods['fromMap']!))) {
classBuffer.writeln(
'///Gets a possible [$extClassName] instance from a [Map] value.');
final nullable = annotation.read("nullableFromMapFactory").boolValue;
@ -303,7 +312,7 @@ class ExchangeableObjectGenerator
classBuffer.writeln('final instance = $extClassName(');
final fieldElements = <FieldElement>[];
if (superClass != null) {
fieldElements.addAll(superClass.element2.fields);
fieldElements.addAll(superClass.element.fields);
}
fieldElements.addAll(fieldValuesSorted);
final nonRequiredFields = <String>[];
@ -332,7 +341,7 @@ class ExchangeableObjectGenerator
?.toFunctionValue();
if (customDeserializer != null) {
final deserializerClassName =
customDeserializer.enclosingElement3.name;
customDeserializer.enclosingElement.name;
if (deserializerClassName != null) {
value =
"$deserializerClassName.${customDeserializer.name}($value)";
@ -387,8 +396,9 @@ class ExchangeableObjectGenerator
}
}
if (annotation.read("toMapMethod").boolValue && (!visitor.methods.containsKey("toMap") ||
Util.methodHasIgnore(visitor.methods['toMap']!))) {
if (annotation.read("toMapMethod").boolValue &&
(!visitor.methods.containsKey("toMap") ||
Util.methodHasIgnore(visitor.methods['toMap']!))) {
classBuffer.writeln('///Converts instance to a map.');
classBuffer.writeln('Map<String, dynamic> toMap() {');
classBuffer.writeln('return {');
@ -404,7 +414,7 @@ class ExchangeableObjectGenerator
}
final fieldElements = <FieldElement>[];
if (superClass != null) {
for (final fieldElement in superClass.element2.fields) {
for (final fieldElement in superClass.element.fields) {
if (!fieldElement.isPrivate &&
!fieldElement.hasDeprecated &&
!fieldElement.isStatic &&
@ -434,7 +444,7 @@ class ExchangeableObjectGenerator
?.getField("serializer")
?.toFunctionValue();
if (customSerializer != null) {
final serializerClassName = customSerializer.enclosingElement3.name;
final serializerClassName = customSerializer.enclosingElement.name;
if (serializerClassName != null) {
mapValue =
"$serializerClassName.${customSerializer.name}($mapValue)";
@ -452,30 +462,34 @@ class ExchangeableObjectGenerator
classBuffer.writeln('}');
}
if (annotation.read("toJsonMethod").boolValue && (!visitor.methods.containsKey("toJson") ||
Util.methodHasIgnore(visitor.methods['toJson']!))) {
if (annotation.read("toJsonMethod").boolValue &&
(!visitor.methods.containsKey("toJson") ||
Util.methodHasIgnore(visitor.methods['toJson']!))) {
classBuffer.writeln('///Converts instance to a map.');
classBuffer.writeln('Map<String, dynamic> toJson() {');
classBuffer.writeln('return toMap();');
classBuffer.writeln('}');
}
if (annotation.read("copyMethod").boolValue && (!visitor.methods.containsKey("copy") ||
Util.methodHasIgnore(visitor.methods['copy']!))) {
if (annotation.read("copyMethod").boolValue &&
(!visitor.methods.containsKey("copy") ||
Util.methodHasIgnore(visitor.methods['copy']!))) {
classBuffer.writeln('///Returns a copy of $extClassName.');
classBuffer.writeln('$extClassName copy() {');
classBuffer.writeln('return $extClassName.fromMap(toMap()) ?? $extClassName();');
classBuffer
.writeln('return $extClassName.fromMap(toMap()) ?? $extClassName();');
classBuffer.writeln('}');
}
if (annotation.read("toStringMethod").boolValue && (!visitor.methods.containsKey("toString") ||
Util.methodHasIgnore(visitor.methods['toString']!))) {
if (annotation.read("toStringMethod").boolValue &&
(!visitor.methods.containsKey("toString") ||
Util.methodHasIgnore(visitor.methods['toString']!))) {
classBuffer.writeln('@override');
classBuffer.writeln('String toString() {');
classBuffer.write('return \'$extClassName{');
final fieldNames = <String>[];
if (superClass != null) {
for (final fieldElement in superClass.element2.fields) {
for (final fieldElement in superClass.element.fields) {
final fieldName = fieldElement.name;
if (!fieldElement.isPrivate &&
!fieldElement.hasDeprecated &&
@ -505,34 +519,32 @@ class ExchangeableObjectGenerator
}
String getFromMapValue(String value, DartType elementType) {
final fieldTypeElement = elementType.element2;
final fieldTypeElement = elementType.element;
final isNullable = Util.typeIsNullable(elementType);
if (elementType.getDisplayString(withNullability: false) == "Uri") {
final displayString = elementType.getDisplayString(withNullability: false);
if (displayString == "Uri") {
if (!isNullable) {
return "(Uri.tryParse($value) ?? Uri())";
} else {
return "$value != null ? Uri.tryParse($value) : null";
}
} else if (elementType.getDisplayString(withNullability: false) == "WebUri") {
} else if (displayString == "WebUri") {
if (!isNullable) {
return "WebUri($value)";
} else {
return "$value != null ? WebUri($value) : null";
}
} else if (elementType.getDisplayString(withNullability: false) ==
"Color") {
} else if (displayString == "Color" || displayString == "Color_") {
if (!isNullable) {
return "UtilColor.fromStringRepresentation($value)!";
} else {
return "$value != null ? UtilColor.fromStringRepresentation($value) : null";
}
} else if (elementType.getDisplayString(withNullability: false) ==
"EdgeInsets") {
} else if (displayString == "EdgeInsets") {
return "MapEdgeInsets.fromMap($value?.cast<String, dynamic>())${!isNullable ? '!' : ''}";
} else if (elementType.getDisplayString(withNullability: false) == "Size") {
} else if (displayString == "Size") {
return "MapSize.fromMap($value?.cast<String, dynamic>())${!isNullable ? '!' : ''}";
} else if (elementType.getDisplayString(withNullability: false) ==
"DateTime") {
} else if (displayString == "DateTime") {
if (!isNullable) {
return "DateTime.fromMillisecondsSinceEpoch($value)!";
} else {
@ -541,7 +553,9 @@ class ExchangeableObjectGenerator
} else if (elementType.isDartCoreList || elementType.isDartCoreSet) {
final genericTypes = Util.getGenericTypes(elementType);
final genericType = genericTypes.isNotEmpty ? genericTypes.first : null;
final genericTypeReplaced = genericType != null ? genericType.toString().replaceAll("_", "") : null;
final genericTypeReplaced = genericType != null
? genericType.toString().replaceAll("_", "")
: null;
if (genericType != null && !Util.isDartCoreType(genericType)) {
final genericTypeFieldName = 'e';
return (isNullable ? '$value != null ? ' : '') +
@ -553,7 +567,10 @@ class ExchangeableObjectGenerator
(isNullable ? ' : null' : '');
} else {
if (genericType != null) {
return "$value${isNullable ? '?' : ''}.cast<${genericTypeReplaced}>()";
return (isNullable ? '$value != null ? ' : '') +
"${elementType.isDartCoreSet ? 'Set' : 'List'}<$genericTypeReplaced>.from(" +
"$value!.cast<${genericTypeReplaced}>())" +
(isNullable ? ' : null' : '');
} else {
return value;
}
@ -592,22 +609,20 @@ class ExchangeableObjectGenerator
}
String getToMapValue(String fieldName, DartType elementType) {
final fieldTypeElement = elementType.element2;
final fieldTypeElement = elementType.element;
final isNullable = Util.typeIsNullable(elementType);
if (elementType.getDisplayString(withNullability: false) == "Uri") {
final displayString = elementType.getDisplayString(withNullability: false);
if (displayString == "Uri") {
return fieldName + (isNullable ? '?' : '') + '.toString()';
} else if (elementType.getDisplayString(withNullability: false) == "WebUri") {
} else if (displayString == "WebUri") {
return fieldName + (isNullable ? '?' : '') + '.toString()';
} else if (elementType.getDisplayString(withNullability: false) ==
"Color") {
} else if (displayString == "Color" || displayString == "Color_") {
return fieldName + (isNullable ? '?' : '') + '.toHex()';
} else if (elementType.getDisplayString(withNullability: false) ==
"EdgeInsets") {
} else if (displayString == "EdgeInsets") {
return fieldName + (isNullable ? '?' : '') + '.toMap()';
} else if (elementType.getDisplayString(withNullability: false) == "Size") {
} else if (displayString == "Size") {
return fieldName + (isNullable ? '?' : '') + '.toMap()';
} else if (elementType.getDisplayString(withNullability: false) ==
"DateTime") {
} else if (displayString == "DateTime") {
return fieldName + (isNullable ? '?' : '') + '.millisecondsSinceEpoch';
} else if (elementType.isDartCoreList || elementType.isDartCoreSet) {
final genericType = Util.getGenericTypes(elementType).first;
@ -619,7 +634,9 @@ class ExchangeableObjectGenerator
getToMapValue('$genericTypeFieldName', genericType) +
').toList()';
} else {
return elementType.isDartCoreSet ? "$fieldName${(isNullable ? '?' : '')}.toList()" : fieldName;
return elementType.isDartCoreSet
? "$fieldName${(isNullable ? '?' : '')}.toList()"
: fieldName;
}
} else if (fieldTypeElement != null && hasToMapMethod(fieldTypeElement)) {
return fieldName +

View File

@ -82,7 +82,7 @@ abstract class Util {
}
static bool canHaveGenerics(DartType type) {
final element = type.element2;
final element = type.element;
if (element is ClassElement) {
return element.typeParameters.isNotEmpty;
}
@ -104,6 +104,6 @@ abstract class Util {
type.isDartCoreSet ||
type.isDartCoreString ||
type.isDartCoreSymbol ||
type.isDynamic;
type is DynamicType;
}
}

View File

@ -5,177 +5,202 @@ packages:
dependency: transitive
description:
name: _fe_analyzer_shared
url: "https://pub.dartlang.org"
sha256: "405666cd3cf0ee0a48d21ec67e65406aad2c726d9fa58840d3375e7bdcd32a07"
url: "https://pub.dev"
source: hosted
version: "49.0.0"
version: "60.0.0"
analyzer:
dependency: transitive
description:
name: analyzer
url: "https://pub.dartlang.org"
sha256: "1952250bd005bacb895a01bf1b4dc00e3ba1c526cf47dca54dfe24979c65f5b3"
url: "https://pub.dev"
source: hosted
version: "5.1.0"
version: "5.12.0"
args:
dependency: transitive
description:
name: args
url: "https://pub.dartlang.org"
sha256: c372bb384f273f0c2a8aaaa226dad84dc27c8519a691b888725dec59518ad53a
url: "https://pub.dev"
source: hosted
version: "2.3.1"
version: "2.4.1"
async:
dependency: transitive
description:
name: async
url: "https://pub.dartlang.org"
sha256: "947bfcf187f74dbc5e146c9eb9c0f10c9f8b30743e341481c1e2ed3ecc18c20c"
url: "https://pub.dev"
source: hosted
version: "2.9.0"
version: "2.11.0"
boolean_selector:
dependency: transitive
description:
name: boolean_selector
url: "https://pub.dartlang.org"
sha256: "6cfb5af12253eaf2b368f07bacc5a80d1301a071c73360d746b7f2e32d762c66"
url: "https://pub.dev"
source: hosted
version: "2.1.0"
version: "2.1.1"
build:
dependency: "direct main"
description:
name: build
url: "https://pub.dartlang.org"
sha256: "43865b79fbb78532e4bff7c33087aa43b1d488c4fdef014eaef568af6d8016dc"
url: "https://pub.dev"
source: hosted
version: "2.3.1"
version: "2.4.0"
build_config:
dependency: transitive
description:
name: build_config
url: "https://pub.dartlang.org"
sha256: bf80fcfb46a29945b423bd9aad884590fb1dc69b330a4d4700cac476af1708d1
url: "https://pub.dev"
source: hosted
version: "1.1.0"
version: "1.1.1"
build_daemon:
dependency: transitive
description:
name: build_daemon
url: "https://pub.dartlang.org"
sha256: "5f02d73eb2ba16483e693f80bee4f088563a820e47d1027d4cdfe62b5bb43e65"
url: "https://pub.dev"
source: hosted
version: "3.1.0"
version: "4.0.0"
build_resolvers:
dependency: transitive
description:
name: build_resolvers
url: "https://pub.dartlang.org"
sha256: db49b8609ef8c81cca2b310618c3017c00f03a92af44c04d310b907b2d692d95
url: "https://pub.dev"
source: hosted
version: "2.0.10"
version: "2.2.0"
build_runner:
dependency: "direct dev"
description:
name: build_runner
url: "https://pub.dartlang.org"
sha256: "87e06c939450b9b94e3e1bb2d46e0e9780adbff5500d3969f2ba2de6bbb860cb"
url: "https://pub.dev"
source: hosted
version: "2.2.1"
version: "2.4.2"
build_runner_core:
dependency: transitive
description:
name: build_runner_core
url: "https://pub.dartlang.org"
sha256: "30859c90e9ddaccc484f56303931f477b1f1ba2bab74aa32ed5d6ce15870f8cf"
url: "https://pub.dev"
source: hosted
version: "7.2.4"
version: "7.2.8"
build_test:
dependency: "direct dev"
description:
name: build_test
url: "https://pub.dartlang.org"
sha256: "927ef98b58c5603ec58923c0bb943a74743e58149732665885bb1eb92983befe"
url: "https://pub.dev"
source: hosted
version: "2.1.5"
version: "2.1.7"
built_collection:
dependency: transitive
description:
name: built_collection
url: "https://pub.dartlang.org"
sha256: "376e3dd27b51ea877c28d525560790aee2e6fbb5f20e2f85d5081027d94e2100"
url: "https://pub.dev"
source: hosted
version: "5.1.1"
built_value:
dependency: transitive
description:
name: built_value
url: "https://pub.dartlang.org"
sha256: "2f17434bd5d52a26762043d6b43bb53b3acd029b4d9071a329f46d67ef297e6d"
url: "https://pub.dev"
source: hosted
version: "8.4.1"
version: "8.5.0"
characters:
dependency: transitive
description:
name: characters
url: "https://pub.dartlang.org"
sha256: "04a925763edad70e8443c99234dc3328f442e811f1d8fd1a72f1c8ad0f69a605"
url: "https://pub.dev"
source: hosted
version: "1.2.1"
version: "1.3.0"
checked_yaml:
dependency: transitive
description:
name: checked_yaml
url: "https://pub.dartlang.org"
sha256: feb6bed21949061731a7a75fc5d2aa727cf160b91af9a3e464c5e3a32e28b5ff
url: "https://pub.dev"
source: hosted
version: "2.0.1"
version: "2.0.3"
code_builder:
dependency: transitive
description:
name: code_builder
url: "https://pub.dartlang.org"
sha256: "0d43dd1288fd145de1ecc9a3948ad4a6d5a82f0a14c4fdd0892260787d975cbe"
url: "https://pub.dev"
source: hosted
version: "4.3.0"
version: "4.4.0"
collection:
dependency: transitive
description:
name: collection
url: "https://pub.dartlang.org"
sha256: "4a07be6cb69c84d677a6c3096fcf960cc3285a8330b4603e0d463d15d9bd934c"
url: "https://pub.dev"
source: hosted
version: "1.16.0"
version: "1.17.1"
convert:
dependency: transitive
description:
name: convert
url: "https://pub.dartlang.org"
sha256: "0f08b14755d163f6e2134cb58222dd25ea2a2ee8a195e53983d57c075324d592"
url: "https://pub.dev"
source: hosted
version: "3.0.2"
version: "3.1.1"
coverage:
dependency: transitive
description:
name: coverage
url: "https://pub.dartlang.org"
sha256: "2fb815080e44a09b85e0f2ca8a820b15053982b2e714b59267719e8a9ff17097"
url: "https://pub.dev"
source: hosted
version: "1.6.1"
version: "1.6.3"
crypto:
dependency: transitive
description:
name: crypto
url: "https://pub.dartlang.org"
sha256: ff625774173754681d66daaf4a448684fb04b78f902da9cb3d308c19cc5e8bab
url: "https://pub.dev"
source: hosted
version: "3.0.2"
version: "3.0.3"
csslib:
dependency: transitive
description:
name: csslib
url: "https://pub.dartlang.org"
sha256: b36c7f7e24c0bdf1bf9a3da461c837d1de64b9f8beb190c9011d8c72a3dfd745
url: "https://pub.dev"
source: hosted
version: "0.17.2"
dart_style:
dependency: transitive
description:
name: dart_style
url: "https://pub.dartlang.org"
sha256: f4f1f73ab3fd2afcbcca165ee601fe980d966af6a21b5970c6c9376955c528ad
url: "https://pub.dev"
source: hosted
version: "2.2.4"
version: "2.3.1"
file:
dependency: transitive
description:
name: file
url: "https://pub.dartlang.org"
sha256: "1b92bec4fc2a72f59a8e15af5f52cd441e4a7860b49499d69dfa817af20e925d"
url: "https://pub.dev"
source: hosted
version: "6.1.4"
fixnum:
dependency: transitive
description:
name: fixnum
url: "https://pub.dartlang.org"
sha256: "25517a4deb0c03aa0f32fd12db525856438902d9c16536311e76cdc57b31d7d1"
url: "https://pub.dev"
source: hosted
version: "1.0.1"
version: "1.1.0"
flutter:
dependency: "direct main"
description: flutter
@ -185,177 +210,210 @@ packages:
dependency: "direct main"
description:
name: flutter_inappwebview_internal_annotations
url: "https://pub.dartlang.org"
sha256: "064a8ccbc76217dcd3b0fd6c6ea6f549e69b2849a0233b5bb46af9632c3ce2ff"
url: "https://pub.dev"
source: hosted
version: "1.1.0"
frontend_server_client:
dependency: transitive
description:
name: frontend_server_client
url: "https://pub.dartlang.org"
sha256: "408e3ca148b31c20282ad6f37ebfa6f4bdc8fede5b74bc2f08d9d92b55db3612"
url: "https://pub.dev"
source: hosted
version: "2.1.3"
version: "3.2.0"
glob:
dependency: transitive
description:
name: glob
url: "https://pub.dartlang.org"
sha256: "4515b5b6ddb505ebdd242a5f2cc5d22d3d6a80013789debfbda7777f47ea308c"
url: "https://pub.dev"
source: hosted
version: "2.1.0"
version: "2.1.1"
graphs:
dependency: transitive
description:
name: graphs
url: "https://pub.dartlang.org"
sha256: "772db3d53d23361d4ffcf5a9bb091cf3ee9b22f2be52cd107cd7a2683a89ba0e"
url: "https://pub.dev"
source: hosted
version: "2.1.0"
version: "2.3.0"
html:
dependency: transitive
description:
name: html
url: "https://pub.dartlang.org"
sha256: "58e3491f7bf0b6a4ea5110c0c688877460d1a6366731155c4a4580e7ded773e8"
url: "https://pub.dev"
source: hosted
version: "0.15.0"
version: "0.15.3"
http_multi_server:
dependency: transitive
description:
name: http_multi_server
url: "https://pub.dartlang.org"
sha256: "97486f20f9c2f7be8f514851703d0119c3596d14ea63227af6f7a481ef2b2f8b"
url: "https://pub.dev"
source: hosted
version: "3.2.1"
http_parser:
dependency: transitive
description:
name: http_parser
url: "https://pub.dartlang.org"
sha256: "2aa08ce0341cc9b354a498388e30986515406668dbcc4f7c950c3e715496693b"
url: "https://pub.dev"
source: hosted
version: "4.0.1"
version: "4.0.2"
io:
dependency: transitive
description:
name: io
url: "https://pub.dartlang.org"
sha256: "2ec25704aba361659e10e3e5f5d672068d332fc8ac516421d483a11e5cbd061e"
url: "https://pub.dev"
source: hosted
version: "1.0.3"
version: "1.0.4"
js:
dependency: transitive
description:
name: js
url: "https://pub.dartlang.org"
sha256: f2c445dce49627136094980615a031419f7f3eb393237e4ecd97ac15dea343f3
url: "https://pub.dev"
source: hosted
version: "0.6.4"
version: "0.6.7"
json_annotation:
dependency: transitive
description:
name: json_annotation
url: "https://pub.dartlang.org"
sha256: b10a7b2ff83d83c777edba3c6a0f97045ddadd56c944e1a23a3fdf43a1bf4467
url: "https://pub.dev"
source: hosted
version: "4.7.0"
version: "4.8.1"
logging:
dependency: transitive
description:
name: logging
url: "https://pub.dartlang.org"
sha256: "04094f2eb032cbb06c6f6e8d3607edcfcb0455e2bb6cbc010cb01171dcb64e6d"
url: "https://pub.dev"
source: hosted
version: "1.0.2"
version: "1.1.1"
matcher:
dependency: transitive
description:
name: matcher
url: "https://pub.dartlang.org"
sha256: "6501fbd55da300384b768785b83e5ce66991266cec21af89ab9ae7f5ce1c4cbb"
url: "https://pub.dev"
source: hosted
version: "0.12.12"
version: "0.12.15"
material_color_utilities:
dependency: transitive
description:
name: material_color_utilities
url: "https://pub.dartlang.org"
sha256: d92141dc6fe1dad30722f9aa826c7fbc896d021d792f80678280601aff8cf724
url: "https://pub.dev"
source: hosted
version: "0.1.5"
version: "0.2.0"
meta:
dependency: transitive
description:
name: meta
url: "https://pub.dartlang.org"
sha256: "3c74dbf8763d36539f114c799d8a2d87343b5067e9d796ca22b5eb8437090ee3"
url: "https://pub.dev"
source: hosted
version: "1.8.0"
version: "1.9.1"
mime:
dependency: transitive
description:
name: mime
url: "https://pub.dartlang.org"
sha256: e4ff8e8564c03f255408decd16e7899da1733852a9110a58fe6d1b817684a63e
url: "https://pub.dev"
source: hosted
version: "1.0.2"
version: "1.0.4"
node_preamble:
dependency: transitive
description:
name: node_preamble
url: "https://pub.dartlang.org"
sha256: "6e7eac89047ab8a8d26cf16127b5ed26de65209847630400f9aefd7cd5c730db"
url: "https://pub.dev"
source: hosted
version: "2.0.1"
version: "2.0.2"
package_config:
dependency: transitive
description:
name: package_config
url: "https://pub.dartlang.org"
sha256: "1c5b77ccc91e4823a5af61ee74e6b972db1ef98c2ff5a18d3161c982a55448bd"
url: "https://pub.dev"
source: hosted
version: "2.1.0"
path:
dependency: transitive
description:
name: path
url: "https://pub.dartlang.org"
sha256: "8829d8a55c13fc0e37127c29fedf290c102f4e40ae94ada574091fe0ff96c917"
url: "https://pub.dev"
source: hosted
version: "1.8.2"
version: "1.8.3"
pool:
dependency: transitive
description:
name: pool
url: "https://pub.dartlang.org"
sha256: "20fe868b6314b322ea036ba325e6fc0711a22948856475e2c2b6306e8ab39c2a"
url: "https://pub.dev"
source: hosted
version: "1.5.1"
protobuf:
dependency: transitive
description:
name: protobuf
sha256: "01dd9bd0fa02548bf2ceee13545d4a0ec6046459d847b6b061d8a27237108a08"
url: "https://pub.dev"
source: hosted
version: "2.1.0"
pub_semver:
dependency: transitive
description:
name: pub_semver
url: "https://pub.dartlang.org"
sha256: "40d3ab1bbd474c4c2328c91e3a7df8c6dd629b79ece4c4bd04bee496a224fb0c"
url: "https://pub.dev"
source: hosted
version: "2.1.1"
version: "2.1.4"
pubspec_parse:
dependency: transitive
description:
name: pubspec_parse
url: "https://pub.dartlang.org"
sha256: c63b2876e58e194e4b0828fcb080ad0e06d051cb607a6be51a9e084f47cb9367
url: "https://pub.dev"
source: hosted
version: "1.2.1"
version: "1.2.3"
shelf:
dependency: transitive
description:
name: shelf
url: "https://pub.dartlang.org"
sha256: ad29c505aee705f41a4d8963641f91ac4cee3c8fad5947e033390a7bd8180fa4
url: "https://pub.dev"
source: hosted
version: "1.4.0"
version: "1.4.1"
shelf_packages_handler:
dependency: transitive
description:
name: shelf_packages_handler
url: "https://pub.dartlang.org"
sha256: "89f967eca29607c933ba9571d838be31d67f53f6e4ee15147d5dc2934fee1b1e"
url: "https://pub.dev"
source: hosted
version: "3.0.1"
version: "3.0.2"
shelf_static:
dependency: transitive
description:
name: shelf_static
url: "https://pub.dartlang.org"
sha256: a41d3f53c4adf0f57480578c1d61d90342cd617de7fc8077b1304643c2d85c1e
url: "https://pub.dev"
source: hosted
version: "1.1.1"
version: "1.1.2"
shelf_web_socket:
dependency: transitive
description:
name: shelf_web_socket
url: "https://pub.dartlang.org"
sha256: "9ca081be41c60190ebcb4766b2486a7d50261db7bd0f5d9615f2d653637a84c1"
url: "https://pub.dev"
source: hosted
version: "1.0.2"
version: "1.0.4"
sky_engine:
dependency: transitive
description: flutter
@ -365,142 +423,162 @@ packages:
dependency: "direct main"
description:
name: source_gen
url: "https://pub.dartlang.org"
sha256: "378a173055cd1fcd2a36e94bf254786d6812688b5f53b6038a2fd180a5a5e210"
url: "https://pub.dev"
source: hosted
version: "1.2.5"
version: "1.3.1"
source_map_stack_trace:
dependency: transitive
description:
name: source_map_stack_trace
url: "https://pub.dartlang.org"
sha256: "84cf769ad83aa6bb61e0aa5a18e53aea683395f196a6f39c4c881fb90ed4f7ae"
url: "https://pub.dev"
source: hosted
version: "2.1.0"
version: "2.1.1"
source_maps:
dependency: transitive
description:
name: source_maps
url: "https://pub.dartlang.org"
sha256: "708b3f6b97248e5781f493b765c3337db11c5d2c81c3094f10904bfa8004c703"
url: "https://pub.dev"
source: hosted
version: "0.10.10"
version: "0.10.12"
source_span:
dependency: transitive
description:
name: source_span
url: "https://pub.dartlang.org"
sha256: "53e943d4206a5e30df338fd4c6e7a077e02254531b138a15aec3bd143c1a8b3c"
url: "https://pub.dev"
source: hosted
version: "1.9.1"
version: "1.10.0"
stack_trace:
dependency: transitive
description:
name: stack_trace
url: "https://pub.dartlang.org"
sha256: c3c7d8edb15bee7f0f74debd4b9c5f3c2ea86766fe4178eb2a18eb30a0bdaed5
url: "https://pub.dev"
source: hosted
version: "1.10.0"
version: "1.11.0"
stream_channel:
dependency: transitive
description:
name: stream_channel
url: "https://pub.dartlang.org"
sha256: "83615bee9045c1d322bbbd1ba209b7a749c2cbcdcb3fdd1df8eb488b3279c1c8"
url: "https://pub.dev"
source: hosted
version: "2.1.1"
stream_transform:
dependency: transitive
description:
name: stream_transform
url: "https://pub.dartlang.org"
sha256: "14a00e794c7c11aa145a170587321aedce29769c08d7f58b1d141da75e3b1c6f"
url: "https://pub.dev"
source: hosted
version: "2.0.0"
version: "2.1.0"
string_scanner:
dependency: transitive
description:
name: string_scanner
url: "https://pub.dartlang.org"
sha256: "556692adab6cfa87322a115640c11f13cb77b3f076ddcc5d6ae3c20242bedcde"
url: "https://pub.dev"
source: hosted
version: "1.1.1"
version: "1.2.0"
term_glyph:
dependency: transitive
description:
name: term_glyph
url: "https://pub.dartlang.org"
sha256: a29248a84fbb7c79282b40b8c72a1209db169a2e0542bce341da992fe1bc7e84
url: "https://pub.dev"
source: hosted
version: "1.2.1"
test:
dependency: "direct dev"
description:
name: test
url: "https://pub.dartlang.org"
sha256: "4f92f103ef63b1bbac6f4bd1930624fca81b2574464482512c4f0896319be575"
url: "https://pub.dev"
source: hosted
version: "1.21.6"
version: "1.24.2"
test_api:
dependency: transitive
description:
name: test_api
url: "https://pub.dartlang.org"
sha256: daadc9baabec998b062c9091525aa95786508b1c48e9c30f1f891b8bf6ff2e64
url: "https://pub.dev"
source: hosted
version: "0.4.14"
version: "0.5.2"
test_core:
dependency: transitive
description:
name: test_core
url: "https://pub.dartlang.org"
sha256: "3642b184882f79e76ca57a9230fb971e494c3c1fd09c21ae3083ce891bcc0aa1"
url: "https://pub.dev"
source: hosted
version: "0.4.18"
version: "0.5.2"
timing:
dependency: transitive
description:
name: timing
url: "https://pub.dartlang.org"
sha256: "70a3b636575d4163c477e6de42f247a23b315ae20e86442bebe32d3cabf61c32"
url: "https://pub.dev"
source: hosted
version: "1.0.0"
version: "1.0.1"
typed_data:
dependency: transitive
description:
name: typed_data
url: "https://pub.dartlang.org"
sha256: facc8d6582f16042dd49f2463ff1bd6e2c9ef9f3d5da3d9b087e244a7b564b3c
url: "https://pub.dev"
source: hosted
version: "1.3.1"
version: "1.3.2"
vector_math:
dependency: transitive
description:
name: vector_math
url: "https://pub.dartlang.org"
sha256: "80b3257d1492ce4d091729e3a67a60407d227c27241d6927be0130c98e741803"
url: "https://pub.dev"
source: hosted
version: "2.1.2"
version: "2.1.4"
vm_service:
dependency: transitive
description:
name: vm_service
url: "https://pub.dartlang.org"
sha256: "1311639ad908dfdcb64734ac1fbd60416234c06e4351846783a79c56848a5185"
url: "https://pub.dev"
source: hosted
version: "9.4.0"
version: "11.7.0"
watcher:
dependency: transitive
description:
name: watcher
url: "https://pub.dartlang.org"
sha256: "6a7f46926b01ce81bfc339da6a7f20afbe7733eff9846f6d6a5466aa4c6667c0"
url: "https://pub.dev"
source: hosted
version: "1.0.1"
version: "1.0.2"
web_socket_channel:
dependency: transitive
description:
name: web_socket_channel
url: "https://pub.dartlang.org"
sha256: d88238e5eac9a42bb43ca4e721edba3c08c6354d4a53063afaa568516217621b
url: "https://pub.dev"
source: hosted
version: "2.2.0"
version: "2.4.0"
webkit_inspection_protocol:
dependency: transitive
description:
name: webkit_inspection_protocol
url: "https://pub.dartlang.org"
sha256: "67d3a8b6c79e1987d19d848b0892e582dbb0c66c57cc1fef58a177dd2aa2823d"
url: "https://pub.dev"
source: hosted
version: "1.2.0"
yaml:
dependency: transitive
description:
name: yaml
url: "https://pub.dartlang.org"
sha256: "75769501ea3489fca56601ff33454fe45507ea3bfb014161abc3b43ae25989d5"
url: "https://pub.dev"
source: hosted
version: "3.1.1"
version: "3.1.2"
sdks:
dart: ">=2.18.0 <3.0.0"
dart: ">=3.0.0-134.0.dev <4.0.0"
flutter: ">=2.5.0"

View File

@ -10,11 +10,11 @@ environment:
dependencies:
flutter:
sdk: flutter
build: ^2.3.1
source_gen: ^1.2.5
build: ^2.4.0
source_gen: ^1.3.1
flutter_inappwebview_internal_annotations: ^1.1.0
dev_dependencies:
build_runner: ^2.2.1
build_test: ^2.1.5
test: ^1.21.1
build_runner: ^2.4.2
build_test: ^2.1.7
test: ^1.24.2

View File

@ -25,6 +25,8 @@ apply plugin: 'com.android.application'
apply from: "$flutterRoot/packages/flutter_tools/gradle/flutter.gradle"
android {
namespace 'com.pichillilorenzo.flutterwebviewexample'
compileOptions {
sourceCompatibility 1.8
targetCompatibility 1.8
@ -32,9 +34,6 @@ android {
compileSdkVersion 33
lintOptions {
disable 'InvalidPackage'
}
defaultConfig {
// TODO: Specify your own unique Application ID (https://developer.android.com/studio/build/application-id.html).
@ -54,6 +53,10 @@ android {
signingConfig signingConfigs.debug
}
}
namespace 'com.pichillilorenzo.flutterwebviewexample'
lint {
disable 'InvalidPackage'
}
}
flutter {

View File

@ -1,5 +1,4 @@
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.pichillilorenzo.flutterwebviewexample">
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
<!-- Flutter needs it to communicate with the running application
to allow setting breakpoints, to provide hot reload, etc.
-->

View File

@ -1,5 +1,4 @@
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.pichillilorenzo.flutterwebviewexample">
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
<!-- The INTERNET permission is required for development. Specifically,
flutter needs it to communicate with the running application

View File

@ -1,5 +1,4 @@
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.pichillilorenzo.flutterwebviewexample">
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
<!-- Flutter needs it to communicate with the running application
to allow setting breakpoints, to provide hot reload, etc.
-->

View File

@ -1,12 +1,12 @@
buildscript {
ext.kotlin_version = '1.6.10'
ext.kotlin_version = '1.6.21'
repositories {
google()
mavenCentral()
}
dependencies {
classpath 'com.android.tools.build:gradle:4.1.0'
classpath 'com.android.tools.build:gradle:7.4.2'
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
}
}
@ -26,6 +26,6 @@ subprojects {
project.evaluationDependsOn(':app')
}
task clean(type: Delete) {
tasks.register("clean", Delete) {
delete rootProject.buildDir
}

View File

@ -2,3 +2,6 @@ org.gradle.jvmargs=-Xmx1536M
android.useAndroidX=true
android.enableJetifier=true
android.enableR8=true
android.defaults.buildfeatures.buildconfig=true
android.nonTransitiveRClass=false
android.nonFinalResIds=false

View File

@ -3,4 +3,4 @@ distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-6.7-all.zip
distributionUrl=https\://services.gradle.org/distributions/gradle-7.6-all.zip

View File

@ -45,7 +45,7 @@ void openAndClose() {
activityButton: ActivityButton(
templateImage: UIImage(systemName: "sun.max"),
extensionIdentifier:
"com.pichillilorenzo.flutter-inappwebview6-example.test")));
"com.pichillilorenzo.flutter-inappwebview-example7.test")));
await chromeSafariBrowser.opened.future;
expect(chromeSafariBrowser.isOpened(), true);
expect(() async {

View File

@ -27,4 +27,4 @@ final TEST_SERVICE_WORKER_URL = WebUri(
'https://mdn.github.io/dom-examples/service-worker/simple-service-worker/');
final TEST_WEBVIEW_ASSET_LOADER_DOMAIN = 'my.custom.domain.com';
final TEST_WEBVIEW_ASSET_LOADER_URL = WebUri(
'https://$TEST_WEBVIEW_ASSET_LOADER_DOMAIN/assets/flutter_assets/assets/website/index.html');
'https://$TEST_WEBVIEW_ASSET_LOADER_DOMAIN/assets/flutter_assets/test_assets/website/index.html');

View File

@ -1,6 +1,6 @@
#!/bin/sh
# This is a generated file; do not edit or check into version control.
export "FLUTTER_ROOT=/Users/lorenzopichilli/fvm/versions/3.3.6"
export "FLUTTER_ROOT=/Users/lorenzopichilli/fvm/versions/3.10.0"
export "FLUTTER_APPLICATION_PATH=/Users/lorenzopichilli/Desktop/flutter_inappwebview/example"
export "COCOAPODS_PARALLEL_CODE_SIGN=true"
export "FLUTTER_TARGET=lib/main.dart"

View File

@ -3,21 +3,20 @@
archiveVersion = 1;
classes = {
};
objectVersion = 50;
objectVersion = 54;
objects = {
/* Begin PBXBuildFile section */
020EF14E4245221B2C22ACE5 /* Pods_Runner.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = B0FC2CF7A6002799890B3102 /* Pods_Runner.framework */; };
1498D2341E8E89220040F4C2 /* GeneratedPluginRegistrant.m in Sources */ = {isa = PBXBuildFile; fileRef = 1498D2331E8E89220040F4C2 /* GeneratedPluginRegistrant.m */; };
25A517508F43E58C47090625 /* (null) in Frameworks */ = {isa = PBXBuildFile; };
3B3967161E833CAA004F5970 /* AppFrameworkInfo.plist in Resources */ = {isa = PBXBuildFile; fileRef = 3B3967151E833CAA004F5970 /* AppFrameworkInfo.plist */; };
6143FF37290959650014A1FC /* UniformTypeIdentifiers.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 6143FF36290959650014A1FC /* UniformTypeIdentifiers.framework */; };
6143FF3A290959650014A1FC /* Media.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 6143FF39290959650014A1FC /* Media.xcassets */; };
6143FF3C290959650014A1FC /* ActionViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6143FF3B290959650014A1FC /* ActionViewController.swift */; };
6143FF3F290959650014A1FC /* MainInterface.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 6143FF3D290959650014A1FC /* MainInterface.storyboard */; };
6143FF43290959650014A1FC /* test.appex in Embed App Extensions */ = {isa = PBXBuildFile; fileRef = 6143FF35290959650014A1FC /* test.appex */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
6143FF43290959650014A1FC /* test.appex in Embed Foundation Extensions */ = {isa = PBXBuildFile; fileRef = 6143FF35290959650014A1FC /* test.appex */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
61FF730023634CA10069C557 /* libsqlite3.tbd in Frameworks */ = {isa = PBXBuildFile; fileRef = 61FF72FF23634CA10069C557 /* libsqlite3.tbd */; };
74858FAF1ED2DC5600515810 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 74858FAE1ED2DC5600515810 /* AppDelegate.swift */; };
75018AFBF33C6954B9C375F0 /* Pods_Runner.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 86871EBA13742A6D5F3F398B /* Pods_Runner.framework */; };
97C146FE1CF9000F007C117D /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 97C146FD1CF9000F007C117D /* Assets.xcassets */; };
97C147011CF9000F007C117D /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 97C146FF1CF9000F007C117D /* LaunchScreen.storyboard */; };
EDC1147F21735BC200D2247A /* Main.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 97C146FA1CF9000F007C117D /* Main.storyboard */; };
@ -34,15 +33,15 @@
/* End PBXContainerItemProxy section */
/* Begin PBXCopyFilesBuildPhase section */
6174FE1725CEB74E00A5020C /* Embed App Extensions */ = {
6174FE1725CEB74E00A5020C /* Embed Foundation Extensions */ = {
isa = PBXCopyFilesBuildPhase;
buildActionMask = 2147483647;
dstPath = "";
dstSubfolderSpec = 13;
files = (
6143FF43290959650014A1FC /* test.appex in Embed App Extensions */,
6143FF43290959650014A1FC /* test.appex in Embed Foundation Extensions */,
);
name = "Embed App Extensions";
name = "Embed Foundation Extensions";
runOnlyForDeploymentPostprocessing = 0;
};
/* End PBXCopyFilesBuildPhase section */
@ -62,6 +61,8 @@
74858FAD1ED2DC5600515810 /* Runner-Bridging-Header.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "Runner-Bridging-Header.h"; sourceTree = "<group>"; };
74858FAE1ED2DC5600515810 /* AppDelegate.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = "<group>"; };
7AFA3C8E1D35360C0083082E /* Release.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; name = Release.xcconfig; path = Flutter/Release.xcconfig; sourceTree = "<group>"; };
80ABE07D2023159E36035B32 /* Pods-Runner.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.debug.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.debug.xcconfig"; sourceTree = "<group>"; };
86871EBA13742A6D5F3F398B /* Pods_Runner.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_Runner.framework; sourceTree = BUILT_PRODUCTS_DIR; };
9740EEB21CF90195004384FC /* Debug.xcconfig */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.xcconfig; name = Debug.xcconfig; path = Flutter/Debug.xcconfig; sourceTree = "<group>"; };
9740EEB31CF90195004384FC /* Generated.xcconfig */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.xcconfig; name = Generated.xcconfig; path = Flutter/Generated.xcconfig; sourceTree = "<group>"; };
97C146EE1CF9000F007C117D /* Runner.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Runner.app; sourceTree = BUILT_PRODUCTS_DIR; };
@ -69,9 +70,7 @@
97C146FD1CF9000F007C117D /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = "<group>"; };
97C147001CF9000F007C117D /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/LaunchScreen.storyboard; sourceTree = "<group>"; };
97C147021CF9000F007C117D /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
9D199BB70329114343003314 /* Pods-Runner.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.release.xcconfig"; path = "Pods/Target Support Files/Pods-Runner/Pods-Runner.release.xcconfig"; sourceTree = "<group>"; };
B0FC2CF7A6002799890B3102 /* Pods_Runner.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_Runner.framework; sourceTree = BUILT_PRODUCTS_DIR; };
B23847D2EEA83886DC92B60F /* Pods-Runner.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.debug.xcconfig"; path = "Pods/Target Support Files/Pods-Runner/Pods-Runner.debug.xcconfig"; sourceTree = "<group>"; };
AA4061AE397745454F676BAB /* Pods-Runner.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-Runner.release.xcconfig"; path = "Target Support Files/Pods-Runner/Pods-Runner.release.xcconfig"; sourceTree = "<group>"; };
/* End PBXFileReference section */
/* Begin PBXFrameworksBuildPhase section */
@ -88,8 +87,7 @@
buildActionMask = 2147483647;
files = (
61FF730023634CA10069C557 /* libsqlite3.tbd in Frameworks */,
25A517508F43E58C47090625 /* (null) in Frameworks */,
020EF14E4245221B2C22ACE5 /* Pods_Runner.framework in Frameworks */,
75018AFBF33C6954B9C375F0 /* Pods_Runner.framework in Frameworks */,
);
runOnlyForDeploymentPostprocessing = 0;
};
@ -101,8 +99,8 @@
children = (
61FF730123634DD10069C557 /* flutter_downloader.framework */,
61FF72FF23634CA10069C557 /* libsqlite3.tbd */,
B0FC2CF7A6002799890B3102 /* Pods_Runner.framework */,
6143FF36290959650014A1FC /* UniformTypeIdentifiers.framework */,
86871EBA13742A6D5F3F398B /* Pods_Runner.framework */,
);
name = Frameworks;
sourceTree = "<group>";
@ -118,13 +116,13 @@
path = test;
sourceTree = "<group>";
};
647DC95AB5350DB6D2264FFE /* Pods */ = {
7AC6E2111A9BB885C2D9F6EE /* Pods */ = {
isa = PBXGroup;
children = (
B23847D2EEA83886DC92B60F /* Pods-Runner.debug.xcconfig */,
9D199BB70329114343003314 /* Pods-Runner.release.xcconfig */,
80ABE07D2023159E36035B32 /* Pods-Runner.debug.xcconfig */,
AA4061AE397745454F676BAB /* Pods-Runner.release.xcconfig */,
);
name = Pods;
path = Pods;
sourceTree = "<group>";
};
9740EEB11CF90186004384FC /* Flutter */ = {
@ -145,8 +143,8 @@
97C146F01CF9000F007C117D /* Runner */,
6143FF38290959650014A1FC /* test */,
97C146EF1CF9000F007C117D /* Products */,
647DC95AB5350DB6D2264FFE /* Pods */,
50BAF1DF19E018DDF2B149B9 /* Frameworks */,
7AC6E2111A9BB885C2D9F6EE /* Pods */,
);
sourceTree = "<group>";
};
@ -206,14 +204,14 @@
isa = PBXNativeTarget;
buildConfigurationList = 97C147051CF9000F007C117D /* Build configuration list for PBXNativeTarget "Runner" */;
buildPhases = (
3F62E6580DEAFBE72C090A85 /* [CP] Check Pods Manifest.lock */,
DC1BB9CDFB0410A7329D249A /* [CP] Check Pods Manifest.lock */,
9740EEB61CF901F6004384FC /* Run Script */,
97C146EA1CF9000F007C117D /* Sources */,
97C146EB1CF9000F007C117D /* Frameworks */,
97C146EC1CF9000F007C117D /* Resources */,
3B06AD1E1E4923F5004D2608 /* Thin Binary */,
903A9F2558754FA70D0A7EA8 /* [CP] Embed Pods Frameworks */,
6174FE1725CEB74E00A5020C /* Embed App Extensions */,
6174FE1725CEB74E00A5020C /* Embed Foundation Extensions */,
DFFD8453B8E169BF6BE74B49 /* [CP] Embed Pods Frameworks */,
);
buildRules = (
);
@ -231,6 +229,7 @@
97C146E61CF9000F007C117D /* Project object */ = {
isa = PBXProject;
attributes = {
BuildIndependentTargetsInParallel = YES;
LastSwiftUpdateCheck = 1400;
LastUpgradeCheck = 1300;
ORGANIZATIONNAME = "The Chromium Authors";
@ -298,10 +297,12 @@
/* Begin PBXShellScriptBuildPhase section */
3B06AD1E1E4923F5004D2608 /* Thin Binary */ = {
isa = PBXShellScriptBuildPhase;
alwaysOutOfDate = 1;
buildActionMask = 2147483647;
files = (
);
inputPaths = (
"${TARGET_BUILD_DIR}/${INFOPLIST_PATH}",
);
name = "Thin Binary";
outputPaths = (
@ -310,54 +311,9 @@
shellPath = /bin/sh;
shellScript = "/bin/sh \"$FLUTTER_ROOT/packages/flutter_tools/bin/xcode_backend.sh\" embed_and_thin\n";
};
3F62E6580DEAFBE72C090A85 /* [CP] Check Pods Manifest.lock */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputPaths = (
"${PODS_PODFILE_DIR_PATH}/Podfile.lock",
"${PODS_ROOT}/Manifest.lock",
);
name = "[CP] Check Pods Manifest.lock";
outputPaths = (
"$(DERIVED_FILE_DIR)/Pods-Runner-checkManifestLockResult.txt",
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "diff \"${PODS_PODFILE_DIR_PATH}/Podfile.lock\" \"${PODS_ROOT}/Manifest.lock\" > /dev/null\nif [ $? != 0 ] ; then\n # print error to STDERR\n echo \"error: The sandbox is not in sync with the Podfile.lock. Run 'pod install' or update your CocoaPods installation.\" >&2\n exit 1\nfi\n# This output is used by Xcode 'outputs' to avoid re-running this script phase.\necho \"SUCCESS\" > \"${SCRIPT_OUTPUT_FILE_0}\"\n";
showEnvVarsInLog = 0;
};
903A9F2558754FA70D0A7EA8 /* [CP] Embed Pods Frameworks */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputPaths = (
"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-frameworks.sh",
"${BUILT_PRODUCTS_DIR}/OrderedSet/OrderedSet.framework",
"${BUILT_PRODUCTS_DIR}/flutter_downloader/flutter_downloader.framework",
"${BUILT_PRODUCTS_DIR}/flutter_inappwebview/flutter_inappwebview.framework",
"${BUILT_PRODUCTS_DIR}/integration_test/integration_test.framework",
"${BUILT_PRODUCTS_DIR}/path_provider_ios/path_provider_ios.framework",
"${BUILT_PRODUCTS_DIR}/url_launcher_ios/url_launcher_ios.framework",
);
name = "[CP] Embed Pods Frameworks";
outputPaths = (
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/OrderedSet.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/flutter_downloader.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/flutter_inappwebview.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/integration_test.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/path_provider_ios.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/url_launcher_ios.framework",
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "\"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-frameworks.sh\"\n";
showEnvVarsInLog = 0;
};
9740EEB61CF901F6004384FC /* Run Script */ = {
isa = PBXShellScriptBuildPhase;
alwaysOutOfDate = 1;
buildActionMask = 2147483647;
files = (
);
@ -370,6 +326,56 @@
shellPath = /bin/sh;
shellScript = "/bin/sh \"$FLUTTER_ROOT/packages/flutter_tools/bin/xcode_backend.sh\" build\n";
};
DC1BB9CDFB0410A7329D249A /* [CP] Check Pods Manifest.lock */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputFileListPaths = (
);
inputPaths = (
"${PODS_PODFILE_DIR_PATH}/Podfile.lock",
"${PODS_ROOT}/Manifest.lock",
);
name = "[CP] Check Pods Manifest.lock";
outputFileListPaths = (
);
outputPaths = (
"$(DERIVED_FILE_DIR)/Pods-Runner-checkManifestLockResult.txt",
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "diff \"${PODS_PODFILE_DIR_PATH}/Podfile.lock\" \"${PODS_ROOT}/Manifest.lock\" > /dev/null\nif [ $? != 0 ] ; then\n # print error to STDERR\n echo \"error: The sandbox is not in sync with the Podfile.lock. Run 'pod install' or update your CocoaPods installation.\" >&2\n exit 1\nfi\n# This output is used by Xcode 'outputs' to avoid re-running this script phase.\necho \"SUCCESS\" > \"${SCRIPT_OUTPUT_FILE_0}\"\n";
showEnvVarsInLog = 0;
};
DFFD8453B8E169BF6BE74B49 /* [CP] Embed Pods Frameworks */ = {
isa = PBXShellScriptBuildPhase;
buildActionMask = 2147483647;
files = (
);
inputPaths = (
"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-frameworks.sh",
"${BUILT_PRODUCTS_DIR}/OrderedSet/OrderedSet.framework",
"${BUILT_PRODUCTS_DIR}/flutter_downloader/flutter_downloader.framework",
"${BUILT_PRODUCTS_DIR}/flutter_inappwebview/flutter_inappwebview.framework",
"${BUILT_PRODUCTS_DIR}/integration_test/integration_test.framework",
"${BUILT_PRODUCTS_DIR}/path_provider_foundation/path_provider_foundation.framework",
"${BUILT_PRODUCTS_DIR}/url_launcher_ios/url_launcher_ios.framework",
);
name = "[CP] Embed Pods Frameworks";
outputPaths = (
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/OrderedSet.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/flutter_downloader.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/flutter_inappwebview.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/integration_test.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/path_provider_foundation.framework",
"${TARGET_BUILD_DIR}/${FRAMEWORKS_FOLDER_PATH}/url_launcher_ios.framework",
);
runOnlyForDeploymentPostprocessing = 0;
shellPath = /bin/sh;
shellScript = "\"${PODS_ROOT}/Target Support Files/Pods-Runner/Pods-Runner-frameworks.sh\"\n";
showEnvVarsInLog = 0;
};
/* End PBXShellScriptBuildPhase section */
/* Begin PBXSourcesBuildPhase section */
@ -447,11 +453,15 @@
INFOPLIST_KEY_CFBundleDisplayName = test;
INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2022 The Chromium Authors. All rights reserved.";
IPHONEOS_DEPLOYMENT_TARGET = 16.0;
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @executable_path/../../Frameworks";
LD_RUNPATH_SEARCH_PATHS = (
"$(inherited)",
"@executable_path/Frameworks",
"@executable_path/../../Frameworks",
);
MARKETING_VERSION = 1.0;
MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE;
MTL_FAST_MATH = YES;
PRODUCT_BUNDLE_IDENTIFIER = "com.pichillilorenzo.flutter-inappwebview6-example.test";
PRODUCT_BUNDLE_IDENTIFIER = "com.pichillilorenzo.flutter-inappwebview-example7.test";
PRODUCT_NAME = "$(TARGET_NAME)";
SKIP_INSTALL = YES;
SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG;
@ -481,10 +491,14 @@
INFOPLIST_KEY_CFBundleDisplayName = test;
INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2022 The Chromium Authors. All rights reserved.";
IPHONEOS_DEPLOYMENT_TARGET = 16.0;
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @executable_path/../../Frameworks";
LD_RUNPATH_SEARCH_PATHS = (
"$(inherited)",
"@executable_path/Frameworks",
"@executable_path/../../Frameworks",
);
MARKETING_VERSION = 1.0;
MTL_FAST_MATH = YES;
PRODUCT_BUNDLE_IDENTIFIER = "com.pichillilorenzo.flutter-inappwebview6-example.test";
PRODUCT_BUNDLE_IDENTIFIER = "com.pichillilorenzo.flutter-inappwebview-example7.test";
PRODUCT_NAME = "$(TARGET_NAME)";
SKIP_INSTALL = YES;
SWIFT_EMIT_LOC_STRINGS = YES;
@ -518,6 +532,7 @@
CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES;
CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
CLANG_WARN_STRICT_PROTOTYPES = YES;
CLANG_WARN_SUSPICIOUS_MOVE = YES;
@ -526,7 +541,7 @@
"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
COPY_PHASE_STRIP = NO;
DEBUG_INFORMATION_FORMAT = dwarf;
ENABLE_BITCODE = YES;
ENABLE_BITCODE = NO;
ENABLE_STRICT_OBJC_MSGSEND = YES;
ENABLE_TESTABILITY = YES;
GCC_C_LANGUAGE_STANDARD = gnu99;
@ -543,7 +558,7 @@
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GCC_WARN_UNUSED_FUNCTION = YES;
GCC_WARN_UNUSED_VARIABLE = YES;
IPHONEOS_DEPLOYMENT_TARGET = 11.0;
IPHONEOS_DEPLOYMENT_TARGET = 12.0;
MTL_ENABLE_DEBUG_INFO = YES;
ONLY_ACTIVE_ARCH = YES;
SDKROOT = iphoneos;
@ -576,6 +591,7 @@
CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES;
CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
CLANG_WARN_STRICT_PROTOTYPES = YES;
CLANG_WARN_SUSPICIOUS_MOVE = YES;
@ -584,7 +600,7 @@
"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer";
COPY_PHASE_STRIP = NO;
DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
ENABLE_BITCODE = YES;
ENABLE_BITCODE = NO;
ENABLE_NS_ASSERTIONS = NO;
ENABLE_STRICT_OBJC_MSGSEND = YES;
GCC_C_LANGUAGE_STANDARD = gnu99;
@ -595,9 +611,10 @@
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GCC_WARN_UNUSED_FUNCTION = YES;
GCC_WARN_UNUSED_VARIABLE = YES;
IPHONEOS_DEPLOYMENT_TARGET = 11.0;
IPHONEOS_DEPLOYMENT_TARGET = 12.0;
MTL_ENABLE_DEBUG_INFO = NO;
SDKROOT = iphoneos;
SWIFT_COMPILATION_MODE = wholemodule;
SWIFT_OPTIMIZATION_LEVEL = "-Owholemodule";
SWIFT_VERSION = 5.0;
TARGETED_DEVICE_FAMILY = "1,2";
@ -622,12 +639,15 @@
"$(PROJECT_DIR)/Flutter",
);
INFOPLIST_FILE = Runner/Info.plist;
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks";
LD_RUNPATH_SEARCH_PATHS = (
"$(inherited)",
"@executable_path/Frameworks",
);
LIBRARY_SEARCH_PATHS = (
"$(inherited)",
"$(PROJECT_DIR)/Flutter",
);
PRODUCT_BUNDLE_IDENTIFIER = "com.pichillilorenzo.flutter-inappwebview6-example";
PRODUCT_BUNDLE_IDENTIFIER = "com.pichillilorenzo.flutter-inappwebview-example7";
PRODUCT_NAME = "$(TARGET_NAME)";
PROVISIONING_PROFILE_SPECIFIER = "";
SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h";
@ -654,12 +674,15 @@
"$(PROJECT_DIR)/Flutter",
);
INFOPLIST_FILE = Runner/Info.plist;
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks";
LD_RUNPATH_SEARCH_PATHS = (
"$(inherited)",
"@executable_path/Frameworks",
);
LIBRARY_SEARCH_PATHS = (
"$(inherited)",
"$(PROJECT_DIR)/Flutter",
);
PRODUCT_BUNDLE_IDENTIFIER = "com.pichillilorenzo.flutter-inappwebview6-example";
PRODUCT_BUNDLE_IDENTIFIER = "com.pichillilorenzo.flutter-inappwebview-example7";
PRODUCT_NAME = "$(TARGET_NAME)";
PROVISIONING_PROFILE_SPECIFIER = "";
SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h";

View File

@ -51,6 +51,8 @@
<string>Need location</string>
<key>NSMicrophoneUsageDescription</key>
<string>InAppWebView requires access to mic.</string>
<key>UIApplicationSupportsIndirectInputEvents</key>
<true/>
<key>UIBackgroundModes</key>
<array>
<string>fetch</string>

View File

@ -1,19 +0,0 @@
//
// Generated file. Do not edit.
//
// ignore_for_file: directives_ordering
// ignore_for_file: lines_longer_than_80_chars
// ignore_for_file: depend_on_referenced_packages
import 'package:flutter_inappwebview/flutter_inappwebview.dart';
import 'package:url_launcher_web/url_launcher_web.dart';
import 'package:flutter_web_plugins/flutter_web_plugins.dart';
// ignore: public_member_api_docs
void registerPlugins(Registrar registrar) {
FlutterInAppWebViewWebPlatform.registerWith(registrar);
UrlLauncherPlugin.registerWith(registrar);
registrar.registerMessageHandler();
}

View File

@ -115,6 +115,7 @@ class _InAppBrowserExampleScreenState extends State<InAppBrowserExampleScreen> {
toolbarTopBackgroundColor: Colors.blue,
presentationStyle: ModalPresentationStyle.POPOVER),
webViewSettings: InAppWebViewSettings(
isInspectable: kDebugMode,
useShouldOverrideUrlLoading: true,
useOnLoadResource: true,
),

View File

@ -17,6 +17,7 @@ class _InAppWebViewExampleScreenState extends State<InAppWebViewExampleScreen> {
InAppWebViewController? webViewController;
InAppWebViewSettings settings = InAppWebViewSettings(
isInspectable: kDebugMode,
mediaPlaybackRequiresUserGesture: false,
allowsInlineMediaPlayback: true,
iframeAllow: "camera; microphone",

View File

@ -24,7 +24,7 @@ Future main() async {
// await Permission.storage.request();
if (!kIsWeb && defaultTargetPlatform == TargetPlatform.android) {
await InAppWebViewController.setWebContentsDebuggingEnabled(true);
await InAppWebViewController.setWebContentsDebuggingEnabled(kDebugMode);
}
if (!kIsWeb) {

View File

@ -6,7 +6,7 @@ import FlutterMacOS
import Foundation
import flutter_inappwebview
import path_provider_macos
import path_provider_foundation
import url_launcher_macos
func RegisterGeneratedPlugins(registry: FlutterPluginRegistry) {

View File

@ -1,4 +1,4 @@
platform :osx, '10.11'
platform :osx, '10.14'
# CocoaPods analytics sends network stats synchronously affecting flutter build latency.
ENV['COCOAPODS_DISABLE_STATS'] = 'true'

View File

@ -3,7 +3,7 @@
archiveVersion = 1;
classes = {
};
objectVersion = 51;
objectVersion = 54;
objects = {
/* Begin PBXAggregateTarget section */
@ -277,6 +277,7 @@
};
3399D490228B24CF009A79C7 /* ShellScript */ = {
isa = PBXShellScriptBuildPhase;
alwaysOutOfDate = 1;
buildActionMask = 2147483647;
files = (
);
@ -403,7 +404,7 @@
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GCC_WARN_UNUSED_FUNCTION = YES;
GCC_WARN_UNUSED_VARIABLE = YES;
MACOSX_DEPLOYMENT_TARGET = 10.11;
MACOSX_DEPLOYMENT_TARGET = 10.14;
MTL_ENABLE_DEBUG_INFO = NO;
SDKROOT = macosx;
SWIFT_COMPILATION_MODE = wholemodule;
@ -482,7 +483,7 @@
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GCC_WARN_UNUSED_FUNCTION = YES;
GCC_WARN_UNUSED_VARIABLE = YES;
MACOSX_DEPLOYMENT_TARGET = 10.11;
MACOSX_DEPLOYMENT_TARGET = 10.14;
MTL_ENABLE_DEBUG_INFO = YES;
ONLY_ACTIVE_ARCH = YES;
SDKROOT = macosx;
@ -529,7 +530,7 @@
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
GCC_WARN_UNUSED_FUNCTION = YES;
GCC_WARN_UNUSED_VARIABLE = YES;
MACOSX_DEPLOYMENT_TARGET = 10.11;
MACOSX_DEPLOYMENT_TARGET = 10.14;
MTL_ENABLE_DEBUG_INFO = NO;
SDKROOT = macosx;
SWIFT_COMPILATION_MODE = wholemodule;

View File

@ -12,7 +12,7 @@ version: 1.0.0+1
publish_to: none
environment:
sdk: ">=2.14.0 <3.0.0"
sdk: ">=2.15.0 <4.0.0"
flutter: ">=3.0.0"
dependencies:
@ -22,11 +22,11 @@ dependencies:
# The following adds the Cupertino Icons font to your application.
# Use with the CupertinoIcons class for iOS style icons.
cupertino_icons: ^1.0.4
flutter_downloader: 1.7.3
path_provider: 2.0.9
permission_handler: 10.0.2
url_launcher: 6.1.6
pointer_interceptor: ^0.9.3+3
flutter_downloader: 1.10.2
path_provider: 2.0.15
permission_handler: 10.2.0
url_launcher: 6.1.11
pointer_interceptor: ^0.9.3+4
# connectivity: ^0.4.5+6
flutter_inappwebview:
path: ../
@ -61,10 +61,12 @@ flutter:
- assets/js/
- assets/css/
- assets/images/
- assets/website/
- test_assets/
- test_assets/js/
- test_assets/css/
- test_assets/images/
- test_assets/website/
# To add assets to your application, add an assets section, like this:
# assets:

View File

@ -427,8 +427,9 @@ public class InAppWebView: WKWebView, UIScrollViewDelegate, WKUIDelegate,
isFindInteractionEnabled = settings.isFindInteractionEnabled
}
// debugging is always enabled for iOS,
// there isn't any option to set about it such as on Android.
if #available(iOS 16.4, *) {
isInspectable = settings.isInspectable
}
if settings.clearCache {
clearCache()
@ -464,14 +465,16 @@ public class InAppWebView: WKWebView, UIScrollViewDelegate, WKUIDelegate,
configuration.defaultWebpagePreferences.allowsContentJavaScript = settings.javaScriptEnabled
}
if #available(iOS 14.5, *) {
if #available(iOS 15.0, *) {
configuration.preferences.isTextInteractionEnabled = settings.isTextInteractionEnabled
}
if #available(iOS 15.4, *) {
configuration.preferences.isSiteSpecificQuirksModeEnabled = settings.isSiteSpecificQuirksModeEnabled
configuration.preferences.isElementFullscreenEnabled = settings.isElementFullscreenEnabled
}
if #available(iOS 16.4, *) {
configuration.preferences.shouldPrintBackgrounds = settings.shouldPrintBackgrounds
}
}
}
@ -1187,16 +1190,13 @@ public class InAppWebView: WKWebView, UIScrollViewDelegate, WKUIDelegate,
}
}
if #available(iOS 14.5, *) {
if #available(iOS 15.0, *) {
if newSettingsMap["upgradeKnownHostsToHTTPS"] != nil && settings?.upgradeKnownHostsToHTTPS != newSettings.upgradeKnownHostsToHTTPS {
configuration.upgradeKnownHostsToHTTPS = newSettings.upgradeKnownHostsToHTTPS
}
if newSettingsMap["isTextInteractionEnabled"] != nil && settings?.isTextInteractionEnabled != newSettings.isTextInteractionEnabled {
configuration.preferences.isTextInteractionEnabled = newSettings.isTextInteractionEnabled
}
}
if #available(iOS 15.0, *) {
if newSettingsMap["underPageBackgroundColor"] != nil, settings?.underPageBackgroundColor != newSettings.underPageBackgroundColor,
let underPageBackgroundColor = newSettings.underPageBackgroundColor, !underPageBackgroundColor.isEmpty {
self.underPageBackgroundColor = UIColor(hexString: underPageBackgroundColor)
@ -1214,12 +1214,19 @@ public class InAppWebView: WKWebView, UIScrollViewDelegate, WKUIDelegate,
setMinimumViewportInset(minViewportInset, maximumViewportInset: maxViewportInset)
}
}
if #available(iOS 16.0, *) {
if newSettingsMap["isFindInteractionEnabled"] != nil, settings?.isFindInteractionEnabled != newSettings.isFindInteractionEnabled {
isFindInteractionEnabled = newSettings.isFindInteractionEnabled
}
}
if #available(iOS 16.4, *) {
if newSettingsMap["isInspectable"] != nil, settings?.isInspectable != newSettings.isInspectable {
isInspectable = newSettings.isInspectable
}
if newSettingsMap["shouldPrintBackgrounds"] != nil, settings?.shouldPrintBackgrounds != newSettings.shouldPrintBackgrounds {
configuration.preferences.shouldPrintBackgrounds = newSettings.shouldPrintBackgrounds
}
}
scrollView.isScrollEnabled = !(newSettings.disableVerticalScroll && newSettings.disableHorizontalScroll)
@ -2738,13 +2745,21 @@ public class InAppWebView: WKWebView, UIScrollViewDelegate, WKUIDelegate,
self.evaluateJavaScript("""
if(window.\(JAVASCRIPT_BRIDGE_NAME)[\(_callHandlerID)] != null) {
window.\(JAVASCRIPT_BRIDGE_NAME)[\(_callHandlerID)](\(json));
window.\(JAVASCRIPT_BRIDGE_NAME)[\(_callHandlerID)].resolve(\(json));
delete window.\(JAVASCRIPT_BRIDGE_NAME)[\(_callHandlerID)];
}
""", completionHandler: nil)
}
callback.error = { (code: String, message: String?, details: Any?) in
print(code + ", " + (message ?? ""))
let errorMessage = code + (message != nil ? ", " + (message ?? "") : "")
print(errorMessage)
self.evaluateJavaScript("""
if(window.\(JAVASCRIPT_BRIDGE_NAME)[\(_callHandlerID)] != null) {
window.\(JAVASCRIPT_BRIDGE_NAME)[\(_callHandlerID)].reject(new Error('\(errorMessage.replacingOccurrences(of: "\'", with: "\\'"))'));
delete window.\(JAVASCRIPT_BRIDGE_NAME)[\(_callHandlerID)];
}
""", completionHandler: nil)
}
if let channelDelegate = webView.channelDelegate {

View File

@ -78,6 +78,8 @@ public class InAppWebViewSettings: ISettings<InAppWebView> {
var isFindInteractionEnabled = false
var minimumViewportInset: UIEdgeInsets? = nil
var maximumViewportInset: UIEdgeInsets? = nil
var isInspectable = false
var shouldPrintBackgrounds = false
override init(){
super.init()
@ -150,11 +152,9 @@ public class InAppWebViewSettings: ISettings<InAppWebView> {
realSettings["limitsNavigationsToAppBoundDomains"] = configuration.limitsNavigationsToAppBoundDomains
realSettings["javaScriptEnabled"] = configuration.defaultWebpagePreferences.allowsContentJavaScript
}
if #available(iOS 14.5, *) {
if #available(iOS 15.0, *) {
realSettings["isTextInteractionEnabled"] = configuration.preferences.isTextInteractionEnabled
realSettings["upgradeKnownHostsToHTTPS"] = configuration.upgradeKnownHostsToHTTPS
}
if #available(iOS 15.0, *) {
realSettings["underPageBackgroundColor"] = webView.underPageBackgroundColor.hexString
}
if #available(iOS 15.4, *) {
@ -168,6 +168,10 @@ public class InAppWebViewSettings: ISettings<InAppWebView> {
if #available(iOS 16.0, *) {
realSettings["isFindInteractionEnabled"] = webView.isFindInteractionEnabled
}
if #available(iOS 16.4, *) {
realSettings["isInspectable"] = webView.isInspectable
realSettings["shouldPrintBackgrounds"] = configuration.preferences.shouldPrintBackgrounds
}
}
return realSettings
}

View File

@ -26,7 +26,7 @@ window.\(JAVASCRIPT_BRIDGE_NAME).callHandler = function() {
var _callHandlerID = setTimeout(function(){});
window.webkit.messageHandlers['callHandler'].postMessage( {'handlerName': arguments[0], '_callHandlerID': _callHandlerID, 'args': JSON.stringify(Array.prototype.slice.call(arguments, 1)), '_windowId': _windowId} );
return new Promise(function(resolve, reject) {
window.\(JAVASCRIPT_BRIDGE_NAME)[_callHandlerID] = resolve;
window.\(JAVASCRIPT_BRIDGE_NAME)[_callHandlerID] = {resolve: resolve, reject: reject};
});
};
\(WEB_MESSAGE_LISTENER_JS_SOURCE)

View File

@ -2,7 +2,6 @@ import 'dart:async';
import 'package:flutter/services.dart';
import 'webview_feature.dart';
import '../types/main.dart';
import '../in_app_webview/in_app_webview_settings.dart';
///Class that manages Service Workers used by [WebView].
///
@ -121,16 +120,6 @@ class ServiceWorkerController {
await _channel.invokeMethod('getCacheMode', args));
}
///Gets how Service Workers will set the `X-Requested-With` header on HTTP requests.
///This method should only be called if [WebViewFeature.isFeatureSupported] returns `true` for [WebViewFeature.REQUESTED_WITH_HEADER_CONTROL].
///
///**Official Android API**: https://developer.android.com/reference/androidx/webkit/ServiceWorkerWebSettingsCompat#getRequestedWithHeaderMode()
static Future<RequestedWithHeaderMode?> getRequestedWithHeaderMode() async {
Map<String, dynamic> args = <String, dynamic>{};
return RequestedWithHeaderMode.fromNativeValue(
await _channel.invokeMethod('getRequestedWithHeaderMode', args));
}
///Enables or disables content URL access from Service Workers.
///This method should only be called if [WebViewFeature.isFeatureSupported] returns `true` for [WebViewFeature.SERVICE_WORKER_CONTENT_ACCESS].
///
@ -178,20 +167,6 @@ class ServiceWorkerController {
args.putIfAbsent("mode", () => mode.toNativeValue());
await _channel.invokeMethod('setCacheMode', args);
}
///Sets how Service Workers will set the `X-Requested-With` header on requests.
///If you are calling this method, you may also want to call [InAppWebViewSettings.requestedWithHeaderMode]
///with the same parameter value to configure non-ServiceWorker requests.
///The default behavior may vary depending on the WebView implementation.
///This method should only be called if [WebViewFeature.isFeatureSupported] returns `true` for [WebViewFeature.REQUESTED_WITH_HEADER_CONTROL].
///
///**Official Android API**: https://developer.android.com/reference/androidx/webkit/ServiceWorkerWebSettingsCompat#setRequestedWithHeaderMode(int)
static Future<void> setRequestedWithHeaderMode(
RequestedWithHeaderMode mode) async {
Map<String, dynamic> args = <String, dynamic>{};
args.putIfAbsent("mode", () => mode.toNativeValue());
await _channel.invokeMethod('setRequestedWithHeaderMode', args);
}
}
///Class used by clients to capture Service Worker related callbacks.

View File

@ -1,5 +1,6 @@
import 'dart:async';
import 'package:flutter/services.dart';
import 'package:flutter_inappwebview/src/cookie_manager.dart';
import 'package:flutter_inappwebview_internal_annotations/flutter_inappwebview_internal_annotations.dart';
import '../in_app_webview/in_app_webview_controller.dart';
import '../in_app_webview/in_app_webview_settings.dart';
@ -22,6 +23,7 @@ class WebViewFeature_ {
// ignore: unused_field
final String _value;
const WebViewFeature_._internal(this._value);
@ExchangeableObjectMethod(ignore: true)
@ -208,10 +210,6 @@ class WebViewFeature_ {
static const ALGORITHMIC_DARKENING =
const WebViewFeature_._internal("ALGORITHMIC_DARKENING");
///This feature covers [InAppWebViewSettings.requestedWithHeaderMode].
static const REQUESTED_WITH_HEADER_CONTROL =
const WebViewFeature_._internal("REQUESTED_WITH_HEADER_CONTROL");
///This feature covers [InAppWebViewSettings.enterpriseAuthenticationAppLinkPolicyEnabled].
static const ENTERPRISE_AUTHENTICATION_APP_LINK_POLICY =
const WebViewFeature_._internal(
@ -221,6 +219,14 @@ class WebViewFeature_ {
static const GET_VARIATIONS_HEADER =
const WebViewFeature_._internal("GET_VARIATIONS_HEADER");
///This feature covers cookie attributes of [CookieManager.getCookie] and [CookieManager.getCookies] methods.
static const GET_COOKIE_INFO =
const WebViewFeature_._internal("GET_COOKIE_INFO");
///This feature covers cookie attributes of [CookieManager.getCookie] and [CookieManager.getCookies] methods.
static const REQUESTED_WITH_HEADER_ALLOW_LIST =
const WebViewFeature_._internal("REQUESTED_WITH_HEADER_ALLOW_LIST");
///Return whether a feature is supported at run-time. On devices running Android version `Build.VERSION_CODES.LOLLIPOP` and higher,
///this will check whether a feature is supported, depending on the combination of the desired feature, the Android version of device,
///and the WebView APK on the device. If running on a device with a lower API level, this will always return `false`.
@ -244,6 +250,7 @@ class AndroidWebViewFeature_ {
// ignore: unused_field
final String _value;
const AndroidWebViewFeature_._internal(this._value);
@ExchangeableObjectMethod(ignore: true)

View File

@ -48,6 +48,10 @@ class WebViewFeature {
static const FORCE_DARK_STRATEGY =
WebViewFeature._internal('FORCE_DARK_STRATEGY', 'FORCE_DARK_STRATEGY');
///This feature covers cookie attributes of [CookieManager.getCookie] and [CookieManager.getCookies] methods.
static const GET_COOKIE_INFO =
WebViewFeature._internal('GET_COOKIE_INFO', 'GET_COOKIE_INFO');
///This feature covers [InAppWebViewController.getVariationsHeader].
static const GET_VARIATIONS_HEADER = WebViewFeature._internal(
'GET_VARIATIONS_HEADER', 'GET_VARIATIONS_HEADER');
@ -92,9 +96,9 @@ class WebViewFeature {
static const RECEIVE_WEB_RESOURCE_ERROR = WebViewFeature._internal(
'RECEIVE_WEB_RESOURCE_ERROR', 'RECEIVE_WEB_RESOURCE_ERROR');
///This feature covers [InAppWebViewSettings.requestedWithHeaderMode].
static const REQUESTED_WITH_HEADER_CONTROL = WebViewFeature._internal(
'REQUESTED_WITH_HEADER_CONTROL', 'REQUESTED_WITH_HEADER_CONTROL');
///This feature covers cookie attributes of [CookieManager.getCookie] and [CookieManager.getCookies] methods.
static const REQUESTED_WITH_HEADER_ALLOW_LIST = WebViewFeature._internal(
'REQUESTED_WITH_HEADER_ALLOW_LIST', 'REQUESTED_WITH_HEADER_ALLOW_LIST');
///This feature covers [InAppWebViewController.setSafeBrowsingAllowlist].
static const SAFE_BROWSING_ALLOWLIST = WebViewFeature._internal(
@ -230,6 +234,7 @@ class WebViewFeature {
WebViewFeature.ENTERPRISE_AUTHENTICATION_APP_LINK_POLICY,
WebViewFeature.FORCE_DARK,
WebViewFeature.FORCE_DARK_STRATEGY,
WebViewFeature.GET_COOKIE_INFO,
WebViewFeature.GET_VARIATIONS_HEADER,
WebViewFeature.GET_WEB_CHROME_CLIENT,
WebViewFeature.GET_WEB_VIEW_CLIENT,
@ -241,7 +246,7 @@ class WebViewFeature {
WebViewFeature.PROXY_OVERRIDE_REVERSE_BYPASS,
WebViewFeature.RECEIVE_HTTP_ERROR,
WebViewFeature.RECEIVE_WEB_RESOURCE_ERROR,
WebViewFeature.REQUESTED_WITH_HEADER_CONTROL,
WebViewFeature.REQUESTED_WITH_HEADER_ALLOW_LIST,
WebViewFeature.SAFE_BROWSING_ALLOWLIST,
WebViewFeature.SAFE_BROWSING_ENABLE,
WebViewFeature.SAFE_BROWSING_HIT,

View File

@ -78,25 +78,25 @@ class ChromeSafariBrowserSettings_ implements ChromeSafariBrowserOptions {
///
///**Supported Platforms/Implementations**:
///- Android
Color? toolbarBackgroundColor;
Color_? toolbarBackgroundColor;
///Sets the navigation bar color. Has no effect on Android API versions below L.
///
///**Supported Platforms/Implementations**:
///- Android
Color? navigationBarColor;
Color_? navigationBarColor;
///Sets the navigation bar divider color. Has no effect on Android API versions below P.
///
///**Supported Platforms/Implementations**:
///- Android
Color? navigationBarDividerColor;
Color_? navigationBarDividerColor;
///Sets the color of the secondary toolbar.
///
///**Supported Platforms/Implementations**:
///- Android
Color? secondaryToolbarColor;
Color_? secondaryToolbarColor;
///Set to `true` to enable the url bar to hide as the user scrolls down on the page. The default value is `false`.
///
@ -224,7 +224,7 @@ class ChromeSafariBrowserSettings_ implements ChromeSafariBrowserOptions {
///
///**Supported Platforms/Implementations**:
///- iOS
Color? preferredBarTintColor;
Color_? preferredBarTintColor;
///Set the custom color of the control buttons on the navigation bar and the toolbar.
///
@ -232,7 +232,7 @@ class ChromeSafariBrowserSettings_ implements ChromeSafariBrowserOptions {
///
///**Supported Platforms/Implementations**:
///- iOS
Color? preferredControlTintColor;
Color_? preferredControlTintColor;
///Set the custom modal presentation style when presenting the WebView. The default value is [ModalPresentationStyle.FULL_SCREEN].
///

View File

@ -290,8 +290,9 @@ class ChromeSafariBrowserSettings implements ChromeSafariBrowserOptions {
? UtilColor.fromStringRepresentation(map['toolbarBackgroundColor'])
: null,
);
instance.additionalTrustedOrigins =
map['additionalTrustedOrigins']?.cast<String>();
instance.additionalTrustedOrigins = map['additionalTrustedOrigins'] != null
? List<String>.from(map['additionalTrustedOrigins']!.cast<String>())
: null;
instance.alwaysUseBrowserUI = map['alwaysUseBrowserUI'];
instance.barCollapsingEnabled = map['barCollapsingEnabled'];
instance.dismissButtonStyle =

View File

@ -1,6 +1,7 @@
import 'dart:async';
import 'dart:collection';
import 'dart:typed_data';
import 'dart:ui';
import 'package:flutter/services.dart';

View File

@ -121,7 +121,7 @@ class InAppBrowserSettings_
///- Android native WebView
///- iOS
///- MacOS
Color? toolbarTopBackgroundColor;
Color_? toolbarTopBackgroundColor;
///Set to `true` to hide the url bar on the toolbar at the top. The default value is `false`.
///
@ -180,13 +180,13 @@ class InAppBrowserSettings_
///
///**Supported Platforms/Implementations**:
///- iOS
Color? toolbarTopBarTintColor;
Color_? toolbarTopBarTintColor;
///Set the tint color to apply to the navigation items and bar button items.
///
///**Supported Platforms/Implementations**:
///- iOS
Color? toolbarTopTintColor;
Color_? toolbarTopTintColor;
///Set to `true` to hide the toolbar at the bottom of the WebView. The default value is `false`.
///
@ -198,13 +198,13 @@ class InAppBrowserSettings_
///
///**Supported Platforms/Implementations**:
///- iOS
Color? toolbarBottomBackgroundColor;
Color_? toolbarBottomBackgroundColor;
///Set the tint color to apply to the bar button items.
///
///**Supported Platforms/Implementations**:
///- iOS
Color? toolbarBottomTintColor;
Color_? toolbarBottomTintColor;
///Set to `true` to set the toolbar at the bottom translucent. The default value is `true`.
///
@ -222,7 +222,7 @@ class InAppBrowserSettings_
///
///**Supported Platforms/Implementations**:
///- iOS
Color? closeButtonColor;
Color_? closeButtonColor;
///Set the custom modal presentation style when presenting the WebView. The default value is [ModalPresentationStyle.FULL_SCREEN].
///

View File

@ -1378,9 +1378,10 @@ class InAppWebViewController {
// convert result to json
try {
return jsonEncode(await javaScriptHandlersMap[handlerName]!(args));
} catch (error) {
developer.log(error.toString(), name: this.runtimeType.toString());
return null;
} catch (error, stacktrace) {
developer.log(error.toString() + '\n' + stacktrace.toString(),
name: 'JavaScript Handler "$handlerName"');
throw Exception(error.toString().replaceFirst('Exception: ', ''));
}
}
break;

View File

@ -2,6 +2,7 @@ import 'package:flutter/foundation.dart';
import 'package:flutter/widgets.dart';
import 'package:flutter_inappwebview/src/types/user_preferred_content_mode.dart';
import 'package:flutter_inappwebview_internal_annotations/flutter_inappwebview_internal_annotations.dart';
import 'dart:typed_data';
import '../android/webview_asset_loader.dart';
import '../types/action_mode_menu_item.dart';
@ -14,7 +15,6 @@ import '../types/mixed_content_mode.dart';
import '../types/over_scroll_mode.dart';
import '../types/referrer_policy.dart';
import '../types/renderer_priority_policy.dart';
import '../types/requested_with_header_mode.dart';
import '../types/sandbox.dart';
import '../types/scrollbar_style.dart';
import '../types/scrollview_content_inset_adjustment_behavior.dart';
@ -881,7 +881,7 @@ as it can cause framerate drops on animations in Android 9 and lower (see [Hybri
apiUrl:
"https://developer.android.com/reference/android/view/View#setVerticalScrollbarThumbDrawable(android.graphics.drawable.Drawable)")
])
Color? verticalScrollbarThumbColor;
Color_? verticalScrollbarThumbColor;
///Sets the vertical scrollbar track color.
@SupportedPlatforms(platforms: [
@ -891,7 +891,7 @@ as it can cause framerate drops on animations in Android 9 and lower (see [Hybri
apiUrl:
"https://developer.android.com/reference/android/view/View#setVerticalScrollbarTrackDrawable(android.graphics.drawable.Drawable)")
])
Color? verticalScrollbarTrackColor;
Color_? verticalScrollbarTrackColor;
///Sets the horizontal scrollbar thumb color.
@SupportedPlatforms(platforms: [
@ -901,7 +901,7 @@ as it can cause framerate drops on animations in Android 9 and lower (see [Hybri
apiUrl:
"https://developer.android.com/reference/android/view/View#setHorizontalScrollbarThumbDrawable(android.graphics.drawable.Drawable)")
])
Color? horizontalScrollbarThumbColor;
Color_? horizontalScrollbarThumbColor;
///Sets the horizontal scrollbar track color.
@SupportedPlatforms(platforms: [
@ -911,7 +911,7 @@ as it can cause framerate drops on animations in Android 9 and lower (see [Hybri
apiUrl:
"https://developer.android.com/reference/android/view/View#setHorizontalScrollbarTrackDrawable(android.graphics.drawable.Drawable)")
])
Color? horizontalScrollbarTrackColor;
Color_? horizontalScrollbarTrackColor;
///Control whether algorithmic darkening is allowed.
///
@ -935,17 +935,6 @@ as it can cause framerate drops on animations in Android 9 and lower (see [Hybri
])
bool? algorithmicDarkeningAllowed;
///Sets how the WebView will set the `X-Requested-With` header on requests.
///If you are calling this method, you may also want to call [ServiceWorkerWebSettingsCompat.setRequestedWithHeaderMode]
///with the same parameter value to configure ServiceWorker requests.
///The default behavior may vary depending on the WebView implementation.
@SupportedPlatforms(platforms: [
AndroidPlatform(
note:
"available on Android only if [WebViewFeature.REQUESTED_WITH_HEADER_CONTROL] feature is supported.")
])
RequestedWithHeaderMode_? requestedWithHeaderMode;
///Sets whether EnterpriseAuthenticationAppLinkPolicy if set by admin is allowed to have any
///effect on WebView.
///
@ -968,6 +957,23 @@ as it can cause framerate drops on animations in Android 9 and lower (see [Hybri
@SupportedPlatforms(platforms: [AndroidPlatform()])
Uint8List? defaultVideoPoster;
///Set an allow-list of origins to receive the X-Requested-With HTTP header from the WebView owning the passed [InAppWebViewSettings].
///
///Historically, this header was sent on all requests from WebView, containing the app package name of the embedding app. Depending on the version of installed WebView, this may no longer be the case, as the header was deprecated in late 2022, and its use discontinued.
///
///Apps can use this method to restore the legacy behavior for servers that still rely on the deprecated header, but it should not be used to identify the webview to first-party servers under the control of the app developer.
///
///The format of the strings in the allow-list follows the origin rules of [InAppWebViewController.addWebMessageListener].
@SupportedPlatforms(platforms: [
AndroidPlatform(
apiName: "WebSettingsCompat.setRequestedWithHeaderOriginAllowList",
apiUrl:
"https://developer.android.com/reference/androidx/webkit/WebSettingsCompat#setRequestedWithHeaderOriginAllowList(android.webkit.WebSettings,java.util.Set%3Cjava.lang.String%3E)",
note:
"available on Android only if [WebViewFeature.REQUESTED_WITH_HEADER_ALLOW_LIST] feature is supported.")
])
Set<String>? requestedWithHeaderOriginAllowList;
///Set to `true` to disable the bouncing of the WebView when the scrolling has reached an edge of the content. The default value is `false`.
@SupportedPlatforms(platforms: [IOSPlatform()])
bool? disallowOverScroll;
@ -1357,8 +1363,10 @@ as it can cause framerate drops on animations in Android 9 and lower (see [Hybri
///
///Also, on MacOS:
///- [WebView.onScrollChanged]
@SupportedPlatforms(
platforms: [IOSPlatform(available: "13.0"), MacOSPlatform()])
@SupportedPlatforms(platforms: [
IOSPlatform(available: "13.0"),
MacOSPlatform(available: "10.15")
])
bool? applePayAPIEnabled;
///Used in combination with [WebView.initialUrlRequest] or [WebView.initialData] (using the `file://` scheme), it represents the URL from which to read the web content.
@ -1397,13 +1405,13 @@ as it can cause framerate drops on animations in Android 9 and lower (see [Hybri
apiUrl:
"https://developer.apple.com/documentation/webkit/wkwebview/3850574-underpagebackgroundcolor")
])
Color? underPageBackgroundColor;
Color_? underPageBackgroundColor;
///A Boolean value indicating whether text interaction is enabled or not.
///The default value is `true`.
@SupportedPlatforms(platforms: [
IOSPlatform(
available: "14.5",
available: "15.0",
apiName: "WKPreferences.isTextInteractionEnabled",
apiUrl:
"https://developer.apple.com/documentation/webkit/wkpreferences/3727362-istextinteractionenabled"),
@ -1499,6 +1507,40 @@ as it can cause framerate drops on animations in Android 9 and lower (see [Hybri
])
EdgeInsets? maximumViewportInset;
///Controls whether this WebView is inspectable in Web Inspector.
///
///The default value is `false`.
@SupportedPlatforms(platforms: [
IOSPlatform(
available: "16.4",
apiName: "WKWebView.isInspectable",
apiUrl:
"https://developer.apple.com/documentation/webkit/wkwebview/4111163-isinspectable"),
MacOSPlatform(
available: "13.3",
apiName: "WKWebView.isInspectable",
apiUrl:
"https://developer.apple.com/documentation/webkit/wkwebview/4111163-isinspectable")
])
bool? isInspectable;
///A Boolean value that indicates whether to include any background color or graphics when printing content.
///
///The default value is `false`.
@SupportedPlatforms(platforms: [
IOSPlatform(
available: "16.4",
apiName: "WKWebView.shouldPrintBackgrounds",
apiUrl:
"https://developer.apple.com/documentation/webkit/wkpreferences/4104043-shouldprintbackgrounds"),
MacOSPlatform(
available: "13.3",
apiName: "WKWebView.shouldPrintBackgrounds",
apiUrl:
"https://developer.apple.com/documentation/webkit/wkpreferences/4104043-shouldprintbackgrounds")
])
bool? shouldPrintBackgrounds;
///Specifies a feature policy for the `<iframe>`.
///The policy defines what features are available to the `<iframe>` based on the origin of the request
///(e.g. access to the microphone, camera, battery, web-share API, etc.).
@ -1648,9 +1690,9 @@ as it can cause framerate drops on animations in Android 9 and lower (see [Hybri
this.horizontalScrollbarThumbColor,
this.horizontalScrollbarTrackColor,
this.algorithmicDarkeningAllowed = false,
this.requestedWithHeaderMode,
this.enterpriseAuthenticationAppLinkPolicyEnabled = true,
this.defaultVideoPoster,
this.requestedWithHeaderOriginAllowList,
this.disallowOverScroll = false,
this.enableViewportScale = false,
this.suppressesIncrementalRendering = false,
@ -1692,6 +1734,8 @@ as it can cause framerate drops on animations in Android 9 and lower (see [Hybri
this.isFindInteractionEnabled = false,
this.minimumViewportInset,
this.maximumViewportInset,
this.isInspectable = false,
this.shouldPrintBackgrounds = false,
this.allowBackgroundAudioPlaying = false,
this.webViewAssetLoader,
this.iframeAllow,

File diff suppressed because one or more lines are too long

View File

@ -6,7 +6,6 @@ export 'android/main.dart';
export 'apple/main.dart';
export 'x509_certificate/main.dart';
export 'web_storage/main.dart';
export 'types/main.dart';
export 'cookie_manager.dart';
export 'in_app_localhost_server.dart';
export 'content_blocker.dart';

View File

@ -24,14 +24,14 @@ class PullToRefreshSettings_ {
///**Supported Platforms/Implementations**:
///- Android native WebView
///- iOS
Color? color;
Color_? color;
///The background color of the refresh control.
///
///**Supported Platforms/Implementations**:
///- Android native WebView
///- iOS
Color? backgroundColor;
Color_? backgroundColor;
///The distance to trigger a sync in dips.
///

View File

@ -21,7 +21,7 @@ class AttributedString_ {
///The value of this attribute is a [Color] object.
///Use this attribute to specify the color of the background area behind the text.
///If you do not specify this attribute, no background color is drawn.
Color? backgroundColor;
Color_? backgroundColor;
///The vertical offset for the position of the text.
///
@ -40,7 +40,7 @@ class AttributedString_ {
///The value of this attribute is a [Color] object.
///Use this attribute to specify the color of the text during rendering.
///If you do not specify this attribute, the text is rendered in black.
Color? foregroundColor;
Color_? foregroundColor;
///The kerning of the text.
///
@ -68,7 +68,7 @@ class AttributedString_ {
///The color of the strikethrough.
///
///The value of this attribute is a [Color] object. The default value is `null`, indicating same as foreground color.
Color? strikethroughColor;
Color_? strikethroughColor;
///The strikethrough style of the text.
///
@ -81,7 +81,7 @@ class AttributedString_ {
///The value of this parameter is a [Color] object.
///If it is not defined (which is the case by default), it is assumed to be the same as the value of foregroundColor;
///otherwise, it describes the outline color.
Color? strokeColor;
Color_? strokeColor;
///The width of the stroke.
///
@ -103,7 +103,7 @@ class AttributedString_ {
///
///The value of this attribute is a [Color] object.
///The default value is `null`, indicating same as foreground color.
Color? underlineColor;
Color_? underlineColor;
///The underline style of the text.
///
@ -144,7 +144,7 @@ class IOSNSAttributedString_ {
///The value of this attribute is a [Color] object.
///Use this attribute to specify the color of the background area behind the text.
///If you do not specify this attribute, no background color is drawn.
Color? backgroundColor;
Color_? backgroundColor;
///The vertical offset for the position of the text.
///
@ -163,7 +163,7 @@ class IOSNSAttributedString_ {
///The value of this attribute is a [Color] object.
///Use this attribute to specify the color of the text during rendering.
///If you do not specify this attribute, the text is rendered in black.
Color? foregroundColor;
Color_? foregroundColor;
///The kerning of the text.
///
@ -191,7 +191,7 @@ class IOSNSAttributedString_ {
///The color of the strikethrough.
///
///The value of this attribute is a [Color] object. The default value is `null`, indicating same as foreground color.
Color? strikethroughColor;
Color_? strikethroughColor;
///The strikethrough style of the text.
///
@ -204,7 +204,7 @@ class IOSNSAttributedString_ {
///The value of this parameter is a [Color] object.
///If it is not defined (which is the case by default), it is assumed to be the same as the value of foregroundColor;
///otherwise, it describes the outline color.
Color? strokeColor;
Color_? strokeColor;
///The width of the stroke.
///
@ -226,7 +226,7 @@ class IOSNSAttributedString_ {
///
///The value of this attribute is a [Color] object.
///The default value is `null`, indicating same as foreground color.
Color? underlineColor;
Color_? underlineColor;
///The underline style of the text.
///

View File

@ -47,10 +47,18 @@ class ClientCertChallenge extends URLAuthenticationChallenge {
final instance = ClientCertChallenge(
protectionSpace: URLProtectionSpace.fromMap(
map['protectionSpace']?.cast<String, dynamic>())!,
androidKeyTypes: map['keyTypes']?.cast<String>(),
androidPrincipals: map['principals']?.cast<String>(),
keyTypes: map['keyTypes']?.cast<String>(),
principals: map['principals']?.cast<String>(),
androidKeyTypes: map['keyTypes'] != null
? List<String>.from(map['keyTypes']!.cast<String>())
: null,
androidPrincipals: map['principals'] != null
? List<String>.from(map['principals']!.cast<String>())
: null,
keyTypes: map['keyTypes'] != null
? List<String>.from(map['keyTypes']!.cast<String>())
: null,
principals: map['principals'] != null
? List<String>.from(map['principals']!.cast<String>())
: null,
);
return instance;
}

View File

@ -1,6 +1,7 @@
import 'package:flutter_inappwebview_internal_annotations/flutter_inappwebview_internal_annotations.dart';
import '../cookie_manager.dart';
import '../android/webview_feature.dart';
import 'http_cookie_same_site_policy.dart';
part 'cookie.g.dart';
@ -9,44 +10,88 @@ part 'cookie.g.dart';
@ExchangeableObject()
class Cookie_ {
///The cookie name.
@SupportedPlatforms(platforms: [
IOSPlatform(),
MacOSPlatform(),
AndroidPlatform(),
WebPlatform()
])
String name;
///The cookie value.
@SupportedPlatforms(platforms: [
IOSPlatform(),
MacOSPlatform(),
AndroidPlatform(),
WebPlatform()
])
dynamic value;
///The cookie expiration date in milliseconds.
///
///**NOTE**: on Android it will be always `null`.
@SupportedPlatforms(platforms: [
IOSPlatform(),
MacOSPlatform(),
AndroidPlatform(
note:
"available on Android only if [WebViewFeature.GET_COOKIE_INFO] feature is supported.")
])
int? expiresDate;
///Indicates if the cookie is a session only cookie.
///
///**NOTE**: on Android it will be always `null`.
@SupportedPlatforms(platforms: [
IOSPlatform(),
MacOSPlatform()
])
bool? isSessionOnly;
///The cookie domain.
///
///**NOTE**: on Android it will be always `null`.
@SupportedPlatforms(platforms: [
IOSPlatform(),
MacOSPlatform(),
AndroidPlatform(
note:
"available on Android only if [WebViewFeature.GET_COOKIE_INFO] feature is supported.")
])
String? domain;
///The cookie same site policy.
///
///**NOTE**: on Android it will be always `null`.
@SupportedPlatforms(platforms: [
IOSPlatform(),
MacOSPlatform(),
AndroidPlatform(
note:
"available on Android only if [WebViewFeature.GET_COOKIE_INFO] feature is supported.")
])
HTTPCookieSameSitePolicy_? sameSite;
///Indicates if the cookie is secure or not.
///
///**NOTE**: on Android it will be always `null`.
@SupportedPlatforms(platforms: [
IOSPlatform(),
MacOSPlatform(),
AndroidPlatform(
note:
"available on Android only if [WebViewFeature.GET_COOKIE_INFO] feature is supported.")
])
bool? isSecure;
///Indicates if the cookie is a http only cookie.
///
///**NOTE**: on Android it will be always `null`.
@SupportedPlatforms(platforms: [
IOSPlatform(),
MacOSPlatform(),
AndroidPlatform(
note:
"available on Android only if [WebViewFeature.GET_COOKIE_INFO] feature is supported.")
])
bool? isHttpOnly;
///The cookie path.
///
///**NOTE**: on Android it will be always `null`.
@SupportedPlatforms(platforms: [
IOSPlatform(),
MacOSPlatform(),
AndroidPlatform(
note:
"available on Android only if [WebViewFeature.GET_COOKIE_INFO] feature is supported.")
])
String? path;
Cookie_(

View File

@ -10,43 +10,87 @@ part of 'cookie.dart';
class Cookie {
///The cookie domain.
///
///**NOTE**: on Android it will be always `null`.
///**NOTE for Android native WebView**: available on Android only if [WebViewFeature.GET_COOKIE_INFO] feature is supported.
///
///**Supported Platforms/Implementations**:
///- iOS
///- MacOS
///- Android native WebView
String? domain;
///The cookie expiration date in milliseconds.
///
///**NOTE**: on Android it will be always `null`.
///**NOTE for Android native WebView**: available on Android only if [WebViewFeature.GET_COOKIE_INFO] feature is supported.
///
///**Supported Platforms/Implementations**:
///- iOS
///- MacOS
///- Android native WebView
int? expiresDate;
///Indicates if the cookie is a http only cookie.
///
///**NOTE**: on Android it will be always `null`.
///**NOTE for Android native WebView**: available on Android only if [WebViewFeature.GET_COOKIE_INFO] feature is supported.
///
///**Supported Platforms/Implementations**:
///- iOS
///- MacOS
///- Android native WebView
bool? isHttpOnly;
///Indicates if the cookie is secure or not.
///
///**NOTE**: on Android it will be always `null`.
///**NOTE for Android native WebView**: available on Android only if [WebViewFeature.GET_COOKIE_INFO] feature is supported.
///
///**Supported Platforms/Implementations**:
///- iOS
///- MacOS
///- Android native WebView
bool? isSecure;
///Indicates if the cookie is a session only cookie.
///
///**NOTE**: on Android it will be always `null`.
///**Supported Platforms/Implementations**:
///- iOS
///- MacOS
bool? isSessionOnly;
///The cookie name.
///
///**Supported Platforms/Implementations**:
///- iOS
///- MacOS
///- Android native WebView
///- Web but iframe requires same origin
String name;
///The cookie path.
///
///**NOTE**: on Android it will be always `null`.
///**NOTE for Android native WebView**: available on Android only if [WebViewFeature.GET_COOKIE_INFO] feature is supported.
///
///**Supported Platforms/Implementations**:
///- iOS
///- MacOS
///- Android native WebView
String? path;
///The cookie same site policy.
///
///**NOTE**: on Android it will be always `null`.
///**NOTE for Android native WebView**: available on Android only if [WebViewFeature.GET_COOKIE_INFO] feature is supported.
///
///**Supported Platforms/Implementations**:
///- iOS
///- MacOS
///- Android native WebView
HTTPCookieSameSitePolicy? sameSite;
///The cookie value.
///
///**Supported Platforms/Implementations**:
///- iOS
///- MacOS
///- Android native WebView
///- Web but iframe requires same origin
dynamic value;
Cookie(
{this.domain,

View File

@ -203,7 +203,6 @@ export 'webview_package_info.dart'
show WebViewPackageInfo, AndroidWebViewPackageInfo;
export 'webview_render_process_action.dart' show WebViewRenderProcessAction;
export 'window_features.dart' show WindowFeatures, IOSWKWindowFeatures;
export 'requested_with_header_mode.dart' show RequestedWithHeaderMode;
export 'find_session.dart' show FindSession;
export 'search_result_display_style.dart' show SearchResultDisplayStyle;
export 'content_blocker_trigger_load_context.dart'

View File

@ -70,7 +70,7 @@ class PermissionRequestResponse {
final instance = PermissionRequestResponse();
instance.action =
PermissionRequestResponseAction.fromNativeValue(map['action']);
instance.resources = map['resources'].cast<String>();
instance.resources = List<String>.from(map['resources']!.cast<String>());
return instance;
}

View File

@ -1,19 +0,0 @@
import 'package:flutter_inappwebview_internal_annotations/flutter_inappwebview_internal_annotations.dart';
part 'requested_with_header_mode.g.dart';
///Class used to set how the WebView will set the `X-Requested-With` header on requests.
@ExchangeableEnum()
class RequestedWithHeaderMode_ {
// ignore: unused_field
final int _value;
const RequestedWithHeaderMode_._internal(this._value);
///In this mode the WebView will not add an `X-Requested-With` header on HTTP requests automatically.
static const NO_HEADER = const RequestedWithHeaderMode_._internal(0);
///In this mode the WebView automatically add an `X-Requested-With` header to outgoing requests,
///if the application or the loaded webpage has not already set a header value.
///The value of this automatically added header will be the package name of the app. This is the default mode.
static const APP_PACKAGE_NAME = const RequestedWithHeaderMode_._internal(1);
}

View File

@ -1,81 +0,0 @@
// GENERATED CODE - DO NOT MODIFY BY HAND
part of 'requested_with_header_mode.dart';
// **************************************************************************
// ExchangeableEnumGenerator
// **************************************************************************
///Class used to set how the WebView will set the `X-Requested-With` header on requests.
class RequestedWithHeaderMode {
final int _value;
final int _nativeValue;
const RequestedWithHeaderMode._internal(this._value, this._nativeValue);
// ignore: unused_element
factory RequestedWithHeaderMode._internalMultiPlatform(
int value, Function nativeValue) =>
RequestedWithHeaderMode._internal(value, nativeValue());
///In this mode the WebView automatically add an `X-Requested-With` header to outgoing requests,
///if the application or the loaded webpage has not already set a header value.
///The value of this automatically added header will be the package name of the app. This is the default mode.
static const APP_PACKAGE_NAME = RequestedWithHeaderMode._internal(1, 1);
///In this mode the WebView will not add an `X-Requested-With` header on HTTP requests automatically.
static const NO_HEADER = RequestedWithHeaderMode._internal(0, 0);
///Set of all values of [RequestedWithHeaderMode].
static final Set<RequestedWithHeaderMode> values = [
RequestedWithHeaderMode.APP_PACKAGE_NAME,
RequestedWithHeaderMode.NO_HEADER,
].toSet();
///Gets a possible [RequestedWithHeaderMode] instance from [int] value.
static RequestedWithHeaderMode? fromValue(int? value) {
if (value != null) {
try {
return RequestedWithHeaderMode.values
.firstWhere((element) => element.toValue() == value);
} catch (e) {
return null;
}
}
return null;
}
///Gets a possible [RequestedWithHeaderMode] instance from a native value.
static RequestedWithHeaderMode? fromNativeValue(int? value) {
if (value != null) {
try {
return RequestedWithHeaderMode.values
.firstWhere((element) => element.toNativeValue() == value);
} catch (e) {
return null;
}
}
return null;
}
///Gets [int] value.
int toValue() => _value;
///Gets [int] native value.
int toNativeValue() => _nativeValue;
@override
int get hashCode => _value.hashCode;
@override
bool operator ==(value) => value == _value;
@override
String toString() {
switch (_value) {
case 1:
return 'APP_PACKAGE_NAME';
case 0:
return 'NO_HEADER';
}
return _value.toString();
}
}

View File

@ -64,7 +64,8 @@ class UserScript {
iosForMainFrameOnly: map['forMainFrameOnly'],
source: map['source'],
);
instance.allowedOriginRules = map['allowedOriginRules'].cast<String>();
instance.allowedOriginRules =
Set<String>.from(map['allowedOriginRules']!.cast<String>());
instance.contentWorld = map['contentWorld'];
instance.forMainFrameOnly = map['forMainFrameOnly'];
return instance;

View File

@ -576,3 +576,9 @@ void debugLog(
}
}
}
// Class used only by the build_runner for @ExchangeableObject annotation.
// For some strange reason, Color is not recognized anymore by the dart analyzer correctly.
class Color_ extends Color {
Color_(int value) : super(value);
}

View File

@ -138,8 +138,9 @@ public class InAppWebView: WKWebView, WKUIDelegate,
}
}
// debugging is always enabled for iOS,
// there isn't any option to set about it such as on Android.
if #available(macOS 13.3, *) {
isInspectable = settings.isInspectable
}
if settings.clearCache {
clearCache()
@ -170,15 +171,16 @@ public class InAppWebView: WKWebView, WKUIDelegate,
if #available(macOS 11.0, *) {
configuration.defaultWebpagePreferences.allowsContentJavaScript = settings.javaScriptEnabled
}
if #available(macOS 11.3, *) {
configuration.preferences.isTextInteractionEnabled = settings.isTextInteractionEnabled
}
if #available(macOS 12.3, *) {
configuration.preferences.isSiteSpecificQuirksModeEnabled = settings.isSiteSpecificQuirksModeEnabled
configuration.preferences.isElementFullscreenEnabled = settings.isElementFullscreenEnabled
}
if #available(macOS 13.3, *) {
configuration.preferences.shouldPrintBackgrounds = settings.shouldPrintBackgrounds
}
}
}
@ -730,6 +732,14 @@ public class InAppWebView: WKWebView, WKUIDelegate,
configuration.preferences.isSiteSpecificQuirksModeEnabled = newSettings.isSiteSpecificQuirksModeEnabled
}
}
if #available(macOS 13.3, *) {
if newSettingsMap["isInspectable"] != nil, settings?.isInspectable != newSettings.isInspectable {
isInspectable = newSettings.isInspectable
}
if newSettingsMap["shouldPrintBackgrounds"] != nil, settings?.shouldPrintBackgrounds != newSettings.shouldPrintBackgrounds {
configuration.preferences.shouldPrintBackgrounds = newSettings.shouldPrintBackgrounds
}
}
self.settings = newSettings
}
@ -2102,13 +2112,21 @@ public class InAppWebView: WKWebView, WKUIDelegate,
self.evaluateJavaScript("""
if(window.\(JAVASCRIPT_BRIDGE_NAME)[\(_callHandlerID)] != null) {
window.\(JAVASCRIPT_BRIDGE_NAME)[\(_callHandlerID)](\(json));
window.\(JAVASCRIPT_BRIDGE_NAME)[\(_callHandlerID)].resolve(\(json));
delete window.\(JAVASCRIPT_BRIDGE_NAME)[\(_callHandlerID)];
}
""", completionHandler: nil)
}
callback.error = { (code: String, message: String?, details: Any?) in
print(code + ", " + (message ?? ""))
let errorMessage = code + (message != nil ? ", " + (message ?? "") : "")
print(errorMessage)
self.evaluateJavaScript("""
if(window.\(JAVASCRIPT_BRIDGE_NAME)[\(_callHandlerID)] != null) {
window.\(JAVASCRIPT_BRIDGE_NAME)[\(_callHandlerID)].reject(new Error('\(errorMessage.replacingOccurrences(of: "\'", with: "\\'"))'));
delete window.\(JAVASCRIPT_BRIDGE_NAME)[\(_callHandlerID)];
}
""", completionHandler: nil)
}
if let channelDelegate = webView.channelDelegate {

View File

@ -51,6 +51,8 @@ public class InAppWebViewSettings: ISettings<InAppWebView> {
var isSiteSpecificQuirksModeEnabled = true
var upgradeKnownHostsToHTTPS = true
var isElementFullscreenEnabled = true
var isInspectable = false
var shouldPrintBackgrounds = false
override init(){
super.init()
@ -58,7 +60,7 @@ public class InAppWebViewSettings: ISettings<InAppWebView> {
override func parse(settings: [String: Any?]) -> InAppWebViewSettings {
let _ = super.parse(settings: settings)
if #available(iOS 13.0, *) {} else {
if #available(macOS 10.15, *) {} else {
applePayAPIEnabled = false
}
return self
@ -68,12 +70,10 @@ public class InAppWebViewSettings: ISettings<InAppWebView> {
var realSettings: [String: Any?] = toMap()
if let webView = obj {
let configuration = webView.configuration
if #available(iOS 9.0, *) {
realSettings["userAgent"] = webView.customUserAgent
realSettings["applicationNameForUserAgent"] = configuration.applicationNameForUserAgent
realSettings["allowsAirPlayForMediaPlayback"] = configuration.allowsAirPlayForMediaPlayback
realSettings["allowsLinkPreview"] = webView.allowsLinkPreview
}
realSettings["userAgent"] = webView.customUserAgent
realSettings["applicationNameForUserAgent"] = configuration.applicationNameForUserAgent
realSettings["allowsAirPlayForMediaPlayback"] = configuration.allowsAirPlayForMediaPlayback
realSettings["allowsLinkPreview"] = webView.allowsLinkPreview
realSettings["javaScriptCanOpenWindowsAutomatically"] = configuration.preferences.javaScriptCanOpenWindowsAutomatically
if #available(macOS 10.12, *) {
realSettings["mediaPlaybackRequiresUserGesture"] = configuration.mediaTypesRequiringUserActionForPlayback == .all
@ -105,6 +105,10 @@ public class InAppWebViewSettings: ISettings<InAppWebView> {
realSettings["isSiteSpecificQuirksModeEnabled"] = configuration.preferences.isSiteSpecificQuirksModeEnabled
realSettings["isElementFullscreenEnabled"] = configuration.preferences.isElementFullscreenEnabled
}
if #available(macOS 13.3, *) {
realSettings["isInspectable"] = webView.isInspectable
realSettings["shouldPrintBackgrounds"] = configuration.preferences.shouldPrintBackgrounds
}
}
return realSettings
}

View File

@ -26,7 +26,7 @@ window.\(JAVASCRIPT_BRIDGE_NAME).callHandler = function() {
var _callHandlerID = setTimeout(function(){});
window.webkit.messageHandlers['callHandler'].postMessage( {'handlerName': arguments[0], '_callHandlerID': _callHandlerID, 'args': JSON.stringify(Array.prototype.slice.call(arguments, 1)), '_windowId': _windowId} );
return new Promise(function(resolve, reject) {
window.\(JAVASCRIPT_BRIDGE_NAME)[_callHandlerID] = resolve;
window.\(JAVASCRIPT_BRIDGE_NAME)[_callHandlerID] = {resolve: resolve, reject: reject};
});
};
\(WEB_MESSAGE_LISTENER_JS_SOURCE)

View File

@ -12,9 +12,7 @@ extension WKFrameInfo {
public func toMap () -> [String:Any?] {
var securityOrigin: [String:Any?]? = nil
if #available(iOS 9.0, *) {
securityOrigin = self.securityOrigin.toMap()
}
securityOrigin = self.securityOrigin.toMap()
// fix: self.request throws EXC_BREAKPOINT when coming from WKNavigationAction.sourceFrame
let request: URLRequest? = self.value(forKey: "request") as? URLRequest
return [

View File

@ -34,7 +34,7 @@ public class WebAuthenticationSessionManager: ChannelDelegate {
create(id: id, url: url, callbackURLScheme: callbackURLScheme, settings: initialSettings, result: result)
break
case "isAvailable":
if #available(iOS 11.0, *) {
if #available(macOS 10.15, *) {
result(true)
} else {
result(false)
@ -47,7 +47,7 @@ public class WebAuthenticationSessionManager: ChannelDelegate {
}
public func create(id: String, url: String, callbackURLScheme: String?, settings: [String: Any?], result: @escaping FlutterResult) {
if #available(iOS 11.0, *) {
if #available(macOS 10.15, *) {
let sessionUrl = URL(string: url) ?? URL(string: "about:blank")!
let initialSettings = WebAuthenticationSessionSettings()
let _ = initialSettings.parse(settings: settings)

View File

@ -1,12 +1,12 @@
name: flutter_inappwebview
description: A Flutter plugin that allows you to add an inline webview, to use an headless webview, and to open an in-app browser window.
version: 6.0.0-beta.21
version: 6.0.0-beta.23
homepage: https://inappwebview.dev/
repository: https://github.com/pichillilorenzo/flutter_inappwebview
issue_tracker: https://github.com/pichillilorenzo/flutter_inappwebview/issues
environment:
sdk: ">=2.14.0 <3.0.0"
sdk: ">=2.15.0 <4.0.0"
flutter: ">=3.0.0"
dependencies: