在React Native上为android创建自定义UI组件失败。应用程序崩溃

时间:2015-09-28 18:05:06

标签: reactjs react-native

由于Facebook登录按钮本身可用,我想要一个适用于Android的React Native包装器组件。所以,我试着写它。但应用程序甚至在开始之前就崩溃了。 我的github存储库是: https://github.com/lalith26/react-native-fb-login-android

我做了以下事情:

  1. 我为LoginButton facebook小部件创建了管理器:
  2. https://github.com/lalith26/react-native-fb-login-android/blob/master/android/app/src/main/java/com/fbloginbutton2/FBLoginButtonManager.java

    1. 我创建了一个扩展MainReactPackage的ReactPackage:
    2. https://github.com/lalith26/react-native-fb-login-android/blob/master/android/app/src/main/java/com/fbloginbutton2/FBLoginButtonReactPackage.java

      1. 我在MainActivity中添加了新的ReactPackage:
      2. https://github.com/lalith26/react-native-fb-login-android/blob/master/android/app/src/main/java/com/fbloginbutton2/MainActivity.java#L29

        1. 我包含了facebook登录sdk的gradle依赖
        2. https://github.com/lalith26/react-native-fb-login-android/blob/master/android/app/build.gradle#L28

          1. 我将JS组件包装为Native Component:
          2. https://github.com/lalith26/react-native-fb-login-android/blob/master/fblogin.js

            1. 最后我使用了JS组件:
            2. https://github.com/lalith26/react-native-fb-login-android/blob/master/index.android.js#L21

              我通过网络阅读并发现必须传递propTypes。我也试过了。但应用程序在启动时崩溃了。我无法看到任何日志。所以,我无法找到问题的实际原因。 我为一个按钮尝试了相同的一组步骤,它工作正常。

              有什么我只是做错了。请帮忙..

              我通过logcat访问了模拟器的日志。它显示:

                

              E / AndroidRuntime(2550):进程:com.fbloginbutton2,PID:2550   E / AndroidRuntime(2550):java.lang.ExceptionInInitializerError   E / AndroidRuntime(2550):at   com.fbloginbutton2.FBLoginButtonManager.createViewInstance(FBLoginButtonManager.java:29)   E / AndroidRuntime(2550):at   com.fbloginbutton2.FBLoginButtonManager.createViewInstance(FBLoginButtonManager.java:15)   E / AndroidRuntime(2550):at   com.facebook.react.uimanager.ViewManager.createView(ViewManager.java:41)   E / AndroidRuntime(2550):at   com.facebook.react.uimanager.NativeViewHierarchyManager.createView(NativeViewHierarchyManager.java:172)   E / AndroidRuntime(2550):at   com.facebook.react.uimanager.UIViewOperationQueue $ CreateViewOperation.execute(UIViewOperationQueue.java:137)   E / AndroidRuntime(2550):at   com.facebook.react.uimanager.UIViewOperationQueue $ 1.run(UIViewOperationQueue.java:574)   E / AndroidRuntime(2550):at   com.facebook.react.uimanager.UIViewOperationQueue $ DispatchUIFrameCallback.doFrameGuarded(UIViewOperationQueue.java:622)   E / AndroidRuntime(2550):at   com.facebook.react.uimanager.GuardedChoreographerFrameCallback.doFrame(GuardedChoreographerFrameCallback.java:32)   E / AndroidRuntime(2550):at   com.facebook.react.uimanager.ReactChoreographer $ ReactChoreographerDispatcher.doFrame(ReactChoreographer.java:114)   E / AndroidRuntime(2550):at   android.view.Choreographer $ CallbackRecord.run(Choreographer.java:765)   E / AndroidRuntime(2550):at   android.view.Choreographer.doCallbacks(Choreographer.java:580)   E / AndroidRuntime(2550):at   android.view.Choreographer.doFrame(Choreographer.java:549)   E / AndroidRuntime(2550):at   android.view.Choreographer $ FrameDisplayEventReceiver.run(Choreographer.java:753)   E / AndroidRuntime(2550):at   android.os.Handler.handleCallback(Handler.java:739)E / AndroidRuntime(   2550):在android.os.Handler.dispatchMessage(Handler.java:95)   E / AndroidRuntime(2550):在android.os.Looper.loop(Looper.java:135)   E / AndroidRuntime(2550):at   android.app.ActivityThread.main(ActivityThread.java:5221)   E / AndroidRuntime(2550):at java.lang.reflect.Method.invoke(Native   方法)E / AndroidRuntime(2550):at   java.lang.reflect.Method.invoke(Method.java:372)E / AndroidRuntime(   2550):at   com.android.internal.os.ZygoteInit $ MethodAndArgsCaller.run(ZygoteInit.java:899)   E / AndroidRuntime(2550):at   com.android.internal.os.ZygoteInit.main(ZygoteInit.java:694)   E / AndroidRuntime(2550):引起:null E / AndroidRuntime(2550):at   com.facebook.internal.Validate.sdkInitialized(Validate.java:99)   E / AndroidRuntime(2550):at   com.facebook.FacebookSdk.getCallbackRequestCodeOffset(FacebookSdk.java:735)   E / AndroidRuntime(2550):at   com.facebook.internal.CallbackManagerImpl $ RequestCodeOffset.toRequestCode(CallbackManagerImpl.java:109)   E / AndroidRuntime(2550):at   com.facebook.login.widget.LoginButton。(LoginButton.java:58)   E / AndroidRuntime(2550):... 21更多W / ActivityManager(1327):
                强制完成活动com.fbloginbutton2 / .MainActivity   E / EGL_emulation(1373):tid 1373:eglCreateSyncKHR(1181):错误0x3004   (EGL_BAD_ATTRIBUTE)

2 个答案:

答案 0 :(得分:11)

我发现很难找到关于这个问题的简单示例或文档,所以这里是我的代码示例,扩展了KenBurnsView(https://github.com/flavioarfaria/KenBurnsView),我希望这个例子简单而有用:

KenBurnsViewManager.Java:

import com.flaviofaria.kenburnsview.KenBurnsView;

import com.facebook.react.uimanager.SimpleViewManager;
import com.facebook.react.uimanager.ThemedReactContext;
import com.facebook.react.uimanager.ReactProp;

import java.io.InputStream;

import android.graphics.drawable.Drawable;
import android.util.Log;

public class KenBurnsViewManager extends SimpleViewManager<KenBurnsView> {

  public static final String REACT_CLASS = "KenBurnsView";
  private ThemedReactContext ctx;

  @Override
  public String getName() {
    return REACT_CLASS;
  }

  @Override
  protected KenBurnsView createViewInstance(ThemedReactContext context) {
    ctx = context;
    return new KenBurnsView(context);
  }

  @ReactProp(name = "source")
  public void setSource(KenBurnsView view, String source) {
    try {
      InputStream ims = ctx.getAssets().open("images/" + source);
      Drawable d = Drawable.createFromStream(ims, null);
      view.setImageDrawable(d);
    } catch (Exception ex) {
      Log.e("KenBurnsView", "setSource", ex);
    }
  }
}

KenBurnsViewPackage.Java:

import com.facebook.react.ReactPackage;
import com.facebook.react.bridge.JavaScriptModule;
import com.facebook.react.bridge.NativeModule;
import com.facebook.react.bridge.ReactApplicationContext;
import com.facebook.react.uimanager.ViewManager;

import java.util.Collections;
import java.util.List;
import java.util.Arrays;
import java.util.ArrayList;

public class KenBurnsViewPackage implements ReactPackage {
    @Override
    public List<NativeModule> createNativeModules(
        ReactApplicationContext reactContext) {

        List<NativeModule> modules = new ArrayList<>();

        return modules;
    }

    @Override
    public List<ViewManager> createViewManagers(
            ReactApplicationContext reactContext) {
        return Arrays.<ViewManager>asList(
            new KenBurnsViewManager()
        );
    }

    @Override
    public List<Class<? extends JavaScriptModule>> createJSModules() {
      return Collections.emptyList();
    }
}

更新MainActivity.Java:

mReactInstanceManager = ReactInstanceManager.builder()
                .setApplication(getApplication())
                .setBundleAssetName("index.android.bundle")
                .setJSMainModuleName("index.android")
                .addPackage(new MainReactPackage())
                .addPackage(new KenBurnsViewPackage()) // <- add package
                .setUseDeveloperSupport(BuildConfig.DEBUG)
                .setInitialLifecycleState(LifecycleState.RESUMED)
                .build();

更新android / app / build.gradle:

dependencies {
    compile fileTree(dir: "libs", include: ["*.jar"])
    compile "com.android.support:appcompat-v7:23.0.1"
    compile "com.facebook.react:react-native:0.16.+"
    compile "com.flaviofaria:kenburnsview:1.0.6"
}

KenBurnsView.js:

var { requireNativeComponent, PropTypes, View } = require('react-native');

var iface = {
  propTypes: {
    ...View.propTypes,
    source: PropTypes.string,
  },
};

module.exports = requireNativeComponent('KenBurnsView', iface);

就是这样,现在你可以添加新的自定义KenBurnsView组件,例如:

var KenBurnsView = require('./KenBurnsView');
.
.
.
<KenBurnsView source={'image.jpg'} style={{width:null, height: 300}}/>

答案 1 :(得分:0)