我有一个已升级的 React Native 应用程序。回到旧时代,如果您访问一篇新闻文章,该文章有超链接,并且您单击了超链接,它会将您重定向到手机浏览器并打开那里的链接,但它不再这样做,因为我们必须升级react-native-autoheight-webview
库,所以为 0.6.1 版本所做的补丁现在已经消失了。该补丁允许超链接在单独的浏览器中打开。
我一直在尝试重复这个过程,以便我们能够得到相同的行为。所以我将这段代码添加到node_modules/react-native-autoheight-webview/AutoHeightWebView/index.js
file:
const _onLoadStart = event => {
if (event.nativeEvent.url.startsWith("http")) {
this.stopLoading();
Linking.openURL(event.nativeEvent.url).catch(err => console.log('An error occurred', err));
} else {
const {onLoadStart} = this.props;
onLoadStart && onLoadStart(event);
}
}
const { currentSource, script } = reduceData(props);
const { width, height } = size;
useEffect(
() =>
onSizeUpdated &&
onSizeUpdated({
height,
width
}),
[width, height, onSizeUpdated]
);
return (
<WebView
{...props}
ref={webView}
onMessage={handleMessage}
onLoadStart={_onLoadStart}
style={[
styles.webView,
{
width,
height
},
style
]}
injectedJavaScript={script}
source={currentSource}
/>
);
}),
(prevProps, nextProps) => !shouldUpdate({ prevProps, nextProps })
);
但这没有任何作用。
我也在同一个文件中尝试过:
const uri = `${media}/1.0/articles`;
return (
<WebView
{...props}
ref={webView}
onMessage={handleMessage}
source={{uri}}
onNavigationStateChange={(event) => {
if (event.url !== uri) {
this.webview.stopLoading();
Linking.openURL(event.url);
}
}}
style={[
styles.webView,
{
width,
height
},
style
]}
injectedJavaScript={script}
source={currentSource}
/>
);
没事了。
我无法回到过去[email protected] /cdn-cgi/l/email-protection
并制作另一个补丁包,因为该版本与React Native 60s版本控制不兼容,即我们不再使用index.ios.js/index.android.js
但反而index.js
.
最早的包react-native-autoheight-webview
将是 1.0.0 并且该版本没有实际意义,因为WebView
and Linking
模块不再在react-native
图书馆,但里面react-native-webview
库,它看起来并不支持相同的属性来让用户在单独的浏览器中打开超链接,而不是在应用程序的 Web 视图中打开超链接。至少我的尝试没有成功。
我还尝试了免费套餐react-native-webview-bridge
来救援,但该包开始使我的应用程序在 iOS 和 Android 端崩溃,所以这不是一个可行的解决方案。以下是此方法失败的几个示例:
Undefined symbols for architecture arm64:
"_RCTJSNavigationScheme", referenced from:
-[RCTWebViewBridgeManager constantsToExport] in libReact-Native-Webview-Bridge.a(RCTWebViewBridgeManager.o)
-[RCTWebViewBridge webView:shouldStartLoadWithRequest:navigationType:] in libReact-Native-Webview-Bridge.a(RCTWebViewBridge.o)
ld: symbol(s) not found for architecture arm64
clang: error: linker command failed with exit code 1 (use -v to see invocation)
在 iOS 端,在 Android 端,我收到此错误:
2019-10-17 13:01:14.292 15725-15839/com.nfibengage.dv E/AndroidRuntime: FATAL EXCEPTION: mqt_native_modules
Process: com.nfibengage.dv, PID: 15725
java.lang.NoClassDefFoundError: Failed resolution of: Lcom/facebook/react/views/webv
我想归根结底,我如何通过 DOM 与 React Native 通信,成功指示我的应用程序在外部浏览器中打开外部链接?
我在 `node_modules/react-native-autoheight-webview/AutoHeightWebView/index.js 中尝试了此配置:
jsCode = () => {
const attachEvent = function(elem, event, callback) {
event = event.replace(/^on/g, '');
if ('addEventListener' in window) {
elem.addEventListener(event, callback, false);
} else if ('attachEvent' in window) {
elem.attachEvent('on' + event, callback);
} else {
const registered = elem['on' + event];
elem['on' + event] = registered ? function(e) {
registered(e);
callback(e);
} : callback;
}
return elem;
}
const all_links = document.querySelectorAll('a[href]');
if (all_links) {
for (var i in all_links) {
if (all_links.hasOwnProperty(i)) {
attachEvent(all_links[i], 'onclick', function(e) {
if (!new RegExp('^https?:\/\/' + location.host, 'gi').test(this.href)) {
// handle external URL
e.preventDefault();
window.postMessage(JSON.stringify({
external_url_open: this.href
}));
}
});
}
}
}
}
render() {
const { height, width } = this.state;
const { style, originWhitelist } = this.props;
const { source, script } = this.getUpdatedState(this.props, getBaseScript);
return (
<WebView
{...this.props}
originWhitelist={originWhitelist || ['*']}
ref={this.webView}
onMessage={this.onMessage}
style={[
styles.webView,
{
width,
height
},
style
]}
injectedJavaScript={this.jsCode}
source={source}
/>
);
}
}
使用本文档作为指南:https://medium.com/@elhardoum/opening-external-links-in-browser-in-react-native-webview-18fe6a66312a https://medium.com/@elhardoum/opening-external-links-in-browser-in-react-native-webview-18fe6a66312a
它对我没有任何作用。
接下来我尝试添加onNavigationStateChange
财产归我ActionAlertFeedCard
:
import React from "react";
import {
Text,
StyleSheet,
View,
TouchableOpacity,
Platform
} from "react-native";
import { WebView } from "react-native-webview";
import { TextButton } from "react-native-material-buttons";
import PropTypes from "prop-types";
import format from "date-fns/format";
import { Card, Divider } from "common-components";
import { v2Colors, feedContentStyles, v2ButtonStyles } from "theme";
import { moderateScale } from "react-native-size-matters";
//prettier-ignore
const getHtml = content => `<body style="font-family: -apple-system, Roboto, sans-serif; font-size: ${moderateScale(32, 0.2)}px;">${content}</body>`;
const ActionAlertFeedCard = ({
completed,
content,
datePosted,
mainActionButtonPress,
secondaryActionButtonPress,
style,
title
}) => (
<Card style={style}>
<View style={feedContentStyles.header}>
<Text style={feedContentStyles.title}>{"ACTION ALERT"}</Text>
<Text style={feedContentStyles.postDate}>
{`${completed ? "Completed" : "Posted"} ${format(
datePosted,
"MMM D, YYYY"
)}`}
</Text>
</View>
<Divider />
<View style={feedContentStyles.content}>
<Text style={feedContentStyles.contentTitle}>{title}</Text>
<WebView
useWebKit={true}
scrollEnabled={false}
style={styles.webview}
source={{
html: getHtml(content)
}}
onNavigationStateChange={event => {
console.log("url of webpage" + event.url);
}}
// scalesPageToFit={Platform.OS !== "ios"}
/>
新闻文章从未完成加载。