2011年4月8日 星期五

SD card read/write功能

SD card read/write功能
功能:讀寫SD card

AndroidManifest.xml
    加入權限"android.permission.WRITE_EXTERNAL_STORAGE"

 Xxx.java
    // Write
    private writeToSdCard() {
        File vSDCard= null;
        try {
            // 獲得外部外接裝置位置
            vSDCard= Environment.getExternalStorageDirectory();
 
            // vSDCard.getParent() - "/" ; vSDCard.getName() - "sdcard"
            FileWriter vFile = new FileWriter(vSDCard.getParent() + vSDCard.getName() + "/Log.txt", true);
            // 使用這種方式有可能會得到錯誤的路徑,所以改用下面的方式
            // vSDCard.getAbsolutePath() - 擷取目前位置路徑
            FileWriter vFile = new FileWriter(vSDCard.getAbsolutePath() + "/Log.txt", true);
    
            // write the data to file
            vFile.append("," + status + "," + level + "," + "\n");
            vFile.close();
        }
        catch (Exception e) {
        }
    }

    // Read
    private void readFromSdCard() {
        File vSDCard= null;
        try {
            // 獲得外部外接裝置位置
            vSDCard= Environment.getExternalStorageDirectory();
 
            // read data form sd card file
            FileReader vFile = new FileReader( vSDCard.getAbsolutePath() + "/sd_test.txt" );
            StringBuffer sb = new StringBuffer();
            int c;
            // if value = "-1", it mean the end of the file
            while ((c = vFile.read()) != -1) {
                sb.append((char) c);
            }
            vFile.close();
        }
        catch (Exception e) {
        }
    }

Timer物件

Timer物件
可以用來排定"排程",在設定的週期裡重複執行
使用到HandlerMessage物件

    // 新增Timer Task
    public void OnCreate (Bundle bundle) {
        ..........
        timer = new Timer();
        // 這裡的時間以毫秒(ms)為單位
        timer.schedule(new mytask(), 1, 1000);
        start_time = System.currentTimeMillis();
    }

    public void OnDestory () {
        super.onDestory();
        timer.cancel();
    }

    private class mytask extends TimerTask {
        public void run() {
            Message message = new Message();
            message.what = 1;
            mHandler.sendMessage(message);
        }
    }

    private Handler mHandler = new Handler(){
        public void handleMessage(Message msg) {
            if (msg.what == 1) {
                Toast.makeText(
                    BattService.this,
                    String.valueOf((System.currentTimeMillis()-start_time)/1000) + "s",
                    Toast.LENGTH_LONG).show();
                record_log();
            }
        };
    };

BroadcastReceiver物件

BroadcastReceiver物件
有部分資訊,會經由Android系統透過廣播的方式傳送給應用程式或服務。
而BroadcastReceiver就是用來接收這一類訊息的物件

    // 加入filter,選擇要receiver的對象
    IntentFilter filter = new IntentFilter();
    filter.addAction(Intent.ACTION_BATTERY_CHANGED);
    registerReceiver(mBroadcastReceiver, filter);

    // BroadcastReceive(以電池為例)
    private BroadcastReceiver mBroadcastReceiver = new BroadcastReceiver() {
        public void onReceive(Context context, Intent intent) {
            String action = intent.getAction();
            if (action.equals(Intent.ACTION_BATTERY_CHANGED)) {
                switch (intent.getIntExtra("status", 0)) {
                case BatteryManager.BATTERY_STATUS_UNKNOWN:
                    bat_status = "unknown";
                    break;
                case BatteryManager.BATTERY_STATUS_CHARGING:
                    bat_status = "charge";
                    break;
                case BatteryManager.BATTERY_STATUS_DISCHARGING:
                    bat_status = "discharge";
                    break;
                case BatteryManager.BATTERY_STATUS_NOT_CHARGING:
                    bat_status = "not_charge";
                    break;
                case BatteryManager.BATTERY_STATUS_FULL:
                    bat_status = "full";
                    break;
                }
   
                bat_level = intent.getIntExtra("level", 0);
            }
        }
    };

    // close when leaving
    protected void onDestroy() {
        super.onDestroy();
        unregisterReceiver(mBroadcastReceiver);
    }

設定Brightness功能

設定Brightness功能
在提及設定Brightness功能之前要先介紹一下目前Android設定Brightness的方式。
目前Android設定Brightness的方式大致上分為二種:
1. 調整目前AP的亮度,離開AP會返回系統設定亮度
2. 調整系統亮度,但是設定值要在亮度有被修改時才會更新
    例如:進入設定亮度頁面,再離開,或修改AP亮度。

若要在AP裡設定系統亮度,則需要使用到上述二個部分。
相關程式碼如下:

AndroidManifest.xml
    加入權限"android.permission.WRITE_SETTINGS"

Xxx.java
// 可以利用SeekBar物件當作設定值的輸入
// 修改系統亮度設定
    // 先將亮度設定模式調整為手動
    Settings.System.putInt(
        getContentResolver(),
        Settings.System.SCREEN_BRIGHTNESS_MODE,
        Settings.System.SCREEN_BRIGHTNESS_MODE_MANUAL);
    // 修改系統亮度設定 (setting rage : 0~255)
    Settings.System.putInt(getContentResolver(),Settings.System.SCREEN_BRIGHTNESS,value);

    // 修改目前視窗亮度 (setting rage : 0.0~1.0)
    WindowManager.LayoutParams lp = getWindow().getAttributes();
    lp.screenBrightness = value/255f;
    getWindow().setAttributes(lp);

*當設定值0時,會造成Android系統將整個螢幕關閉的問題。

Rotation問題

Rotation問題
問題:
在Android的系統裡,當Activity在執行的狀態下,旋轉螢幕,系統會將Activity關閉,重新啟動。當這種情形發生時,有可能會造成目前狀態下的資料遺失。

解決方案:
目前提供二種解決方法:
1. 當旋轉事件發生時,利用SharedPreferences物件將參數儲存,然後在重新啟動時再將參數重新導入。

// 偵測旋轉的動作
    // 在AndroidiManifest.xml的activity裡加入下面程式碼
    AndroidiManifest.xml
    <activity
        ....
        android:configChanges="orientation|keyboardHidden"
        .....
    </activity>

    Xxx.java
    public void onConfigurationChanged(Configuration newConfig) {
        super.onConfigurationChanged(newConfig);
        if (this.getResources().getConfiguration().orientation ==
            Configuration.ORIENTATION_LANDSCAPE)  {
            // 旋轉方向變為landscape時執行
        }
        else if (this.getResources().getConfiguration().orientation ==
            Configuration.ORIENTATION_PORTRAIT) {
            // 旋轉方向變為portrait時執行
        }
    }

2. 將AP的畫面鎖定在同一方向


    在AndroidiManifest.xml的activity下加入
    AndroidiManifest.xml
    <activity
        ....
        android:screenOrientation="portrait"
        .....
    </activity>

Wake up lock功能

Wake up lock功能
功能:程式執行時,鎖定在Wake up狀態

AndroidManifest.xml
Add "android.permission.WAKE_LOCK" user permission

    private PowerManager.WakeLock wl;

    // 利用PowerManager取得service,設定wake up狀態
    public void onCreate(Bundle savedInstanceState) {
        .............................
        PowerManager pm = (PowerManager) getSystemService(Context.POWER_SERVICE);
        wl = pm.newWakeLock(PowerManager.SCREEN_BRIGHT_WAKE_LOCK, "My Tag");
        wl.acquire();

    }

    // 離開時,釋放控制權
    protected void onDestroy() {
        super.onDestroy();
        wl.release();
    }

2011年4月7日 星期四

Dialog物件

Dialog物件
Dialog物件分成4種:
    AlertDialog, ProgressDialog, DatePickerDialog, TimePickerDialog
這裡只介紹最基本的AlertDialog
其他使用方式可在官網的Dev Gudie - Framework Topics - User Interface - Creating Dialogs查詢

Adding buttons
    AlertDialog.Builder builder = new AlertDialog.Builder(this);
    builder

        .setMessage("Are you sure you want to exit?")
        
.setCancelable(false)
        // 有setPositiveButton, setNegativeButton, setNeutralButton
        
.setPositiveButton("Yes", new DialogInterface.OnClickListener() {
           
public void onClick(DialogInterface dialog, int id) {
               
MyActivity.this.finish();
            
}
       
})
       
.setNegativeButton("No", new DialogInterface.OnClickListener() {
           
public void onClick(DialogInterface dialog, int id) {
                dialog
.cancel();
           
}
       
});
    AlertDialog alert = builder.create();

Adding a list
    final CharSequence[] items = {"Red", "Green", "Blue"};
    AlertDialog.Builder builder = new AlertDialog.Builder(this);
    builder
.setTitle("Pick a color");
    builder
.setItems(items, new DialogInterface.OnClickListener() {
       
public void onClick(DialogInterface dialog, int item) {
           
Toast.makeText(getApplicationContext(), items[item], Toast.LENGTH_SHORT).show();
       
}
    });
    AlertDialog alert = builder.create();


Adding checkboxes and radio buttons
    final CharSequence[] items = {"Red", "Green", "Blue"};
    AlertDialog.Builder builder = new AlertDialog.Builder(this);
    builder
.setTitle("Pick a color");
    builder
.setSingleChoiceItems(items, -1, new DialogInterface.OnClickListener() {
       
public void onClick(DialogInterface dialog, int item) {
           
Toast.makeText(getApplicationContext(), items[item], Toast.LENGTH_SHORT).show();
       
}
    });
    AlertDialog alert = builder.create();