[英]Ejected Expo app cannot find custom native module in NativeModules
I have a React Native app, that was built using Expo, which I then ejected to ExpoKit. 我有一个React Native应用程序,它是使用Expo构建的,然后我将其弹出到ExpoKit。
I followed this tutorial to try to implement a custom native Android module, with a few changes due to the layout of an ejected ExpoKit app. 我按照本教程尝试实现自定义原生Android模块,由于弹出的ExpoKit应用程序的布局而进行了一些更改。 Thus, the
android
directory is laid out as follows: 因此,
android
目录的布局如下:
// <workspace>/android/app/src/main/java/com/reactlibrary/ToastModule.java
package com.reactlibrary;
import android.widget.Toast;
import com.facebook.react.bridge.NativeModule;
import com.facebook.react.bridge.ReactApplicationContext;
import com.facebook.react.bridge.ReactContext;
import com.facebook.react.bridge.ReactContextBaseJavaModule;
import com.facebook.react.bridge.ReactMethod;
import java.util.Map;
import java.util.HashMap;
public class ToastModule extends ReactContextBaseJavaModule {
private static final String DURATION_SHORT_KEY = "SHORT";
private static final String DURATION_LONG_KEY = "LONG";
public ToastModule(ReactApplicationContext reactContext) {
super(reactContext);
}
@Override
public String getName() {
return "ToastExample";
}
@Override
public Map<String, Object> getConstants() {
final Map<String, Object> constants = new HashMap<>();
constants.put(DURATION_SHORT_KEY, Toast.LENGTH_SHORT);
constants.put(DURATION_LONG_KEY, Toast.LENGTH_LONG);
return constants;
}
@ReactMethod
public void show(String message, int duration) {
Toast.makeText(getReactApplicationContext(), message, duration).show();
}
}
// <workspace>/android/app/src/main/java/com/reactlibrary/ToastPackage.java
package com.reactlibrary;
import com.facebook.react.ReactPackage;
import com.facebook.react.bridge.NativeModule;
import com.facebook.react.bridge.ReactApplicationContext;
import com.facebook.react.uimanager.ViewManager;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
public class CustomToastPackage implements ReactPackage {
@Override
public List<ViewManager> createViewManagers(ReactApplicationContext reactContext) {
return Collections.emptyList();
}
@Override
public List<NativeModule> createNativeModules(ReactApplicationContext reactContext) {
List<NativeModule> modules = new ArrayList<>();
modules.add(new ToastModule(reactContext));
return modules;
}
}
// <workspace>/android/app/src/main/java/host/exp/exponent/MainApplication.java
package host.exp.exponent;
// other imports
import com.reactlibrary.CustomToastPackage
public class MainApplication extends ExpoApplication implements AppLoaderPackagesProviderInterface<ReactPackage> {
// Needed for `react-native link`
public List<ReactPackage> getPackages() {
return Arrays.<ReactPackage>asList(
// Needed for `react-native link`
new MainReactPackage(),
new KCKeepAwakePackage(),
new CustomToastPackage()
);
}
// other methods...
}
Finally, in my React Native application, I load it like so: 最后,在我的React Native应用程序中,我像这样加载它:
// <workspace>/src/utils/native-modules.ts
import { NativeModules } from 'react-native'
export const { ToastExample } = NativeModules
I would expect ToastExample
in native-modules.ts
to return some API that I can interact with, in this case, the methods exposed by the CustomToastPackage
. 我希望
native-modules.ts
ToastExample
返回一些我可以与之交互的API,在本例中是CustomToastPackage
公开的方法。
ToastExample
is undefined. ToastExample
未定义。
Please make a module declaration on the same path. 请在同一路径上进行模块声明。
// <workspace>/android/app/src/main/java/com/reactlibrary/index.js
import { NativeModules } from "react-native";
const { ToastExample } = NativeModules;
export default ToastExample;
Usage 用法
import {
NativeModules
} from "react-native";
...
const { ToastExample } = NativeModules;
...
ToastExample.show('Awesome', ToastExample.SHORT);
Judging from your code, you custom package creation looks correct. 从您的代码来看,您自定义包创建看起来是正确的。 Assuming the android code is also built before running the app (not just a package reload from the bundler), I would expect this to work.
假设在运行应用程序之前也构建了android代码(不仅仅是从bundle中重新加载包),我希望这可以工作。
You do not show an actual method request on ToastExample, so at which point did you determine that ToastExample is undefined? 您没有在ToastExample上显示实际的方法请求,那么您在哪一点确定ToastExample未定义? Did you use a debugger for this?
你有没有使用调试器?
import { NativeModules } from 'react-native';
const { ToastExample } = NativeModules;
showTest = () => {
ToastExample.show('test', ToastExample.SHORT);
}
If you'd set a breakpoint inside the showTest function, it's possible a debugger returns a ReferenceError when evaluating the 'ToastExample' inside a debug console, while the code runs fine. 如果你在showTest函数中设置一个断点,调试器在评估调试控制台内的'ToastExample'时可能会返回一个ReferenceError,而代码运行正常。 So did the code actually break at run-time?
那么代码实际上是在运行时中断了吗?
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.