10/18/2011 1 Android 12-2 Intents Part2 Inter‐ProcessCommunicationUsingBundles VictorMatos ClevelandStateUniversity Notesarebasedon: AndroidDevelopers http://developer.android.com/index.html 12.Android–Intents–Part2 Intents AndroidIntents An activity usually presents a single visual user interface from which a number of An activity usually presents a single visual user interface from which a number of actionscouldbeperformed. Movingfromoneactivitytoanotherisaccomplishedbyhavingthecurrent activitystartthenextonethroughsocalledintents. Intent {action + data} Activity ‐ 1 22 {action data} requestCode requestResult [optionaldata ] Activity ‐ 1 startActivityForResult … onActivityResult() … Activity‐2 onResult() … … 10/18/2011 2 12.Android–Intents–Part2 Intents AndroidBundles MostprogramminglanguagessupportthenotionofIPC metho d ‐calling with argumentsflowingbirectionallyfromthecallertotheinvokedmethod. Inandroidthecallingactivityissuesaninvocationtoanotheractivityusingan Intent object. NotablyinAndroid,thecallerdoesnotstopwaitingfor the called activity to return results Instead a listening 33 the called activity to return results . Instead a list ening ‐ method[onActivityResult( )]shouldbeused. IPCInter‐ProcessCommunication 12.Android–Intents–Part2 Intents AndroidBundles NormallytheIPCexpressionsactualparameterlist,and formalparameterlist areusedtodesignatedthesignatureof particpatingarguments,andthecurrentlysupplieddata. Insteadofusingthetraditionalformal/actualparameterlists, AndroidreliesontheconceptofIntentstoestablishInter‐process‐ 44 communication. Intentsoptionallycarryanamedactuallistorbundle fo rdata exchange. 10/18/2011 3 12.Android–Intents–Part2 Intents AndroidBundles TheAndroidBundle containerisasimplemechanismusedtopassdatabetween activities. ABundle isatype‐safecollectionof <name,value> pairs. ThereisasetofputXXX andgetXXX methodstostoreandretrieve(singleand array)valuesofprimitivedatatypesfrom/tothebundles.Forexample 55 Bundle myBundle = new Bundle(); myBundle.putDouble ("var1", 3.1415); Double v1 = myBundle.getDouble("var1"); 12.Android–Intents–Part2 Intents AndroidIntents&Bundles Activit y 1:Sender Activit y 2:Receiver IntentmyIntentA1A2=newIntent(Activity1.this, Activity2.class); BundlemyBundle1=newBundle(); myBundle1.putInt("val1",123); myIntentA1A2.putExtras(myBundle1); startActivityForResult(myIntentA1A2,1122); y y INTENT requestCode ( 1122 ) Senderclass/Receiverclass 66 requestCode ( 1122 ) resultCode Extras:{val1=123 } 10/18/2011 4 12.Android–Intents–Part2 Intents AndroidIntents&Bundles Activit y 1:Sender Activit y 2:Receiver y y INTENT Cd ( 1122 ) Senderclass/Receiverclass IntentmyCallerIntent2=getIntent(); BundlemyBundle =myCallerIntent.getExtras(); int val1=myBundle.getInt("val1"); 77 request C o d e ( 1122 ) resultCode Extras:{val1=123 } 12.Android–Intents–Part2 Intents AndroidIntents&Bundles Activit y 1:Sender Activit y 2:Receiver y y INTENT Cd ( 1122 ) Senderclass/Receiverclass myBundle.putString("val1",456); myCallerIntent.putExtras(myBundle); setResult(Activity.RESULT_OK, myCallerIntent); 88 request C o d e ( 1122 ) resultCode (OK) Extras:{val1=456} 10/18/2011 5 12.Android–Intents–Part2 Intents AndroidBundlesAvailableat:http://developer.android.com/reference/android/os/Bundle.html Exam p le of Public Methods void clear() Removes all elements from the mapping of this Bundle. Object clone () Object clone () Clones the current Bundle. boolean containsKey(String key) Returns true if the given key is contained in the mapping of this Bundle. void putIntArray (String key, int[] value) Inserts an int array value into the mapping of this Bundle, replacing any existing value for the given key. void putString(String key, String value) Inserts a String value into the mapping of this Bundle, replacing any existing value for the given key. void putStringArray (String key, String[] value) Inserts a String array value into the mapping of this Bundle, replacing any 99 existing value for the given key. void putStringArrayList(String key, ArrayList<String> value) Inserts an ArrayList value into the mapping of this Bundle, replacing any existing value for the given key. void remove (String key) Removes any entry with the given key from the mapping of this Bundle. int size() Returns the number of mappings contained in this Bundle. 12.Android–Intents–Part2 Intents Tutorial1.ActivityExcahange Activity1collectstwovaluesfromitsUIandcallsActivity2tocomputethe sumofthem.TheresultissentbackfromActivity2toActivity1. 1010 10/18/2011 6 12.Android–Intents–Part2 Intents Tutorial1.ActivityExcahange Step1. CreateGUIforActivity1(main1.xml) <?xmlversion="1.0"encoding="utf‐8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="vertical"android:layout_width="fill_parent" android:layout_height="fill_parent"> <TextView android:text="Activity1" android:textSize="22sp" android:background =" #ff0000ff " android:background #ff0000ff android:layout_width="fill_parent" android:layout_height="wrap_content"/> <EditText android:hint="Enterfirstvalue(asigneddouble)" android:id="@+id/EditText01" android:layout_width="fill_parent" android:layout_height="wrap_content" android:inputType="numberDecimal|numberSigned|number"/> <EditText android:hint="Secondvalue(apositiveinteger)" android:id="@+id/EditText02" android:layout_width="fill_parent" android:layout_height="wrap_content" android:inputType="number"/> <Button 1111 <Button android:text="AddValues" android:id="@+id/btnAdd" android:layout_width="wrap_content" android:layout_height="wrap_content"/> <TextView android:background="#ff0000ff" android:text="Sumis " android:textSize="28sp" android:id="@+id/TextView01" android:layout_width="fill_parent" android:layout_height="wrap_content"/> </LinearLayout> Note.Theelementandroid:inputStyle indicatesthefirstvaluecouldbenumeric,with optionaldecimalsandsign. 12.Android–Intents–Part2 Intents Tutorial1.ActivityExcahange Step2. CreateGUIforActivity2(main2.xml) <?xmlversion="1.0"encoding="utf‐8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="vertical" android:layout_width="fill_parent" android:layout_height="fill_parent" android:background="#ff888888"> < TextView < TextView android:text="Activity2" android:textSize="22sp" android:background="#ff0000ff" android:layout_width="fill_parent" android:layout_height="wrap_content"/> <EditText android:text="Datareveived " android:id="@+id/etDataReceived" android:layout_width="fill_parent" android:layout_height="wrap_content"/> <Button android:text="Done‐ Callback" android:id =" @+id/ btnDone " 1212 android:id @+id/ btnDone android:layout_width="wrap_content" android:layout_height="wrap_content"/> </LinearLayout> 10/18/2011 7 12.Android–Intents–Part2 Intents Tutorial1.ActivityExcahange Step3. Activity1.Afterclickingthebuttondata,fromUIisputinabundleandsentto Activity2.Alistenerremainsalertwaitingforresultstocomefromthecalledactivity. package cis493.matos.intent2b; //Activity1:gettwoinputvaluesfromuser,puttheminabumble.callActivity2toaddthetwonumbers,showresult import ; public class Activity1 extends Activity { public class Activity1 extends Activity { EditText txtVal1; EditText txtVal2; TextView lblResult; ButtonbtnAdd; @Override public void onCreate(BundlesavedInstanceState){ super.onCreate(savedInstanceState); setContentView(R.layout.main1); txtVal1 =(EditText)findViewById(R.id.EditText01); txtVal2 =(EditText)findViewById(R.id.EditText02); lblResult =(TextView)findViewById(R.id.TextView01); btnAdd =(Button)findViewById(R.id.btnAdd); btnAdd.setOnClickListener(new OnClickListener(){ @Override public void onClick(Viewv){ //getvaluesfromtheUI Doublev1=Double.parseDouble(txtVal1.getText().toString()); Double v2 = Double. parseDouble ( txtVal2 .getText(). toString ()); 1313 Double v2 Double. parseDouble ( txtVal2 .getText(). toString ()); //createintenttocallActivity2 IntentmyIntentA1A2=new Intent(Activity1.this, Activity2.class); //createacontainertoshipdata BundlemyData =new Bundle(); //add<key,value>dataitemstothecontainer myData.putDouble("val1",v1); myData.putDouble("val2",v2); //attachthecontainertotheintent myIntentA1A2.putExtras(myData); //callActivity2,tellyourlocallistenertowait forresponse startActivityForResult(myIntentA1A2,101); } }); }//onCreate 12.Android–Intents–Part2 Intents Tutorial1.ActivityExcahangecont. Step3.Activity1.Afterclickingthebuttondata,fromUIisputinabundleandsentto Activity2.Alistenerremainsalertwaitingforresultstocomefromthecalledactivity. ////////////////////////////////////////////////////////////////////////////// //locallistenerreceivingcallbacksfromotheractivities @Override protected void onActivityResult(int requestCode,int resultCode,Intentdata){ super.onActivityResult(requestCode,resultCode,data); try { if ((requestCode ==101)&&(resultCode ==Activity.RESULT_OK)){ BundlemyResults =data.getExtras(); Doublevresult =myResults.getDouble("vresult"); lblResult.setText("Sumis" +vresult); } } catch (Exceptione){ lbl l ( "bl " d " " ld ) 1414 lbl Resu l t.setText ( " Pro bl ems‐ " +requestCo d e+ " " +resu l tCo d e ) ; } }//onActivityResult }//Activity1 10/18/2011 8 12.Android–Intents–Part2 Intents Tutorial1.ActivityExcahangecont. Step4. Activity2.CalledfromActivity1.Extractsinputdatafromthebundleattachedto theintent.Performslocalcomputation.Addsresulttobundle.ReturnsOKsignal. package cis493.matos.intent2b; import ...; //returnsendinganOKsignaltocallingactivity setResult(Activity.RESULT_OK,myLocalIntent); //experiment:removecomment public class Activity2extends Activityimplements OnClickListener{ EditText dataReceived; ButtonbtnDone; @Override protected void onCreate(BundlesavedInstanceState){ super.onCreate(savedInstanceState); setContentView(R.layout.main2); dataReceived =(EditText)findViewById(R.id.etDataReceived); btnDone =(Button)findViewById(R.id.btnDone); btnDone.setOnClickListener(this); //pickcallmadetoActivity2viaIntent IntentmyLocalIntent =getIntent(); //lookintothebundlesenttoActivity2fordataitems BundlemyBundle =myLocalIntent.getExtras(); Double v1 = myBundle.getDouble ( " val1 " ); //finish(); }//onCreate @Override public void onClick(Viewv){ //closecurrentscreen‐ terminateActivity2 finish(); }//onClick }//Activity2 1515 Double v1 myBundle.getDouble ( val1 ); Doublev2=myBundle.getDouble("val2"); //operateontheinputdata DoublevResult =v1+v2; //forillustrationpurposes.showdatareceived&result dataReceived.setText("Datareceivedis\n" +"val1=" +v1+"\nval2=" +v2 +"\n\nresult=" +vResult); //addtothebundlethecomputedresult myBundle.putDouble("vresult", vResult); //attachupdatedbumbletoinvokingintent myLocalIntent.putExtras(myBundle); 12.Android–Intents–Part2 Intents Tutorial1.ActivityExcahangecont. Step5. Updatetheapplication‘smanifest.Addnew<activity>tagfor“Activity2“ <?xml version="1.0" encoding="utf-8"?> <manifest xmlns:android="http://schemas.android.com/apk/res/android" package="cis493.matos.intent2b" android:versionCode="1" android:versionName="1.0"> <application android:icon="@drawable/icon" android:label="@string/app_name"> <activity android:name=".Activity1" android:label="@string/app_name"> <intent-filter> <action android:name="android.intent.action.MAIN" /> <category android:name="android.intent.category.LAUNCHER" /> </intent-filter> </activity> <activity android:name=".Activity2"> </activity> / add 1616 < / application> <uses-sdk android:minSdkVersion="4" /> </manifest> 10/18/2011 9 12.Android–Intents–Part2 Intents Tutorial2::Activity1invokesActivity2usinganIntent.Abundleconatingasetof differentdatatypes issentback‐and‐forthbetweenbothactivities (see12IntentDemo3.zip). Thisexampleissimilartoprevious. Youmaywanttoskipit. 1717 //Activity1:Invokingauser‐definedsub‐activitysendingandreceivingresultsfromthesub‐activity package cis493.intents3; 12.Android–Intents–Part2 Intents Tutorial2:Activity1invokesActivity2usinganIntent.Abundleconatingasetof differentdatatypes issentback‐and‐forthbetweenbothactivities (see12IntentDemo3.zip). import ...; public class Activity1extends Activity{ TextView label1; TextView label1Returned; ButtonbtnCallActivity2; //arbitraryinterprocess communicationID(justanickname !) private final int IPC_ID =(int)(10001*Math.random()); @Override public void onCreate(BundlesavedInstanceState){ super.onCreate(savedInstanceState); try { setContentView(R.layout.main); lbl1 ( TtVi ) fi dVi B Id (R id lbl1 ) l a b e l1 = ( T ex tVi ew ) fi n dVi ew B y Id (R . id . l a b e l1 ) ; label1Returned =(TextView)findViewById(R.id.label1Returned); btnCallActivity2 =(Button)findViewById(R.id.btnCallActivity2); btnCallActivity2.setOnClickListener(new Clicker1()); //fordemonstrationpurposes‐ showintoplabel label1.setText("Activity1(sending )\n\n" +"RequestCode ID:" +IPC_ID +"\n" +"myString1:HelloAndroid" +"\n" +"myDouble1:3.141592" +"\n" +"myIntArray:{123}"); }catch (Exceptione){ Toast.makeText(getBaseContext(),e.getMessage(),Toast.LENGTH_LONG ).show(); } }//onCreate 1818 10/18/2011 10 private class Clicker1implements OnClickListener { public void onClick(Viewv){ try { 12.Android–Intents–Part2 Intents Tutorial2:Activity1invokesActivity2usinganIntent.Abundleconatingasetof differentdatatypes issentback‐and‐forthbetweenbothactivities (see12IntentDemo3.zip). //createanIntenttotalktoActivit y2 IntentmyIntentA1A2=new Intent(Activity1.this, Activity2.class); //prepareaBundleandaddthedatapiecestobesent BundlemyData =new Bundle(); myData.putInt("myRequestCode",IPC_ID); myData.putString("myString1","HelloAndroid"); myData.putDouble("myDouble1",3.141592); int []myLittleArray ={1,2,3}; myData.putIntArray("myIntArray1",myLittleArray); //bindthe BundleandtheIntentthattalkstoActivity2 myIntentA1A2.putExtras(myData); //callActivity2andwaitforresults startActivityForResult(myIntentA1A2,I PC_ID); }catch (Exceptione){ Toast.makeText(getBaseContext(),e.getMessage(),Toast.LENGTH_LONG).show(); } }//onClick }//Clicker1 1919 @Override protected void onActivityResult(int requestCode,int resultCode,Intentdata){ super.onActivityResult(requestCode,resultCode,data); { 12.Android–Intents–Part2 Intents Tutorial2:Activity1invokesActivity2usinganIntent.Abundleconatingasetof differentdatatypes issentback‐and‐forthbetweenbothactivities (see12IntentDemo3.zip). try { //checkthattheseresultsareforus if (IPC_ID ==requestCode){ //Activity2isover‐ seewhathappened if (resultCode ==Activity.RESULT_OK){ //good‐ wehavesomedatasentbackfromActivity2 BundlemyReturnedData =data.getExtras(); StringmyReturnedString1=myReturnedData.getString("myReturnedString1"); DoublemyReturnedDouble1=myReturnedData.getDouble("myReturnedDouble1"); StringmyReturnedString2=myReturnedData.getString("myCurrentTime"); //displayin thebottomlabel label1Returned.setText( "requestCode:" +requestCode +"\n" +"resultCode:" + resultCode +"\n" +"returnedString1:" +myReturnedString1+"\n" +"returnedDouble:" + Double.toString(myReturnedDouble1)+"\n" +"returnedString2:" +myReturnedString2); }else { //userpressedtheBACKbutton label1.setText("SelectionCANCELLED!"); }//if } }catch (Exceptione){ Toast.makeText(getBaseContext(),e.getMessage(),Toast.LENGTH_LONG).show(); }//try }//onActivityResult }//AndroIntent1 2020 [...]... android: id="@+id/btnCallActivity2" android: id="@+id/caption1" android: layout_width="149px" android: layout_width="fill_parent" android: layout_height="wrap_content" android: layout_height="wrap_content" android: text="Call Activity2" android: background="#ffff3300" android: textStyle="bold" android: padding="4sp" android: padding="6sp" android: text=" Activity1 " > android: textSize 20 px android: textSize= "20 px" android: textStyle="bold"... xmlns :android= "http://schemas .android. com/apk/res /android" android: background="#ff555555">