/* * 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.gtask.data; // 声明包路径net.micode.notes.gtask.data import android.database.Cursor; // 导入android.database.Cursor类 import android.util.Log; // 导入android.util.Log类 import net.micode.notes.data.Notes; // 导入net.micode.notes.data.Notes类 import net.micode.notes.data.Notes.NoteColumns; // 导入net.micode.notes.data.Notes.NoteColumns类 import net.micode.notes.gtask.exception.ActionFailureException; // 导入net.micode.notes.gtask.exception.ActionFailureException类 import net.micode.notes.tool.GTaskStringUtils; // 导入net.micode.notes.tool.GTaskStringUtils类 import org.json.JSONException; // 导入org.json.JSONException类 import org.json.JSONObject; // 导入org.json.JSONObject类 import java.util.ArrayList; // 导入java.util.ArrayList类 public class TaskList extends Node { // 定义一个继承自Node的类TaskList private static final String TAG = TaskList.class.getSimpleName(); // 声明TAG常量并赋值 private int mIndex; // 声明整型变量mIndex private ArrayList mChildren; // 声明ArrayList类型变量mChildren public TaskList() { // 定义TaskList构造方法 super(); // 调用父类构造方法 mChildren = new ArrayList(); // 实例化mChildren为一个新的ArrayList mIndex = 1; // 将mIndex初始化为1 } public JSONObject getCreateAction(int actionId) { // 定义一个返回JSONObject类型的方法getCreateAction,参数为actionId JSONObject js = new JSONObject(); // 创建一个新的JSONObject对象 try { // 异常处理开始 // action_type js.put(GTaskStringUtils.GTASK_JSON_ACTION_TYPE, // 设置动作类型为创建 GTaskStringUtils.GTASK_JSON_ACTION_TYPE_CREATE); // action_id js.put(GTaskStringUtils.GTASK_JSON_ACTION_ID, actionId); // 设置动作ID // index js.put(GTaskStringUtils.GTASK_JSON_INDEX, mIndex); // 设置索引 // entity_delta JSONObject entity = new JSONObject(); // 创建实体变化的JSONObject对象 entity.put(GTaskStringUtils.GTASK_JSON_NAME, getName()); // 设置实体名 entity.put(GTaskStringUtils.GTASK_JSON_CREATOR_ID, "null"); // 设置创建者ID entity.put(GTaskStringUtils.GTASK_JSON_ENTITY_TYPE, // 设置实体类型 GTaskStringUtils.GTASK_JSON_TYPE_GROUP); js.put(GTaskStringUtils.GTASK_JSON_ENTITY_DELTA, entity); // 将实体变化添加到JSONObject中 } catch (JSONException e) { // 捕获JSONException异常 Log.e(TAG, e.toString()); // 输出错误日志 e.printStackTrace(); // 打印异常堆栈信息 throw new ActionFailureException("fail to generate tasklist-create jsonobject"); // 抛出ActionFailureException异常 } return js; // 返回JSONObject对象 } public JSONObject getUpdateAction(int actionId) { // 定义一个返回JSONObject类型的方法getUpdateAction,参数为actionId JSONObject js = new JSONObject(); // 创建一个新的JSONObject对象 try { // 异常处理开始 // action_type js.put(GTaskStringUtils.GTASK_JSON_ACTION_TYPE, // 设置动作类型为更新 GTaskStringUtils.GTASK_JSON_ACTION_TYPE_UPDATE); // action_id js.put(GTaskStringUtils.GTASK_JSON_ACTION_ID, actionId); // 设置动作ID // id js.put(GTaskStringUtils.GTASK_JSON_ID, getGid()); // 设置ID // entity_delta JSONObject entity = new JSONObject(); // 创建实体变化的JSONObject对象 entity.put(GTaskStringUtils.GTASK_JSON_NAME, getName()); // 设置实体名 entity.put(GTaskStringUtils.GTASK_JSON_DELETED, getDeleted()); // 设置是否已删除 js.put(GTaskStringUtils.GTASK_JSON_ENTITY_DELTA, entity); // 将实体变化添加到JSONObject中 } catch (JSONException e) { // 捕获JSONException异常 Log.e(TAG, e.toString()); // 输出错误日志 e.printStackTrace(); // 打印异常堆栈信息 throw new ActionFailureException("fail to generate tasklist-update jsonobject"); // 抛出ActionFailureException异常 } return js; // 返回JSONObject对象 } /** * 根据远程JSON设置内容 * @param js 远程JSON对象 */ public void setContentByRemoteJSON(JSONObject js) { if (js != null) { try { // id if (js.has(GTaskStringUtils.GTASK_JSON_ID)) { // 检查JSON对象中是否包含id字段 setGid(js.getString(GTaskStringUtils.GTASK_JSON_ID)); // 设置id属性值为JSON中id字段的值 } // last_modified if (js.has(GTaskStringUtils.GTASK_JSON_LAST_MODIFIED)) { // 检查JSON对象中是否包含last_modified字段 setLastModified(js.getLong(GTaskStringUtils.GTASK_JSON_LAST_MODIFIED)); // 设置last_modified属性值为JSON中last_modified字段的长整型值 } // name if (js.has(GTaskStringUtils.GTASK_JSON_NAME)) { // 检查JSON对象中是否包含name字段 setName(js.getString(GTaskStringUtils.GTASK_JSON_NAME)); // 设置name属性值为JSON中name字段的值 } } catch (JSONException e) { // 捕获JSON异常 Log.e(TAG, e.toString()); // 记录异常日志 e.printStackTrace(); // 打印异常堆栈信息 throw new ActionFailureException("fail to get tasklist content from jsonobject"); // 抛出自定义异常 } } } /** * 根据本地JSON设置内容 * @param js 本地JSON对象 */ public void setContentByLocalJSON(JSONObject js) { if (js == null || !js.has(GTaskStringUtils.META_HEAD_NOTE)) { // 如果JSON对象为空或者不包含META_HEAD_NOTE字段 Log.w(TAG, "setContentByLocalJSON: nothing is avaiable"); // 记录警告日志 } try { JSONObject folder = js.getJSONObject(GTaskStringUtils.META_HEAD_NOTE); // 获取JSON对象中的META_HEAD_NOTE字段作为文件夹对象 if (folder.getInt(NoteColumns.TYPE) == Notes.TYPE_FOLDER) { // 如果文件夹类型为普通类型 String name = folder.getString(NoteColumns.SNIPPET); // 获取文件夹名称 setName(GTaskStringUtils.MIUI_FOLDER_PREFFIX + name); // 设置name属性值为MIUI_FOLDER_PREFFIX和文件夹名称的组合 } else if (folder.getInt(NoteColumns.TYPE) == Notes.TYPE_SYSTEM) { // 如果文件夹类型为系统类型 if (folder.getLong(NoteColumns.ID) == Notes.ID_ROOT_FOLDER) // 如果文件夹ID为根目录ID setName(GTaskStringUtils.MIUI_FOLDER_PREFFIX + GTaskStringUtils.FOLDER_DEFAULT); // 设置name属性值为MIUI_FOLDER_PREFFIX和默认文件夹名称的组合 else if (folder.getLong(NoteColumns.ID) == Notes.ID_CALL_RECORD_FOLDER) // 如果文件夹ID为通话记录文件夹ID setName(GTaskStringUtils.MIUI_FOLDER_PREFFIX + GTaskStringUtils.FOLDER_CALL_NOTE); // 设置name属性值为MIUI_FOLDER_PREFFIX和通话记录文件夹名称的组合 else Log.e(TAG, "invalid system folder"); // 记录错误日志 } else { Log.e(TAG, "error type"); // 记录错误日志 } } catch (JSONException e) { // 捕获JSON异常 Log.e(TAG, e.toString()); // 记录异常日志 e.printStackTrace(); // 打印异常堆栈信息 } } /** * 从内容中获取本地JSON对象 * * @return 本地JSON对象 */ public JSONObject getLocalJSONFromContent() { try { JSONObject js = new JSONObject(); // 创建一个新的JSON对象 JSONObject folder = new JSONObject(); // 创建一个新的文件夹JSON对象 String folderName = getName(); // 获取任务名称 if (getName().startsWith(GTaskStringUtils.MIUI_FOLDER_PREFFIX)) { // 如果任务名称以MIUI_FOLDER_PREFFIX开头 folderName = folderName.substring(GTaskStringUtils.MIUI_FOLDER_PREFFIX.length(), folderName.length()); // 使用剩余的部分作为文件夹名称 } folder.put(NoteColumns.SNIPPET, folderName); // 将文件夹名称放入文件夹JSON对象中 if (folderName.equals(GTaskStringUtils.FOLDER_DEFAULT) || folderName.equals(GTaskStringUtils.FOLDER_CALL_NOTE)) { folder.put(NoteColumns.TYPE, Notes.TYPE_SYSTEM); // 如果文件夹名称为默认文件夹或通话记录文件夹,将文件夹类型设置为系统类型 } else { folder.put(NoteColumns.TYPE, Notes.TYPE_FOLDER); // 否则将文件夹类型设置为普通类型 } js.put(GTaskStringUtils.META_HEAD_NOTE, folder); // 将文件夹JSON对象放入本地JSON对象中 return js; // 返回本地JSON对象 } catch (JSONException e) { // 捕获JSON异常 Log.e(TAG, e.toString()); // 记录异常日志 e.printStackTrace(); // 打印异常堆栈信息 return null; // 返回空值 } } /** * 获取同步操作 * * @param c 游标 * @return 同步操作类型 */ public int getSyncAction(Cursor c) { try { if (c.getInt(SqlNote.LOCAL_MODIFIED_COLUMN) == 0) { // 没有本地更新 if (c.getLong(SqlNote.SYNC_ID_COLUMN) == getLastModified()) { // 双方都没有更新 return SYNC_ACTION_NONE; // 返回无操作 } else { // 应用远程到本地 return SYNC_ACTION_UPDATE_LOCAL; // 返回更新本地操作 } } else { // 验证gtask id if (!c.getString(SqlNote.GTASK_ID_COLUMN).equals(getGid())) { Log.e(TAG, "gtask id doesn't match"); // 记录错误日志 return SYNC_ACTION_ERROR; // 返回错误操作 } if (c.getLong(SqlNote.SYNC_ID_COLUMN) == getLastModified()) { // 仅本地修改 return SYNC_ACTION_UPDATE_REMOTE; // 返回更新远程操作 } else { // 对于文件夹冲突,只应用本地修改 return SYNC_ACTION_UPDATE_REMOTE; // 返回更新远程操作 } } } catch (Exception e) { // 捕获异常 Log.e(TAG, e.toString()); // 记录异常日志 e.printStackTrace(); // 打印异常堆栈信息 } return SYNC_ACTION_ERROR; // 返回错误操作 } /** * 获取子任务数量 * * @return 子任务数量 */ public int getChildTaskCount() { return mChildren.size(); // 返回子任务列表的大小 } /** * 添加子任务 * * @param task 要添加的子任务 * @return 是否成功添加子任务 */ public boolean addChildTask(Task task) { boolean ret = false; // 默认添加子任务失败 if (task != null && !mChildren.contains(task)) { ret = mChildren.add(task); // 将子任务添加到子任务列表中 if (ret) { // 需要设置前一个兄弟任务和父任务 task.setPriorSibling(mChildren.isEmpty() ? null : mChildren .get(mChildren.size() - 1)); // 设置前一个兄弟任务为当前子任务列表的最后一个任务(如果存在) task.setParent(this); // 设置父任务为当前任务 } } return ret; // 返回是否成功添加子任务 } /** * 添加子任务 * * @param task 要添加的子任务 * @param index 要添加的位置 * @return 是否成功添加子任务 */ public boolean addChildTask(Task task, int index) { if (index < 0 || index > mChildren.size()) { // 如果位置索引小于0或大于子任务列表的大小 Log.e(TAG, "add child task: invalid index"); // 记录错误日志 return false; // 返回添加失败 } int pos = mChildren.indexOf(task); // 获取任务在子任务列表中的位置 if (task != null && pos == -1) { // 如果任务不为空且不在列表中 mChildren.add(index, task); // 在指定位置添加任务 // update the task list Task preTask = null; Task afterTask = null; if (index != 0) preTask = mChildren.get(index - 1); if (index != mChildren.size() - 1) afterTask = mChildren.get(index + 1); task.setPriorSibling(preTask); // 设置前一个兄弟任务 if (afterTask != null) afterTask.setPriorSibling(task); // 设置后一个兄弟任务 } return true; // 返回添加成功 } /** * 移除子任务 * * @param task 要移除的子任务 * @return 是否成功移除子任务 */ public boolean removeChildTask(Task task) { boolean ret = false; // 默认移除子任务失败 int index = mChildren.indexOf(task); // 获取任务在子任务列表中的位置 if (index != -1) { // 如果任务在列表中 ret = mChildren.remove(task); // 从列表中移除任务 if (ret) { // reset prior sibling and parent task.setPriorSibling(null); // 重置前一个兄弟任务 task.setParent(null); // 重置父任务 // update the task list if (index != mChildren.size()) { mChildren.get(index).setPriorSibling( index == 0 ? null : mChildren.get(index - 1)); // 更新任务列表中其他任务的前一个兄弟任务 } } } return ret; // 返回是否成功移除子任务 } /** * 移动子任务到指定位置 * * @param task 要移动的子任务 * @param index 目标位置 * @return 是否成功移动子任务 */ public boolean moveChildTask(Task task, int index) { if (index < 0 || index >= mChildren.size()) { // 如果目标位置索引小于0或大于等于子任务列表的大小 Log.e(TAG, "move child task: invalid index"); // 记录错误日志 return false; // 返回移动失败 } int pos = mChildren.indexOf(task); // 获取任务在子任务列表中的位置 if (pos == -1) { // 如果任务不在列表中 Log.e(TAG, "move child task: the task should in the list"); // 记录错误日志 return false; // 返回移动失败 } if (pos == index) return true; return (removeChildTask(task) && addChildTask(task, index)); // 移除任务并添加到指定位置 } /** * 根据gid查找子任务 * * @param gid gid * @return 子任务 */ public Task findChildTaskByGid(String gid) { for (int i = 0; i < mChildren.size(); i++) { // 循环遍历子任务列表 Task t = mChildren.get(i); // 获取当前子任务 if (t.getGid().equals(gid)) { // 如果子任务的gid与指定的相同 return t; // 返回该子任务 } } return null; // 如果未找到匹配的子任务,则返回null } /** * 获取子任务在列表中的索引 * * @param task 子任务 * @return 索引 */ public int getChildTaskIndex(Task task) { return mChildren.indexOf(task); // 返回子任务在列表中的索引 } /** * 根据索引获取子任务 * * @param index 索引 * @return 子任务 */ public Task getChildTaskByIndex(int index) { if (index < 0 || index >= mChildren.size()) { // 如果索引小于0或大于等于子任务列表的大小 Log.e(TAG, "getTaskByIndex: invalid index"); // 记录错误日志 return null; // 返回null } return mChildren.get(index); // 返回对应索引处的子任务 } /** * 根据gid获取子任务 * * @param gid gid * @return 子任务 */ public Task getChilTaskByGid(String gid) { for (Task task : mChildren) { // 遍历子任务列表 if (task.getGid().equals(gid)) // 如果子任务的gid与指定的相同 return task; // 返回该子任务 } return null; // 如果未找到匹配的子任务,则返回null } /** * 获取子任务列表 * * @return 子任务列表 */ public ArrayList getChildTaskList() { return this.mChildren; // 返回子任务列表 } /** * 设置索引 * * @param index 索引 */ public void setIndex(int index) { this.mIndex = index; // 设置索引 } /** * 获取索引 * * @return 索引 */ public int getIndex() { return this.mIndex; // 返回索引 } }