【BMI指数计算器V3.0】项目实战
生活随笔
收集整理的這篇文章主要介紹了
【BMI指数计算器V3.0】项目实战
小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.
【BMI指數(shù)計算器V3.0】項目實戰(zhàn)震撼發(fā)布,歡迎前來交流~~~,如果是剛來的朋友可以先從
【BMI指數(shù)計算器V1.0】項目實戰(zhàn),【BMI指數(shù)計算器V2.0】項目實戰(zhàn)開始,這樣循序漸進(jìn)更能感受到每一個版本更新的依據(jù),從而更好的學(xué)習(xí)。
更新列表
?1.增加了用戶計算的歷史記錄; ?2.增加了對歷史記錄的單條刪除(長按條目); ?3.增加了對歷史記錄的清空功能; ?4.增加了刪除歷史記錄的二次提示按鈕,并制作了通用對話框工具; ?5.增加了推出APP的對話框確認(rèn)功能。
項目效果圖
?靜態(tài)效果圖:? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?
? ?動態(tài)效果圖: ? ? ? ?
項目結(jié)構(gòu)
? ? 圖片資源
| ? ? | ? ?? | ??? ? |
| ? ? | ? ? | |
| ? | ?? | |
| ?? | ??? | |
| ??? | ?? | |
| ? | ? | ? |
技術(shù)預(yù)告
?本次更新功能中需要用到的技術(shù): ? ??1.SQLite數(shù)據(jù)庫技術(shù)(創(chuàng)建數(shù)據(jù)庫,數(shù)據(jù)表,增,刪,改,查); ? ? 2.ListView列表控件,BaseAdapter適配器,數(shù)據(jù)模型; ? ? 3.對話框技術(shù)(AlertDialog); ? ? 4.異步任務(wù)類(AsynTask,多線程概念)
界面開發(fā)
? step1:首先準(zhǔn)備資源,將圖片拷貝到drawable-hdpi文件夾中 ? step2:編寫資源文件(colors.xml顏色資源,dimens.xml尺寸資源,strings.xml字符串資源,drawable背景切換圖片資源) ?? 顏色資源:values/colors.xml <?xml version="1.0" encoding="utf-8"?> <resources xmlns:android="http://schemas.android.com/apk/res/android"><!-- 顏色資源文件 --><!-- 白色 --><color name="white" >#ffffff</color><color name = "black">#000000</color><!-- 透明 --><color name = "tran">#00000000</color><color name = "gray">#808080</color> </resources>? ?尺寸資源:values/dimens.xml
? <resources><!-- 尺寸資源文件 --><!-- Default screen margins, per the Android Design guidelines. --><dimen name="activity_horizontal_margin">16dp</dimen><dimen name="activity_vertical_margin">16dp</dimen><dimen name="text_22">22sp</dimen><dimen name="text_14">14sp</dimen><dimen name="text_16">16sp</dimen><dimen name="text_18">18sp</dimen><dimen name="text_15">15sp</dimen><dimen name="margin_40">40dp</dimen><dimen name="margin_16">16dp</dimen><dimen name="margin_14">14dp</dimen><dimen name="margin_10">10dp</dimen><dimen name="margin_8">8dp</dimen><dimen name="padding_16">16dp</dimen><dimen name="w_50">50dp</dimen><dimen name="h_25">25dp</dimen></resources>? ??字符串資源 :values/strings.xml
<?xml version="1.0" encoding="utf-8"?> <resources><!-- 字符串資源文件 --><string name="app_name">BMI指數(shù)計算器</string><string name="hello_world">Hello world!</string><string name="action_settings">Settings</string><string name="title">BMI指數(shù)計算器</string><string name="height">您的身高</string><string name="cm">(厘米)cm</string><string name="weight">您的體重</string><string name="kg">(千克)kg </string><string name="cala">計算</string><string name="clear">清除</string><string name="weight_bmi">您的體重指數(shù):</string><string name="weight_state">您的體重狀況:</string><string name="weight_bmi1">體重指數(shù):</string><string name="weight_state1">體重狀況:</string><string name="tip1">身高不能為空</string><string name="tip2">輸入格式不正確</string><string name="tip3">體重不能為空</string><string name="standard_who">WHO標(biāo)準(zhǔn)</string><string name="standard_area">亞洲標(biāo)準(zhǔn)</string><string name="height_round">身高范圍100~200</string><string name="weight_round">體重范圍30~150</string><string name="history">歷史記錄</string><string name="empty">空空如也~~~</string><!-- 對話框相關(guān)字符串資源 --><string name="delete">刪除</string><string name="clear1">清空</string><string name="back">退出程序</string><string name="delete_message">您確定要刪除該記錄嗎?</string><string name="clear1_message">您確定要清空所有記錄嗎?</string><string name="back_message">您確定要退出程序嗎?</string><string name="ok">確定</string><string name="cancel">取消</string></resources>
? 背景切換圖片資源:drawable
? ?返回按鈕背景:drawable/btn_back_bg.xml ? ?<?xml version="1.0" encoding="utf-8"?> <selector xmlns:android="http://schemas.android.com/apk/res/android"><item android:drawable="@drawable/btn_back_pressed" android:state_pressed="true"></item><item android:drawable="@drawable/btn_back_normal"></item></selector>
? ?計算/重新計算按鈕背景:drawable/btn_cala_bg.xml
<?xml version="1.0" encoding="utf-8"?> <selector xmlns:android="http://schemas.android.com/apk/res/android" ><item android:drawable="@drawable/btn_cala_pressed" android:state_pressed="true"></item><item android:drawable="@drawable/btn_cala_normal"></item></selector>
???刪除按鈕背景:drawable/btn_delete_bg.xml
<?xml version="1.0" encoding="utf-8"?> <selector xmlns:android="http://schemas.android.com/apk/res/android"><item android:drawable="@drawable/btn_delete_pressed" android:state_pressed="true"></item><item android:drawable="@drawable/btn_delete_nomal"></item></selector>
? ?歷史記錄按鈕背景:drawable/btn_history_bg.xml
<?xml version="1.0" encoding="utf-8"?> <selector xmlns:android="http://schemas.android.com/apk/res/android"><item android:drawable="@drawable/btn_history_pressed" android:state_pressed="true"></item><item android:drawable="@drawable/btn_history_normal"></item></selector>
? ?確定/取消按鈕背景:drawable/btn_ok_bg.xml
<?xml version="1.0" encoding="utf-8"?> <selector xmlns:android="http://schemas.android.com/apk/res/android"><item android:drawable="@drawable/btn_ok_pressed" android:state_pressed="true"></item><item android:drawable="@drawable/btn_ok_normal"></item></selector>
? ?單選按鈕背景:drawable/rb_standard_bg.xml
<?xml version="1.0" encoding="utf-8"?> <selector xmlns:android="http://schemas.android.com/apk/res/android" ><item android:drawable="@drawable/rb_checked" android:state_checked="true"></item><item android:drawable="@drawable/rb_normal" android:state_checked="false"></item></selector><span style="color:#ff0000;"> </span>
? ?step3:歡迎界面開發(fā)
? ?layout/activity_welcome.xml
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"android:layout_width="match_parent"android:layout_height="match_parent"android:background="@drawable/welcome" ></RelativeLayout>
? step4:主界面開發(fā)
? layout/activity_main.xml
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"android:id="@+id/container"android:layout_width="match_parent"android:layout_height="match_parent"android:background="@drawable/main"android:orientation="vertical" ><!-- 標(biāo)題欄 --><RelativeLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content"android:background="@drawable/title_bg" ><!-- 標(biāo)題文本控件 --><TextViewandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_centerInParent="true"android:text="@string/title"android:textColor="@color/white"android:textSize="@dimen/text_22"android:textStyle="bold" /><ImageButtonandroid:id="@+id/ib_history"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_alignParentRight="true"android:layout_centerVertical="true"android:layout_marginRight="@dimen/margin_14"android:background="@drawable/btn_history_bg" /></RelativeLayout><LinearLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content"android:layout_marginTop="@dimen/margin_40"android:orientation="vertical" ><LinearLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content"android:gravity="center_vertical"android:orientation="vertical" ><LinearLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content"android:gravity="center_horizontal"android:orientation="horizontal" ><TextViewandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:text="@string/height"android:textColor="@color/white"android:textSize="@dimen/text_16" /><EditTextandroid:id="@+id/et_height"android:layout_width="wrap_content"android:layout_height="wrap_content"android:background="@drawable/input_bg"android:gravity="center_horizontal"android:inputType="numberDecimal"android:singleLine="true"android:textSize="@dimen/text_16" ></EditText><TextViewandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:text="@string/cm"android:textColor="@color/white"android:textSize="@dimen/text_16" /></LinearLayout><LinearLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content"android:baselineAligned="true"android:gravity="center_horizontal"android:orientation="horizontal" ><TextViewandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:text="@string/weight"android:textColor="@color/white"android:textSize="@dimen/text_16" /><EditTextandroid:id="@+id/et_weight"android:layout_width="wrap_content"android:layout_height="wrap_content"android:background="@drawable/input_bg"android:gravity="center_horizontal"android:inputType="numberDecimal"android:singleLine="true"android:textSize="@dimen/text_16" /><TextViewandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:text="@string/kg"android:textColor="@color/white"android:textSize="@dimen/text_16" /></LinearLayout></LinearLayout><!-- 標(biāo)準(zhǔn)可選組布局 --><RadioGroupandroid:id="@+id/rg_standard"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_gravity="center_horizontal"android:layout_marginTop="@dimen/margin_14"android:orientation="horizontal" ><!-- WHO標(biāo)準(zhǔn)單選按鈕 --><RadioButtonandroid:id="@+id/rb_who"android:layout_width="wrap_content"android:layout_height="wrap_content"android:button="@drawable/rb_standard_bg"android:checked="true"android:text="@string/standard_who"android:textColor="@color/white"android:textSize="@dimen/margin_14" ></RadioButton><!-- 亞洲標(biāo)準(zhǔn)單選按鈕 --><RadioButtonandroid:id="@+id/rb_area"android:layout_width="wrap_content"android:layout_height="wrap_content"android:button="@drawable/rb_standard_bg"android:text="@string/standard_area"android:textColor="@color/white"android:textSize="@dimen/margin_14" ></RadioButton></RadioGroup><Buttonandroid:id="@+id/btn_cala"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_gravity="center_horizontal"android:layout_marginTop="@dimen/margin_16"android:background="@drawable/btn_cala_bg"android:text="@string/cala"android:textColor="@color/white"android:textSize="@dimen/text_18" /><LinearLayoutandroid:id="@+id/ll_result"android:layout_width="match_parent"android:layout_height="wrap_content"android:layout_marginTop="@dimen/margin_16"android:gravity="center_horizontal"android:orientation="vertical" ><LinearLayoutandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:gravity="center_vertical"android:orientation="horizontal" ><ImageViewandroid:id="@+id/iv_state"android:layout_width="wrap_content"android:layout_height="wrap_content"android:src="@drawable/r1" /><LinearLayoutandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_marginLeft="@dimen/margin_14"android:background="@drawable/info"android:orientation="vertical"android:padding="@dimen/padding_16" ><TextViewandroid:id="@+id/tv_bmi"android:layout_width="wrap_content"android:layout_height="wrap_content"android:text="@string/weight_bmi"android:textColor="@color/white"android:textSize="@dimen/text_16" /><TextViewandroid:id="@+id/tv_state"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_marginTop="@dimen/margin_14"android:text="@string/weight_state"android:textColor="@color/white"android:textSize="@dimen/text_16" /></LinearLayout></LinearLayout><Buttonandroid:id="@+id/btn_clear"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_gravity="center_horizontal"android:layout_marginTop="@dimen/margin_16"android:background="@drawable/btn_cala_bg"android:text="@string/clear"android:textColor="@color/white"android:textSize="@dimen/text_18" /></LinearLayout></LinearLayout></LinearLayout>
? step5:歷史記錄界面開發(fā)
? layout/activity_history_record.xml ?<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"android:layout_width="match_parent"android:layout_height="match_parent"android:background="@drawable/main"android:orientation="vertical" ><RelativeLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content"android:background="@drawable/title_bg" ><!-- 返回上一層界面按鈕 --><ImageButtonandroid:id="@+id/ib_back"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_alignParentLeft="true"android:layout_centerVertical="true"android:layout_marginLeft="@dimen/margin_14"android:background="@drawable/btn_back_bg" /><!-- 標(biāo)題文本控件 --><TextViewandroid:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_centerInParent="true"android:text="@string/history"android:textColor="@color/white"android:textSize="@dimen/text_22"android:textStyle="bold" /><!-- 清空歷史記錄按鈕 --><ImageButtonandroid:id="@+id/ib_clear"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_alignParentRight="true"android:layout_centerVertical="true"android:layout_marginRight="@dimen/margin_14"android:background="@drawable/btn_delete_bg" /></RelativeLayout><!-- 歷史記錄列表 --><TextViewandroid:id = "@+id/tv_empty"android:layout_width="match_parent"android:layout_height="match_parent"android:gravity="center"android:textColor="@color/white"android:textSize="@dimen/text_18"android:text="@string/empty"/><LinearLayoutandroid:id="@+id/ll_history"android:layout_width="match_parent"android:layout_height="match_parent"android:visibility="gone"android:orientation="vertical" ><Viewandroid:layout_width="match_parent"android:layout_height="3dp"android:background="@drawable/line" /><ListViewandroid:id="@+id/lv_history"android:layout_width="match_parent"android:layout_height="match_parent"android:cacheColorHint="@color/tran"android:divider="@drawable/line"android:dividerHeight="3dp"android:scrollbars="none" /></LinearLayout></LinearLayout>
? step6:歷史記錄列表條目界面開發(fā)
? layout/history_list_item.xml
<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"android:layout_width="match_parent"android:layout_height="match_parent"android:gravity="center_vertical"android:orientation="horizontal" ><ImageViewandroid:id="@+id/iv_state_icon"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_margin="@dimen/margin_8"android:background="@drawable/ic_launcher" /><LinearLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content"android:orientation="vertical" ><RelativeLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content" ><TextViewandroid:id="@+id/tv_weight_bmi"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_alignParentLeft="true"android:text="@string/weight_bmi1"android:textColor="@color/white"android:textSize="@dimen/text_15"android:textStyle="bold" /><TextViewandroid:id="@+id/tv_weight_state"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_alignParentRight="true"android:layout_marginRight="@dimen/margin_8"android:text="@string/weight_state1"android:textColor="@color/white"android:textSize="@dimen/text_15"android:textStyle="bold" /></RelativeLayout><RelativeLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content" ><TextViewandroid:id="@+id/tv_height"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_alignParentLeft="true"android:text="@string/weight_bmi"android:textColor="@color/white"android:textSize="@dimen/text_15" /><TextViewandroid:id="@+id/tv_weight"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_alignParentRight="true"android:layout_marginRight="@dimen/margin_8"android:text="@string/weight_state"android:textColor="@color/white"android:textSize="@dimen/text_15" /></RelativeLayout><RelativeLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content" ><TextViewandroid:id="@+id/tv_date"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_alignParentLeft="true"android:text="@string/weight_bmi"android:textColor="@color/white"android:textSize="@dimen/text_15" /></RelativeLayout></LinearLayout></LinearLayout>
? ?step7:通用對話框界面開發(fā)
? ?layout/dialog_layout.xml ? ?<span style="font-size:14px;"><?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"android:layout_width="match_parent"android:layout_height="wrap_content"android:orientation="vertical" ><!-- 對話框布局 --><LinearLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content"android:layout_marginTop="@dimen/margin_8"android:background="@drawable/dialog_bg"android:gravity="center_horizontal"android:orientation="vertical" ><TextViewandroid:id="@+id/tv_dialog_title"android:layout_width="wrap_content"android:layout_height="wrap_content"android:text="@string/delete"android:textColor="@color/black"android:textSize="@dimen/text_18"android:textStyle="bold" /><TextViewandroid:id="@+id/tv_message"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_gravity="center"android:layout_marginTop="@dimen/margin_16"android:text="@string/delete_message"android:textColor="@color/black"android:textSize="@dimen/text_14"android:textStyle="bold" /></LinearLayout><LinearLayoutandroid:layout_width="match_parent"android:layout_height="wrap_content"android:layout_gravity="bottom"android:background="@drawable/ok_cancel_bg"android:orientation="horizontal" ><Buttonandroid:id="@+id/btn_ok"android:layout_width="0dp"android:layout_height="wrap_content"android:layout_margin="@dimen/margin_8"android:layout_weight="1"android:background="@drawable/btn_ok_bg"android:gravity="center"android:text="@string/ok"android:textColor="@color/black"android:textSize="@dimen/text_14" /><Buttonandroid:id="@+id/btn_cancel"android:layout_width="0dp"android:layout_height="wrap_content"android:layout_margin="@dimen/margin_8"android:layout_weight="1"android:background="@drawable/btn_ok_bg"android:gravity="center"android:text="@string/cancel"android:textColor="@color/black"android:textSize="@dimen/text_14" /></LinearLayout></LinearLayout></span>
功能開發(fā)
? ?step1:歡迎界面功能開發(fā)? ?com.kedi.bmi.ui/WelcomeActivity
? ?說明:在AndroidManifest.xml中注冊WelcomeActivity
<span style="font-size:14px;">package com.kedi.bmi.ui;import com.kedi.bmi.R;import android.app.Activity; import android.content.Intent; import android.os.Bundle; import android.os.Handler; import android.view.Window;/*** 歡迎姐界面類* * @author 科弟* */ public class WelcomeActivity extends Activity {// 控制界面顯示2秒執(zhí)行界面挑轉(zhuǎn)的類private Handler mHandler = new Handler();@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);//去掉系統(tǒng)標(biāo)題欄requestWindowFeature(Window.FEATURE_NO_TITLE);//關(guān)聯(lián)XML界面setContentView(R.layout.activity_welcome);//postDelayed()方法的作用:2000毫秒后執(zhí)行某操作mHandler.postDelayed(new Runnable() {@Overridepublic void run() {//意圖類,指定界面跳轉(zhuǎn)的源界面與目標(biāo)界面Intent intent = new Intent(WelcomeActivity.this,MainActivity.class);//執(zhí)行跳轉(zhuǎn)startActivity(intent);//關(guān)閉歡迎界面finish();}}, 2000);} }</span><span style="font-weight: bold; font-size: 18px;"> </span>
? ?step2:主界面功能開發(fā) ? ? ?com.kedi.bmi.ui/MainActivity ? ?說明:在AndroidManifest.xml中注冊MainActivity
?<span style="font-size:14px;">package com.kedi.bmi.ui;import java.text.DecimalFormat;import android.annotation.SuppressLint; import android.app.Activity; import android.content.Context; import android.content.Intent; import android.content.SharedPreferences; import android.content.SharedPreferences.Editor; import android.os.Bundle; import android.view.KeyEvent; import android.view.View; import android.view.View.OnClickListener; import android.view.Window; import android.widget.Button; import android.widget.EditText; import android.widget.ImageButton; import android.widget.ImageView; import android.widget.LinearLayout; import android.widget.RadioButton; import android.widget.RadioGroup; import android.widget.RadioGroup.OnCheckedChangeListener; import android.widget.TextView; import android.widget.Toast;import com.kedi.bmi.R; import com.kedi.bmi.dao.BmiDao; import com.kedi.bmi.listener.OnClickOkListener; import com.kedi.bmi.model.Bmi; import com.kedi.bmi.utils.DataUtil; import com.kedi.bmi.utils.DialogUtil;/*** BMI指數(shù)計算器主界面管理類* * @author 科弟* */ @SuppressLint("ShowToast") public class MainActivity extends Activity implements OnClickListener,OnCheckedChangeListener {private EditText mHeightInputEt;// 身高輸入框private EditText mWeightInputEt;// 體重輸入框private Button mCalaBtn;// 計算按鈕private LinearLayout mResultLl;// 計算結(jié)果布局private TextView mWeightBmiTv;// 體重指數(shù)文本private TextView mWeightStateTv;// 體重狀態(tài)文本private Button mClearBtn;// 清除按鈕private double height;// 身高private double weight;// 體重private double bmi;// bmi指數(shù)值private String state;// 體重狀態(tài)private String weightBmi;// 您的體重指數(shù):private String weightState;// 您的體重狀況:private ImageView mStateIv;// 體重狀態(tài)圖標(biāo)// 可取體重狀態(tài)值數(shù)組private String[] states = { "偏瘦", "正常", "偏胖", "肥胖", "重度肥胖", "極重度肥胖" };// 體重狀態(tài)圖片id數(shù)組private int[] state_imageIds = { R.drawable.r1, R.drawable.r2,R.drawable.r3, R.drawable.r4, R.drawable.r5, R.drawable.r6 };private int state_imageId;// 當(dāng)前體重狀態(tài)圖片id// 標(biāo)準(zhǔn)相關(guān)布局或控件private RadioGroup mStandardRg;// 標(biāo)準(zhǔn)可選組布局private RadioButton mWhoStandardRb;// WHO標(biāo)準(zhǔn)單選按鈕private RadioButton mAreaStandardRb;// 亞洲標(biāo)準(zhǔn)單選按鈕private static final int WHO_STANDARD = 0x1;// WHO標(biāo)準(zhǔn)private static final int AREA_STANDARD = 0x2;// 亞洲標(biāo)準(zhǔn)private int mCurrentStandard = WHO_STANDARD;// 當(dāng)前標(biāo)準(zhǔn)private SharedPreferences sp;// 保存小量數(shù)據(jù)的類,數(shù)據(jù)會保存到指定文件名的XML文件中private static final String FILE_NAME = "data.xml";// 文件名// 歷史記錄相關(guān)private ImageButton mHistoryIb;// 操作數(shù)據(jù)庫的業(yè)務(wù)邏輯類private BmiDao mBmiDao;@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);// 去掉系統(tǒng)標(biāo)題欄requestWindowFeature(Window.FEATURE_NO_TITLE);// 關(guān)聯(lián)布局文件setContentView(R.layout.activity_main);// 初始化布局或控件initView();// 注冊控件點(diǎn)擊事件setViewListener();weightBmi = getResources().getString(R.string.weight_bmi);// 您的體重指數(shù):weightState = getResources().getString(R.string.weight_state);// 您的體重狀況:mBmiDao = new BmiDao(this);}/*** 初始化布局或控件的方法*/private void initView() {mHeightInputEt = (EditText) this.findViewById(R.id.et_height);// 身高輸入框mWeightInputEt = (EditText) this.findViewById(R.id.et_weight);// 體重輸入框mCalaBtn = (Button) this.findViewById(R.id.btn_cala);// 計算按鈕mResultLl = (LinearLayout) this.findViewById(R.id.ll_result);// 計算結(jié)果布局mWeightBmiTv = (TextView) this.findViewById(R.id.tv_bmi);// 體重指數(shù)文本mWeightStateTv = (TextView) this.findViewById(R.id.tv_state);// 體重狀態(tài)文本mStateIv = (ImageView) this.findViewById(R.id.iv_state);mClearBtn = (Button) this.findViewById(R.id.btn_clear);// 清除按鈕// 默認(rèn)顯示計算按鈕(VISIBLE),隱藏結(jié)果布局(GONE)mCalaBtn.setVisibility(View.VISIBLE);mResultLl.setVisibility(View.GONE);mStandardRg = (RadioGroup) this.findViewById(R.id.rg_standard);// 標(biāo)準(zhǔn)可選組布局mWhoStandardRb = (RadioButton) this.findViewById(R.id.rb_who);// WHO標(biāo)準(zhǔn)單選按鈕mAreaStandardRb = (RadioButton) this.findViewById(R.id.rb_area);// 亞洲標(biāo)準(zhǔn)單選按鈕// 歷史記錄相關(guān)mHistoryIb = (ImageButton) this.findViewById(R.id.ib_history);}/*** 注冊控件點(diǎn)擊事件的方法*/private void setViewListener() {// 注冊點(diǎn)擊事件mCalaBtn.setOnClickListener(this);mClearBtn.setOnClickListener(this);// 注冊選擇事件mStandardRg.setOnCheckedChangeListener(this);// 歷史記錄相關(guān)mHistoryIb.setOnClickListener(this);}@Overridepublic void onClick(View v) {int id = v.getId();switch (id) {case R.id.btn_cala:// 計算邏輯// 獲取身高輸入框數(shù)據(jù)String heightStr = mHeightInputEt.getText().toString().trim();// 判斷身高輸入框數(shù)據(jù)是否為空if ("".equals(heightStr) || heightStr.length() == 0) {Toast.makeText(this, getResources().getString(R.string.tip1), 0).show();} else {try {// 將String類型轉(zhuǎn)化成Double類型height = Double.valueOf(heightStr);// 對身高數(shù)據(jù)范圍進(jìn)行判斷(100.0~200.0)if (height < 100.0 || height > 200.0) {Toast.makeText(this,getResources().getString(R.string.height_round),Toast.LENGTH_SHORT).show();} else {String weightStr = mWeightInputEt.getText().toString().trim();// 體重數(shù)據(jù)非空判斷if ("".equals(weightStr) || weightStr.length() == 0) {Toast.makeText(this,getResources().getString(R.string.tip3),Toast.LENGTH_SHORT).show();} else {try {weight = Double.valueOf(weightStr);// 體重數(shù)據(jù)范圍判斷(30.0~150.0)if (weight < 30.0 || weight > 150.0) {Toast.makeText(this,getResources().getString(R.string.weight_round),Toast.LENGTH_SHORT).show();} else {// 計算bmi值calaBmi(mCurrentStandard);// 隱藏計算按鈕(GONE),顯示結(jié)果布局(VISIBLE)setViewVisible(false);}} catch (Exception e) {Toast.makeText(this,getResources().getString(R.string.tip2),Toast.LENGTH_SHORT).show();}}}} catch (Exception e) {Toast.makeText(this,getResources().getString(R.string.tip2),Toast.LENGTH_SHORT).show();}}break;case R.id.btn_clear:// 清除setViewVisible(true);break;case R.id.ib_history:// 跳轉(zhuǎn)到歷史記錄界面Intent intent = new Intent(MainActivity.this,HistoryRecordActivity.class);startActivity(intent);break;}}/*** 計算bmi值*/private void calaBmi(int standard) {// height/100.0 cm換算成mheight = height / 100.0;bmi = weight / (height * height);if (standard == WHO_STANDARD) {if (bmi < 18.5) {state = states[0];state_imageId = state_imageIds[0];} else if (bmi >= 18.5 && bmi <= 24.9) {state = states[1];state_imageId = state_imageIds[1];} else if (bmi > 24.9 && bmi <= 29.9) {state = states[2];state_imageId = state_imageIds[2];} else if (bmi > 29.9 && bmi <= 34.9) {state = states[3];state_imageId = state_imageIds[3];} else if (bmi > 34.9 && bmi <= 39.9) {state = states[4];state_imageId = state_imageIds[4];} else {state = states[5];state_imageId = state_imageIds[5];}} else {if (bmi < 18.5) {state = states[0];state_imageId = state_imageIds[0];} else if (bmi >= 18.5 && bmi <= 22.9) {state = states[1];state_imageId = state_imageIds[1];} else if (bmi > 22.9 && bmi <= 24.9) {state = states[2];state_imageId = state_imageIds[2];} else if (bmi > 24.9 && bmi <= 29.9) {state = states[3];state_imageId = state_imageIds[3];} else if (bmi > 29.9 && bmi <= 39.9) {state = states[4];state_imageId = state_imageIds[4];} else {state = states[5];state_imageId = state_imageIds[5];}}mStateIv.setImageResource(state_imageId);</strong></span><span style="font-size:14px;"> <span style="color:#ff0000;"><strong> //實現(xiàn)了數(shù)據(jù)庫功能后再添加此功能// 將計算結(jié)果插入數(shù)據(jù)庫Bmi bmiObj = new Bmi();bmiObj.setHeigth(Double.valueOf(DataUtil.getData(height * 100.0)));bmiObj.setWeigth(Double.valueOf(DataUtil.getData(weight)));bmiObj.setBmiNum(Double.valueOf(DataUtil.getData(bmi)));bmiObj.setBmiState(state);bmiObj.setStateIconId(state_imageId + "");// 當(dāng)前系統(tǒng)時間(單位:毫秒)bmiObj.setCalaTime(System.currentTimeMillis());mBmiDao.insertBmi(bmiObj);</strong></span><strong style="font-size:18px;"></strong></span>}/*** 控制計算按鈕與結(jié)果布局的顯示與隱藏* * @param visible*/private void setViewVisible(boolean visible) {if (visible) {mCalaBtn.setVisibility(View.VISIBLE);mResultLl.setVisibility(View.GONE);// 清空數(shù)據(jù)mWeightBmiTv.setText("");mWeightStateTv.setText("");mHeightInputEt.setText("");mWeightInputEt.setText("");height = 0.0;weight = 0.0;} else {// 獲得焦點(diǎn)mHeightInputEt.requestFocus();// 格式化數(shù)據(jù)的類mCalaBtn.setVisibility(View.GONE);mResultLl.setVisibility(View.VISIBLE);DecimalFormat format = new DecimalFormat("0.0");mWeightBmiTv.setText(weightBmi + format.format(bmi));mWeightStateTv.setText(weightState + state);}}@Overridepublic void onCheckedChanged(RadioGroup rg, int arg1) {int id = rg.getCheckedRadioButtonId();switch (id) {case R.id.rb_who:// 選中Who單選按鈕mCurrentStandard = WHO_STANDARD;break;case R.id.rb_area:// 選中亞洲單選按鈕mCurrentStandard = AREA_STANDARD;break;default:mCurrentStandard = WHO_STANDARD;break;}}@Overrideprotected void onResume() {super.onResume();// 獲取當(dāng)前用戶選擇的標(biāo)準(zhǔn)sp = this.getSharedPreferences(FILE_NAME, Context.MODE_PRIVATE);mCurrentStandard = sp.getInt("standard", WHO_STANDARD);// 根據(jù)用戶上次選擇的標(biāo)準(zhǔn)初始化單選框的選擇狀態(tài)switch (mCurrentStandard) {case WHO_STANDARD:mWhoStandardRb.setChecked(true);mAreaStandardRb.setChecked(false);break;case AREA_STANDARD:mWhoStandardRb.setChecked(false);mAreaStandardRb.setChecked(true);break;default:mWhoStandardRb.setChecked(true);mAreaStandardRb.setChecked(false);break;}}@Overrideprotected void onPause() {super.onPause();// 保存當(dāng)前用戶選擇的標(biāo)準(zhǔn)sp = this.getSharedPreferences(FILE_NAME, Context.MODE_PRIVATE);Editor editor = sp.edit();editor.putInt("standard", mCurrentStandard);editor.commit();}<strong><span style="color:#ff0000;"> //實現(xiàn)了對話框功能后再添加此功能</span></strong></span><strong><span style="font-size:14px;color:#ff0000;"> @Overridepublic boolean onKeyDown(int keyCode, KeyEvent event) {// 監(jiān)聽用戶按鍵,如果按回退鍵,退出程序if (keyCode == KeyEvent.KEYCODE_BACK) {// 獲得對話框標(biāo)題與提示消息String title = getResources().getString(R.string.back);String message = getResources().getString(R.string.back_message);DialogUtil.showDialog(this, title, message,new OnClickOkListener() {@Overridepublic void onClick(View view) {//退出程序MainActivity.this.finish();}});}return true;}</span></strong>
step3:工具類開發(fā)
??數(shù)據(jù)格式化工具:com.kedi.bmi.utils/DataUtil.java
? ?package com.kedi.bmi.utils;import java.text.DecimalFormat;/*** 數(shù)據(jù)格式化工具* * @author 科弟* */ public class DataUtil {private static DecimalFormat format = new DecimalFormat("0.0");public static String getData(double data) {return format.format(data);} }
??日期格式化工具類:com.kedi.bmi.utils/DateUtil.java
package com.kedi.bmi.utils;import java.sql.Date; import java.text.SimpleDateFormat;/*** 日期格式化工具類* * @author 科弟* */ public class DateUtil {private static SimpleDateFormat format = new SimpleDateFormat("yyyy年MM月dd日 hh:mm:ss");public static String getDate(long time) {Date date = new Date(time);return format.format(date);} } 通用對話框確定按鈕點(diǎn)擊事件監(jiān)聽器開發(fā):com.kedi.bmi.listener/OnClickOkListener.java
說明:因為通用對話框要在不同的場景下使用,在不同場景下點(diǎn)擊確定按鈕要執(zhí)行不同的功能,所以開發(fā)一個 確定按鈕點(diǎn)擊事件監(jiān)聽器,在通用對話框工具類中通過回調(diào)的方式把具體的點(diǎn)擊事件的處理回調(diào)到具體場景下
實現(xiàn)對應(yīng)的功能,這樣才能保證通用對話框不依賴具體使用場景,從而達(dá)到通用的目的。 package com.kedi.bmi.listener;import android.view.View;/*** 監(jiān)聽對話框OK按鈕點(diǎn)擊事件的監(jiān)聽器接口* * @author 科弟* */ public interface OnClickOkListener {public void onClick(View view); }
通用對話框工具類:com.kedi.bmi.utils/DialogUtil.java
package com.kedi.bmi.utils;import android.app.AlertDialog; import android.app.Dialog; import android.content.Context; import android.view.View; import android.view.View.OnClickListener; import android.widget.Button; import android.widget.TextView;import com.kedi.bmi.R; import com.kedi.bmi.listener.OnClickOkListener;/*** 通用對話框工具類* * @author 科弟* */ public class DialogUtil {private static Dialog mDialog;/*** 顯示對話框的方法* * @param context* 上下文* @param title* 對話框標(biāo)題* @param message* 對話框提示信息* @param onClickOkListener* 監(jiān)聽對話框OK按鈕點(diǎn)擊事件的監(jiān)聽器接口*/public static void showDialog(Context context, String title,String message, final OnClickOkListener onClickOkListener) {// 創(chuàng)建對話框Builder(生產(chǎn)者,構(gòu)建者)對象AlertDialog.Builder builder = new AlertDialog.Builder(context);// 獲得對話框布局View view = View.inflate(context, R.layout.dialog_layout, null);TextView titleTv = (TextView) view.findViewById(R.id.tv_dialog_title);TextView messageTv = (TextView) view.findViewById(R.id.tv_message);Button okBtn = (Button) view.findViewById(R.id.btn_ok);Button cancelBtn = (Button) view.findViewById(R.id.btn_cancel);// 綁定內(nèi)容titleTv.setText(title);messageTv.setText(message);// 注冊ok,cancel的點(diǎn)擊事件監(jiān)聽器okBtn.setOnClickListener(new OnClickListener() {@Overridepublic void onClick(View v) {// 回調(diào)給調(diào)用者處理onClickOkListener.onClick(v);mDialog.cancel();}});cancelBtn.setOnClickListener(new OnClickListener() {@Overridepublic void onClick(View arg0) {if (mDialog != null) {mDialog.cancel();}}});// 設(shè)置對話框布局builder.setView(view);// 創(chuàng)建對話框mDialog = builder.create();// 顯示對話框mDialog.show();} }
? step4:歷史記錄功能開發(fā)
? ? ? ?數(shù)據(jù)模型:com.kedi.bmi.model/Bmi.java ? ? ? ?package com.kedi.bmi.model;/*** 指數(shù)數(shù)據(jù)實體類(數(shù)據(jù)模型)* * @author 科弟* */ public class Bmi {// 唯一標(biāo)識private int id;// 身高private double heigth;// 體重private double weigth;// 體重指數(shù)private double bmiNum;// 體重狀態(tài)private String bmiState;// 體重狀態(tài)圖片名private String stateIconId;// 計算時間private long calaTime;/*** 構(gòu)造方法*/public Bmi() {}/*** 構(gòu)造方法* * @param id* @param heigth* @param weigth* @param bmiNum* @param bmiState* @param stateIconId* @param calaTime*/public Bmi(int id, double heigth, double weigth, double bmiNum,String bmiState, String stateIconId, long calaTime) {super();this.id = id;this.heigth = heigth;this.weigth = weigth;this.bmiNum = bmiNum;this.bmiState = bmiState;this.stateIconId = stateIconId;this.calaTime = calaTime;}public int getId() {return id;}public void setId(int id) {this.id = id;}public double getHeigth() {return heigth;}public void setHeigth(double heigth) {this.heigth = heigth;}public double getWeigth() {return weigth;}public void setWeigth(double weigth) {this.weigth = weigth;}public double getBmiNum() {return bmiNum;}public void setBmiNum(double bmiNum) {this.bmiNum = bmiNum;}public String getBmiState() {return bmiState;}public void setBmiState(String bmiState) {this.bmiState = bmiState;}public String getStateIconId() {return stateIconId;}public void setStateIconId(String stateIconId) {this.stateIconId = stateIconId;}public long getCalaTime() {return calaTime;}public void setCalaTime(long calaTime) {this.calaTime = calaTime;}@Overridepublic String toString() {return "Bmi [id=" + id + ", heigth=" + heigth + ", weigth=" + weigth+ ", bmiNum=" + bmiNum + ", bmiState=" + bmiState+ ", stateIconId=" + stateIconId + ", calaTime=" + calaTime+ "]";}}
? ? SQLite數(shù)據(jù)庫版本工具:com.kedi.bmi.db/DbVersionHelper.java ??package com.kedi.bmi.db;import android.content.Context; import android.database.sqlite.SQLiteDatabase; import android.database.sqlite.SQLiteDatabase.CursorFactory; import android.database.sqlite.SQLiteOpenHelper;/*** SQLite數(shù)據(jù)庫版本管理子類 ,* 繼承與SQLiteOpenHelper(SQLite數(shù)據(jù)庫版本管理類,此類為抽象類,需要實現(xiàn)onCreate(),onUpgrade()兩個方法)* * @author 科弟* */ public class DbVersionHelper extends SQLiteOpenHelper {// 定義數(shù)據(jù)庫名常量public static final String DB_NAME = "bmi.db";// 定義數(shù)據(jù)表名public static final String TABLE_NAME = "bmi";// 數(shù)據(jù)庫版本號public static final int DB_VERSION = 1;/*** 構(gòu)造方法* * @param context* :上下文* @param name* :數(shù)據(jù)庫名* @param factory* :游標(biāo)工廠,游標(biāo)代表指向某條數(shù)據(jù)記錄的指針* @param version* :數(shù)據(jù)庫版本號*/public DbVersionHelper(Context context, String name, CursorFactory factory,int version) {super(context, name, factory, version);}/*** 構(gòu)造方法*/public DbVersionHelper(Context context) {super(context, DB_NAME, null, DB_VERSION);}/*** 創(chuàng)建數(shù)據(jù)表或初始化數(shù)據(jù)記錄的方法 SQLiteDatabase db:是被創(chuàng)建的數(shù)據(jù)庫*/@Overridepublic void onCreate(SQLiteDatabase db) {// 創(chuàng)建數(shù)據(jù)表的SQL語句String createTableSql = "create table "+ TABLE_NAME+ " ( id integer primary key autoincrement, heigth integer,weigth integer,bmiNum integer,bmiState text,stateIconId text,calaTime integer )";// 執(zhí)行創(chuàng)建數(shù)據(jù)表的SQL語句去創(chuàng)建數(shù)據(jù)表db.execSQL(createTableSql);}/*** 更新數(shù)據(jù)庫或數(shù)據(jù)表的方法 SQLiteDatabase db: 是要更新的數(shù)據(jù)庫, int oldVersion:舊數(shù)據(jù)庫版本號, int* newVersion:新數(shù)據(jù)庫版本號*/@Overridepublic void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {// 判斷如果數(shù)據(jù)庫的新版本號大于就版本號,則執(zhí)行更新數(shù)據(jù)庫的邏輯if (newVersion > oldVersion) {// 刪除已有的數(shù)據(jù)表 EXISTSString dropTableSql = "drop table if exists " + TABLE_NAME;db.execSQL(dropTableSql);// 重新創(chuàng)建數(shù)據(jù)庫,代表升級數(shù)據(jù)庫onCreate(db);}}}
? ?SQLite數(shù)據(jù)庫操作業(yè)務(wù)邏輯類(增,刪,改,查歷史記錄邏輯):com.kedi.bmi.dao/BmiDao.java
package com.kedi.bmi.dao;import java.util.ArrayList; import java.util.List;import android.content.ContentValues; import android.content.Context; import android.database.Cursor; import android.database.sqlite.SQLiteDatabase;import com.kedi.bmi.db.DbVersionHelper; import com.kedi.bmi.model.Bmi;/*** 操作數(shù)據(jù)庫的業(yè)務(wù)邏輯類* * @author 科弟* */ public class BmiDao {// 數(shù)據(jù)庫版本管理類private DbVersionHelper mDbVersionHelper;// 數(shù)據(jù)庫類private SQLiteDatabase mDb;public BmiDao(Context context) {mDbVersionHelper = new DbVersionHelper(context);}/*** 插入數(shù)據(jù)的方法(增)*/public void insertBmi(Bmi bmi) {// 打開數(shù)據(jù)庫mDb = mDbVersionHelper.getWritableDatabase();// 創(chuàng)建一個存放一條數(shù)據(jù)記錄的對象ContentValues values = new ContentValues();// 將Bmi對象封裝的數(shù)據(jù)保存到ContentValues對象中// values.put("id", bmi.getId());values.put("heigth", bmi.getHeigth());values.put("weigth", bmi.getWeigth());values.put("bmiNum", bmi.getBmiNum());values.put("bmiState", bmi.getBmiState());values.put("stateIconId", bmi.getStateIconId());values.put("calaTime", bmi.getCalaTime());/** mDb.insert(table, nullColumnHack, values)插入數(shù)據(jù)記錄的方法: 參數(shù)介紹:* table:要插入數(shù)據(jù)的表的名稱 values:一個ContentValues對象,類似一個map.通過鍵值對的形式存儲值。* nullColumnHack* :當(dāng)values參數(shù)為空或者里面沒有內(nèi)容的時候,我們insert是會失敗的(底層數(shù)據(jù)庫不允許插入一個空行),為了防止這種情況* ,我們要在這里指定一個 列名,到時候如果發(fā)現(xiàn)將要插入的行為空行時,就會將你指定的這個列名的值設(shè)為null,然后再向數(shù)據(jù)庫中插入。* 如果我們不添加nullColumnHack的話,那么我們的sql語句最終的結(jié)果將會類似 insert into* tableName()values();這顯然是不允許的。而如果我們添加上nullColumnHack呢,sql將會變成這樣,* insert into tableName (nullColumnHack)values(null);這樣很顯然就是可以的。*/mDb.insert(DbVersionHelper.TABLE_NAME, "id", values);// 關(guān)閉數(shù)據(jù)庫close();}/*** 刪除某行數(shù)據(jù)記錄(刪)*/public void deleteBmi(Bmi bmi) {// 打開數(shù)據(jù)庫mDb = mDbVersionHelper.getWritableDatabase();/** mDb.delete(table, whereClause, whereArgs)刪除數(shù)據(jù)記錄的方法 參數(shù)說明:* table:是要刪除的數(shù)據(jù)記錄所在的數(shù)據(jù)表名 whereClause:刪除數(shù)據(jù)記錄的條件(包含占位符) whereArgs:占位符的具體值*/mDb.delete(DbVersionHelper.TABLE_NAME, "id=?",new String[] { bmi.getId() + "" });// 關(guān)閉數(shù)據(jù)庫close();}/*** 刪除所有數(shù)據(jù)記錄(刪)*/public void deleteBmis() {// 打開數(shù)據(jù)庫mDb = mDbVersionHelper.getWritableDatabase();/** mDb.delete(table, whereClause, whereArgs)刪除數(shù)據(jù)記錄的方法 參數(shù)說明:* table:是要刪除的數(shù)據(jù)記錄所在的數(shù)據(jù)表名 whereClause:刪除數(shù)據(jù)記錄的條件(包含占位符) whereArgs:占位符的具體值*/mDb.delete(DbVersionHelper.TABLE_NAME, null, null);// 關(guān)閉數(shù)據(jù)庫close();}/*** 修改某條數(shù)據(jù)記錄(改)*/public void updateBmi(Bmi bmi) {// 打開數(shù)據(jù)庫mDb = mDbVersionHelper.getWritableDatabase();// 創(chuàng)建一個存放一條數(shù)據(jù)記錄的對象ContentValues values = new ContentValues();// 將Bmi對象封裝的數(shù)據(jù)保存到ContentValues對象中values.put("heigth", bmi.getHeigth());values.put("weigth", bmi.getWeigth());values.put("bmiNum", bmi.getBmiNum());values.put("bmiState", bmi.getBmiState());values.put("stateIconId", bmi.getStateIconId());values.put("calaTime", bmi.getCalaTime());/** mDb.update(table, values, whereClause, whereArgs)修改方法 參數(shù)說明:* table:是要更新的數(shù)據(jù)所在的數(shù)據(jù)表名 values:要更新的數(shù)據(jù)集 whereClause:更新數(shù)據(jù)的條件(包含占位符)* whereArgs:占位符的具體值*/mDb.update(DbVersionHelper.TABLE_NAME, values, "id=?",new String[] { bmi.getId() + "" });// 關(guān)閉數(shù)據(jù)庫close();}/*** 獲取所有的數(shù)據(jù)(查)* * @return*/public List<Bmi> getBmis() {// 創(chuàng)建存放多個Bmi對象的List集合List<Bmi> list = new ArrayList<Bmi>();// 獲得可讀數(shù)據(jù)庫mDb = mDbVersionHelper.getReadableDatabase();/** mDb.query(distinct, table, columns, selection, selectionArgs,* groupBy, having, orderBy, limit)查詢數(shù)據(jù)的方法 參數(shù)說明: distinct:為true時表示過濾重復(fù)數(shù)據(jù)* table:代表數(shù)據(jù)表名 columns:要查詢的列名 new String[]{"*"}代表查詢所有列* selection:要查詢的條件(包含占位符),值為null是代表無條件查詢 selectionArgs:占位符的具體值* groupBy:是否分組 having:函數(shù)支持聲明 orderBy:排序(DESC 降序,ASC升序) limit:按指定范圍查詢數(shù)據(jù)*/Cursor cursor = mDb.query(true, DbVersionHelper.TABLE_NAME,new String[] { "*" }, null, null, null, null, "calaTime desc",null);if (cursor != null) {// cursor是游標(biāo),也相當(dāng)于數(shù)據(jù)集,可以遍歷獲得數(shù)據(jù)集中的所有數(shù)據(jù)// 遍歷獲得數(shù)據(jù)集中的所有數(shù)據(jù)while (cursor.moveToNext()) {// 獲取每一列的數(shù)據(jù)int id = cursor.getInt(cursor.getColumnIndex("id"));double heigth = cursor.getDouble(cursor.getColumnIndex("heigth"));double weigth = cursor.getDouble(cursor.getColumnIndex("weigth"));double bmiNum = cursor.getDouble(cursor.getColumnIndex("bmiNum"));String bmiState = cursor.getString(cursor.getColumnIndex("bmiState"));String stateIconId= cursor.getString(cursor.getColumnIndex("stateIconId"));long calaTime = cursor.getLong(cursor.getColumnIndex("calaTime"));// 封裝數(shù)據(jù)到Bmi對象中Bmi bmi = new Bmi(id, heigth, weigth, bmiNum, bmiState,stateIconId, calaTime);// 存放數(shù)據(jù)到List集合中l(wèi)ist.add(bmi);}}close();return list;}/*** 關(guān)閉數(shù)據(jù)庫的方法*/public void close() {if (mDb != null && mDb.isOpen()) {mDb.close();}} }
? 說明:通用對話框,數(shù)據(jù)庫功能以及開發(fā)完成,此時可以考慮在MainActivity中把退出程序功能和計算后將數(shù) ? 據(jù)插入數(shù)據(jù)庫以記錄的功能補(bǔ)上(也就是的MainActivity中紅色文字內(nèi)容)。
? ?歷史記錄列表數(shù)據(jù)適配器開發(fā):com.kedi.bmi.adapter/HistoryRecordAdapter.java
??package com.kedi.bmi.adapter;import java.util.List;import android.content.Context; import android.view.View; import android.view.ViewGroup; import android.widget.BaseAdapter; import android.widget.ImageView; import android.widget.TextView;import com.kedi.bmi.R; import com.kedi.bmi.model.Bmi; import com.kedi.bmi.utils.DataUtil; import com.kedi.bmi.utils.DateUtil;/*** 歷史列表數(shù)據(jù)適配器* * @author 科弟* */ public class HistoryRecordAdapter extends BaseAdapter {private Context mContext;// 上下文private List<Bmi> mDatas;// 數(shù)據(jù)集public HistoryRecordAdapter() {}public HistoryRecordAdapter(Context mContext, List<Bmi> mDatas) {super();this.mContext = mContext;this.mDatas = mDatas;}@Overridepublic int getCount() {return mDatas.size();}@Overridepublic Object getItem(int position) {return mDatas.get(position);}@Overridepublic long getItemId(int position) {return position;}@Overridepublic View getView(int position, View convertView, ViewGroup parent) {ViewHolder viewHolder = null;if (convertView == null) {// 將XML布局轉(zhuǎn)化為View對象convertView = View.inflate(mContext, R.layout.history_list_item,null);// 將控件保存到ViewHolder類中,方便使用ListView的歷史緩存(convertView)viewHolder = new ViewHolder();viewHolder.mStateIconIv = (ImageView) convertView.findViewById(R.id.iv_state_icon);viewHolder.mWeightBmiTv = (TextView) convertView.findViewById(R.id.tv_weight_bmi);viewHolder.mWeightStateTv = (TextView) convertView.findViewById(R.id.tv_weight_state);viewHolder.mHeightTv = (TextView) convertView.findViewById(R.id.tv_height);viewHolder.mWeightTv = (TextView) convertView.findViewById(R.id.tv_weight);viewHolder.mDateTv = (TextView) convertView.findViewById(R.id.tv_date);convertView.setTag(viewHolder);} else {viewHolder = (ViewHolder) convertView.getTag();}Bmi bmi = mDatas.get(position);// 綁定數(shù)據(jù)viewHolder.mStateIconIv.setImageResource(Integer.valueOf(bmi.getStateIconId()));viewHolder.mWeightBmiTv.setText(mContext.getResources().getString(R.string.weight_bmi1)+ bmi.getBmiNum());viewHolder.mWeightStateTv.setText(mContext.getResources().getString(R.string.weight_state1)+ bmi.getBmiState());viewHolder.mHeightTv.setText(bmi.getHeigth()+ mContext.getResources().getString(R.string.cm));viewHolder.mWeightTv.setText(bmi.getWeigth()+ mContext.getResources().getString(R.string.kg));viewHolder.mDateTv.setText(DateUtil.getDate(bmi.getCalaTime()));return convertView;}/*** 視圖封裝類,Google官方推薦寫法* * @author 科弟* */class ViewHolder {private ImageView mStateIconIv;// 體重狀態(tài)圖標(biāo)控件private TextView mWeightBmiTv;// 體重指數(shù)控件private TextView mWeightStateTv;// 體重狀態(tài)控件private TextView mHeightTv;// 身高控件private TextView mWeightTv;// 體重控件private TextView mDateTv;// 日期事件控件} }
? ?所有的歷史記錄準(zhǔn)備工作做好后,就可以開發(fā)歷史記錄業(yè)務(wù)邏輯功能了。
? ?歷史記錄業(yè)務(wù)邏輯功能開發(fā):com.kedi.bmi.ui/HistoryRecordActivity.java
? ?說明:在AndroidManifest.xml中注冊HistoryRecordActivity
package com.kedi.bmi.ui;import java.util.List;import android.app.Activity; import android.os.AsyncTask; import android.os.Bundle; import android.view.View; import android.view.View.OnClickListener; import android.view.Window; import android.widget.AdapterView; import android.widget.AdapterView.OnItemLongClickListener; import android.widget.ImageButton; import android.widget.LinearLayout; import android.widget.ListView; import android.widget.TextView; import android.widget.Toast;import com.kedi.bmi.R; import com.kedi.bmi.adapter.HistoryRecordAdapter; import com.kedi.bmi.dao.BmiDao; import com.kedi.bmi.listener.OnClickOkListener; import com.kedi.bmi.model.Bmi; import com.kedi.bmi.utils.DialogUtil;/*** 歷史計算記錄Activity類* * @author 科弟* */ public class HistoryRecordActivity extends Activity implements OnClickListener,OnItemLongClickListener {private LinearLayout mHistoryLl;// 歷史記錄布局private TextView mEmptyTv;// 當(dāng)歷史列表為空時,顯示該文本提示private ListView mHistoryLv;// 歷史記錄列表視圖private HistoryRecordAdapter mAdapter;// 數(shù)據(jù)適配器private List<Bmi> mDatas;// 數(shù)據(jù)集合private ImageButton mBackIb;// 回退按鈕private ImageButton mClearIb;// 清空按鈕private BmiDao bmiDao;// 操作數(shù)據(jù)庫的業(yè)務(wù)邏輯類@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);// 取消系統(tǒng)默認(rèn)標(biāo)題欄requestWindowFeature(Window.FEATURE_NO_TITLE);// 關(guān)聯(lián)XML布局界面setContentView(R.layout.activity_history_record);bmiDao = new BmiDao(HistoryRecordActivity.this);initView();setListener();// 創(chuàng)建獲取數(shù)據(jù)的異步任務(wù)類并調(diào)用execute()方法執(zhí)行異步任務(wù)new InsertDataAsynkTask().execute();}/*** 初始化視圖的方法*/private void initView() {mHistoryLl = (LinearLayout) this.findViewById(R.id.ll_history);mEmptyTv = (TextView) this.findViewById(R.id.tv_empty);mHistoryLv = (ListView) this.findViewById(R.id.lv_history);mBackIb = (ImageButton) this.findViewById(R.id.ib_back);mClearIb = (ImageButton) this.findViewById(R.id.ib_clear);}/*** 注冊點(diǎn)擊事件監(jiān)聽器*/private void setListener() {mBackIb.setOnClickListener(this);mClearIb.setOnClickListener(this);// 注冊ListView列表條目長按事件監(jiān)聽器mHistoryLv.setOnItemLongClickListener(this);}/*** 從數(shù)據(jù)庫查詢數(shù)據(jù)的一步任務(wù)類(查詢數(shù)據(jù)庫是耗時操作,最好用一步方式)* * @author 科弟* */class InsertDataAsynkTask extends AsyncTask<Void, Void, List<Bmi>> {/*** 子線程方法,做好事操作*/@Overrideprotected List<Bmi> doInBackground(Void... arg0) {return bmiDao.getBmis();}@Overrideprotected void onPostExecute(List<Bmi> result) {super.onPostExecute(result);mDatas = result;if (mDatas != null && mDatas.size() > 0) {// 隱藏空文本提示,顯示歷史列表布局mHistoryLl.setVisibility(View.VISIBLE);mEmptyTv.setVisibility(View.GONE);mAdapter = new HistoryRecordAdapter(HistoryRecordActivity.this,mDatas);mHistoryLv.setAdapter(mAdapter);} else {// 顯示空文本提示,隱藏歷史列表布局mHistoryLl.setVisibility(View.GONE);mEmptyTv.setVisibility(View.VISIBLE);}}}@Overridepublic void onClick(View v) {int id = v.getId();switch (id) {case R.id.ib_back:// 銷毀當(dāng)前Activityfinish();break;case R.id.ib_clear:// 彈出二次確認(rèn)對話框// 獲得對話框標(biāo)題與提示消息String title = getResources().getString(R.string.clear1);String message = getResources().getString(R.string.clear1_message);if (mDatas != null && mDatas.size() > 0) {DialogUtil.showDialog(this, title, message,new OnClickOkListener() {@Overridepublic void onClick(View view) {// 清空所有歷史數(shù)據(jù)deleteBmis();}});} else {Toast.makeText(this, getResources().getString(R.string.empty),Toast.LENGTH_SHORT).show();}break;}}@Overridepublic boolean onItemLongClick(AdapterView<?> adapterView, View view,final int position, long arg3) {// 彈出二次確認(rèn)對話框// 獲得對話框標(biāo)題與提示消息String title = getResources().getString(R.string.delete);String message = getResources().getString(R.string.delete_message);DialogUtil.showDialog(this, title, message, new OnClickOkListener() {@Overridepublic void onClick(View view) {// 刪除當(dāng)前條目deleteBmi(position);}});return false;}/*** 清空所有歷史數(shù)據(jù)的方法*/private void deleteBmis() {// 清空集合mDatas.clear();// 刷新界面mAdapter.notifyDataSetChanged();// 清空數(shù)據(jù)庫bmiDao.deleteBmis();// 顯示空文本提示,隱藏歷史列表布局mHistoryLl.setVisibility(View.GONE);mEmptyTv.setVisibility(View.VISIBLE);}/*** 刪除當(dāng)前條目的方法* * @param position*/private void deleteBmi(int position) {// 刪除當(dāng)前條目// 刪除數(shù)據(jù)庫對應(yīng)位置對象對應(yīng)Id的數(shù)據(jù)記錄bmiDao.deleteBmi(mDatas.get(position));// 刪除集合中對應(yīng)位置的數(shù)據(jù)mDatas.remove(position);// 刷新界面mAdapter.notifyDataSetChanged();if (mDatas.size() <= 0) {// 顯示空文本提示,隱藏歷史列表布局mHistoryLl.setVisibility(View.GONE);mEmptyTv.setVisibility(View.VISIBLE);} else {// 隱藏空文本提示,顯示歷史列表布局mHistoryLl.setVisibility(View.VISIBLE);mEmptyTv.setVisibility(View.GONE);}} }
? step5:檢查所有的Activity是否都在AndroidManifest.xml注冊表文件中注冊。 ?? ? 說明:好的習(xí)慣是每創(chuàng)建完對應(yīng)的Activity就緊接著把它注冊到AndroidManifest.xml注冊表文件中,要不然 ? ?很容易最后忘掉。
? ?AndroidManifest.xml
<?xml version="1.0" encoding="utf-8"?> <manifest xmlns:android="http://schemas.android.com/apk/res/android"package="com.kedi.bmi"android:versionCode="3"android:versionName="3.0" ><!-- 配置SDK的最小版本號為14,最大版本號為19 --><uses-sdkandroid:minSdkVersion="14"android:targetSdkVersion="19" /><applicationandroid:allowBackup="true"android:icon="@drawable/ic_launcher"android:label="@string/app_name"android:theme="@style/AppTheme" ><!-- 注冊主界面Activity --><activityandroid:name=".ui.MainActivity"android:screenOrientation="portrait" ></activity><!-- 注冊歡迎界面Activity --><activityandroid:name=".ui.WelcomeActivity"android:screenOrientation="portrait" ><!-- 配置action,category,使得WelcomeActivity成為第一啟動界面 --><intent-filter><action android:name="android.intent.action.MAIN" /><category android:name="android.intent.category.LAUNCHER" /></intent-filter></activity><activityandroid:name=".ui.HistoryRecordActivity"android:screenOrientation="portrait" /></application></manifest>
?結(jié)語
? ? ? 到此【BMI指數(shù)計算器V3.0】的所有功能就都開發(fā)完成了,不知有沒有朋友耐著性子一步一步跟過來,Android項目開發(fā)專欄主要側(cè)重項目的整體開發(fā)和技術(shù)的用法,所以沒有具體展開講解每一個技術(shù)的原理,對于沒有基礎(chǔ)的朋友,建議先掌握基礎(chǔ)技術(shù),在練手的時候可以耐著性子一步一步跟過來做著個項目,相信會有質(zhì)的提高。同時希望朋友們能為我提些好的建議,以把博文做的更好,幫助到更多的朋友!總結(jié)
以上是生活随笔為你收集整理的【BMI指数计算器V3.0】项目实战的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 建筑工程量计算机构,建筑工程量计算公式大
- 下一篇: 安全HCIP之IPS入侵防御