Android小项目——简易备忘录的实现

简易备忘录主要实现功能类似手机默认备忘录,可以对备忘录目录进行增添和删除。在编辑页面,可以显示当前时间,编辑备忘录标题,备忘录内容,设置时间提醒,插入图片等


文章目录

    • Android小项目——简易备忘录的实现
  • 前言
  • 一、主界面UI及功能
    • 主要功能介绍
    • 主界面的xml代码
    • 主界面的java代码
  • 二、新建备忘录页面
    • 主要功能介绍
    • xml代码
    • java代码
  • 三、编辑已保存备忘录页面
    • 主要功能介绍
    • xml代码
    • JAVA代码
  • 四、数据存储
  • 五、实体类——Memo
  • 总结


前言

简易备忘录主要实现功能类似手机默认备忘录,可以对备忘录目录进行增添和删除。在编辑页面,可以显示当前时间,编辑备忘录标题,备忘录内容,设置时间提醒,插入图片等


一、主界面UI及功能

主要功能介绍

  • 单击加号图标可以新建一个备忘录并跳转到编辑页面
  • 单击备忘录列表中的子项,可以进入已保存备忘录页面对备忘录内容进行修改
  • 长按备忘录列表中的子项,可以对该条备忘录进行选择性删除
    Android小项目——简易备忘录_第1张图片

主界面的xml代码

            

主界面的java代码

package test_5;import androidx.appcompat.app.AppCompatActivity;import androidx.recyclerview.widget.LinearLayoutManager;import androidx.recyclerview.widget.RecyclerView;import android.app.AlertDialog;import android.content.ContentResolver;import android.content.ContentUris;import android.content.ContentValues;import android.content.DialogInterface;import android.content.Intent;import android.database.Cursor;import android.database.sqlite.SQLiteDatabase;import android.net.Uri;import android.os.Bundle;import android.provider.CalendarContract;import android.provider.SyncStateContract;import android.util.Log;import android.view.View;import android.widget.Button;import android.widget.EditText;import android.widget.ImageView;import android.widget.Toast;import com.example.test.R;import org.litepal.crud.DataSupport;import org.litepal.exceptions.DataSupportException;import org.litepal.tablemanager.Connector;import java.util.ArrayList;import java.util.Iterator;import java.util.List;import butterknife.BindView;import butterknife.ButterKnife;import butterknife.OnClick;import static com.example.test.R.id.img_add;public class MainActivity extends AppCompatActivity {         private ArrayList <Integer> memoId = new ArrayList<>();    private List<Memo> mMemoList;    @BindView(R.id.img_add)    ImageView mAddImage;    @BindView(R.id.memo_list)    RecyclerView mDataList;    private static final String TAG = "MainActivity";    private MemoAdapter mMemoDataAdapter;    private String mTitle;    private String mBody;    private String mCreateTime;    private String mValues;    private String mModifyTime;    private String mIsTipsChecked;    //设置点击事件,点击图片跳转至编辑页面    @OnClick({     R.id.img_add})    public void onClicked() {             Intent intent = new Intent(MainActivity.this, EditActivity.class);        startActivity(intent);    }    //点击item,编辑已有内容的备忘录    @Override    protected void onCreate(Bundle savedInstanceState) {             super.onCreate(savedInstanceState);        setContentView(R.layout.main_activity);      ButterKnife.bind(this);        initView();        initData();        initEvent();    }    //初始化数据    private void initData() {             //获取数据库里的内容        mMemoList = new ArrayList<>();        mMemoList = DataSupport.findAll(Memo.class);        for (Memo memo: mMemoList) {                 Memo mMemo = new Memo();            int id = memo.getId();            mMemo.setId(id);            memoId.add(id);            mMemo.setTitle(memo.getTitle());            mMemo.setText(memo.getText());            mMemo.setCreateTime(memo.getCreateTime());            mMemo.setTipsChecked(memo.isTipsChecked());        }        mMemoDataAdapter.setData(mMemoList);    }    private void initEvent() {             //点击图标跳转到编辑页面        mAddImage.setOnClickListener(new View.OnClickListener() {                 @Override            public void onClick(View v) {                     Intent intent = new Intent(MainActivity.this, EditActivity.class);                startActivity(intent);            }        });        //点击item跳转到编辑页面        mMemoDataAdapter.setOnItemClickLinstener(new MemoAdapter.OnItemClickLinstener() {                 @Override            public void onClick(int position, String title, String body, boolean tipsChecked) {                     Toast.makeText(MainActivity.this, "clicked..." + position, Toast.LENGTH_SHORT).show();                Intent intent = new Intent(MainActivity.this, AmendActivity.class);                //将数据显示在AmendActivity中                Bundle bundle = new Bundle();                bundle.putInt(Constants.MEMO_ID, position + 1);                bundle.putString(Constants.MEMO_TITLE, title);                bundle.putString(Constants.MEMO_BODY, body);                bundle.putBoolean(Constants.MEMO_NEED_TIPS, tipsChecked);                intent.putExtras(bundle);                startActivity(intent);            }        });        //长按item删除        mMemoDataAdapter.setOnItemLongClickLinstener(new MemoAdapter.OnItemLongClickListener() {                 @Override            public void onLongClick(int position, String title, String body) {                     Toast.makeText(MainActivity.this, "long click", Toast.LENGTH_SHORT).show();                //提示dialog                Memo mMemo = new Memo();                mMemo.setTitle(title);                mMemo.setText(body);                Integer currentId = memoId.get(position);                mMemo.setId(currentId);                showDialog(position, mMemo);            }        });    }//    提示dialog是否删除该记录    private void showDialog(final int position, final Memo record) {             AlertDialog.Builder dialog = new AlertDialog.Builder(MainActivity.this);        dialog.setTitle("提示:");        dialog.setMessage("是否删除当前记录(添加的提醒事件将会同时被删除)");        dialog.setPositiveButton("删除", new DialogInterface.OnClickListener() {                 @Override            public void onClick(DialogInterface dialog, int which) {                     //删除数据库中的记录                doDelete(position, record);            }        });        dialog.setNegativeButton("取消", new DialogInterface.OnClickListener() {                 @Override            public void onClick(DialogInterface dialog, int which) {                     //停留在当前页面                Toast.makeText(MainActivity.this, "已取消删除", Toast.LENGTH_SHORT).show();            }        });        dialog.show();    }    //删除数据库中的记录    // 同时删除提醒事件    public void doDelete(int position, Memo record) {             int currentMemoId = record.getId();        Log.d(TAG, "currente memo id  is " + currentMemoId);        Log.d(TAG, "currente memo position  is " + position);        //memo.db删除数据        DataSupport.deleteAll(Memo.class,  "id = ?",  "currentMemoId");        //列表中删除该记录        mMemoDataAdapter.removeItem(position);        //判断是否删除提醒事件        boolean tipsChecked = record.isTipsChecked();        Log.d(TAG, "tipsChecked" + tipsChecked);        if (tipsChecked) {                 //删除提醒事件            //可以获取到备忘录的title和body            String deleteTitle = record.getTitle();            //根据title和body查询calendar中的id            queryPosition(deleteTitle);        }        //更新数据/ui        mDataList.post(new Runnable() {                 @Override            public void run() {                     mMemoDataAdapter.notifyDataSetChanged();            }        });    }    private void queryPosition(String deleteTitle) {             //遍历calendar的数据库来找到对应memo的id        //查询事件        ContentResolver contentResolver = getContentResolver();        Uri uri = Uri.parse("content://com.android.calendar/events");        Cursor cursor = contentResolver.query(uri, new String[]{     CalendarContract.Events._ID}, CalendarContract.Events.TITLE + "=" + deleteTitle, null, null, null);        String[] columnNames = cursor.getColumnNames();        while (cursor.moveToNext()) {                 for (String columnName : columnNames) {                     mValues = cursor.getString(cursor.getColumnIndex(columnName));                Log.d(TAG, columnName + "==" + mValues);            }        }        long deleteEventId = Integer.parseInt(mValues);        Log.d(TAG, "deleteEventId is " + deleteEventId);        cursor.close();        //根据ID删除calendar表中的数据        if (deleteEventId != 0) {                 Uri deleteEventUri = ContentUris.withAppendedId(Uri.parse("content://com.android.calendar/events"), deleteEventId);            getContentResolver().delete(deleteEventUri, null, null);        }    }    //初始化控件    private void initView() {             //数据列表        mDataList = findViewById(R.id.memo_list);        //recyclerview的基本设置        LinearLayoutManager linearLayoutManager = new LinearLayoutManager(this, RecyclerView.VERTICAL, false);        linearLayoutManager.setStackFromEnd(true);        linearLayoutManager.setReverseLayout(true);        mDataList.setLayoutManager(linearLayoutManager);        mMemoDataAdapter = new MemoAdapter();        mDataList.setAdapter(mMemoDataAdapter);        //创建数据库        Connector.getDatabase();    }}

二、新建备忘录页面

主要功能介绍

  • 单击返回图标可以返回主界面
  • 在标题输入框可以输入备忘录标题
  • 在内容输入区域可以输入备忘录内容
  • 点击图片图标可以进行图片插入(此功能目前有bug,点击即程序闪退)
  • 点击“是否设置提醒”的checkbox,则可以设置备忘录提醒的日期和时间
  • 点击保存按钮即可对备忘录内容进行保存,并跳转到主界面
  • 点击清空按钮即可清空备忘录内容
    页面布局:Android小项目——简易备忘录_第2张图片

xml代码

代码如下(示例):

<?xml version="1.0" encoding="utf-8"?>                                                                                                                                                                                                                            

java代码

package test_5;import androidx.annotation.NonNull;import androidx.annotation.RequiresApi;import androidx.appcompat.app.AppCompatActivity;import android.Manifest;import android.app.AlertDialog;import android.app.DatePickerDialog;import android.app.TimePickerDialog;import android.content.ContentResolver;import android.content.ContentValues;import android.content.DialogInterface;import android.content.Intent;import android.content.pm.PackageManager;import android.database.Cursor;import android.net.Uri;import android.os.Build;import android.os.Bundle;import android.provider.CalendarContract;import android.util.Log;import android.view.View;import android.widget.Button;import android.widget.CheckBox;import android.widget.CompoundButton;import android.widget.DatePicker;import android.widget.EditText;import android.widget.ImageView;import android.widget.TextView;import android.widget.TimePicker;import android.widget.Toast;import com.bumptech.glide.Glide;import com.example.test.R;import org.litepal.tablemanager.Connector;import java.util.Calendar;import java.util.Date;import java.util.List;import java.util.TimeZone;import butterknife.BindView;import butterknife.ButterKnife;import static test_5.MyTimeFormat.getTimeStr;import static test_5.MyTimeFormat.myDateFormat;public class EditActivity extends AppCompatActivity implements ImagePickerConfig.OnImageSelectedFinishLisenter {         @BindView(R.id.btn_back)    ImageView mBackBtn;    @BindView(R.id.content)    EditText mContextEv;    @BindView(R.id.btn_save)    Button mSaveBtn;    @BindView(R.id.btn_clean)    Button mCleanBtn;    @BindView(R.id.edit)    EditText mMomeTitle;    @BindView(R.id.edit_time)    TextView mEditTime;    @BindView(R.id.memo_is_time)    CheckBox mIsTip;    @BindView(R.id.check_data)    TextView mTipsDate;    @BindView(R.id.check_time)    TextView mTipsTime;    @BindView(R.id.insert_image_btn)    View mInsertImageBtn;    @BindView(R.id.image_picker_one)    ImageView mImageViewOne;    @BindView(R.id.image_picker_two)    ImageView mImageViewTwo;    @BindView(R.id.image_picker_three)    ImageView mImageViewThree;    private static final String TAG = "EditActivity";    private static final int PREMISSION_REQUEST_CODE = 1;    private static final int MAX_SELECTED_COUNT = 3;    private Integer year;    private Integer month;    private Integer dayOfMonth;    private Integer hour;    private Integer minute;    private DatePickerDialog dialogDate;    private TimePickerDialog dialogTime;    private String mCreateDate;    private String mDispCreateDate;    private int mYear;    private int mMonth;    private int mDay;    private Calendar mCalendar;    private int mHour;    private int mMinute;    private int mSecond;    private boolean mTipIsChecked;    //动态获取权限时的请求码    private static final int PERMISSION_REQUEST_CODE = 1;    private long mEventId;    private int mMyHourOfDay;    private int mMyMinute;    private int mMyDayOfMonth;    private int mMyYear;    private int mMyMonth;    private String mTitle;    private String mBody;    public int mSelectedSize;    private ImagePickerConfig mPickerConfig;    @RequiresApi(api = Build.VERSION_CODES.M)    @Override    protected void onCreate(Bundle savedInstanceState) {             super.onCreate(savedInstanceState);        setContentView(R.layout.edit_activity);        ButterKnife.bind(this);        checkCalendarPermission();        checkImagePermission();        getDate();        initCalendar();        initView();        initEvent();        initPickerConfig();    }    private void initPickerConfig() {             mPickerConfig = ImagePickerConfig.getInstance();        mPickerConfig.setMaxSelectedCount(MAX_SELECTED_COUNT);        mPickerConfig.setOnImageSelectedFinishLisenter(this);    }    //检查是否有读写相册权限    @RequiresApi(api = Build.VERSION_CODES.M)    private void checkImagePermission() {             int readExStroagePresmission = checkSelfPermission(Manifest.permission.READ_EXTERNAL_STORAGE);        Log.d(TAG, "readExStroagePresmission" + readExStroagePresmission);        if (readExStroagePresmission == PackageManager.PERMISSION_GRANTED) {                 //有权限        } else {                 //没有权限,需要去申请权限            requestPermissions(new String[]{     Manifest.permission.READ_EXTERNAL_STORAGE}, PREMISSION_REQUEST_CODE);        }    }    //查询日历,验证URL    @RequiresApi(api = Build.VERSION_CODES.M)    private void queryCalender() {             ContentResolver contentResolver = getContentResolver();        Uri uri = CalendarContract.Calendars.CONTENT_URI;        if (checkSelfPermission(Manifest.permission.READ_CALENDAR) != PackageManager.PERMISSION_GRANTED) {                 return;        }        Cursor query = contentResolver.query(uri, null, null, null, null);        String[] columnNames = query.getColumnNames();        for (String columnName : columnNames) {                 Log.d(TAG, "columnName -- > " + columnName);        }        query.close();    }    //创建日历用户    private void initCalendar() {             TimeZone timeZone = TimeZone.getDefault();        ContentValues value = new ContentValues();        value.put(CalendarContract.Calendars.NAME, "yy");        value.put(CalendarContract.Calendars.ACCOUNT_NAME, "mygmailaddress@gmail.com");        value.put(CalendarContract.Calendars.ACCOUNT_TYPE, "com.android.exchange");        value.put(CalendarContract.Calendars.CALENDAR_DISPLAY_NAME, "mytt");        value.put(CalendarContract.Calendars.VISIBLE, 1);        value.put(CalendarContract.Calendars.CALENDAR_COLOR, -9206951);        value.put(CalendarContract.Calendars.CALENDAR_ACCESS_LEVEL, CalendarContract.Calendars.CAL_ACCESS_OWNER);        value.put(CalendarContract.Calendars.SYNC_EVENTS, 1);        value.put(CalendarContract.Calendars.CALENDAR_TIME_ZONE, timeZone.getID());        value.put(CalendarContract.Calendars.OWNER_ACCOUNT, "mygmailaddress@gmail.com");        value.put(CalendarContract.Calendars.CAN_ORGANIZER_RESPOND, 0);        Uri calendarUri = CalendarContract.Calendars.CONTENT_URI;        calendarUri = calendarUri.buildUpon()                .appendQueryParameter(CalendarContract.CALLER_IS_SYNCADAPTER, "true").appendQueryParameter(CalendarContract.Calendars.ACCOUNT_NAME, "mygmailaddress@gmail.com").appendQueryParameter(CalendarContract.Calendars.ACCOUNT_TYPE, "com.android.exchange").build();        getContentResolver().insert(calendarUri, value);    }    //检查是否获取日历的读写权限    @RequiresApi(api = Build.VERSION_CODES.M)    private void checkCalendarPermission() {             int writePermission = checkSelfPermission(Manifest.permission.WRITE_CALENDAR);        int readPermission = checkSelfPermission(Manifest.permission.READ_CALENDAR);        if (writePermission == PackageManager.PERMISSION_GRANTED && readPermission == PackageManager.PERMISSION_GRANTED) {                 //有读写日历的权限            Log.d(TAG, "has permission...");        } else {                 //没有权限            //需要获取权限            Log.d(TAG, "no permission...");            requestPermissions(new String[]{     Manifest.permission.READ_CALENDAR, Manifest.permission.WRITE_CALENDAR}, PERMISSION_REQUEST_CODE);        }    }    //判断请求码结果来决定是否能成功获取权限    @Override    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {             if (requestCode == PERMISSION_REQUEST_CODE) {                 //权限检查的结果            if (grantResults.length == 3 &&                    grantResults[0] == PackageManager.PERMISSION_GRANTED &&                    grantResults[1] == PackageManager.PERMISSION_GRANTED &&                    grantResults[2] == PackageManager.PERMISSION_GRANTED) {                     //此时有权限                Toast.makeText(this, "有权限", Toast.LENGTH_SHORT).show();            } else {                     //此时没有权限                //可以给出一个提示:                //用户点击确定后重新调用请求权限                //用户点击取消后就不再获取权限了                finish();                Toast.makeText(this, "没有权限", Toast.LENGTH_SHORT).show();            }        }    }    //获取当前时间    private void getDate() {             mCalendar = Calendar.getInstance();        mYear = mCalendar.get(Calendar.YEAR);        mMonth = mCalendar.get(Calendar.MONTH);        mDay = mCalendar.get(Calendar.DAY_OF_MONTH);        mHour = mCalendar.get(java.util.Calendar.HOUR_OF_DAY);        mMinute = mCalendar.get(java.util.Calendar.MINUTE);        mSecond = mCalendar.get(java.util.Calendar.SECOND);    }    //点击事件    private void initEvent() {             //返回        mBackBtn.setOnClickListener(new View.OnClickListener() {                 @Override            public void onClick(View v) {                     //获取输入内容                String title = mMomeTitle.getText().toString().trim();                String body = mContextEv.getText().toString().trim();                if (!title.equals("") && !body.equals("")) {                         //如果标题,内容都不为空,则显示dialog                    showDialog(title, body);                } else {                         //如果都为空则返回                    startIntent();                }            }        });        //保存        mSaveBtn.setOnClickListener(new View.OnClickListener() {                 @RequiresApi(api = Build.VERSION_CODES.M)            @Override            public void onClick(View v) {                     //获取输入内容                mTitle = mMomeTitle.getText().toString().trim();                mBody = mContextEv.getText().toString().trim();                Log.d(TAG, "title is " + mTitle);                Log.d(TAG, "body is " + mBody);                if (canDoSave(mTitle, mBody)) {                         saveInToDb(mTitle, mBody);                    if (mTipIsChecked) {                             Toast.makeText(EditActivity.this, "保存成功", Toast.LENGTH_SHORT).show();                        setTipIntoCalendar();                        startIntent();                    } else {                             startIntent();                    }                }            }        });        mCleanBtn.setOnClickListener(new View.OnClickListener() {                 @Override            public void onClick(View v) {                     mContextEv.setText(" ");            }        });        //是否设置提醒事件,checkbox是否被选中        mIsTip.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {                 @Override            public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {                     mTipIsChecked = isChecked;                Log.d(TAG, "mChecked" + isChecked);                if (isChecked) {                         //选择设置提醒的话就选择时间                    mTipsDate.setVisibility(View.VISIBLE);                } else {                         //无法设置提醒                    mTipsDate.setVisibility(View.GONE);                    mTipsTime.setVisibility(View.GONE);                }            }        });        //选择事件日期        mTipsDate.setOnClickListener(new View.OnClickListener() {                 @Override            public void onClick(View v) {                     Toast.makeText(EditActivity.this, "1111", Toast.LENGTH_SHORT).show();                //选择事件时间                showDatePickerDialog();                //设置time为可见                mTipsTime.setVisibility(View.VISIBLE);            }        });        //选择提醒时间        mTipsTime.setOnClickListener(new View.OnClickListener() {                 @Override            public void onClick(View v) {                     //选择时间                showTimePickerDialog();            }        });        //插入图片被点击了,跳转到picker界面        mInsertImageBtn.setOnClickListener(new View.OnClickListener() {                 @Override            public void onClick(View v) {                     startActivity(new Intent(EditActivity.this, PickerActivity.class));            }        });}    //设置提醒时间    private void showTimePickerDialog() {             TimePickerDialog.OnTimeSetListener listener = new TimePickerDialog.OnTimeSetListener() {                 @Override            public void onTimeSet(TimePicker view, int hourOfDay, int minute) {                     //记录下当前选择的时间,设置到提醒事件中去                mMyHourOfDay = hourOfDay;                mMyMinute = minute;                mTipsTime.setText(hourOfDay + ":" + minute);            }        };        TimePickerDialog dialog = new TimePickerDialog(this, 0, listener, mHour, mMinute, true);        dialog.show();    }    //设置事件日期    private void showDatePickerDialog() {             DatePickerDialog.OnDateSetListener listener = new DatePickerDialog.OnDateSetListener() {                 @Override            public void onDateSet(DatePicker view, int year, int month, int dayOfMonth) {                     //显示设置的会见                //记录下当前所选的日子,设置到提醒事件中去                mMyYear = year;                mMyMonth = ++month;                mMyDayOfMonth = dayOfMonth;                mTipsDate.setText(year + "-" + mMyMonth + "-" + dayOfMonth);            }        };        DatePickerDialog datePickerDialog = new DatePickerDialog(this, 0, listener, mYear, mMonth, mDay);        datePickerDialog.show();    }    //将内容保存到数据库    private void saveInToDb(String title, String body) {             Memo mMemo = new Memo();        mMemo.setTitle(title);        mMemo.setText(body);        mMemo.setCreateTime(mDispCreateDate);        mMemo.setTipsChecked(mTipIsChecked);        mMemo.save();    }    //向日历中插入提醒事件    @RequiresApi(api = Build.VERSION_CODES.M)    private void setTipIntoCalendar() {             //插入事件        //前面查询出来的        long calID = 1;        //时间创建        java.util.Calendar beginTime = java.util.Calendar.getInstance();        //Month value is 0-based. e.g., 0 for January.        //开始时间        int month = mMyMonth - 1;        beginTime.set(mMyYear, month, mMyDayOfMonth, mMyHourOfDay, mMyMinute);        long startMillis = beginTime.getTimeInMillis();        java.util.Calendar endTime = java.util.Calendar.getInstance();        //结束时间        endTime.set(mMyYear, month, mMyDayOfMonth, mMyHourOfDay, mMyMinute + 45);        long endMillis = endTime.getTimeInMillis();        Log.d(TAG, "beginTime -- > " + mMyYear + "-" + month + "-" + mMyDayOfMonth + "-" + mMyHourOfDay + "-" + mMyMinute);        Log.d(TAG, "endTime -- > " + mMyYear + "-" + month + "-" + mMyDayOfMonth + "-" + mMyHourOfDay + "-" + mMyMinute + 45);        //准备好插入事件数据库的内容        ContentResolver cr = getContentResolver();        ContentValues values = new ContentValues();        //开始时间        values.put(CalendarContract.Events.DTSTART, startMillis);        //结束时间        values.put(CalendarContract.Events.DTEND, endMillis);        //标题        values.put(CalendarContract.Events.TITLE, mTitle);        //描述        values.put(CalendarContract.Events.DESCRIPTION, mBody);        //日历ID        values.put(CalendarContract.Events.CALENDAR_ID, calID);        //时间时区        String timeZone = TimeZone.getDefault().getID();        Log.d(TAG, "time zone -- > " + timeZone);        values.put(CalendarContract.Events.EVENT_TIMEZONE, timeZone);        if (checkSelfPermission(Manifest.permission.WRITE_CALENDAR) != PackageManager.PERMISSION_GRANTED) {                 return;        }        Uri uri = cr.insert(CalendarContract.Events.CONTENT_URI, values);        Log.d(TAG, "insert result --- > " + uri);        //插入提醒        //获取当前插入事件的ID        String strUri = String.valueOf(uri);        String currentId = strUri.replace("content://com.android.calendar/events/", "");        mEventId = Integer.valueOf(currentId);        ContentValues remindValues = new ContentValues();        //15分钟前进行提醒        remindValues.put(CalendarContract.Reminders.MINUTES, 15);        remindValues.put(CalendarContract.Reminders.EVENT_ID, mEventId);        remindValues.put(CalendarContract.Reminders.METHOD, CalendarContract.Reminders.METHOD_ALERT);        Uri reminduri = cr.insert(CalendarContract.Reminders.CONTENT_URI, remindValues);        Log.d(TAG, "result uri -- > " + reminduri);    }    //判断能否保存    private boolean canDoSave(String title, String body) {             //用于判断能否进行保存动作        //true:此时说明可以保存内容,保存内容至数据库中        //flase:不能保存,需要写内容        boolean flag = true;        if (title.equals("")) {                 Toast.makeText(this, "标题不能为空", Toast.LENGTH_SHORT).show();            flag = false;        }        if (title.length() > 10) {                 Toast.makeText(this, "标题过长", Toast.LENGTH_SHORT).show();            flag = false;        }        if (body.length() > 200) {                 Toast.makeText(this, "内容过长", Toast.LENGTH_SHORT).show();            flag = false;        }        if (body.equals("")) {                 Toast.makeText(this, "内容不能为空", Toast.LENGTH_SHORT).show();            flag = false;        }        if (mTipIsChecked) {                 //如果选中“添加提醒事件”,就需要将日期时间填写完整才可以            if (mTipsDate.getText().toString().equals("请选择日期") || mTipsTime.getText().toString().equals("请选择时间")) {                     Toast.makeText(this, "日期/时间不能为空", Toast.LENGTH_SHORT).show();                flag = false;            }        }        return flag;    }    //显示dialog    private void showDialog(final String title, final String body) {             AlertDialog.Builder dialog = new AlertDialog.Builder(EditActivity.this);        dialog.setTitle("提示:");        dialog.setMessage("是否保存当前内容");        dialog.setPositiveButton("保存", new DialogInterface.OnClickListener() {                 @RequiresApi(api = Build.VERSION_CODES.M)            @Override            public void onClick(DialogInterface dialog, int which) {                     Log.d(TAG, "保存");                //将数据保存至数据库,设置提醒事件                if (canDoSave(title, body)) {                         saveInToDb(title, body);                    if (mTipIsChecked) {                             setTipIntoCalendar();                        startIntent();                    } else {                             startIntent();                    }                }            }        });        dialog.setNegativeButton("取消", new DialogInterface.OnClickListener() {                 @Override            public void onClick(DialogInterface dialog, int which) {                     //停留在当前页面                Log.d(TAG, "取消");            }        });        dialog.show();    }    //页面跳转    private void startIntent() {             Intent intent = new Intent(EditActivity.this, MainActivity.class);        startActivity(intent);    }    //初始化操作    private void initView() {             //初始化当前时间        Date date = new Date(System.currentTimeMillis());        //创建的时间,存入数据库,数据库根据时间先后显示列表        mCreateDate = myDateFormat(date, DateFormat.NORMAL_TIME);        mDispCreateDate = getTimeStr(date);        if (mEditTime.getText().length() != 0) {                 mEditTime.setText(mDispCreateDate);        }        dialogDate = null;        dialogTime = null;        hour = 0;        minute = 0;        year = 0;        month = 0;        dayOfMonth = 0;        //初始化数据库        Connector.getDatabase();    }    @Override    public void onSelectedFinish(List<ImageItem> selectedResult) {             //所选择的图片列表在该处回来了        for (ImageItem imageItem : selectedResult) {                 Log.d(TAG, "image item is " + imageItem);        }        mSelectedSize = selectedResult.size();        Log.d(TAG, "selected size is " + mSelectedSize);        mPickerConfig.setSelectResult(selectedResult);        mPickerConfig.setSeletcedSize(mSelectedSize);        setPics(selectedResult);    }    private void setPics(List<ImageItem> selectedResult) {             switch (mSelectedSize) {                 case 1:                Glide.with(mImageViewOne.getContext()).load(selectedResult.get(0).getPath()).into(mImageViewOne);                mImageViewOne.setVisibility(View.VISIBLE);                mImageViewTwo.setVisibility(View.GONE);                mImageViewThree.setVisibility(View.GONE);                break;            case 2:                Glide.with(mImageViewOne.getContext()).load(selectedResult.get(0).getPath()).into(mImageViewOne);                Glide.with(mImageViewTwo.getContext()).load(selectedResult.get(1).getPath()).into(mImageViewTwo);                mImageViewOne.setVisibility(View.VISIBLE);                mImageViewTwo.setVisibility(View.VISIBLE);                mImageViewThree.setVisibility(View.GONE);                break;            case 3:                Glide.with(mImageViewOne.getContext()).load(selectedResult.get(0).getPath()).into(mImageViewOne);                Glide.with(mImageViewTwo.getContext()).load(selectedResult.get(1).getPath()).into(mImageViewTwo);                Glide.with(mImageViewThree.getContext()).load(selectedResult.get(2).getPath()).into(mImageViewThree);                mImageViewOne.setVisibility(View.VISIBLE);                mImageViewTwo.setVisibility(View.VISIBLE);                mImageViewThree.setVisibility(View.VISIBLE);                break;        }    }}

三、编辑已保存备忘录页面

主要功能介绍

与编辑页面功能一致
Android小项目——简易备忘录_第3张图片

xml代码

<?xml version="1.0" encoding="utf-8"?>                                                                                                                                                                                                                                

JAVA代码

package test_5;import androidx.annotation.NonNull;import androidx.annotation.RequiresApi;import androidx.appcompat.app.AlertDialog;import androidx.appcompat.app.AppCompatActivity;import android.Manifest;import android.app.DatePickerDialog;import android.app.TimePickerDialog;import android.app.slice.Slice;import android.content.ContentResolver;import android.content.ContentValues;import android.content.DialogInterface;import android.content.Intent;import android.content.IntentFilter;import android.content.pm.PackageManager;import android.content.pm.ProviderInfo;import android.database.Cursor;import android.graphics.ColorSpace;import android.net.Uri;import android.os.Build;import android.os.Bundle;import android.provider.CalendarContract;import android.provider.SyncStateContract;import android.util.Log;import android.view.View;import android.widget.Button;import android.widget.CheckBox;import android.widget.CompoundButton;import android.widget.DatePicker;import android.widget.EditText;import android.widget.ImageView;import android.widget.TextView;import android.widget.TimePicker;import android.widget.Toast;import com.bumptech.glide.Glide;import com.example.test.R;import org.litepal.crud.DataSupport;import org.litepal.tablemanager.Connector;import java.text.SimpleDateFormat;import java.util.Calendar;import java.util.Date;import java.util.GregorianCalendar;import java.util.List;import butterknife.BindView;import butterknife.ButterKnife;import static test_5.MyTimeFormat.getTimeStr;public class AmendActivity extends AppCompatActivity implements ImagePickerConfig.OnImageSelectedFinishLisenter{         @BindView(R.id.amend_btn_back)    ImageView mBackBtn;    @BindView(R.id.amend_edit_time)    TextView mCurrentTime;    @BindView(R.id.amend_edit)    EditText mTitle;    @BindView(R.id.amend_content)    EditText mContent;    @BindView(R.id.amend_memo_is_time)    CheckBox mCheckBox;    @BindView(R.id.amend_check_data)    TextView mDataPicker;    @BindView(R.id.amend_check_time)    TextView mTimePicker;    @BindView(R.id.amend_btn_save)    Button mSaveBtn;    @BindView(R.id.amend_btn_clean)    Button mCleanBtn;    @BindView(R.id.amend_insert_image_btn)    View mInsertImage;    @BindView(R.id.amend_pic_one)    ImageView mPicOne;    @BindView(R.id.amend_pic_two)    ImageView mPicTwo;    @BindView(R.id.amend_pic_three)    ImageView mPicThree;    private static final int PERMISSION_REQUEST_CODE = 2;    private static final int MAX_SELECTED_COUNT = 3;    private static final int PREMISSION_REQUEST_CODE = 1;    private Calendar mCalendar;    private int mMinute;    private int mHour;    private int mDay;    private int mMonth;    private int mSecond;    private int mYear;    private DatePickerDialog dialogDate;    private TimePickerDialog dialogTime;    private Integer year;    private Integer month;    private Integer dayOfMonth;    private Integer hour;    private Integer minute;    private int mMyHourOfDay;    private int mMyMinute;    private int mMyDayOfMonth;    private int mMyYear;    private int mMyMonth;    private boolean mCurrentCheckResult;    private Memo mMemo;    private boolean mIsNeedTips;    private boolean isChanged = false;    private ImagePickerConfig mPickerConfig;        private String mEditDate;    private static final String TAG = "AmendActivity";    @RequiresApi(api = Build.VERSION_CODES.M)    @Override    protected void onCreate(Bundle savedInstanceState) {             super.onCreate(savedInstanceState);        setContentView(R.layout.amend_activity);        ButterKnife.bind(this);        checkCalendarPremission();        checkImagePremission();        initConfig();        getDate();        initView();        initData();        initEvent();    }    /**     * 检查是否获取相册的读写权限     * 安卓6.0以上需要动态获取权限     */@RequiresApi(api = Build.VERSION_CODES.M)private void checkImagePremission() {         int readExStroagePermission = checkSelfPermission(Manifest.permission.READ_EXTERNAL_STORAGE);    Log.d(TAG, "readExStroagePermission" + readExStroagePermission);    if (readExStroagePermission == PackageManager.PERMISSION_GRANTED ) {             //有权限    } else {             //没有权限        requestPermissions(new String[] {     Manifest.permission.READ_EXTERNAL_STORAGE}, PERMISSION_REQUEST_CODE);    }}private void initConfig() {         mPickerConfig = ImagePickerConfig.getInstance();    mPickerConfig.setMaxSelectedCount(MAX_SELECTED_COUNT);    mPickerConfig.setOnImageSelectedFinishLisenter((ImagePickerConfig.OnImageSelectedFinishLisenter) this);}            //返回    private void initEvent() {             mBackBtn.setOnClickListener(new View.OnClickListener() {                 @Override            public void onClick(View v) {                     //输入获取内容                String title = mTitle.getText().toString().trim();                String body = mContent.getText().toString().trim();                if (!title.equals("") && !body.equals("")) {                         showBackDialog(title, body);                } else {                         startIntent();                }            }        });        //保存        mSaveBtn.setOnClickListener(new View.OnClickListener() {                 @Override            public void onClick(View v) {                     //获取输入内容                String title = mTitle.getText().toString().trim();                String body = mContent.getText().toString().trim();                Log.d(TAG, "title is " + title);                Log.d(TAG, "body is " + body);                if (canDoSave(title, body)) {                         updateDb(title, body);                    startIntent();                }            }        });        //清空        mCleanBtn.setOnClickListener(new View.OnClickListener() {                 @Override            public void onClick(View v) {                     mContent.setText(" ");            }        });        //监听checkBox的变化        mCheckBox.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {                 @Override            public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {                     isChanged = true;                mCurrentCheckResult = isChecked;                //如果被选中                if (mCurrentCheckResult) {                         mDataPicker.setVisibility(View.VISIBLE);                    mTimePicker.setVisibility(View.VISIBLE);                } else {                         //如果没有被选中                    mDataPicker.setVisibility(View.GONE);                    mTimePicker.setVisibility(View.GONE);                }            }        });        //选择事件日期        mDataPicker.setOnClickListener(new View.OnClickListener() {                 @Override            public void onClick(View v) {                     Toast.makeText(AmendActivity.this, "选择时间" , Toast.LENGTH_SHORT).show();                //选择事件时间                showDataPickerDialog();            }        });        //选择提醒时间        mTimePicker.setOnClickListener(new View.OnClickListener() {                 @Override            public void onClick(View v) {                     //选择时间                showTimePickerDialog();            }        });        //插入图片        mInsertImage.setOnClickListener(new View.OnClickListener() {                 @Override            public void onClick(View v) {                     startActivity(new Intent(AmendActivity.this, PickerActivity.class));            }        });    }    //指定日历的相关操作,增删改    private void doCalendarEvent() {             if (isChanged) {                 //如果状态改变了            if (mCurrentCheckResult) {                     //当前选中了,insert                Log.d(TAG, "do insert");            } else {                     //当前没选中,delete                Log.d(TAG, "do delete");            }        } else {                 //如果状态没改变            if (mIsNeedTips) {                     //需要事件提醒,update                Log.d(TAG, "do update");            } else {                     //不需要事件提醒,nothing                Log.d(TAG, "do nothing");            }        }    }    //设置提醒事件    private void showTimePickerDialog() {             TimePickerDialog.OnTimeSetListener listener = new TimePickerDialog.OnTimeSetListener() {                 @Override            public void onTimeSet(TimePicker view, int hourOfDay, int minute) {                     mMyHourOfDay = hourOfDay;                mMyMinute = minute;                mTimePicker.setText(hourOfDay + ":" + minute);            }        };        TimePickerDialog dialog = new TimePickerDialog(this, 0, listener, mHour, mMinute, true);        dialog.show();    }    //设置事件日期    private void showDataPickerDialog() {             DatePickerDialog.OnDateSetListener listener = new DatePickerDialog.OnDateSetListener() {                 @Override            public void onDateSet(DatePicker view, int year, int month, int dayOfMonth) {                     //                mMyYear = year;                mMyMonth = ++month;                mMyDayOfMonth = dayOfMonth;                mDataPicker.setText(year + "-" +mMyMonth + "-" + dayOfMonth);            }        };        DatePickerDialog datePickerDialog = new DatePickerDialog(this, 0, listener, mYear, mMonth, mDay);        datePickerDialog.show();    }    //能否保存    private boolean canDoSave(String title, String body) {             //用于判断能否保存动作        //true:可以保存内容,保存内容至数据库中        //false:不能保存,需要写内容        boolean flag = true;        if (title.equals("")) {                 flag = false;        }        if (title.length() >10) {                 flag = false;        }        if (body.length() > 200) {                 flag = false;        }        if (body.equals("")) {                 flag = false;        }        if (mCurrentCheckResult) {                 //如果选中“添加提醒事件”,就需要将日期时间填写完整            if (mDataPicker.getText().toString().equals("") || mTimePicker.getText().toString().equals("")) {                     flag = false;            }        }        return flag;    }    //显示dialog    private void showBackDialog(final String title, final String body) {             AlertDialog.Builder dialog = new AlertDialog.Builder(AmendActivity.this);        dialog.setTitle("提示:");        dialog.setMessage("是否保存当前内容");        dialog.setPositiveButton("保存", new DialogInterface.OnClickListener() {                 @Override            public void onClick(DialogInterface dialog, int which) {                     //将更新保存至数据库中                if (canDoSave(title, body)) {                         updateDb(title, body);                    startIntent();                }            }        });        dialog.setNegativeButton("取消", new DialogInterface.OnClickListener() {                 @Override            public void onClick(DialogInterface dialog, int which) {                     //跳转至首页                startIntent();            }        });        dialog.show();    }    //将修改内容保存到数据库中    private void updateDb(String title, String body) {             ContentValues values = new ContentValues();        values.put(Constants.MEMO_TITLE, title);        values.put(Constants.MEMO_BODY, body);        values.put(Constants.MEMO_MODIFY_TIME, mEditDate);        values.put(Constants.MEMO_NEED_TIPS, mCurrentCheckResult);        Log.d(TAG, "mCurrentCheckResult" + mCurrentCheckResult);        DataSupport.update(Memo.class, values, mMemo.getId());        Toast.makeText(this, "修改成功!", Toast.LENGTH_SHORT).show();    }    //从MainActivity点击到该页面,将数据回显    private void initData() {             Intent intent = this.getIntent();        Bundle bundle = intent.getExtras();        //获取bundle中的数据        if (bundle != null) {                 String memoTitle = intent.getStringExtra(Constants.MEMO_TITLE);            String memoContent = intent.getStringExtra(Constants.MEMO_BODY);            int memoId = intent.getIntExtra(Constants.MEMO_ID, 0);            mIsNeedTips = intent.getBooleanExtra(Constants.MEMO_NEED_TIPS, false);            //设置数据            mMemo = new Memo();            mMemo.setTitle(memoTitle);            mMemo.setText(memoContent);            mMemo.setId(memoId);            mMemo.setTipsChecked(mIsNeedTips);            if (mIsNeedTips) {                     //如果设置了提醒事件,就将日期和时间显现出来                mDataPicker.setVisibility(View.VISIBLE);                mTimePicker.setVisibility(View.VISIBLE);                mCheckBox.setChecked(mIsNeedTips);                setDateAndTime(memoTitle);            }            mContent.setText(memoContent);            mContent.setText(memoTitle);        }    }    //根据title获取到设置提醒的日期和时间    private void setDateAndTime(String memoTitle) {             ContentResolver contentResolver = getContentResolver();        Uri uri = Uri.parse("content://com.android.calendar/events");        Cursor cursor = contentResolver.query(uri, new String[]{     CalendarContract.Events.DTSTART}, CalendarContract.Events.TITLE + "=" + memoTitle, null, null, null);        String[] columnNames = cursor.getColumnNames();        while (cursor.moveToNext()) {                 for (String columnName : columnNames) {                     String startTimeStr = cursor.getString(cursor.getColumnIndex(columnName));                //将秒数转化为日期                getTipsDate(startTimeStr);                Log.d(TAG, columnName + "==" + startTimeStr);            }        }    }    //通过数据库中设置的时间获取提醒事件的时间    private void getTipsDate(String startTimeStr) {             long time = Long.parseLong(startTimeStr);        Date date = new Date(time);        GregorianCalendar gregorianCalendar = new GregorianCalendar();        gregorianCalendar.setTime(date);        //将日期格式进行分割:为date+time        SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");        String currentTime = dateFormat.format(gregorianCalendar.getTime());        Log.d(TAG, "currentTime is" +currentTime);        String[] dateAndTime = currentTime.split(" ");        String tipsDate = dateAndTime[0];        String tipsTime = dateAndTime[1];        Log.d(TAG, "tipsDate" + tipsDate);        Log.d(TAG, "tipsTime" + tipsTime);        mDataPicker.setText(tipsDate);        mTimePicker.setText(tipsTime);    }    //初始化当前时间    private void initView() {             Date date = new Date(System.currentTimeMillis());        //创建的时间,存入数据库,数据库根据时间先后显示列表        mEditDate = getTimeStr(date);        if (mCurrentTime.getText().length() != 0) {                 mCurrentTime.setText(mEditDate);        }        dialogDate = null;        dialogTime = null;        hour = 0;        minute = 0;        year = 0;        month = 0;        dayOfMonth = 0;        //初始化数据库        Connector.getDatabase();        //获取到之前选择的图片并显示出来        List<ImageItem> selectResult = mPickerConfig.getSelectResult();        int seletcedSize = mPickerConfig.getSeletcedSize();        if (selectResult != null) {                 for (ImageItem imageItem : selectResult) {                     Log.d(TAG, "image item is " + imageItem.getPath());            }            Log.d(TAG, "selected size is " + seletcedSize);        }        if (selectResult != null) {                 //显示图片            switch (seletcedSize) {                     case 1:                    Glide.with(mPicOne.getContext()).load(selectResult.get(0).getPath()).into(mPicOne);                    mPicOne.setVisibility(View.VISIBLE);                    mPicTwo.setVisibility(View.GONE);                    mPicThree.setVisibility(View.GONE);                    break;                case 2:                    Glide.with(mPicOne.getContext()).load(selectResult.get(0).getPath()).into(mPicOne);                    Glide.with(mPicTwo.getContext()).load(selectResult.get(1).getPath()).into(mPicTwo);                    mPicOne.setVisibility(View.VISIBLE);                    mPicTwo.setVisibility(View.VISIBLE);                    mPicThree.setVisibility(View.GONE);                    break;                case 3:                    Glide.with(mPicOne.getContext()).load(selectResult.get(0).getPath()).into(mPicOne);                    Glide.with(mPicTwo.getContext()).load(selectResult.get(1).getPath()).into(mPicTwo);                    Glide.with(mPicThree.getContext()).load(selectResult.get(2).getPath()).into(mPicThree);                    mPicOne.setVisibility(View.VISIBLE);                    mPicTwo.setVisibility(View.VISIBLE);                    mPicThree.setVisibility(View.VISIBLE);                    break;            }        } else {                 mPicOne.setVisibility(View.GONE);            mPicTwo.setVisibility(View.GONE);            mPicThree.setVisibility(View.GONE);        }    }    //页面跳转    private void startIntent() {             Intent intent = new Intent(AmendActivity.this, MainActivity.class);        startActivity(intent);    }    //检查是否有读写日历的权限    @RequiresApi(api = Build.VERSION_CODES.M)    private void checkCalendarPremission() {             int writePermission = checkSelfPermission(Manifest.permission.WRITE_CALENDAR);        int readPermission = checkSelfPermission(Manifest.permission.READ_CALENDAR);        if (writePermission == PackageManager.PERMISSION_GRANTED && readPermission == PackageManager.PERMISSION_GRANTED) {                 //有读写权限            Log.d(TAG, "has permission...");        } else  {                 //没有读写权限            Log.d(TAG, "no permission");            requestPermissions(new String[] {     Manifest.permission.READ_CALENDAR, Manifest.permission.WRITE_CALENDAR}, PERMISSION_REQUEST_CODE);        }    }    //判断请求码结果来决定是否能成功获得权限    @Override    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {             if (requestCode == PERMISSION_REQUEST_CODE) {                 if (grantResults.length == 3 &&            grantResults[0] ==PackageManager.PERMISSION_GRANTED &&            grantResults[1] ==PackageManager.PERMISSION_GRANTED &&            grantResults[2] ==PackageManager.PERMISSION_GRANTED) {                     Toast.makeText(this, "有权限", Toast.LENGTH_SHORT).show();            } else {                     //此时没有权限                finish();                Toast.makeText(this, "没有权限", Toast.LENGTH_SHORT).show();            }        }    }    //获取当前时间    private void getDate() {             mCalendar = Calendar.getInstance();        mYear = mCalendar.get(Calendar.YEAR);        mCalendar.get(Calendar.MONTH);        mDay = mCalendar.get(Calendar.DAY_OF_MONTH);        mHour = mCalendar.get(java.util.Calendar.HOUR_OF_DAY);        mMinute = mCalendar.get(java.util.Calendar.MINUTE);        mSecond = mCalendar.get(Calendar.SECOND);    }    @Override    public void onSelectedFinish(List<ImageItem> selectedResult) {             //所选择的图片列表在该处回来了        //设置图片        if (selectedResult != null) {                 setPics(selectedResult);        }    }    private void setPics(List<ImageItem> selectedResult) {             switch (selectedResult.size()) {                 case 1:                Glide.with(mPicOne.getContext()).load(selectedResult.get(0).getPath()).into(mPicOne);                mPicOne.setVisibility(View.VISIBLE);                mPicTwo.setVisibility(View.GONE);                mPicThree.setVisibility(View.GONE);                break;            case 2:                Glide.with(mPicOne.getContext()).load(selectedResult.get(0).getPath()).into(mPicOne);                Glide.with(mPicTwo.getContext()).load(selectedResult.get(1).getPath()).into(mPicTwo);                mPicOne.setVisibility(View.VISIBLE);                mPicTwo.setVisibility(View.VISIBLE);                mPicThree.setVisibility(View.GONE);                break;            case 3:                Glide.with(mPicOne.getContext()).load(selectedResult.get(0).getPath()).into(mPicOne);                Glide.with(mPicTwo.getContext()).load(selectedResult.get(1).getPath()).into(mPicTwo);                Glide.with(mPicThree.getContext()).load(selectedResult.get(2).getPath()).into(mPicThree);                mPicOne.setVisibility(View.VISIBLE);                mPicTwo.setVisibility(View.VISIBLE);                mPicThree.setVisibility(View.VISIBLE);                break;        }    }}

四、数据存储

备忘录数据存储采用系统内置的数据库SQLite,利用LitePal进行操作

五、实体类——Memo

package test_5;import org.litepal.crud.DataSupport;public class Memo extends DataSupport {         public Integer getId() {             return id;    }    public void setId(Integer id) {             this.id = id;    }    public String getTitle() {             return title;    }    public void setTitle(String title) {             this.title = title;    }    public String getText() {             return text;    }    public void setText(String text) {             this.text = text;    }    public Integer getImageId() {             return imageId;    }    public void setImageId(Integer imageId) {             this.imageId = imageId;    }    public String getCreateTime() {             return createTime;    }    public void setCreateTime(String createTime) {             this.createTime = createTime;    }    public boolean isTipsChecked() {             return isTipsChecked;    }    public void setTipsChecked(boolean tipsChecked) {             isTipsChecked = tipsChecked;    }    private Integer id;    private String title;    private String text;    private String createTime;    private boolean isTipsChecked;    private Integer imageId;}

总结

更多相关文章

  1. EventBus 《四》 事件的优先级及其EventBus Demo
  2. Android输入事件从读取到分发一:是谁在读取输入事件
  3. 屏蔽电信流氓广告造成的诡异的问题--Android WebView 长时间不能
  4. 认识一下Android 事件分发机制
  5. android click 和onTouch 事件处理机制
  6. Android 事件处理详解(一) —— 基于监听的事件处理 1
  7. android click 和onTouch 事件处理机制 (转)

随机推荐

  1. golang的编译器是什么
  2. golang 如何判断文件是否存在
  3. golang 管道线程安全吗
  4. golang的zap怎么使用
  5. golang 如何模块化
  6. golang调试工具有哪些?
  7. golang的slice如何去重
  8. golang判断map中指定key是否存在
  9. golang指针传递和值传递的区别是什么?
  10. golang的hashmap怎么扩容