SDK:34
JDK:20.0.2
编写工具:Android Studio 2022.3.1
1.用户登录(没有账号就注册)
2.输入正确密码登录,错误不可登录
3.进入后的主页面包含个人中心、闲置社区、闲置发布、闲置删除四部分
4.个人中心可以注销用户,闲置发布用于发布闲置(闲置发布后在闲置社区显示)
5.删除闲置(输入发布商品的id即可对该商品进行删除)
1.在数据库中创建两个数据表用于保存个人信息和商品信息
2.所有操作都结合SQLite数据库的增、删、查、改
3.记录当前用户的原理:登录成功后将当前用户信息保存在一个自定义类中(该类中创建了相关静态变量并创建了get、set方法,以便于登录成功后通过set赋值,在进入个人中心后通过get获取
4.闲置社区的展示:通过列表展示。这个列表采用了SimpleCursorAdapter适配器自定义布局(该适配器用数据库查询结果的游标作为数据源,但在使用该适配器时数据表中_id列名是必须存在的)
5.该小练习没有添加可以发布图片的模块(可以把选取的图片先转成base64格式再转成二进制存入数据库,读取时再通过二进制转base64再转成图片即可)
数据库名:AppData
数据库表名:
1.用户表User(列名:学号、密码、姓名、手机号码)
2.商品表commodity(列名:商品ID、商品名称、商品发布者、商品价格、联系方式)
用户表User建表语句:
create table User(stu_id integer primary key,passwd varchar(20),name varchar(20),phone integer(20));
商品表commodity建表语句:
create table commodity(_id integer primary key,c_name varchar(20),cr_name varchar(20),c_price integer(20),c_phone integer(20));
整体设计中遇到的小问题:
1.移除过多的信息
2.由于使用SimpleCursorAdapter适配器,以数据库查询结果作为数据源,故必须数据表中必须要有一个列名为_id
MyDBOpenHelper.java(创建数据库、创建表的类)
package com.campus.app.DB;
import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import androidx.annotation.Nullable;
public class MyDBOpenHelper extends SQLiteOpenHelper {
public static final String name = "AppData.db";//定义数据库名称
public static final int version = 1;//定义数据库版本
public MyDBOpenHelper(@Nullable Context context) {
super(context, name, null, version);
}
@Override
public void onCreate(SQLiteDatabase sqLiteDatabase) {
//编写建表语句
//1.用户表User(列名:学号、密码、姓名、手机号码)
sqLiteDatabase.execSQL("create table User(stu_id integer primary key,passwd varchar(20),name varchar(20),phone integer(20));");
//2.商品表(列名:商品ID、商品名称、商品发布者、商品价格、联系方式)
sqLiteDatabase.execSQL("create table commodity(_id integer primary key,c_name varchar(20),cr_name varchar(20),c_price integer(20),c_phone integer(20));");
}
@Override
public void onUpgrade(SQLiteDatabase sqLiteDatabase, int i, int i1) {
}
}
Data_Login.java(接受保存当前登录用户的自定义类)
package com.campus.app;
import java.util.ArrayList;
//接受保存登录后的参数类
//并创建get、set方法用于其他类给当前类的变量赋值或者获取该类变量的值
public class Data_Login {
private static String id ="";//保存学号(常量)
private static String pwd ="";//保存密码(常量)
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getPwd() {
return pwd;
}
public void setPwd(String pwd) {
this.pwd = pwd;
}
}
Deleteidle.java(删除闲置活动类)
package com.campus.app;
import androidx.appcompat.app.AppCompatActivity;
import android.content.Intent;
import android.database.sqlite.SQLiteDatabase;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;
import com.campus.app.DB.MyDBOpenHelper;
public class Deleteidle extends AppCompatActivity {//删除闲置
//创建对象
private TextView shangpinid;
private Button shanchuanniu;
private MyDBOpenHelper myDBOpenHelper; //定义数据库帮助类对象
private SQLiteDatabase db; //定义一个可以操作数据库的对象
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_deleteidle);
initView();//调用将对象与控件绑定方法
btnShanchu();//调用当点击“删除”按钮的实现方法
}
private void btnShanchu() {//创建当点击“删除”按钮的实现方法
shanchuanniu.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
myDBOpenHelper = new MyDBOpenHelper(Deleteidle.this); //实例化数据库帮助类
db = myDBOpenHelper.getWritableDatabase();//打开数据库写权限
db.delete("commodity","_id=?",new String[]{shangpinid.getText().toString()});//输入框输入的id给数据库查询后删除
Toast.makeText(Deleteidle.this, "已为你删除该商品!", Toast.LENGTH_SHORT).show();
finish();
}
});
}
private void initView() {//创建将对象与控件绑定方法
shangpinid = findViewById(R.id.shangpinid);
shanchuanniu = findViewById(R.id.shanchuanniu);
}
}
IdleCommunity.java(闲置社区活动类)
package com.campus.app;
import androidx.appcompat.app.AppCompatActivity;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.os.Bundle;
import android.widget.ArrayAdapter;
import android.widget.CursorAdapter;
import android.widget.ListView;
import android.widget.SimpleAdapter;
import android.widget.SimpleCursorAdapter;
import android.widget.Toast;
import com.campus.app.DB.MyDBOpenHelper;
import java.util.ArrayList;
import java.util.List;
public class IdleCommunity extends AppCompatActivity {//闲置社区
//创建对象
ListView list_view_Idle;
private MyDBOpenHelper myDBOpenHelper; //定义数据库帮助类对象
private SQLiteDatabase db; //定义一个可以操作数据库的对象
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_idle_community);
initView();//调用将对象与控件绑定方法
simpleCAP();//调用准备数据(从数据库中获取数据)+添加到适配器(SimpleCursorAdapter适配器,该适配器用数据库查询数据作为数据源)方法
}
private void simpleCAP() {//创建准备数据(从数据库中获取数据)+添加到适配器(SimpleCursorAdapter适配器,该适配器用数据库查询数据作为数据源)方法
myDBOpenHelper = new MyDBOpenHelper(IdleCommunity.this); //实例化数据库帮助类
db = myDBOpenHelper.getReadableDatabase();//打开数据库读权限
Cursor cursor = db.rawQuery("select * from commodity",null);
if (cursor.moveToNext()){
//使用SimpleCursorAdapter适配器
//这个游标查询到的数据中必须有一个列名为_id否则会报错,所以写sql语句的时候必须要查到_id。显不显示这个id到无所谓
//参数:上下环境、布局文件ID、数据库查询结果的Cursor对象、数据库表中的列名、布局文件中对应的组件ID、行为
CursorAdapter adapter = new SimpleCursorAdapter(IdleCommunity.this,R.layout.listview_css,cursor,new String[]{"cr_name","_id","c_name","c_price","c_phone"},new int[]{R.id.lv_css_crname,R.id.lv_css_c_id,R.id.lv_css_c_name,R.id.lv_css_c_price,R.id.lv_css_cr_phone},CursorAdapter.FLAG_REGISTER_CONTENT_OBSERVER);
//绑定适配器(将适配器绑定到可视化组件上)
list_view_Idle.setAdapter(adapter);
}
}
private void initView() {//创建将对象与控件绑定方法
list_view_Idle = findViewById(R.id.list_view_Idle);
}
}
LogOn.java(登录活动类)
package com.campus.app;
import androidx.appcompat.app.AppCompatActivity;
import android.annotation.SuppressLint;
import android.content.Intent;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;
import com.campus.app.DB.MyDBOpenHelper;
public class LogOn extends AppCompatActivity {//登录
//创建对象
public EditText et_id,et_pwd;
public Button bt_login;
public TextView tv_register;
private MyDBOpenHelper myDBOpenHelper; //定义数据库帮助类对象
private SQLiteDatabase db; //定义一个可以操作数据库的对象
Data_Login d1 = new Data_Login();//实例化用于保存登录的传参类(创建对象)用于主页个人中心的参数,临时保存到Data_Login
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_log_on);
initView();//调用将对象与控件绑定方法
btnRegister();//调用当点击“没有账号,去注册”的实现方法
btnLogin();//调用点击登录按钮的实现方法
}
private void btnLogin() {//创建点击登录按按钮后的方法
bt_login.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
myDBOpenHelper = new MyDBOpenHelper(LogOn.this); //实例化数据库帮助类
db = myDBOpenHelper.getReadableDatabase();//打开数据库读权限
//获取界面上的学号和密码
String stuid= et_id.getText().toString();
String pwd = et_pwd.getText().toString();
//对用户名和密码进行判断
if(stuid.equals("") || pwd.equals("")){//如果没有输入学号或者密码
Toast.makeText(LogOn.this, "学号和密码不能为空", Toast.LENGTH_SHORT).show();
}else {
//从数据库中进行查询
Cursor cursor = db.rawQuery("select * from User where stu_id=? and passwd=?",new String[]{stuid,pwd});
if (cursor.moveToNext())
{
@SuppressLint("Range") String gid = cursor.getString(cursor.getColumnIndex("stu_id"));
@SuppressLint("Range") String gpwd = cursor.getString(cursor.getColumnIndex("passwd"));
if(stuid.equals(gid) && pwd.equals(gpwd))//如果与数据库中的学号和密码匹配
{
//提示登录成功
Toast.makeText(LogOn.this, "登录成功!", Toast.LENGTH_SHORT).show();
//带参数传递临时保存到Data_Login
d1.setId(gid);
d1.setPwd(gpwd);
//跳转到主页,关闭自身部分
Intent it = new Intent(LogOn.this,MainActivity.class);
startActivity(it); //跳转到主页
finish();//关闭自身
}
}else {
Toast.makeText(LogOn.this, "用户名或者密码错误,登陆失败!", Toast.LENGTH_SHORT).show();
et_id.setText("");
et_pwd.setText("");
}
}
}
});
}
private void btnRegister() {//创建当点击“没有账号,去注册”的实现方法
tv_register.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
//跳转到注册页面,关闭自身页面
startActivity(new Intent(LogOn.this,Register.class));
//finish();
}
});
}
private void initView() {//创建将对象与控件绑定方法
et_id = findViewById(R.id.et_id);
et_pwd = findViewById(R.id.et_pwd);
bt_login = findViewById(R.id.bt_login);
tv_register = findViewById(R.id.tv_register);
}
}
MainActivity.java(登录成功后的主页面活动类)
package com.campus.app;
import androidx.appcompat.app.AppCompatActivity;
import androidx.fragment.app.Fragment;
import androidx.viewpager.widget.ViewPager;
import androidx.viewpager2.widget.ViewPager2;
import android.content.Intent;
import android.os.Bundle;
import android.provider.MediaStore;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.LinearLayout;
import android.widget.RadioButton;
import android.widget.RadioGroup;
import android.widget.TextView;
import java.util.ArrayList;
import java.util.List;
public class MainActivity extends AppCompatActivity {//主页
///创建对象
LinearLayout ly_PersonalCenter;//个人中心
LinearLayout ly_IdleCommunity;//闲置社区
LinearLayout ly_Releaseidle;//发布闲置
LinearLayout ly_Deleteidle;//删除闲置
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
initView();//调用将对象与控件绑定方法
btnPersonalCenter();//调用点击个人中心布局区域时的实现方法
btnIdleCommunity();//调用点击闲置社区布局区域时的实现方法
btnReleaseidle();//调用点击发布闲置布局区域时的实现方法
btnDeleteidle();//调用点击删除闲置布局区域时的实现方法
}
private void btnDeleteidle() {//创建点击删除闲置布局区域时的实现方法
ly_Deleteidle.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
//实现页面跳转(当前页面跳转到删除闲置)
startActivity(new Intent(MainActivity.this,Deleteidle.class));
}
});
}
private void btnReleaseidle() {//创建点击发布闲置布局区域时的实现方法
ly_Releaseidle.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
//实现页面跳转(当前页面跳转到发布闲置)
startActivity(new Intent(MainActivity.this,Releaseidle.class));
}
});
}
private void btnIdleCommunity() {//创建点击闲置社区布局区域时的实现方法
ly_IdleCommunity.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
//实现页面跳转(当前页面跳转到闲置社区)
startActivity(new Intent(MainActivity.this,IdleCommunity.class));
}
});
}
private void btnPersonalCenter() {//创建点击个人中心布局区域时的实现方法
ly_PersonalCenter.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
//实现页面跳转(当前页面跳转到个人中心)
startActivity(new Intent(MainActivity.this,PersonalCenter.class));
}
});
}
private void initView() {//创建将对象与控件绑定的方法
ly_PersonalCenter = findViewById(R.id.ly_PersonalCenter);
ly_IdleCommunity = findViewById(R.id.ly_IdleCommunity);
ly_Releaseidle = findViewById(R.id.ly_Releaseidle);
ly_Deleteidle = findViewById(R.id.ly_Deleteidle);
}
}
PersonalCenter.java(个人中心活动类)
package com.campus.app;
import androidx.appcompat.app.AppCompatActivity;
import android.annotation.SuppressLint;
import android.content.Intent;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;
import com.campus.app.DB.MyDBOpenHelper;
public class PersonalCenter extends AppCompatActivity {//个人中心
//绑定控件
private TextView tv_welcome;
private TextView xuehao,mima,xingming,shoujihaoma;
private Button xiugaixinxi,yongjiuzhuxiao;
private MyDBOpenHelper myDBOpenHelper; //定义数据库帮助类对象
private SQLiteDatabase db; //定义一个可以操作数据库的对象
Data_Login d1 = new Data_Login();//实例化用于获取登录保存的临时传参。用于主页个人中心。
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_personal_center);
initView();//调用将对象与控件绑定方法
dataloginGet();//调用获取登录保存的临时传参方法,并将该参数传给文本框,用来显示谁登陆了
dataView();//调用各个文本框的默认值方法(数据库通过当前id查找该用户信息,接着赋给各个文本框)
btnYjzx();//调用点击了永久注销按钮的方法
}
private void btnYjzx() {//创建点击了永久注销按钮的方法
yongjiuzhuxiao.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
myDBOpenHelper = new MyDBOpenHelper(PersonalCenter.this); //实例化数据库帮助类
db = myDBOpenHelper.getWritableDatabase();//打开数据库写权限
db.delete("User","stu_id=?",new String[]{d1.getId()});
Toast.makeText(PersonalCenter.this, "注销成功!期待你的下次登录!", Toast.LENGTH_SHORT).show();
startActivity(new Intent(PersonalCenter.this,LogOn.class));
finish();
}
});
}
private void dataView() {//创建各个文本框的默认值方法(数据库通过当前id查找该用户信息,接着赋给各个文本框)
myDBOpenHelper = new MyDBOpenHelper(PersonalCenter.this); //实例化数据库帮助类
db = myDBOpenHelper.getReadableDatabase();//打开数据库读权限
Cursor cursor = db.rawQuery("select * from User where stu_id =?", new String[]{d1.getId()});
if (cursor.moveToNext()){
@SuppressLint("Range") String pxuehao = cursor.getString(cursor.getColumnIndex("stu_id"));//通过id差得的学号赋给变量pxuehao
@SuppressLint("Range") String pmima = cursor.getString(cursor.getColumnIndex("passwd"));//同上道理 这里表示密码
@SuppressLint("Range") String pxingming = cursor.getString(cursor.getColumnIndex("name"));//同上道理 这里表示姓名
@SuppressLint("Range") String pshoujihaoma = cursor.getString(cursor.getColumnIndex("phone"));//同上道理 这里表示手机号码
xuehao.setText(pxuehao);
mima.setText(pmima);
xingming.setText(pxingming);
shoujihaoma.setText(pshoujihaoma);
}
}
private void dataloginGet() {//创建获取登录保存的临时传参方法,并将该参数传给文本框,用来显示谁登陆了
tv_welcome.setText("ID:"+d1.getId());
}
private void initView() {//创建将对象与控件绑定方法
tv_welcome = findViewById(R.id.tv_welcome);
xuehao = findViewById(R.id.xuehao);
mima = findViewById(R.id.mima);
xingming = findViewById(R.id.xingming);
shoujihaoma = findViewById(R.id.shoujihaoma);
yongjiuzhuxiao = findViewById(R.id.yongjiuzhuxiao);
xiugaixinxi = findViewById(R.id.xiugaixinxi);
}
}
Register.java(注册活动类)
package com.campus.app;
import androidx.appcompat.app.AppCompatActivity;
import android.content.ContentValues;
import android.content.Intent;
import android.database.sqlite.SQLiteDatabase;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;
import com.campus.app.DB.MyDBOpenHelper;
public class Register extends AppCompatActivity {//注册
//创建对象
public EditText et_id_register,et_pwd_register,et_name_register,et_phone_register;
public Button bt_register_register;
private MyDBOpenHelper myDBOpenHelper; //定义数据库帮助类对象
private SQLiteDatabase db; //定义一个可以操作数据库的对象
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_register);
initView();//调用将对象与控件绑定方法
btnRegister();//调用当点击“注册”按钮的实现方法
}
private void btnRegister() {//创建当点击“注册”按钮的实现方法
bt_register_register.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
myDBOpenHelper = new MyDBOpenHelper(Register.this); //实例化数据库帮助类
db = myDBOpenHelper.getWritableDatabase();//打开数据库写权限
ContentValues cv = new ContentValues();//创建一个Content Values对象来保存一行数据
//将从各个输入框中的信息保存
cv.put("stu_id",et_id_register.getText().toString());
cv.put("passwd",et_pwd_register.getText().toString());
cv.put("name",et_name_register.getText().toString());
cv.put("phone",et_phone_register.getText().toString());
if(et_id_register.getText().toString().equals("") || et_pwd_register.getText().toString().equals("") || et_name_register.getText().toString().equals("") || et_phone_register.getText().toString().equals("")){
Toast.makeText(Register.this, "全部都需要填写", Toast.LENGTH_SHORT).show();
}else {
db.insert("User",null,cv);//使用insert方法添加数据
Toast.makeText(Register.this, "注册成功", Toast.LENGTH_SHORT).show();//提示注册成功
//跳转到登录页面,关闭自身页面
startActivity(new Intent(Register.this,LogOn.class));
finish();
}
}
});
}
private void initView() {//创建将对象与控件绑定方法
et_id_register = findViewById(R.id.et_id_register);
et_pwd_register = findViewById(R.id.et_pwd_register);
et_name_register = findViewById(R.id.et_name_register);
et_phone_register = findViewById(R.id.et_phone_register);
bt_register_register = findViewById(R.id.bt_register_register);
}
}
Releaseidle.java(发布闲置活动类)
package com.campus.app;
import androidx.appcompat.app.AppCompatActivity;
import android.annotation.SuppressLint;
import android.content.ContentValues;
import android.content.Intent;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.Toast;
import com.campus.app.DB.MyDBOpenHelper;
public class Releaseidle extends AppCompatActivity {//发布闲置
//创建对象
private EditText r_shangpinid,r_shangpinmingcheng,r_shangpinjiage;
private Button r_fabuanniu;
private MyDBOpenHelper myDBOpenHelper; //定义数据库帮助类对象
private SQLiteDatabase db; //定义一个可以操作数据库的对象
Data_Login d1 = new Data_Login();//实例化用于获取登录保存的临时传参。这里使用用于主页个人中心的参数。
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_releaseidle);
initView();//调用将对象与控件绑定方法
btnFabu();//调用当点击“发布”按钮的实现方法
}
private void btnFabu() {//创建当点击“发布”按钮的实现方法
r_fabuanniu.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
myDBOpenHelper = new MyDBOpenHelper(Releaseidle.this); //实例化数据库帮助类
db = myDBOpenHelper.getWritableDatabase();//打开数据库写权限
ContentValues cv = new ContentValues();//创建一个Content Values对象来保存一行数据
//将从各个输入框中的信息保存
cv.put("_id",r_shangpinid.getText().toString());
cv.put("c_name",r_shangpinmingcheng.getText().toString());
cv.put("cr_name",d1.getId().toString());//将当前登录的姓名作为发布者姓名
cv.put("c_price",r_shangpinjiage.getText().toString());
//通过当前ID查得手机号
Cursor cursor = db.rawQuery("select * from User where stu_id =?", new String[]{d1.getId()});
if (cursor.moveToNext()){
@SuppressLint("Range") String pshoujihaoma = cursor.getString(cursor.getColumnIndex("phone"));//同上道理 这里表示手机号码
cv.put("c_phone",pshoujihaoma);//将手机号写入数据库
}
if(r_shangpinid.getText().toString().equals("") || r_shangpinmingcheng.getText().toString().equals("") || r_shangpinjiage.getText().toString().equals("")){
Toast.makeText(Releaseidle.this, "全部都需要填写", Toast.LENGTH_SHORT).show();
}else {
db.insert("commodity",null,cv);//使用insert方法添加数据
Toast.makeText(Releaseidle.this, "发布成功!可以前往闲置社区查看了!", Toast.LENGTH_SHORT).show();//提示注册成功
//关闭自身页面
finish();
}
}
});
}
private void initView() {//创建将对象与控件绑定的方法、
r_fabuanniu = findViewById(R.id.r_fabuanniu);
r_shangpinid = findViewById(R.id.r_shangpinid);
r_shangpinmingcheng = findViewById(R.id.r_shangpinmingcheng);
r_shangpinjiage = findViewById(R.id.r_shangpinjiage);
}
}
activity_deleteidle.xml(删除闲置页面布局)
activity_idle_community.xml(闲置社区页面布局)
activity_log_on.xml(登录页面布局)
activity_main.xml(用户登录成功后的页面布局)
activity_personal_center.java(个人中心页面布局)
activity_register.xml(注册页面布局)
activity_releaseidle.xml(发布闲置页面布局)
listview_css.xml(自定义每一个子列表的样式布局)
1.代码存在一些BUG
2.个人中心的修改信息功能没有写(添上即可)
3.没有上传图片和展示图片的功能(可以把选取的图片先转成base64格式再转成二进制存入数据库,读取时再通过二进制转base64再转成图片即可)
4.有有一些命名不规范,布局方面不是很美观