先看最终效果:
1.首先创建一个Empty Activity
2.在activity_main.xml里编写主界面布局
根据预览图,主界面需要一个ListView和一个ImageButton,还要给ImageButton添加一个Onclick事件,将按钮的UI图片tianjia.png放入drawable文件夹
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout 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:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity">
<ListView
android:id="@+id/list_view"
android:layout_width="wrap_content"
android:layout_height="650dp"
/>
<ImageButton
android:id="@+id/add"
android:onClick="addAccount"
android:layout_width="80dp"
android:layout_height="80dp"
android:scaleType="centerInside"
android:layout_centerHorizontal="true"
android:background="#00FF0000"
android:src="@drawable/tianjia"
android:layout_below="@+id/list_view" />
</RelativeLayout>
android:background="#00FF0000"这行代码的意思是让imageButton的背景为透明。如果不设置这行代码,背景就是默认的灰色;也可以设置为白色,但是自带的app底色并不是纯白的,仔细看会发现色差:
那么写完主界面布局后Preview里就是这样:
3.接下来开始写ListView,也就是单个item的布局:新建一个布局文件
命名为list_item
<?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="80dp">
<TextView
android:id="@+id/tv_title"
android:layout_width="150dp"
android:layout_height="80dp"
android:layout_marginLeft="10dp"
android:layout_alignParentLeft="true"
android:gravity="center"
android:singleLine="true"
android:textSize="20sp"
android:ellipsize="marquee"
android:text="costTitle" />
<TextView
android:id="@+id/tv_date"
android:layout_width="wrap_content"
android:layout_height="80dp"
android:gravity="center"
android:textSize="20sp"
android:layout_marginLeft="15dp"
android:layout_toRightOf="@+id/tv_title"
android:text="2020-05-31"/>
<TextView
android:id="@+id/tv_money"
android:layout_width="wrap_content"
android:layout_height="80dp"
android:gravity="center"
android:layout_alignParentRight="true"
android:layout_marginRight="20dp"
android:textSize="25sp"
android:textColor="#ffbd27"
android:text="25"/>
</RelativeLayout>
效果:
4.写完listView之后最重要的就是为它添加适配器,这样它才能把获取的数据按照格式显示在主界面中
新建类:
命名为ListAdapter
这里采用的是BaseAdapter
package com.example.myaccountapp;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Adapter;
import android.widget.BaseAdapter;
import android.widget.TextView;
import java.util.List;
public class ListAdapter extends BaseAdapter {
List<costList> mList;
public ListAdapter(List<costList>list)
{
mList=list;
}
@Override
public int getCount() {
return mList.size();
}
@Override
public Object getItem(int position) {
return mList.get(position);
}
@Override
public long getItemId(int position) {
return position;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
View view=mLayoutInflater.inflate(R.layout.list_item,null);
//取出数据赋值
costList item=mList.get(position);
TextView tv_title=view.findViewById(R.id.tv_title);
TextView tv_date=view.findViewById(R.id.tv_date);
TextView tv_money=view.findViewById(R.id.tv_money);
//绑定
tv_title.setText(mList.get(position).getTitle());
tv_date.setText(mList.get(position).getDate());
tv_money.setText(mList.get(position).getMoney());
return view;
}
private List<costList>getmList;
private LayoutInflater mLayoutInflater;
public ListAdapter(Context context,List<costList>list)
{
mList=list;
//通过外部传来的Context初始化LayoutInflater对象
mLayoutInflater=LayoutInflater.from(context);
}
}
5.搭建数据库
Sqlite的运用是重难点
首先创建一个DBHelper类:按第四步的方法新建类,命名为:DBHelper
package com.example.myaccountapp;
import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import androidx.annotation.Nullable;
public class DBHelper extends SQLiteOpenHelper {
private static int DB_VERSION = 1;
private static String DB_NAME = "account_daily.db";
public DBHelper(Context context) {
super(context, DB_NAME ,null, DB_VERSION);
}
@Override
public void onCreate(SQLiteDatabase db) {
String sql="create table account(_id integer primary key autoincrement," +//主键
"Title varchar(20)," +//Title
"Date varchar(20)," +//Date
"Money vaechar(20))";//Money
db.execSQL(sql);
}
@Override
public void onUpgrade(SQLiteDatabase sqLiteDatabase, int i, int i1) {
}
}
然后我们写一个类专门存放赋值和取出这些数据的方法,命名为costList
package com.example.myaccountapp;
public class costList {
private String _id;
private String Title;
private String Date;
private String Money;
public String getMoney() {
return Money;
}
public void setMoney(String money) {
Money = money;
}
public String getDate() {
return Date;
}
public void setDate(String date) {
Date = date;
}
public String getTitle() {
return Title;
}
public void setTitle(String title) {
Title = title;
}
public String get_id() {
return _id;
}
public void set_id(String _id) {
this._id = _id;
}
}
6.来到MainActivity开始写方法:
package com.example.myaccountapp;
import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity;
import android.content.Intent;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.os.Bundle;
import android.view.View;
import android.widget.ArrayAdapter;
import android.widget.BaseAdapter;
import android.widget.ImageButton;
import android.widget.ListView;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
public class MainActivity extends AppCompatActivity {
private DBHelper helper;
private ListView listView;
private ImageButton Add;
private List<costList>list;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
initView();
initData();
}
//初始化
private void initData() {
list=new ArrayList<>();
SQLiteDatabase db=helper.getReadableDatabase();
Cursor cursor=db.query("account",null,null,null,null,
null,null);
while (cursor.moveToNext()){
costList clist=new costList();//构造实例
clist.set_id(cursor.getString(cursor.getColumnIndex("_id")));
clist.setTitle(cursor.getString(cursor.getColumnIndex("Title")));
clist.setDate(cursor.getString(cursor.getColumnIndex("Date")));
clist.setMoney(cursor.getString(cursor.getColumnIndex("Money")));
list.add(clist);
}
//绑定适配器
listView.setAdapter(new ListAdapter(this,list));
db.close();
}
private void initView() {
helper=new DBHelper(MainActivity.this);
listView = findViewById(R.id.list_view);
Add=findViewById(R.id.add);
}
//事件:添加
public void addAccount(View view){
//跳转
Intent intent=new Intent(MainActivity.this,new_cost.class);
startActivityForResult(intent,1);
}
@Override
protected void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if(requestCode==1&&resultCode==1)
{
this.initData();
}
}
}
7.可以看到我们必须给之前的Onclick事件写一个方法(addAccount)。即点击+号按钮跳转到一个新页面,在这个新页面,我们要完成输入Title、Date、Money的操作。
这就需要新建一个Activity,命名为new_cost
生成Activity时系统会同时生成一个java文件和一个layout文件,名为
在这个文件中开始写新建项的布局,如本文开头的第二张图:
<?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:orientation="vertical"
android:gravity="center">
<EditText
android:id="@+id/et_cost_title"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="4dp"
android:hint="Cost Title"
android:textColor="#ffbd27"
/>
<EditText
android:id="@+id/et_cost_money"
android:inputType="number|numberDecimal"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="4dp"
android:hint="Cost Money"
android:textColor="#ffbd27"
/>
<DatePicker
android:id="@+id/dp_cost_date"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_margin="8dp"
android:datePickerMode="spinner"
android:calendarViewShown="false"
/>
<Button
android:onClick="okButton"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="确认"
android:textSize="20dp"
android:textColor="#333333"
android:background="#ffbd27"
android:layout_marginLeft="40dp"
android:layout_marginRight="40dp"
/>
</LinearLayout>
new_cost.java中:
package com.example.myaccountapp;
import androidx.appcompat.app.AppCompatActivity;
import android.content.ContentValues;
import android.database.sqlite.SQLiteDatabase;
import android.os.Bundle;
import android.view.Gravity;
import android.view.View;
import android.widget.DatePicker;
import android.widget.EditText;
import android.widget.Toast;
import java.text.SimpleDateFormat;
import java.util.Date;
public class new_cost extends AppCompatActivity {
private DBHelper helper;
private EditText et_cost_title;
private EditText et_cost_money;
private DatePicker dp_cost_date;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_new_cost);
initView();
}
private void initView() {
helper = new DBHelper(new_cost.this);
et_cost_title = findViewById(R.id.et_cost_title);
et_cost_money = findViewById(R.id.et_cost_money);
dp_cost_date = findViewById(R.id.dp_cost_date);
}
public void okButton(View view) {
String titleStr = et_cost_title.getText().toString().trim();
String moneyStr = et_cost_money.getText().toString().trim();
String dateStr = dp_cost_date.getYear() + "-" + (dp_cost_date.getMonth() + 1) + "-"
+ dp_cost_date.getDayOfMonth();//这里getMonth会比当前月份少一个月,所以要+1
if ("".equals(moneyStr)) {
//可以不填写Title但是不能不填金额
Toast toast = Toast.makeText(this, "请填写金额", Toast.LENGTH_SHORT);
toast.setGravity(Gravity.CENTER, 0, 0);
toast.show();
} else {
SQLiteDatabase db = helper.getWritableDatabase();
ContentValues values = new ContentValues();
values.put("Title", titleStr);
values.put("Money", moneyStr);
values.put("Date", dateStr);
long account = db.insert("account", null, values);
if (account > 0) {
Toast toast = Toast.makeText(this, "保存成功", Toast.LENGTH_SHORT);
toast.setGravity(Gravity.CENTER, 0, 0);
toast.show();
setResult(1);
finish();
} else {
Toast toast = Toast.makeText(this, "请重试", Toast.LENGTH_SHORT);
toast.setGravity(Gravity.CENTER, 0, 0);
toast.show();
db.close();
}
setResult(1);
finish();
}
}
}
toast.setGravity(Gravity.CENTER, 0, 0);这行代码是设置小提示框显示的位置,如果不设置的话,默认是显示在底部的
完成!
接下来还可以优化一下ui,比如把题头栏状态栏换成黄色(默认是绿色的),光标也是可以换色的。还比如把按钮换成圆角样式。大家自己研究吧。
1.0版本只有非常简单的记账功能,也许还会更新2.0,就是增加一些衣食住行分类查看,按月份查看的功能之类的
有什么问题的话可以在评论区问我哦,我有能力的话会尽量解答的。不过我也是新手,总之大家共同进步吧
CSDN突然把我上传的源码调高了积分,贵得离谱,这边提供网盘,有需要自取:
链接:https://pan.baidu.com/s/1-LEyhXZRWzz0hTHJvC8sLg
提取码:f59z
转载:https://blog.csdn.net/qq_40069099/article/details/106601588