Search code examples
javaandroidreact-nativeandroid-intent

How to launch and receive output from another app through intent in react native?


I have create react native application using VSCode and now, I have to integrate the reader device using micro USB host.

I have install the reader app to test the APK. And based from the web, I can call the reader app through intent from my current app. Device weblink here.

Currently, I have try search tutorial for calling native app through intent. But I'm stuck in a way to put the script. Either I should create new file/paste the script below existing/replace the existing in ./android/app/src/main/java/com/myAppName/MainApplication.java and how to call and receive the output from my scanner class in ./src/screens/scanScreens/mainScanner.js

Below is what I have go though but stuck on what should I do next:-

  1. Native Modules
  2. Integration of React-Native Module into an existing Native App (Android)
  3. App-to-app communication with React Native on Android
  4. Stack accepted answer
  5. react-native-intent-launcher

My current MainActivity.java [UPDATED]

package com.myappname;

import com.facebook.react.ReactActivity;
import com.facebook.react.ReactActivityDelegate;
import com.facebook.react.ReactRootView;
import com.swmansion.gesturehandler.react.RNGestureHandlerEnabledRootView;

public class MainActivity extends ReactActivity {

    /**
     * Returns the name of the main component registered from JavaScript.
     * This is used to schedule rendering of the component.
     */
    @Override
    protected String getMainComponentName() {
        return "myAppName";
    }

    @Override
    protected ReactActivityDelegate createReactActivityDelegate() {
        return new ReactActivityDelegate(this, getMainComponentName()) {
        @Override
        protected ReactRootView createRootView() {
        return new RNGestureHandlerEnabledRootView(MainActivity.this);
        }
        };
    }
}
public class ShowKadModule extends ReactContextBaseJavaModule {

    @ReactMethod
    public void showKadApp() {
        final Activity activity = getCurrentActivity();
        Intent intent = new Intent ("com.causalidea.cikad.showkad.READ_MYKAD");
        Bundle extras = new Bundle ();
        extras.putBoolean ("READ_PHOTO", false); // Do not read the photo
        intent.putExtras (extras);
        activity.startActivityForResult (intent, 0); 
     }
     public ShowKadModule(ReactApplicationContext reactContext) {
        super(reactContext);
        // Add the listener for `onActivityResult`
        reactContext.addActivityEventListener(mActivityEventListener);
      }

      @Override
      public String getName() {
        return "ShowKadModule";
      }
     @Override
     public void onActivityResult(int requestCode, int resultCode, final Intent data) {
        if (resultCode == Activity.RESULT_OK) {
            extras = intent.getExtras ();

            if (extras != null) {
                extras.getString ("IC_NUMBER");
                extras.getString ("NAME");
                extras.getString ("GENDER");
                extras.getString ("CITIZENSHIP");

                extras.getString ("BIRTH_DATE");
                extras.getString ("RACE");
                extras.getString ("RELIGION");

                extras.getString ("ADDRESS_1");
                extras.getString ("ADDRESS_2");
                extras.getString ("ADDRESS_3");
                extras.getString ("POSTCODE");
                extras.getString ("CITY");
                extras.getString ("STATE");

                photoByteArray = extras.getByteArray ("PHOTO");

                if (photoByteArray != null) {
                    bitmap = BitmapFactory.decodeByteArray (photoByteArray, 0, photoByteArray.length);
                    imageView.setImageBitmap (bitmap);
                }
            }
        } else if (resultCode == Activity.RESULT_CANCELED) {

        }
     }
}

Solution

  • After go through so many example and tutorial, I have found a simple solutions. By installing react-native-activity-result from here.

    How I perform this is as below:

    import ActivityResult from 'react-native-activity-result';
    
    _onLaunch = async () => {
        const activity = await ActivityResult.resolveActivity('com.causalidea.cikad.showkad.READ_MYKAD');
        if (!activity) {
            console.warn('Please install the othe app.');
            ToastAndroid.show(`MyKAD application reader is not install`, ToastAndroid.SHORT, ToastAndroid.BOTTOM);
        } else {
            console.log(`Activity will be handled by ${activity.package}`);
            ToastAndroid.show(`Activity will be handled by ${activity.package}`, ToastAndroid.SHORT, ToastAndroid.BOTTOM);
        }
    
        // Start an activity for a result
        let uniqueId = 0;
        let args = {READ_PHOTO: false};
        ToastAndroid.show(`Test`, ToastAndroid.SHORT, ToastAndroid.BOTTOM);
        const response = await ActivityResult.startActivityForResult(uniqueId, 'com.causalidea.cikad.showkad.READ_MYKAD', args);
        ToastAndroid.show(`Result code: ${response.resultCode}`, ToastAndroid.LONG, ToastAndroid.BOTTOM);
    
    
        if (response.resultCode !== ActivityResult.OK) {
            ToastAndroid.show(`Invalid result from activity.`, ToastAndroid.SHORT, ToastAndroid.BOTTOM);
            throw new Error('Invalid result from activity.');
        } else {
            console.log('Got the following response: ' + response.data);
            ToastAndroid.show(`Response:\n${JSON.stringify(response)}`, ToastAndroid.SHORT, ToastAndroid.BOTTOM);
        }
    
        // Finish an activity with a result. This will close the caller too.
        //ActivityResult.finish(ActivityResult.OK, 'com.causalidea.cikad.showkad.READ_MYKAD', args);
    }
    

    I can launch the other app and wait for activity result and it act as accordingly.