Java Question Intents

Johan Schoeman

Expert
Licensed User
Longtime User
For the project that I have posted HERE I followed 2 different approaches. The first approach was to make use on Intents. So, my wrapper looked like this:

B4X:
    public void BeginScan(final BA ba,String EventName) {

        myba=ba;
        eventname=EventName.toLowerCase();
        //Intent izx;
        izx=new Intent(BA.applicationContext, CaptureActivity.class);
        ion=new IOnActivityResult() {
           
            @Override
            public void ResultArrived(int arg0, Intent arg1) {
               
                 BA.Log("RESULT ARRIVED");
                String resultbarcodetype = arg1.getStringExtra("resultbarcodetype");
                String resulttext = arg1.getStringExtra("resulttext");   
                byte[] byteArray = arg1.getByteArrayExtra("barcodeimage"); 
                Bitmap image = BitmapFactory.decodeByteArray(byteArray, 0, byteArray.length);
                myba.raiseEvent2(null, false, eventname+"_result", true, new Object[]{resultbarcodetype,resulttext,image}); 

            }
        };
        ba.startActivityForResult(ion, izx);
    }

And in class CaptureActivity.java I had this:

B4X:
  private void handleDecodeInternally(Result rawResult, ResultHandler resultHandler, Bitmap barcode) {
     
      //BA.Log("IN handleDecodeInternally");
      Intent data=new Intent();                                                                 //added by johan schoeman
     
      data.putExtra("resultbarcodetype", rawResult.getBarcodeFormat().toString());              //added by johan schoeman
      data.putExtra("resulttext", rawResult.getText());                                         //added by johan schoeman
      ByteArrayOutputStream stream = new ByteArrayOutputStream();                               //added by johan schoeman
      barcode.compress(Bitmap.CompressFormat.PNG, 100, stream);                                 //added by johan schoeman
      byte[] byteArray = stream.toByteArray();                                                  //added by johan schoeman
      data.putExtra("barcodeimage",byteArray);                                                  //added by johan schoeman      
     
      setResult(RESULT_OK, data);                                                                 //added by johan schoeman

This approach raised "public void ResultArrived(int arg0, Intent arg1)" in the wrapper but only returned the result of the last scan when I am back in the B4A project.

I therefor tried a different approach with the wrapper looking like this (where I raise an Event from within CaptureActivity.java):

B4X:
@Events(values={"scan_result(barcodetype as String, barcodetext as String, barcode as Object)"})
@ActivityObject
@Permissions(values={"android.permission.CAMERA","android.permission.WRITE_EXTERNAL_STORAGE", "android.permission.INTERNET", "android.permission.READ_CONTACTS",
                     "com.android.browser.permission.READ_HISTORY_BOOKMARKS", "android.permission.CHANGE_WIFI_STATE", "android.permission.ACCESS_WIFI_STATE",
                     "android.hardware.camera","android.hardware.camera.autofocus","android.permission.VIBRATE","android.permission.FLASHLIGHT"})

public class zxingstandaloneWrapper {
    @Hide
    public static BA myba;
    private IOnActivityResult ion;

    @Hide
    public static String eventname;

    public static int laserColor = 0xffff0000;
    public static int[] laserAlpha = {0, 64, 128, 192, 255, 192, 128, 64};
    public static int maskColor = 0x880000aa;
    public static int resultColor = 0x55550055;
    public static int resultPointColor = 0xffffffff;
    public static int BACK_CAMERA = 0;
    public static int FRONT_CAMERA = 1;
    Intent izx;
   
    public void BeginScan(final BA ba,String EventName) {

        myba=ba;
        eventname=EventName.toLowerCase();
        //Intent izx;
        izx=new Intent(BA.applicationContext, CaptureActivity.class);
        ion=new IOnActivityResult() {
           
            @Override
            public void ResultArrived(int arg0, Intent arg1) {
               
/*                 BA.Log("RESULT ARRIVED");
                String resultbarcodetype = arg1.getStringExtra("resultbarcodetype");
                String resulttext = arg1.getStringExtra("resulttext");   
                byte[] byteArray = arg1.getByteArrayExtra("barcodeimage"); 
                Bitmap image = BitmapFactory.decodeByteArray(byteArray, 0, byteArray.length);
                myba.raiseEvent2(null, false, eventname+"_result", true, new Object[]{resultbarcodetype,resulttext,image});  */

            }
        };
        ba.startActivityForResult(ion, izx);
    }

And in CaptureActivity.java I did the following:

B4X:
import anywheresoftware.b4a.BA;
import zxingstandalonewrapper.zxingstandaloneWrapper;
...
...
...
...

  private void handleDecodeInternally(Result rawResult, ResultHandler resultHandler, Bitmap barcode) {
     
      //BA.Log("IN handleDecodeInternally");
      //Intent data=new Intent();                                                                 //added by johan schoeman
     
//      data.putExtra("resultbarcodetype", rawResult.getBarcodeFormat().toString());              //added by johan schoeman
//      data.putExtra("resulttext", rawResult.getText());                                         //added by johan schoeman
//      ByteArrayOutputStream stream = new ByteArrayOutputStream();                               //added by johan schoeman
//      barcode.compress(Bitmap.CompressFormat.PNG, 100, stream);                                 //added by johan schoeman
//      byte[] byteArray = stream.toByteArray();                                                  //added by johan schoeman
//      data.putExtra("barcodeimage",byteArray);                                                  //added by johan schoeman      
     
//      setResult(RESULT_OK, data);                                                                 //added by johan schoeman
     
   
    if (zxingstandaloneWrapper.myba.subExists(zxingstandaloneWrapper.eventname + "_scan_result")) {
        zxingstandaloneWrapper.myba.raiseEventFromDifferentThread(this, null, 0, zxingstandaloneWrapper.eventname + "_scan_result", true, new Object[]
                        {rawResult.getBarcodeFormat().toString(), rawResult.getText(), barcode});
    }

When I now return to B4A all the scan results are displayed.

So, the question is : does an Intent only return the last "changed" values in the external activity that was started? The latter approach seems to be the better of the two devils....
 

Erel

B4X founder
Staff member
Licensed User
Longtime User
Raising an event is better than returning an intent as it is more flexible.

BTW, you don't need to check that the sub exists. Just set the throwErrorIfMissingSub to false instead.

does an Intent only return the last "changed" values in the external activity that was started?
I'm not sure that I 100% understand the question. A single result is returned when the activity is closed. The result itself can include many values.
 
Top