好的,这是一种硬核解决方案,可能应该重新编写/编码。此解决方案使用cordova 钩子,并在从a 标记单击它们时将具有http 或https 协议的ALL 链接打开到本机Web 浏览器。例如<a href="https://www.youtube.com/embed">。这不仅会影响 iframe,还会影响所有链接。
请小心,因为这可能会影响您应用中的一些不需要的链接。
我在跑步
- 科尔多瓦 6.1.1
- Cordova-ios 4.1.1
- Cordova-android 5.1.1
首先,您需要在 hooks/after_platform_add 文件夹中创建一个挂钩。仅当您使用 ionic platform add <platform> 或 cordova platform add <platform> 时才会运行挂钩。如果您没有名为 after_platform_add 的文件夹,只需创建一个。然后创建一个文件“01_ios_external_links_hook.js”。
另外请阅读 Cordova hooks 文档:
https://cordova.apache.org/docs/en/latest/guide/appdev/hooks/
似乎不推荐使用多种方法来定义挂钩并为其创建文件夹,因此您应该使用 config.xml 来附加挂钩。
https://cordova.apache.org/docs/en/latest/guide/appdev/hooks/index.html#via-hooks-directory-deprecated
您可以对文件进行任何调用,如果您使用文件夹进行调用,请记住为文件添加访问权限。通常在终端:
chmod +x project/hooks/after_platform_add/01_ios_external_links_hook.js.
请注意,此修复仅适用于 iOS 设备,因为在 android 上您可以通过设置 <allow-intent href="http://*/*" /> 和设置 <access origin="*" /> 来处理此问题。但在最新的 Cordova-ios 和 whitelist-plugin 上,您需要设置 <allow-navigation href="*.youtube.com" /> 或类似的设置以允许 iframe 的内容在 iOS 上加载。这将导致您描述的情况,即来自 iframe 的外部 url 将在 webview 中打开。
但回到解决方案。这是我在 01_ios_external_links.js 文件中的代码:
#!/usr/bin/env node
var fs = require('fs');
var replace = require('replace');
if (fs.existsSync('platforms/ios/CordovaLib/Classes/Private/Plugins/CDVUIWebViewEngine/CDVUIWebViewDelegate.m')) {
console.log('platforms/ios/CordovaLib/Classes/Private/Plugins/CDVUIWebViewEngine/CDVUIWebViewDelegate.m - FOUND: fixing');
replace({
regex: /.*BOOL shouldLoad = YES;*./g,
replacement: 'BOOL shouldLoad = YES; NSURL * requesturl = [request URL]; NSString * url = [[request URL]absoluteString]; NSString * documenturl = [[request mainDocumentURL]absoluteString]; if ((navigationType == UIWebViewNavigationTypeLinkClicked && ([[requesturl scheme] isEqualToString:@"http"] || [[requesturl scheme] isEqualToString:@"https"])) || (([url isEqualToString:documenturl]) && ([[requesturl scheme] isEqualToString:@"http"] || [[requesturl scheme] isEqualToString:@"https"]))) { [[UIApplication sharedApplication] openURL:requesturl]; return NO;}',
paths: ['platforms/ios/CordovaLib/Classes/Private/Plugins/CDVUIWebViewEngine/CDVUIWebViewDelegate.m'],
recursive: true,
silent: true,
});
} else {
console.log('platforms/ios/CordovaLib/Classes/Private/Plugins/CDVUIWebViewEngine/CDVUIWebViewDelegate.m - NOT FOUND');
}
请注意,这是一个有风险的操作,但我当时没有其他方法来处理这个问题。上面的代码在给定的路径中搜索是否有一个名为 CDVUIWebViewDelegate.m 的文件,然后尝试在其中找到一段代码并用另一段代码替换它。但简而言之,上面的代码将修改 CDVUIWebViewDelegate 中针对 iOS 的平台特定代码,并在此文件中添加以下类型的 if 语句:
NSURL * requesturl = [request URL];
NSString * url = [[request URL]absoluteString]; // URL that was requested
NSString * documenturl = [[request mainDocumentURL]absoluteString]; // Main document URL
if ((navigationType == UIWebViewNavigationTypeLinkClicked && ([[requesturl scheme] isEqualToString:@"http"] || [[requesturl scheme] isEqualToString:@"https"])) || (([url isEqualToString:documenturl]) && ([[requesturl scheme] isEqualToString:@"http"] || [[requesturl scheme] isEqualToString:@"https"]))) {
[[UIApplication sharedApplication] openURL:requesturl]; // forward to application router
return NO;
}
考虑到我不是 Objective-c 编码器,这对我自己来说也是全新的,我提出了这个解决方案,因为我没有找到任何其他有效的解决方案来解决我的问题。上面的 if 语句可以而且应该根据您的需要进行修改。我只在开发环境中使用过此代码,需要进一步调查并改进此方法,然后才能将其实施到生产环境中。
请记住,您需要删除并添加平台才能使其生效。这只发生在如上所述添加平台时。
但就是这样。现在您的 iOS 应用程序将在本机浏览器中打开所有 url。希望这可以帮助您找到(更好?)解决此问题的正确方向。