You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
git-test/src/main/java/net/micode/notes/model/WorkingNote.java

704 lines
21 KiB

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

/*
* Copyright (c) 2010-2011, The MiCode Open Source Community (www.micode.net)
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package net.micode.notes.model;
import android.appwidget.AppWidgetManager;
import android.content.ContentUris;
import android.content.Context;
import android.database.Cursor;
import android.text.TextUtils;
import android.util.Log;
import net.micode.notes.data.Notes;
import net.micode.notes.data.Notes.CallNote;
import net.micode.notes.data.Notes.DataColumns;
import net.micode.notes.data.Notes.DataConstants;
import net.micode.notes.data.Notes.NoteColumns;
import net.micode.notes.data.Notes.TextNote;
import net.micode.notes.tool.ResourceParser.NoteBgResources;
/**
* 小米便签的工作便签类
* 用于管理便签的编辑状态和设置
* 是便签编辑界面和数据库之间的桥梁
*/
public class WorkingNote {
/**
* 便签对象,用于处理便签的数据操作
*/
private Note mNote;
/**
* 便签ID
*/
private long mNoteId;
/**
* 便签内容
*/
private String mContent;
/**
* 便签模式0-普通模式1- checklist模式
*/
private int mMode;
/**
* 提醒日期
*/
private long mAlertDate;
/**
* 修改日期
*/
private long mModifiedDate;
/**
* 背景颜色ID
*/
private int mBgColorId;
/**
* 小部件ID
*/
private int mWidgetId;
/**
* 小部件类型
*/
private int mWidgetType;
/**
* 文件夹ID
*/
private long mFolderId;
/**
* 上下文对象
*/
private Context mContext;
/**
* 日志标签,用于在日志系统中标识本类的日志信息
*/
private static final String TAG = "WorkingNote";
/**
* 是否标记为删除
*/
private boolean mIsDeleted;
/**
* 便签设置变化监听器,用于监听便签设置的变化
*/
private NoteSettingChangedListener mNoteSettingStatusListener;
/**
* 便签锁定状态,标识便签是否被密码锁定
*/
private boolean mIsLocked;
/**
* 便签锁定密码,存储加密后的手势密码
*/
private String mLockPassword;
/**
* 密码类型,标识便签使用的密码类型
*/
private String mPasswordType;
/**
* 数字密码存储加密后的6位数字密码
*/
private String mNumericPassword;
/**
* 标题,便签的标题
*/
private String mTitle;
/**
* 数据投影数组,用于从数据库中查询便签数据
*/
public static final String[] DATA_PROJECTION = new String[] {
DataColumns.ID, // 数据ID
DataColumns.CONTENT, // 数据内容
DataColumns.MIME_TYPE, // 数据类型
DataColumns.DATA1, // 扩展数据1
DataColumns.DATA2, // 扩展数据2
DataColumns.DATA3, // 扩展数据3
DataColumns.DATA4, // 扩展数据4
};
/**
* 便签投影数组,用于从数据库中查询便签基本信息
*/
public static final String[] NOTE_PROJECTION = new String[] {
NoteColumns.PARENT_ID, // 父文件夹ID
NoteColumns.ALERTED_DATE, // 提醒日期
NoteColumns.BG_COLOR_ID, // 背景颜色ID
NoteColumns.WIDGET_ID, // 小部件ID
NoteColumns.WIDGET_TYPE, // 小部件类型
NoteColumns.MODIFIED_DATE, // 修改日期
NoteColumns.IS_LOCKED, // 锁定状态
NoteColumns.LOCK_PASSWORD, // 锁定密码
NoteColumns.PASSWORD_TYPE, // 密码类型
NoteColumns.NUMERIC_PASSWORD, // 数字密码
NoteColumns.TITLE // 标题
};
/**
* 数据投影列索引
*/
private static final int DATA_ID_COLUMN = 0; // 数据ID列索引
private static final int DATA_CONTENT_COLUMN = 1; // 数据内容列索引
private static final int DATA_MIME_TYPE_COLUMN = 2; // 数据类型列索引
private static final int DATA_MODE_COLUMN = 3; // 数据模式列索引
/**
* 便签投影列索引
*/
private static final int NOTE_PARENT_ID_COLUMN = 0; // 父文件夹ID列索引
private static final int NOTE_ALERTED_DATE_COLUMN = 1; // 提醒日期列索引
private static final int NOTE_BG_COLOR_ID_COLUMN = 2; // 背景颜色ID列索引
private static final int NOTE_WIDGET_ID_COLUMN = 3; // 小部件ID列索引
private static final int NOTE_WIDGET_TYPE_COLUMN = 4; // 小部件类型列索引
private static final int NOTE_MODIFIED_DATE_COLUMN = 5; // 修改日期列索引
private static final int NOTE_IS_LOCKED_COLUMN = 6; // 锁定状态列索引
private static final int NOTE_LOCK_PASSWORD_COLUMN = 7; // 锁定密码列索引
private static final int NOTE_PASSWORD_TYPE_COLUMN = 8; // 密码类型列索引
private static final int NOTE_NUMERIC_PASSWORD_COLUMN = 9; // 数字密码列索引
private static final int NOTE_TITLE_COLUMN = 10; // 标题列索引
/**
* 构造方法,创建一个新的便签
* @param context 上下文对象
* @param folderId 文件夹ID新便签将存储在此文件夹中
*/
private WorkingNote(Context context, long folderId) {
mContext = context;
mAlertDate = 0; // 初始化为没有提醒
mModifiedDate = System.currentTimeMillis(); // 初始化修改时间为当前时间
mFolderId = folderId; // 设置文件夹ID
mNote = new Note(); // 创建便签对象
mNoteId = 0; // 新便签ID为0
mIsDeleted = false; // 初始化为未删除
mMode = 0; // 初始化为普通模式
mWidgetType = Notes.TYPE_WIDGET_INVALIDE; // 初始化为无效小部件类型
}
/**
* 构造方法,加载一个已存在的便签
* @param context 上下文对象
* @param noteId 便签ID
* @param folderId 文件夹ID
*/
private WorkingNote(Context context, long noteId, long folderId) {
mContext = context;
mNoteId = noteId; // 设置便签ID
mFolderId = folderId; // 设置文件夹ID
mIsDeleted = false; // 初始化为未删除
mNote = new Note(); // 创建便签对象
loadNote(); // 加载便签数据
}
/**
* 加载便签的基本信息
* @throws IllegalArgumentException 当找不到指定ID的便签时抛出
*/
private void loadNote() {
// 查询便签基本信息
Cursor cursor = mContext.getContentResolver().query(
ContentUris.withAppendedId(Notes.CONTENT_NOTE_URI, mNoteId), NOTE_PROJECTION, null,
null, null);
if (cursor != null) {
if (cursor.moveToFirst()) {
// 从游标中获取便签信息
mFolderId = cursor.getLong(NOTE_PARENT_ID_COLUMN);
mBgColorId = cursor.getInt(NOTE_BG_COLOR_ID_COLUMN);
mWidgetId = cursor.getInt(NOTE_WIDGET_ID_COLUMN);
mWidgetType = cursor.getInt(NOTE_WIDGET_TYPE_COLUMN);
mAlertDate = cursor.getLong(NOTE_ALERTED_DATE_COLUMN);
mModifiedDate = cursor.getLong(NOTE_MODIFIED_DATE_COLUMN);
mIsLocked = cursor.getInt(NOTE_IS_LOCKED_COLUMN) > 0;
mLockPassword = cursor.getString(NOTE_LOCK_PASSWORD_COLUMN);
mPasswordType = cursor.getString(NOTE_PASSWORD_TYPE_COLUMN);
mNumericPassword = cursor.getString(NOTE_NUMERIC_PASSWORD_COLUMN);
mTitle = cursor.getString(NOTE_TITLE_COLUMN);
}
cursor.close();
} else {
Log.e(TAG, "No note with id:" + mNoteId);
throw new IllegalArgumentException("Unable to find note with id " + mNoteId);
}
loadNoteData(); // 加载便签详细数据
}
/**
* 加载便签的详细数据
* @throws IllegalArgumentException 当找不到指定ID的便签数据时抛出
*/
private void loadNoteData() {
// 查询便签详细数据
Cursor cursor = mContext.getContentResolver().query(Notes.CONTENT_DATA_URI, DATA_PROJECTION,
DataColumns.NOTE_ID + "=?", new String[] {
String.valueOf(mNoteId)
}, null);
if (cursor != null) {
if (cursor.moveToFirst()) {
do {
String type = cursor.getString(DATA_MIME_TYPE_COLUMN);
if (DataConstants.NOTE.equals(type)) {
// 文本便签数据
mContent = cursor.getString(DATA_CONTENT_COLUMN);
mMode = cursor.getInt(DATA_MODE_COLUMN);
mNote.setTextDataId(cursor.getLong(DATA_ID_COLUMN));
} else if (DataConstants.CALL_NOTE.equals(type)) {
// 通话记录便签数据
mNote.setCallDataId(cursor.getLong(DATA_ID_COLUMN));
} else {
Log.d(TAG, "Wrong note type with type:" + type);
}
} while (cursor.moveToNext());
}
cursor.close();
} else {
Log.e(TAG, "No data with id:" + mNoteId);
throw new IllegalArgumentException("Unable to find note's data with id " + mNoteId);
}
}
/**
* 创建一个空便签
* @param context 上下文对象
* @param folderId 文件夹ID
* @param widgetId 小部件ID
* @param widgetType 小部件类型
* @param defaultBgColorId 默认背景颜色ID
* @return 空便签对象
*/
public static WorkingNote createEmptyNote(Context context, long folderId, int widgetId,
int widgetType, int defaultBgColorId) {
WorkingNote note = new WorkingNote(context, folderId);
note.setBgColorId(defaultBgColorId);
note.setWidgetId(widgetId);
note.setWidgetType(widgetType);
return note;
}
/**
* 加载指定ID的便签
* @param context 上下文对象
* @param id 便签ID
* @return 加载的便签对象
*/
public static WorkingNote load(Context context, long id) {
return new WorkingNote(context, id, 0);
}
/**
* 保存便签
* @return 保存是否成功
*/
public synchronized boolean saveNote() {
if (isWorthSaving()) {
// 如果便签不存在于数据库中,创建新便签
if (!existInDatabase()) {
if ((mNoteId = Note.getNewNoteId(mContext, mFolderId)) == 0) {
Log.e(TAG, "Create new note fail with id:" + mNoteId);
return false;
}
}
// 同步便签数据到数据库
mNote.syncNote(mContext, mNoteId);
/**
* 如果便签关联了小部件,更新小部件内容
*/
if (mWidgetId != AppWidgetManager.INVALID_APPWIDGET_ID
&& mWidgetType != Notes.TYPE_WIDGET_INVALIDE
&& mNoteSettingStatusListener != null) {
mNoteSettingStatusListener.onWidgetChanged();
}
return true;
} else {
return false;
}
}
/**
* 检查便签是否存在于数据库中
* @return 如果便签ID大于0则返回true否则返回false
*/
public boolean existInDatabase() {
return mNoteId > 0;
}
/**
* 检查便签是否值得保存
* @return 如果便签值得保存则返回true否则返回false
*/
private boolean isWorthSaving() {
// 以下情况不保存:
// 1. 便签被标记为删除
// 2. 便签不存在于数据库中且内容为空
// 3. 便签存在于数据库中但没有被修改
if (mIsDeleted || (!existInDatabase() && TextUtils.isEmpty(mContent))
|| (existInDatabase() && !mNote.isLocalModified())) {
return false;
} else {
return true;
}
}
/**
* 设置便签设置变化监听器
* @param l 监听器对象
*/
public void setOnSettingStatusChangedListener(NoteSettingChangedListener l) {
mNoteSettingStatusListener = l;
}
/**
* 设置提醒日期
* @param date 提醒日期
* @param set 是否设置提醒
*/
public void setAlertDate(long date, boolean set) {
if (date != mAlertDate) {
mAlertDate = date;
mNote.setNoteValue(NoteColumns.ALERTED_DATE, String.valueOf(mAlertDate));
}
// 通知监听器提醒日期变化
if (mNoteSettingStatusListener != null) {
mNoteSettingStatusListener.onClockAlertChanged(date, set);
}
}
/**
* 标记便签为删除或恢复删除
* @param mark 是否标记为删除
*/
public void markDeleted(boolean mark) {
mIsDeleted = mark;
// 如果便签关联了小部件,通知监听器小部件变化
if (mWidgetId != AppWidgetManager.INVALID_APPWIDGET_ID
&& mWidgetType != Notes.TYPE_WIDGET_INVALIDE && mNoteSettingStatusListener != null) {
mNoteSettingStatusListener.onWidgetChanged();
}
}
/**
* 设置背景颜色ID
* @param id 背景颜色ID
*/
public void setBgColorId(int id) {
if (id != mBgColorId) {
mBgColorId = id;
// 通知监听器背景颜色变化
if (mNoteSettingStatusListener != null) {
mNoteSettingStatusListener.onBackgroundColorChanged();
}
mNote.setNoteValue(NoteColumns.BG_COLOR_ID, String.valueOf(id));
}
}
/**
* 设置便签模式普通模式或checklist模式
* @param mode 模式0-普通模式1-checklist模式
*/
public void setCheckListMode(int mode) {
if (mMode != mode) {
// 通知监听器模式变化
if (mNoteSettingStatusListener != null) {
mNoteSettingStatusListener.onCheckListModeChanged(mMode, mode);
}
mMode = mode;
mNote.setTextData(TextNote.MODE, String.valueOf(mMode));
}
}
/**
* 设置小部件类型
* @param type 小部件类型
*/
public void setWidgetType(int type) {
if (type != mWidgetType) {
mWidgetType = type;
mNote.setNoteValue(NoteColumns.WIDGET_TYPE, String.valueOf(mWidgetType));
}
}
/**
* 设置小部件ID
* @param id 小部件ID
*/
public void setWidgetId(int id) {
if (id != mWidgetId) {
mWidgetId = id;
mNote.setNoteValue(NoteColumns.WIDGET_ID, String.valueOf(mWidgetId));
}
}
/**
* 设置便签内容
* @param text 便签内容
*/
public void setWorkingText(String text) {
if (!TextUtils.equals(mContent, text)) {
mContent = text;
mNote.setTextData(DataColumns.CONTENT, mContent);
}
}
/**
* 将便签转换为通话记录便签
* @param phoneNumber 电话号码
* @param callDate 通话日期
*/
public void convertToCallNote(String phoneNumber, long callDate) {
mNote.setCallData(CallNote.CALL_DATE, String.valueOf(callDate));
mNote.setCallData(CallNote.PHONE_NUMBER, phoneNumber);
mNote.setNoteValue(NoteColumns.PARENT_ID, String.valueOf(Notes.ID_CALL_RECORD_FOLDER));
}
/**
* 检查便签是否有提醒
* @return 如果有提醒则返回true否则返回false
*/
public boolean hasClockAlert() {
return (mAlertDate > 0 ? true : false);
}
/**
* 获取便签内容
* @return 便签内容
*/
public String getContent() {
return mContent;
}
/**
* 获取提醒日期
* @return 提醒日期
*/
public long getAlertDate() {
return mAlertDate;
}
/**
* 获取修改日期
* @return 修改日期
*/
public long getModifiedDate() {
return mModifiedDate;
}
/**
* 获取背景颜色资源ID
* @return 背景颜色资源ID
*/
public int getBgColorResId() {
return NoteBgResources.getNoteBgResource(mBgColorId);
}
/**
* 获取背景颜色ID
* @return 背景颜色ID
*/
public int getBgColorId() {
return mBgColorId;
}
/**
* 获取标题背景资源ID
* @return 标题背景资源ID
*/
public int getTitleBgResId() {
return NoteBgResources.getNoteTitleBgResource(mBgColorId);
}
/**
* 获取便签模式
* @return 便签模式0-普通模式1-checklist模式
*/
public int getCheckListMode() {
return mMode;
}
/**
* 获取便签ID
* @return 便签ID
*/
public long getNoteId() {
return mNoteId;
}
/**
* 获取文件夹ID
* @return 文件夹ID
*/
public long getFolderId() {
return mFolderId;
}
/**
* 获取小部件ID
* @return 小部件ID
*/
public int getWidgetId() {
return mWidgetId;
}
/**
* 获取小部件类型
* @return 小部件类型
*/
public int getWidgetType() {
return mWidgetType;
}
/**
* 设置便签锁定状态
* @param locked 是否锁定
*/
public void setLocked(boolean locked) {
if (mIsLocked != locked) {
mIsLocked = locked;
mNote.setNoteValue(NoteColumns.IS_LOCKED, String.valueOf(locked ? 1 : 0));
}
}
/**
* 检查便签是否锁定
* @return 是否锁定
*/
public boolean isLocked() {
return mIsLocked;
}
/**
* 设置锁定密码
* @param password 加密后的密码
*/
public void setLockPassword(String password) {
if (!TextUtils.equals(mLockPassword, password)) {
mLockPassword = password;
mNote.setNoteValue(NoteColumns.LOCK_PASSWORD, password);
}
}
/**
* 获取锁定密码
* @return 加密后的密码
*/
public String getLockPassword() {
return mLockPassword;
}
/**
* 设置密码类型
* @param type 密码类型 ("gesture" 或 "numeric")
*/
public void setPasswordType(String type) {
if (!TextUtils.equals(mPasswordType, type)) {
mPasswordType = type;
mNote.setNoteValue(NoteColumns.PASSWORD_TYPE, type);
}
}
/**
* 获取密码类型
* @return 密码类型
*/
public String getPasswordType() {
return mPasswordType;
}
/**
* 设置数字密码
* @param password 加密后的数字密码
*/
public void setNumericPassword(String password) {
if (!TextUtils.equals(mNumericPassword, password)) {
mNumericPassword = password;
mNote.setNoteValue(NoteColumns.NUMERIC_PASSWORD, password);
}
}
/**
* 获取数字密码
* @return 加密后的数字密码
*/
public String getNumericPassword() {
return mNumericPassword;
}
/**
* 设置标题
* @param title 标题内容
*/
public void setTitle(String title) {
if (!TextUtils.equals(mTitle, title)) {
mTitle = title;
mNote.setNoteValue(NoteColumns.TITLE, title);
}
}
/**
* 获取标题
* @return 标题内容
*/
public String getTitle() {
return mTitle;
}
/**
* 便签设置变化监听器接口
* 用于监听便签设置的变化,如背景颜色、提醒时间、小部件等
*/
public interface NoteSettingChangedListener {
/**
* 当便签背景颜色变化时调用
*/
void onBackgroundColorChanged();
/**
* 当用户设置提醒时间时调用
* @param date 提醒日期
* @param set 是否设置提醒
*/
void onClockAlertChanged(long date, boolean set);
/**
* 当用户从便签小部件创建便签时调用
*/
void onWidgetChanged();
/**
* 当在checklist模式和普通模式之间切换时调用
* @param oldMode 切换前的模式
* @param newMode 切换后的模式
*/
void onCheckListModeChanged(int oldMode, int newMode);
}
}