安卓第六夜 凡高的自畫像

Vamei發表於2014-08-08

作者:Vamei 出處:http://www.cnblogs.com/vamei 歡迎轉載,也請保留這段宣告。謝謝!

 

在上一講中,我已經制作了一個簡單的Android應用。專案的主要檔案包括:

  • MainActivity.java
  • activity_main.xml

在這一講,我將擴充應用的功能,從而允許使用者輸入個人資訊。

 

《自畫像》,凡高。凡高一生不得志,精神更是越來越差。在割掉自己的耳朵一部分後,畫家給自己留下了這幅自畫像。在當時,這幅畫依然是無人問津。

 

描述

我將建立一個新的Activity。這個介面允許使用者輸入本人的姓名和部落格地址。這些輸入資料將在會儲存起來。在主介面中再次調出資料,並顯示。相關知識點包括:

  • 啟動Activity。利用Intent,啟動一個新的Activity。
  • 文字輸入。增加EditText輸入欄,讓使用者輸入文字資訊。
  • 資料儲存。將資料存入SharedPreferences,跨Activity讀取。

 

建立新的專案檔案

我們將在應用專案中增加新的檔案。在ADT的檔案導航欄中右鍵點選資料夾,選擇New->Other後,可以得到下面的對話方塊:

 

你可以在這裡選擇想要建立的新檔案的型別,比如XML檔案,Java檔案等。安卓會根據你選擇的型別,做一些預設設定。比如選擇Android Activity後,在AndroidManifest.xml中自動註冊該Activity,從而省去使用者的麻煩。 

 

新Activity的介面

我們要設計一個用於輸入姓名和部落格地址的安卓介面。由於姓名和部落格地址都是字串型別,因此我們可以藉助EditText類的View元素,來增加字串型別的輸入欄。我們還需要提交功能。按鈕是最容易想到的方式。這裡,我沒有使用按鈕,而是為一個TextView增加點選事件監聽。

 

這個檢視的XML佈局檔案為activity_self_edit.xml,如下:

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:paddingBottom="@dimen/activity_vertical_margin"
    android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin" >
    <LinearLayout
      android:orientation="vertical"
      android:layout_width="match_parent"
      android:layout_height="wrap_content" >
      <LinearLayout
        android:id="@+id/input1"
        android:orientation="horizontal"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content" >
        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="Name" />
        <EditText
            android:id="@+id/name"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:hint="full name" />
    </LinearLayout>
    
    <LinearLayout
        android:orientation="horizontal"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_below="@id/input1" >
        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="Blog Address" />
        <EditText
            android:id="@+id/url"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:hint="url" />
    </LinearLayout>
  </LinearLayout>
  
  <TextView
      android:id="@+id/submit"
      android:layout_width="wrap_content"
      android:layout_height="wrap_content"
      android:layout_alignParentBottom="true"
      android:text="Submit" />
</RelativeLayout>

這裡使用了RelativeLayout來佈局。我們可以在該佈局下,說明元素的相對位置。TextView就使用了layout_alignParentBottom屬性,來說明它的下邊緣將對齊母元素的下邊緣。此外,這裡還巢狀使用了LinearLayout。

 

用SharedPreferences儲存資料

我們現在來為檢視編寫SelfEditActivity,以增加資料儲存功能。在提交資料後,這個Activity將通過EditText的getText()方法獲取字元輸入。提交的字串將使用SharedPreferences儲存起來。

SharedPreferences以鍵值對(key-value pair)的方式儲存資料。在寫入時,我們需要說明資料對應的鍵。在讀取時,我們將根據鍵,來獲得對應的資料值。資料可以在整個應用範圍內呼叫。特定許可權下,SharedPrefereces可以跨應用使用。SharedPreferences簡單易用,適合儲存少量的、結構鬆散的資訊。

package me.vamei.vamei;

import android.app.Activity;
import android.content.Context;
import android.content.SharedPreferences;
import android.os.Bundle;
import android.view.View;
import android.widget.EditText;
import android.widget.TextView;

public class SelfEditActivity extends Activity {
    private EditText nameInput;
    private EditText urlInput;
    private TextView tvSubmit;
    
    private SharedPreferences sharedPref;
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_self_edit);
        
        // find views
        tvSubmit   = (TextView) findViewById(R.id.submit);
        nameInput  = (EditText) findViewById(R.id.name);
        urlInput   = (EditText) findViewById(R.id.url);
        
        sharedPref = this.getSharedPreferences("me.vamei.vamei", 
                Context.MODE_PRIVATE);
        
        // submit
        tvSubmit.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                String name = nameInput.getText().toString();
                String url  = urlInput.getText().toString();

                // Save to Shared Preferences
                SharedPreferences.Editor editor = sharedPref.edit();
                editor.putString("name", name);
                editor.putString("url", url);
                editor.commit();

                // End Current Activity
                SelfEditActivity.this.finish();
                
            }
        });
    }    
}

Context物件的getSharedPreferences()獲得SharedPrerences。第一個引數"me.vamei.vamei"說明了該SharedPreferences物件所在的檔名,第二個引數說明了許可權,即只能該應用範圍內私用。使用SharedPreferences.Editor類物件寫入資料時,我們呼叫了putString()方法,以儲存字串型別的資料值。commit()方法將執行寫入。

最後,Activity Context的finish()方法結束當前Activity。

 

從一個Activity啟動另一個Activity

我現在要把MainActivity和新的SelfEditActivity用Intent串聯起來。MainActivity對應的佈局為activity_main.xml,如下:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:orientation="vertical"
    android:layout_width="match_parent"
    android:layout_height="match_parent" >

    <TextView 
        android:id="@+id/welcome"
        android:layout_width="match_parent"
        android:layout_height="wrap_content" />
    
    <Button
        android:id="@+id/author"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="Edit Profile" />
</LinearLayout>

TextView用於顯示使用者資訊。Button用於啟動上面定義的SelfEditActivity。

 

修改MainActivity。相對於上一講,這裡主要增加了兩個功能。一個功能是監聽按鈕,在按鈕點選後啟動SelfEditActivity。另一個功能是從SharedPreferences中獲得儲存的鍵值,即使用者名稱,再將使用者名稱資訊更新到介面上。

package me.vamei.vamei;

import android.app.Activity;
import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.TextView;

public class MainActivity extends Activity {
    private SharedPreferences sharedPref;
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        
        sharedPref = this.getSharedPreferences("me.vamei.vamei", 
                Context.MODE_PRIVATE);
        
        Button btn = (Button) findViewById(R.id.author);
        btn.setOnClickListener(new OnClickListener(){
            @Override
            public void onClick(View view) {
                Intent intent = new Intent(MainActivity.this, SelfEditActivity.class);
                MainActivity.this.startActivity(intent);
            }
        });
    }
    
    @Override
    protected void onResume() {
        super.onResume();
        TextView nameView = (TextView) findViewById(R.id.welcome);
        
        // retrieve content from shared preference, with key "name"
        String   welcome  = "Welcome, " + sharedPref.getString("name", "unknown") + "!";
        nameView.setText(welcome);
    }
}

Intent構造器的第一個引數說明了Context,第二個引數顯式的說明了想要啟動的功能單元,即SelfEditActivity類。startActivity()方法將根據intent引數,建立並啟動對應的功能單元。該方法執行後,新的SelfEditActivity將壓入棧頂,成為啟用的Activity,而MainActivity將暫停。

另一方面,我把資料讀取部分放入了onResume()方法。根據安卓的規定,MainActivity第一次執行,以及每次從暫停中復甦時,都會呼叫該方法。使用者在SelfEditActivity修改返回後,就可以立即獲得最新的資料。使用getString()方法,從SharedPreferences物件獲得鍵位"name"的值。如果"name"鍵不存在,將返回預設值"unknown"。

onResume()

 

最後,用setText()方法,把新的資料載入到檢視的TextView中。

 

執行

在"Edit Profile"中輸入使用者資訊,提交後返回主頁面,效果如下:

總結

RelativeLayout, EditText

Intent, startActivity()

getSharedPreferences(), putString, getString()

onResume()

 

歡迎繼續閱讀“Java快速教程”系列文章 

相關文章