From 90ca66e737155aef12a42ed2aa6f08f1e97016d0 Mon Sep 17 00:00:00 2001 From: lyy <627219260@qq.com> Date: Fri, 10 May 2024 19:42:03 +0800 Subject: [PATCH] =?UTF-8?q?=E7=B2=BE=E8=AF=BB=E6=B3=A8=E9=87=8A?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../net/micode/notes/ui/NoteEditActivity.java | 184 ++++++++++++------ 1 file changed, 125 insertions(+), 59 deletions(-) diff --git a/src/app/src/main/java/net/micode/notes/ui/NoteEditActivity.java b/src/app/src/main/java/net/micode/notes/ui/NoteEditActivity.java index 44975e4..9608127 100644 --- a/src/app/src/main/java/net/micode/notes/ui/NoteEditActivity.java +++ b/src/app/src/main/java/net/micode/notes/ui/NoteEditActivity.java @@ -73,7 +73,8 @@ import java.util.regex.Pattern; public class NoteEditActivity extends Activity implements OnClickListener, - NoteSettingChangedListener, OnTextViewChangeListener {//便签编辑活动 + NoteSettingChangedListener, OnTextViewChangeListener {//便签编辑activity + //继承了点击监听和两个自定义的监听 private class HeadViewHolder { public TextView tvModified; @@ -82,8 +83,8 @@ public class NoteEditActivity extends Activity implements OnClickListener, public TextView tvAlertDate; public ImageView ibSetBgColor; - } - + }//TextView是Android中用于显示文本的一个控件,ImageView是Android中用于显示图像的控件 + //使用Map实现数据存储 private static final Map sBgSelectorBtnsMap = new HashMap(); static { sBgSelectorBtnsMap.put(R.id.iv_bg_yellow, ResourceParser.YELLOW); @@ -91,7 +92,7 @@ public class NoteEditActivity extends Activity implements OnClickListener, sBgSelectorBtnsMap.put(R.id.iv_bg_blue, ResourceParser.BLUE); sBgSelectorBtnsMap.put(R.id.iv_bg_green, ResourceParser.GREEN); sBgSelectorBtnsMap.put(R.id.iv_bg_white, ResourceParser.WHITE); - } + }//put函数是将指定值和指定键相连 private static final Map sBgSelectorSelectionMap = new HashMap(); static { @@ -121,21 +122,26 @@ public class NoteEditActivity extends Activity implements OnClickListener, private static final String TAG = "NoteEditActivity"; private HeadViewHolder mNoteHeaderHolder; + //View: 这是Android SDK中的一个核心类,表示用户界面中的一个矩形区域,能够绘制和响应事件。 + // 基本上,一个 View 对象可以是一个按钮、一个文本字段、一个图片,或者其他任何可以出现在用户界面上的组件。 + private View mHeadViewPanel;//表头 - private View mHeadViewPanel; + private View mNoteBgColorSelector;//背景颜色 - private View mNoteBgColorSelector; + private View mFontSizeSelector;//标签字体 - private View mFontSizeSelector; + //EditText:这是Android SDK中的一个类,代表一个用户可以输入文本的文本框控件。它通常用于表单输入、搜索字段等。 + private EditText mNoteEditor;//文本编辑 - private EditText mNoteEditor; + private View mNoteEditorPanel;//文本编辑的控制板 - private View mNoteEditorPanel; - - private WorkingNote mWorkingNote; + private WorkingNote mWorkingNote;//对模板WorkingNote的初始化 + //SharedPreferences是Android提供的一个轻量级存储类,主要用于保存应用的一些常用配置,例如用户的偏好设置等。 + //它的本质是基于XML文件存储key-value键值对数据,并且提供了简单的API来读取和写入数据。 + //它的特点是简单、轻量,并且数据是持久的(即使应用被关闭或设备重启,数据也会保留) private SharedPreferences mSharedPrefs; - private int mFontSizeId; + private int mFontSizeId;//字体大小 private static final String PREFERENCE_FONT_SIZE = "pref_font_size"; @@ -144,16 +150,22 @@ public class NoteEditActivity extends Activity implements OnClickListener, public static final String TAG_CHECKED = String.valueOf('\u221A'); public static final String TAG_UNCHECKED = String.valueOf('\u25A1'); + //LinearLayout: 这是Android SDK中的一个布局类,用于创建线性布局。线性布局可以水平或垂直地排列其子视图。 private LinearLayout mEditTextList; - private String mUserQuery; + private String mUserQuery;//存储用户的查询或输入。 + + //Pattern: 这是Java的java.util.regex包中的一个类,用于表示一个正则表达式的编译表示形式 private Pattern mPattern; @Override + //onCreate():在Activity创建时调用,通常做一些初始化设置 + //savedInstanceState是一个Bundle对象,它包含Activity之前保存的状态信息 protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); + //设置Activity的UI布局。R.layout.note_edit是一个资源引用,它指向一个XML布局文件,该文件定义了Activity的UI。 this.setContentView(R.layout.note_edit); - + //判断是否是首次创建,不是首次创建从Intent中获取数据 if (savedInstanceState == null && !initActivityState(getIntent())) { finish(); return; @@ -165,6 +177,14 @@ public class NoteEditActivity extends Activity implements OnClickListener, * Current activity may be killed when the memory is low. Once it is killed, for another time * user load this activity, we should restore the former state */ + /* + 当Android设备的内存不足时,系统会杀死一些不再处于前台的Activity,以释放内存供其他应用或系统进程使用。 + 这是Android系统的一种内存管理机制,确保设备能够流畅运行。 + 当某个Activity被系统杀死后,如果用户再次尝试加载或进入这个Activity开发者应该确保Activity能够恢复其之前的状态。 + 通常通过使用onSaveInstanceState和onRestoreInstanceState方法来实现。 + 当Activity即将被杀死时,onSaveInstanceState方法会被调用,开发者可以在这里保存需要恢复的状态。 + 用户再次进入这个Activity时用onRestoreInstanceState恢复保存的状态 + */ @Override protected void onRestoreInstanceState(Bundle savedInstanceState) { super.onRestoreInstanceState(savedInstanceState); @@ -184,26 +204,34 @@ public class NoteEditActivity extends Activity implements OnClickListener, * If the user specified the {@link Intent#ACTION_VIEW} but not provided with id, * then jump to the NotesListActivity */ + //如果用户指定了{@link Intent#ACTION_VIEW}但未提供id,则跳转到NotesListActivity。 + mWorkingNote = null; + //TextUtils.equals() 是Android提供的一个工具方法,用于安全地比较两个字符串是否相等。 + //检查这个Intent的动作是否是ACTION_VIEW。 + //Intent.ACTION_VIEW: 这是一个预定义的Intent操作常量,通常用于表示一个查看某个数据的请求 if (TextUtils.equals(Intent.ACTION_VIEW, intent.getAction())) { long noteId = intent.getLongExtra(Intent.EXTRA_UID, 0); mUserQuery = ""; - /** * Starting from the searched result */ + //根据键值查找ID if (intent.hasExtra(SearchManager.EXTRA_DATA_KEY)) { noteId = Long.parseLong(intent.getStringExtra(SearchManager.EXTRA_DATA_KEY)); mUserQuery = intent.getStringExtra(SearchManager.USER_QUERY); } - + //如果ID在数据库中未找到 if (!DataUtils.visibleInNoteDatabase(getContentResolver(), noteId, Notes.TYPE_NOTE)) { Intent jump = new Intent(this, NotesListActivity.class); startActivity(jump); + //程序将跳转到上面声明的intent——jump showToast(R.string.error_note_not_exist); finish(); return false; - } else { + } + //ID在数据库中找到 + else { mWorkingNote = WorkingNote.load(this, noteId); if (mWorkingNote == null) { Log.e(TAG, "load note failed with note id" + noteId); @@ -211,10 +239,15 @@ public class NoteEditActivity extends Activity implements OnClickListener, return false; } } + //getWindow().setSoftInputMode() 是 Android 开发中用来控制软键盘显示时窗口如何调整的一个方法。 + //SOFT_INPUT_STATE_HIDDEN: 这个常量指定了当活动被创建时,软键盘应该被隐藏。也就是说,当这个活动启动时,输入法键盘不会自动弹出。 + //SOFT_INPUT_ADJUST_RESIZE: 这个常量指定了当软键盘显示时,活动窗口应该调整大小,以确保活动的内容不会被软键盘遮挡。 getWindow().setSoftInputMode( WindowManager.LayoutParams.SOFT_INPUT_STATE_HIDDEN | WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE); - } else if(TextUtils.equals(Intent.ACTION_INSERT_OR_EDIT, intent.getAction())) { + } + //Intent.ACTION_INSERT_OR_EDIT 是 Android 开发中的一个 action,它用于启动一个 activity 来插入或编辑一个特定的数据项。 + else if(TextUtils.equals(Intent.ACTION_INSERT_OR_EDIT, intent.getAction())) { // New note long folderId = intent.getLongExtra(Notes.INTENT_EXTRA_FOLDER_ID, 0); int widgetId = intent.getIntExtra(Notes.INTENT_EXTRA_WIDGET_ID, @@ -245,7 +278,7 @@ public class NoteEditActivity extends Activity implements OnClickListener, widgetType, bgResId); mWorkingNote.convertToCallNote(phoneNumber, callDate); } - } else { + } else {//创建一个新的WorkingNote mWorkingNote = WorkingNote.createEmptyNote(this, folderId, widgetId, widgetType, bgResId); } @@ -263,12 +296,13 @@ public class NoteEditActivity extends Activity implements OnClickListener, } @Override + //onResume(): Activity即将恢复到前台运行时被调用。Activity已可见,可以响应用户的操作 protected void onResume() { super.onResume(); initNoteScreen(); } - private void initNoteScreen() { + private void initNoteScreen() {//对界面的初始化操作 mNoteEditor.setTextAppearance(this, TextAppearanceResources .getTexAppearanceResource(mFontSizeId)); if (mWorkingNote.getCheckListMode() == TextNote.MODE_CHECK_LIST) { @@ -295,12 +329,12 @@ public class NoteEditActivity extends Activity implements OnClickListener, showAlertHeader(); } - private void showAlertHeader() { + private void showAlertHeader() {//闹钟的显示 if (mWorkingNote.hasClockAlert()) { long time = System.currentTimeMillis(); - if (time > mWorkingNote.getAlertDate()) { + if (time > mWorkingNote.getAlertDate()) {//如果系统时间大于了闹钟设置的时间,那么闹钟失效 mNoteHeaderHolder.tvAlertDate.setText(R.string.note_alert_expired); - } else { + } else {//显示闹钟开启的图标 mNoteHeaderHolder.tvAlertDate.setText(DateUtils.getRelativeTimeSpanString( mWorkingNote.getAlertDate(), time, DateUtils.MINUTE_IN_MILLIS)); } @@ -313,6 +347,11 @@ public class NoteEditActivity extends Activity implements OnClickListener, } @Override + /* + 如果 Activity 已经在任务栈的栈顶,并且用户试图再次启动这个 Activity, + 系统不会创建新的 Activity 实例,而是会调用已经在栈顶的 Activity 的 onNewIntent(Intent intent) 方法, + 并传入新的 Intent。这允许 Activity 响应新的 Intent 数据,而不是重新创建整个 Activity。 + */ protected void onNewIntent(Intent intent) { super.onNewIntent(intent); initActivityState(intent); @@ -329,26 +368,30 @@ public class NoteEditActivity extends Activity implements OnClickListener, if (!mWorkingNote.existInDatabase()) { saveNote(); } + //在创建一个新的标签时,先在数据库中匹配 + //如果不存在,那么先在数据库中存储 outState.putLong(Intent.EXTRA_UID, mWorkingNote.getNoteId()); Log.d(TAG, "Save working note id: " + mWorkingNote.getNoteId() + " onSaveInstanceState"); } @Override + //MotionEvent是对屏幕触控的传递机制 public boolean dispatchTouchEvent(MotionEvent ev) { if (mNoteBgColorSelector.getVisibility() == View.VISIBLE && !inRangeOfView(mNoteBgColorSelector, ev)) { mNoteBgColorSelector.setVisibility(View.GONE); return true; - } + }//颜色选择器在屏幕上可见 if (mFontSizeSelector.getVisibility() == View.VISIBLE && !inRangeOfView(mFontSizeSelector, ev)) { mFontSizeSelector.setVisibility(View.GONE); return true; - } + }//字体大小选择器在屏幕上可见 return super.dispatchTouchEvent(ev); } + //对屏幕触控的坐标进行操作 private boolean inRangeOfView(View view, MotionEvent ev) { int []location = new int[2]; view.getLocationOnScreen(location); @@ -364,6 +407,7 @@ public class NoteEditActivity extends Activity implements OnClickListener, } private void initResources() { + //对标签各项属性内容的初始化 mHeadViewPanel = findViewById(R.id.note_title); mNoteHeaderHolder = new HeadViewHolder(); mNoteHeaderHolder.tvModified = (TextView) findViewById(R.id.tv_modified_date); @@ -374,13 +418,13 @@ public class NoteEditActivity extends Activity implements OnClickListener, mNoteEditor = (EditText) findViewById(R.id.note_edit_view); mNoteEditorPanel = findViewById(R.id.sv_note_edit); mNoteBgColorSelector = findViewById(R.id.note_bg_color_selector); - for (int id : sBgSelectorBtnsMap.keySet()) { + for (int id : sBgSelectorBtnsMap.keySet()) {//背景颜色 ImageView iv = (ImageView) findViewById(id); iv.setOnClickListener(this); } mFontSizeSelector = findViewById(R.id.font_size_selector); - for (int id : sFontSizeBtnsMap.keySet()) { + for (int id : sFontSizeBtnsMap.keySet()) {//字体大小 View view = findViewById(id); view.setOnClickListener(this); }; @@ -398,6 +442,8 @@ public class NoteEditActivity extends Activity implements OnClickListener, } @Override + //onPause(): 在当前Activity被其他Activity覆盖或锁屏时调用。 + //表示Activity正在停止,准备从前台返回至后台,此时可以做一些停止动画,数据存储等工作 protected void onPause() { super.onPause(); if(saveNote()) { @@ -406,7 +452,7 @@ public class NoteEditActivity extends Activity implements OnClickListener, clearSettingState(); } - private void updateWidget() { + private void updateWidget() {//和桌面小工具的同步 Intent intent = new Intent(AppWidgetManager.ACTION_APPWIDGET_UPDATE); if (mWorkingNote.getWidgetType() == Notes.TYPE_WIDGET_2X) { intent.setClass(this, NoteWidgetProvider_2x.class); @@ -430,7 +476,7 @@ public class NoteEditActivity extends Activity implements OnClickListener, if (id == R.id.btn_set_bg_color) { mNoteBgColorSelector.setVisibility(View.VISIBLE); findViewById(sBgSelectorSelectionMap.get(mWorkingNote.getBgColorId())).setVisibility( - - View.VISIBLE); + View.VISIBLE); } else if (sBgSelectorBtnsMap.containsKey(id)) { findViewById(sBgSelectorSelectionMap.get(mWorkingNote.getBgColorId())).setVisibility( View.GONE); @@ -453,7 +499,7 @@ public class NoteEditActivity extends Activity implements OnClickListener, } @Override - public void onBackPressed() { + public void onBackPressed() {//返回 if(clearSettingState()) { return; } @@ -473,7 +519,7 @@ public class NoteEditActivity extends Activity implements OnClickListener, return false; } - public void onBackgroundColorChanged() { + public void onBackgroundColorChanged() {//背景颜色 findViewById(sBgSelectorSelectionMap.get(mWorkingNote.getBgColorId())).setVisibility( View.VISIBLE); mNoteEditorPanel.setBackgroundResource(mWorkingNote.getBgColorResId()); @@ -481,7 +527,7 @@ public class NoteEditActivity extends Activity implements OnClickListener, } @Override - public boolean onPrepareOptionsMenu(Menu menu) { + public boolean onPrepareOptionsMenu(Menu menu) {//准备选择菜单,在选项菜单被显示之前被调用 if (isFinishing()) { return true; } @@ -506,45 +552,52 @@ public class NoteEditActivity extends Activity implements OnClickListener, } @Override + //动态改变菜单选项内容 public boolean onOptionsItemSelected(MenuItem item) { switch (item.getItemId()) { case R.id.menu_new_note: - createNewNote(); + createNewNote();//创建一个新的便签 break; - case R.id.menu_delete: + case R.id.menu_delete://删除便签 + //创建关于删除操作的对话框 AlertDialog.Builder builder = new AlertDialog.Builder(this); + //设置标签的标题 builder.setTitle(getString(R.string.alert_title_delete)); + //设置对话框图标 builder.setIcon(android.R.drawable.ic_dialog_alert); + //设置对话框内容 builder.setMessage(getString(R.string.alert_message_delete_note)); + //添加“YES”按钮 builder.setPositiveButton(android.R.string.ok, - new DialogInterface.OnClickListener() { + new DialogInterface.OnClickListener() {//建立按键监听器 public void onClick(DialogInterface dialog, int which) { deleteCurrentNote(); finish(); } }); - builder.setNegativeButton(android.R.string.cancel, null); - builder.show(); + builder.setNegativeButton(android.R.string.cancel, null);//添加“NO”的按钮 + builder.show();//显示对话框 break; - case R.id.menu_font_size: - mFontSizeSelector.setVisibility(View.VISIBLE); + case R.id.menu_font_size://字体大小的编辑 + mFontSizeSelector.setVisibility(View.VISIBLE);// 将字体选择器置为可见 + // 通过id找到相应的大小 findViewById(sFontSelectorSelectionMap.get(mFontSizeId)).setVisibility(View.VISIBLE); break; - case R.id.menu_list_mode: + case R.id.menu_list_mode://选择列表模式 mWorkingNote.setCheckListMode(mWorkingNote.getCheckListMode() == 0 ? TextNote.MODE_CHECK_LIST : 0); break; - case R.id.menu_share: + case R.id.menu_share://分享 getWorkingText(); - sendTo(this, mWorkingNote.getContent()); + sendTo(this, mWorkingNote.getContent());// 用sendto函数将运行文本发送到遍历的本文内 break; - case R.id.menu_send_to_desktop: + case R.id.menu_send_to_desktop://发送到桌面 sendToDesktop(); break; - case R.id.menu_alert: + case R.id.menu_alert://创建提醒 setReminder(); break; - case R.id.menu_delete_remind: + case R.id.menu_delete_remind://删除提醒 mWorkingNote.setAlertDate(0, false); break; default: @@ -553,20 +606,23 @@ public class NoteEditActivity extends Activity implements OnClickListener, return true; } - private void setReminder() { + private void setReminder() {//创建提醒 + // 建立修改时间日期的对话框 DateTimePickerDialog d = new DateTimePickerDialog(this, System.currentTimeMillis()); - d.setOnDateTimeSetListener(new OnDateTimeSetListener() { + //选择提醒的日期 + d.setOnDateTimeSetListener(new OnDateTimeSetListener() {//建立监听器 public void OnDateTimeSet(AlertDialog dialog, long date) { mWorkingNote.setAlertDate(date , true); } }); - d.show(); + d.show();//显示对话框 } /** * Share note to apps that support {@link Intent#ACTION_SEND} action * and {@text/plain} type */ + //分享便签 private void sendTo(Context context, String info) { Intent intent = new Intent(Intent.ACTION_SEND); intent.putExtra(Intent.EXTRA_TEXT, info); @@ -574,9 +630,10 @@ public class NoteEditActivity extends Activity implements OnClickListener, context.startActivity(intent); } + //创建新便签 private void createNewNote() { // Firstly, save current editing notes - saveNote(); + saveNote();//保存当前便签 // For safety, start a new NoteEditActivity finish(); @@ -586,6 +643,7 @@ public class NoteEditActivity extends Activity implements OnClickListener, startActivity(intent); } + //删除当前便签 private void deleteCurrentNote() { if (mWorkingNote.existInDatabase()) { HashSet ids = new HashSet(); @@ -595,43 +653,47 @@ public class NoteEditActivity extends Activity implements OnClickListener, } else { Log.d(TAG, "Wrong note id, should not happen"); } - if (!isSyncMode()) { - if (!DataUtils.batchDeleteNotes(getContentResolver(), ids)) { - Log.e(TAG, "Delete Note error"); - } - } else { +// if (!isSyncMode()) { +// if (!DataUtils.batchDeleteNotes(getContentResolver(), ids)) { +// Log.e(TAG, "Delete Note error"); +// } +// } else { if (!DataUtils.batchMoveToFolder(getContentResolver(), ids, Notes.ID_TRASH_FOLER)) { Log.e(TAG, "Move notes to trash folder error, should not happens"); } - } +// } } mWorkingNote.markDeleted(true); } + //判断是否为同步模式 private boolean isSyncMode() { return NotesPreferenceActivity.getSyncAccountName(this).trim().length() > 0; } + //设置提醒时间 public void onClockAlertChanged(long date, boolean set) { /** * User could set clock to an unsaved note, so before setting the * alert clock, we should save the note first */ if (!mWorkingNote.existInDatabase()) { - saveNote(); + saveNote();//保存便签 } if (mWorkingNote.getNoteId() > 0) { + //若有有运行的便签建立链接器将标签id都存在uri中 Intent intent = new Intent(this, AlarmReceiver.class); intent.setData(ContentUris.withAppendedId(Notes.CONTENT_NOTE_URI, mWorkingNote.getNoteId())); PendingIntent pendingIntent = PendingIntent.getBroadcast(this, 0, intent, 0); + //设置提醒管理器 AlarmManager alarmManager = ((AlarmManager) getSystemService(ALARM_SERVICE)); showAlertHeader(); - if(!set) { + if(!set) {//取消设置 alarmManager.cancel(pendingIntent); - } else { + } else {//如果用户设置了时间,就通过提醒管理器设置一个监听事项 alarmManager.set(AlarmManager.RTC_WAKEUP, date, pendingIntent); } - } else { + } else {//没有运行的便签就报错 /** * There is the condition that user has input nothing (the note is * not worthy saving), we have no note id, remind the user that he @@ -691,6 +753,7 @@ public class NoteEditActivity extends Activity implements OnClickListener, } } + //切换至列表模式 private void switchToListMode(String text) { mEditTextList.removeAllViews(); String[] items = text.split("\n"); @@ -725,6 +788,7 @@ public class NoteEditActivity extends Activity implements OnClickListener, return spannable; } + //获取列表项 private View getListItem(String item, int index) { View view = LayoutInflater.from(this).inflate(R.layout.note_edit_list_item, null); final NoteEditText edit = (NoteEditText) view.findViewById(R.id.et_edit_text); @@ -805,6 +869,7 @@ public class NoteEditActivity extends Activity implements OnClickListener, return hasChecked; } + //保存便签 private boolean saveNote() { getWorkingText(); boolean saved = mWorkingNote.saveNote(); @@ -856,6 +921,7 @@ public class NoteEditActivity extends Activity implements OnClickListener, } } + //编辑小图标的标题 private String makeShortcutIconTitle(String content) { content = content.replace(TAG_CHECKED, ""); content = content.replace(TAG_UNCHECKED, "");