在Day 21 - Android - 化身該篇裡面介紹到一個列表時常用的元件-ListView,當天只有帶到預設所提供的最簡意樣式,今天要將之延伸下去。
另外,昨天最後的一段有想到如何實作了嗎,程式碼可以前往 Mosil's GitHub 去下載嘍
在Day 21 - Android - 化身中,針對每位角色只有名字的列表,好像沒有什麼感覺,而且稍嫌簡略了些~所以今天我們將再利用另外一個預設的樣式。依序前例,就直接再延用昨天的程式繼續下去嘍~
請先到strings.xml裡面增加一段字串內容
<string-array name="creation">
<item>Final Fantasy VII</item>
<item>Final Fantasy VI</item>
<item>Final Fantasy V</item>
</string-array>
這個字串列表的資料是三個角色出現的作品,請注意需要跟原本的字串數量是一樣的,還有其順位的狀況哦!
再來,我們今天要用到的預設樣式名稱為:simple_list_item_2。這個樣式的長相如下
就是一上一下的文字,我們就直接用來呈現名字(上)以及出現作品(下),我們先在 Moogle3Activity.java 的 onCreate() 區段之上,宣告兩個全域的字串常數,用途請往下看:
private final String NAME = "name";
private final String CREATION = "creation";
先來看到這段
因為這次可以使用的元素變多了,所以這次要改用SimpleAdapter來取代原本的ArrayAdapter<String>,而透過上圖我們也看到,需要傳遞的參數也不一樣了,我們就一項一項的來介紹跟增加!
第一個參數:context,就是把現在的這個context-this給放進去。
第二個參數:data,要呈現的資料。而這邊列表中的每個內容裡都需要用到兩個字串元素,而這邊的data自然就不會是"只有"兩個字串,而是兩個等量的字串陣列,先來看到這邊的宣告
/* 先接出兩個來自 strings.xml 裡的字串陣列 */
String[] names = getResources().getStringArray(R.array.leader);
String[] creation = getResources().getStringArray(R.array.creation);
//宣告一個ArrayList來存放這兩個陣列
ArrayList<HashMap<String, String>> leaders = new ArrayList<HashMap<String, String>>();
再回頭看一次上圖,這個參數的格式是一個具key以及value格式的陣列,所以我們用ArrayList<HashMap<String, String>>()來做為這次的類型,接下來就是將兩個陣列放進去
for(int i = 0; i < names.length; i++){
HashMap<String, String> leader = new HashMap<String, String>();
leader.put(NAME, names[i]);
leader.put(CREATION, creation[i]);
leaders.add(leader);
}
承如上面所說,這兩個字串必要是"等量"這段程式才不會發生問題!
第三個參數:from指的就是從data裡面的哪個key取值,所以這裡放得是我們兩個"key"的字串陣列:
new String[]{NAME, CREATION}
第四個參數:to放到哪兩個介面元素裡,
new int[]{android.R.id.text1, android.R.id.text2}
下面是這段的完整片段
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_moogle3);
/* 先接出兩個來自 strings.xml 裡的字串陣列 */
String[] names = getResources().getStringArray(R.array.leader);
String[] creation = getResources().getStringArray(R.array.creation);
//宣告一個ArrayList來存放這兩個陣列
ArrayList<HashMap<String, String>> leaders = new ArrayList<HashMap<String,String>>();
for(int i = 0; i < names.length; i++){
HashMap<String, String> leader = new HashMap<String, String>();
leader.put(NAME, names[i]);
leader.put(CREATION, creation[i]);
leaders.add(leader);
}
setListAdapter(
new SimpleAdapter(
this,
leaders,
android.R.layout.simple_list_item_2,
new String[]{NAME, CREATION},
new int[]{android.R.id.text1, android.R.id.text2}));
mBtnBack = (Button)findViewById(R.id.btn_moogle3_back);
mBtnBack.setOnClickListener(btnClick);
}
如此一來,就完成今天的部份嘍!
而這個介面的長相,當然不只是這樣,請看到下圖
這邊能看到預設的樣式就有這麼多種,而這邊在下當然是…不會全部將之介紹完畢
不過,明天將帶著大家如何"自定"屬於自己的介面。
========================================================
再來,回頭帶各位來看看昨天的程式部份,原本在Day 17 - Android - 無中生有的 Moogle2 裡,在其 setView() 中產生 checkbox 時,就是很單純的用迴圈跑過他,沒有考慮到我們要再將之提取出來使用的狀況,所以我們要先定義一個全域的checkbox陣列,並在迴圈裡將之放入
...
private ArrayList<CheckBox> mChkBoxs;
...
public void onCreate(Bundle savedInstanceState) {
...
//在這裡給予初值
ArrayList<Integer> number = new ArrayList<Integer>();
...
}
private void setView(){
try{
...
for(int i=0; i<=mMoogles.length; i++){
CheckBox chkMoogle = new CheckBox(this);
chkMoogle.setId(i);
chkMoogle.setText(mMoogles[i]);
chkMoogle.setOnCheckedChangeListener(chkMoogles);
mLlMoogles.addView(chkMoogle);
//多了這一行,將新增的chkbox給放到陣列中
mChkBoxs.add(chkMoogle);
}
...
到這邊算是完成我們的介面佈置了,再來是隨機邏輯的部份
ArrayList<Integer> number = new ArrayList<Integer>();
for(int i = 0; i <= bundle.getInt("signal_id"); i++){
int no = 0;
do{
no = (int) (Math.random() * mMoogles.length);
} while(number.contains(no));
number.add(no);
mChkBoxs.get(no).setChecked(true);
}
在下的做法,是利用一個數值陣列記下亂數產出的數值,目前在於不重覆。
然後用迴圈來亂數產出我們從 Chocobo 傳來的數量後,除了將不重覆者放入數值陣列中外,最重要的就是讓該 Checkbox 被勾選起來,而各位也能夠透過上面的程式碼看到,我們從第n個checkbox陣列中取出來設定(setChecked)勾選。而做到這邊就能看到被隨機勾選起來的成果了。
而在下這個做法只是其中一種,若是各位有不同的做法或是想法歡迎提出哦^_^
不過,別忘了,最後還有一個我們昨天提到的重點,我們要將資料傳回去,這段程式被寫在btnBackClick這個偵聽函式裡,
Intent intent = new Intent();
String message = "";
for(int i = 0; i < mChkBoxs.size(); i++){
if(mChkBoxs.get(i).isChecked()){
if(message.equals("")){
message = "選擇了: " + mChkBoxs.get(i).getText().toString();
} else {
message += ", " + mChkBoxs.get(i).getText().toString();
}
}
}
intent.putExtra("message", message);
setResult(Number.MOOGLE2, intent);
其實就是整個迴圈跑過所有的checkbox,來找出有被勾選的項次,然後兜好成 message 字串。
最後就是回到 Chocobo 的 onActivityResult() 區段來做我們的呈現動作即可。
private final String NAME = "name";
private final String CREATION = "creation";
0
今天再這樣複習一次,不知道各位對 startActivityForResult 的機制是否更有印象了呢?
Day 24 - Android - 溝通《 》Day 26 - Android - 第二個世界元素
怪~
最後一段的程式明明不是這樣貼的樣,修改了幾次還是長那樣
這邊再貼一次試試看好了
<pre class="c" name="code">
@Override
protected void onActivityResult(
int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
//從回傳碼來決定要對誰做動作
switch(resultCode){
case Number.MOOGLE2:
Toast.makeText(this
, data.getStringExtra("message")
, Toast.LENGTH_LONG).show();
break;
}
}
看來在這裡是正常的,不知道發生什麼事了