Android的每一個畫面都是一個Activity元件, 多個畫面就需要有多個Activity元件.
主畫面設定檔
應用程式啟動後, 第一個出現的畫面叫主畫面. 在AndroidManifest.xml 設定檔的架構如下
<application
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:theme="@style/AppTheme">
<activity android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
<category android:name=”android.intent.category.LAUNCHER” /> 為應用程式啟動後第一個執行的畫面, 此設定固定不變
切換新增Activity元件
假如今天有A這個主畫面, 然後想到切換到B的畫面, 就需要使用Intent的方式來執成. 底下的說明步驟實際演練一次.
1. 開啟res/layout/activtiy_main.xml, 改為LinearLayout, 放置一個EditText : editTel, 及一顆按鈕 : btnFirst, Text改為 “切換”
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/activity_main"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.asuscomm.mahaljsp.ch11_01_newactivity.MainActivity"
android:orientation="vertical">
<EditText
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:ems="10"
android:id="@+id/editTel"
android:inputType="phone" />
<Button
android:text="切換"
android:onClick="btnFirst_click"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="@+id/btnFirst"/>
</LinearLayout>
2. 在專案按右鍵/new/Activity/Empty Activity, Activity name : SecondActivity, Layout name : activity_second.xml
3. 開啟activity_second.xml, Layout改為LinearLayout, 然後放置一顆按鈕, id為btnSecond, Text改為”返回”
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/activity_second"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.asuscomm.mahaljsp.ch11_01_newactivity.SecondActivity"
android:orientation="vertical">
<LinearLayout
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView
android:text="電話 : "
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="@+id/textView1"/>
<TextView
android:text="TextView"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="@+id/txtTel"/>
</LinearLayout>
<Button
android:text="返回"
android:onClick="btnSecond_click"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="@+id/btnSecond" />
</LinearLayout>
4. 開啟AndroidManifest.xml設定檔, 將設定檔改為如下
<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:supportsRtl="true"
android:theme="@style/AppTheme">
<activity android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity android:name=".SecondActivity"
android:label="第二個畫面">
</activity>
</application>
5. MainActivity.java如下
public class MainActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
public void btnFirst_click(View view){
Intent intent=new Intent(this, SecondActivity.class);
startActivity(intent);
}
}
AndroidManifest.xml設定檔
每新增一個Activity元件, 就需要在設定檔新增<activity>標簽. <activity>標簽常用設定如下
android:name : 元件類別名稱
android:screenOrientation : 有portrait, landscape, locked
<activity
android:name=".SecondActivity"
android:screenOrientation="landscape"
android:label="第二個畫面">
</activity>
Intent
Intent類別用來啟動另一個Activity元件, Service元件, 或是發送廣播. 其建構子有三種
Intent(Context, Class) : 由目前的Context轉換到Class
Intent(String) : 轉換到action
Intent() : 調用setAction()後再進行轉換
class
如上例, 直接new 出Intent, 指定由 this轉換到SecondActivity.class, 再用startActivity(intent)開始進行切換
action
在<activity>標簽中加入如下
<activity
android:name=".SecondActivity"
android:screenOrientation="landscape"
android:label="第二個畫面">
<intent-filter>
<action android:name="com.asuscomm.mahaljsp.IntentTest.Second" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</activity>
<action android:name>請輸入獨一無二之名稱, 而<category android:name=”android.intent.category.DEFAULT” />則為一般的Action.
若為 category.LAUNCHER, 則表示是第一個主畫面.
而在Java程式中使用如下方式啟動
public void btnFirst_click(View view){
Intent intent=new Intent("com.asuscomm.mahaljsp.IntentTest.Second");
startActivity(intent);
}
傳送與接收資料
傳送資料
當由主畫面A切換到B畫面時, 若要連同一些資料也傳送給B, 則可以把資料放入Intent中一起傳送. Intent類別提供 putExtra(字串, 資料)方法. 第二個參數可以是八大原生基本資料, 也可以是String, CharSequence. 另還有一個特殊的Bundle物件
public void btnFirst_click(View view){
Intent intent=new Intent("com.asuscomm.mahaljsp.IntentTest.Second");
intent.putExtra("Tel", editTel.getText().toString());
startActivity(intent);
}
Bundle
Bundle可以把不同的資料形態包在一起, 再使用Intent類別的putExtra(String, Bundle)傳送給啟動元件. 首先創造一個Bundle物件.
Bundle bundle=new Bundle();
再用bundle.putInt(String, int), bundle.putString(String, String)等方法將資料包入Bundle物件. 之後就可以使用Intent的putExtra(String, Bundle), 或putExtras(Bundle)傳送出去
public void btnFirst_click(View view){
Intent intent=new Intent("com.asuscomm.mahaljsp.IntentTest.Second");
Bundle bundle=new Bundle();
bundle.putInt("Age", 23);
bundle.putString("Tel", editTel.getText().toString());
intent.putExtra("Info", bundle);
startActivity(intent);
}
接收資料
被呼叫端啟動後, 可先使用getIntent()取得傳送進來的Intent物件. 再由Intent的intent.getIntExtra(String, default), intent.getStringExtra(String)等方法取得資料.
如果傳送進來的是Bundle物件, 則可使用下列二種方式取得Bundle物件
Bundle bundle=intent.getExtras();
Bundle bundle=intent.getBundleExtra(String);
然後再由bundle.getString(), bundle.getInt()等方式取得資料
回傳
當由主畫面A切換到B畫面, 然後又要由B切回A時, 稱為回傳. 此時由A切到B需使用startActivityForResult(intent, requestCode)進行切換. 待B切回A時, 會執行A的
protected void onActivityResult(int requestCode, int resultCode, Intent data)方法
resultCode是指由B切回的狀況, 有Activity.RESULT_OK及Activity.RESULT_CANCELED二種. 請注意, 當使用者按back鍵切回A, 是屬於Activity.RESULT_CANCELED.
requestCode是由A切換到B, 再切回來A的識別碼, 可用此碼判斷是A的那一個按鈕動作的
接收端B接收Intent後, 若想傳回值給A, 則需使用原來的Intent物件, 置入資料後, 再使用setResult(resultCode, Intent)回傳, 最後再把B自己finish();
完整範例如下


AndroidManifest.xml
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.asuscomm.mahaljsp.ch11_01_newactivity">
<application
android:allowBackup="true"
android:icon="@drawable/lpic"
android:label="@string/app_name"
android:supportsRtl="true"
android:theme="@style/AppTheme">
<activity
android:screenOrientation="locked"
android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity
android:name=".SecondActivity"
android:label="請選擇行星">
<intent-filter>
<action android:name="com.asuscomm.mahaljsp.IntentTest.Second" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</activity>
</application>
</manifest>
arrays.xml
<?xml version="1.0" encoding="utf-8"?>
<resources>
<string-array name="planet_array">
<item>Mercury</item>
<item>Venus</item>
<item>Earth</item>
<item>Mars</item>
<item>Jupiter</item>
<item>Saturn</item>
<item>Uranus</item>
<item>Neptune</item>
<item>Pluto</item>
</string-array>
</resources>
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/activity_main"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.asuscomm.mahaljsp.ch11_01_newactivity.MainActivity"
android:orientation="vertical">
<LinearLayout
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView
android:text="1 "
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="@+id/textView"
android:textSize="20sp" />
<TextView
android:layout_weight="1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textSize="20sp"
android:id="@+id/txt1"/>
<ImageButton
android:onClick="onClick"
android:layout_width="80dp"
android:layout_height="wrap_content"
app:srcCompat="?android:attr/actionModeWebSearchDrawable"
android:id="@+id/bt1"/>
</LinearLayout>
<LinearLayout
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView
android:text="2 "
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textSize="20sp"
android:id="@+id/textView2"/>
<TextView
android:layout_weight="1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textSize="20sp"
android:id="@+id/txt2"/>
<ImageButton
android:onClick="onClick"
android:layout_width="80dp"
android:layout_height="wrap_content"
app:srcCompat="?android:attr/actionModeWebSearchDrawable"
android:id="@+id/bt2"/>
</LinearLayout>
<LinearLayout
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView
android:text="3 "
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textSize="20sp"
android:id="@+id/textView3"/>
<TextView
android:layout_weight="1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textSize="20sp"
android:id="@+id/txt3"/>
<ImageButton
android:onClick="onClick"
android:layout_width="80dp"
android:layout_height="wrap_content"
app:srcCompat="?android:attr/actionModeWebSearchDrawable"
android:id="@+id/bt3"/>
</LinearLayout>
</LinearLayout>
activity_second.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/activity_second"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.asuscomm.mahaljsp.ch11_01_newactivity.SecondActivity"
android:orientation="vertical">
<LinearLayout
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content">
</LinearLayout>
<ListView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="@+id/listView" />
</LinearLayout>
MainActivity.java
public class MainActivity extends AppCompatActivity {
TextView txt1, txt2, txt3;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
processViews();
}
public void processViews(){
txt1=(TextView)findViewById(R.id.txt1);
txt2=(TextView)findViewById(R.id.txt2);
txt3=(TextView)findViewById(R.id.txt3);
}
public void onClick(View view){
Intent intent=new Intent(this, SecondActivity.class);
int requestCode=0;
switch(view.getId()){
case R.id.bt1:
requestCode=0;
break;
case R.id.bt2:
requestCode=1;
break;
case R.id.bt3:
requestCode=2;
break;
}
startActivityForResult(intent, requestCode);
}
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
String planet=data.getStringExtra("Planet");
if(resultCode== Activity.RESULT_OK){
switch(requestCode){
case 0:
txt1.setText(planet);
break;
case 1:
txt2.setText(planet);
break;
case 2:
txt3.setText(planet);
break;
}
}
}
}
SecondActivity.java
public class SecondActivity extends AppCompatActivity {
ListView listView;
Intent intent;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_second);
processViews();
processControllers();
}
public void processViews(){
intent=getIntent();
listView=(ListView)findViewById(R.id.listView);
}
public void processControllers(){
listView.setAdapter(ArrayAdapter.createFromResource(
this, R.array.planet_array, android.R.layout.simple_list_item_1));
listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> adapterView, View view, int i, long l) {
String s=adapterView.getItemAtPosition(i).toString();
intent.putExtra("Planet", s);
setResult(Activity.RESULT_OK, intent);
SecondActivity.this.finish();
}
});
}
}
啟動系統內建Acitivty
Android系統內鍵了許多的Activity元件, 比如撥打電話, 傳送簡訊, web 搜尋, 地圖導覽. 所以在我們自己開發的應用程式中, 可以直接呼叫.
系統內建的Activity都有設定<action>標簽. 但action 名稱又過長, 所以Intent類別就定義了幾個長用的變數, 比如android.intent.action.DIAL, 可以直接使用Intent.ACTION_DIAL來呼叫.
當呼叫這些Activity元件時, 若需要傳入資料, 可先使用如 Uri uri=Uri.parse(“tel:0987454123”)的格式, 利用parse()的方法將字串轉成Uri物件, 然後再用Intent的setData(Uri)將資料傳入
打電話
打電話的Action有ACTION_DIAL : 準備打電話, aCTION_CALL : 立即打電話, 程式碼如下
Intent intent=new Intent();
intent.setAction(Intent.ACTION_DIAL);
Uri uri=Uri.parse("tel:0987454123");
intent.setData(uri);
startActivity(intent);
簡訊
Intent intent=new Intent(Intent.ACTION_SENDTO);
Uri uri=Uri.parse("smsto:0987454123");
intent.setData(uri);
intent.putExtra("sms_body", "測試簡訊傳遞");
startActivity(intent);
電子郵件
Intent intent=new Intent(Intent.ACTION_SEND);
intent.setType("plain/text");
intent.putExtra(Intent.EXTRA_EMAIL, "mahaljsp@gmail.com");
intent.putExtra(Intent.EXTRA_SUBJECT,"eMail測試");
intent.putExtra(Intent.EXTRA_TEXT, "這是郵件的內容");
startActivity(Intent.createChooser(intent, "Send EMail")); //會彈出要使用那一支應用程式
網頁搜尋
Intent intent=new Intent(Intent.ACTION_WEB_SEARCH); intent.putExtra(SearchManager.QUERY, "mahaljsp"); startActivity(intent);
網頁瀏覽
Intent intent=new Intent(Intent.ACTION_VIEW);
Uri uri=Uri.parse("");
intent.setData(uri);
startActivity(intent);
顯示地圖
Intent intent=new Intent(Intent.ACTION_VIEW);
String point="24.06,120.5232";
String zoom="16";
Uri uri=Uri.parse("geo:"+point+"?z="+zoom);
intent.setData(uri);
startActivity(intent);
地圖導航
Intent intent=new Intent(Intent.ACTION_VIEW);
String from="24.06,120.5232";
String to="24.0816363,120.5362556";
Uri uri=Uri.parse("http://maps.google.com/maps?f=d&saddr="+from+"&daddr="+to);
intent.setData(uri);
startActivity(intent);
街景服務
Intent intent=new Intent(Intent.ACTION_VIEW);
String point="24.0813997,120.5388488";
String direction="0";
String streetZoom="1.0";
String vertical="0";
String zoom="16";
Uri uri=Uri.parse("google.streetview:cbll="+point+"&cbp=1,"+direction+
",,"+streetZoom+",0&mz="+zoom);
intent.setData(uri);
startActivity(intent);



