当前位置:   article > 正文

【软件应用开发】小米便签APP维护开发_小米便签二次开发

小米便签二次开发

本文主要介绍在小米便签APP原有功能的基础上,设计并实现了便签添加图片的功能,从开发过程、运行界面、源代码三个方面进行详细介绍。
本文引用小米便签社区开源版代码:https://github.com/MiCode/Notes
小米便签APP维护开发完整源代码地址:https://download.csdn.net/download/weixin_47936614/85436044

开发工具:Android Studio
开发环境:操作系统win10、jdk1.8.0


一、开发过程

  1. 首先在note_edit.xml文件中添加add_img_btn按钮;
  2. 在NoteEditActivity.java文件的onCreate()方法中,为这个“添加图片”按钮设置监听器,点击添加图片按钮时,会触发点击事件;
  3. 重写onActivityResult()来处理返回的数据,并将图片的路径也写入到数据库;
  4. 点击一个note后,会初始化note的内容,并通过convertToImage()将路径转化为图片;
  5. 在退出清单模式之后,仍应该将图片路径的位置替换为图片。

在编辑便签界面添加图片功能的程序流程图如图1所示。
在这里插入图片描述

二、运行界面

在便签编辑界面中,点击“添加图片”按钮,选择相应的图片,插入到便签中,插入图片过程如图2所示。
在这里插入图片描述在这里插入图片描述在这里插入图片描述
在插入图片后可以继续编辑便签,输入相应的文字或图片,保存便签后退出。当用户再次查看便签时,图片和文字在相应的位置展示出来,如图3所示。
在这里插入图片描述在这里插入图片描述
用户在编辑便签界面选择“进入清单模式”,便签进入清单模式,图片以路径方式显示,当用户选择“退出清单模式”后,图片将在相应位置显示出来。如图4所示。
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

三、源代码

  • 添加图片按钮的xml代码(FilePath: MiNotes\app\src\main\res\layout\note_edit.xml)
<ImageButton
        android:id="@+id/add_img_btn"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginLeft="7dp"
        android:layout_marginTop="600dp"
        android:layout_marginBottom="7dp"
        android:src="@android:drawable/ic_menu_gallery" />
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • onCreate()方法(FilePath: MiNotes\app\src\main\java\net\micode\notes\ui\NoteEditActivity.java)
protected void onCreate(Bundle savedInstanceState) {
	super.onCreate(savedInstanceState);
	this.setContentView(R.layout.note_edit);

	if (savedInstanceState == null && !initActivityState(getIntent())) {
		finish();
		return;
	}
	initResources();

	//根据id获取添加图片按钮
	final ImageButton add_img_btn = (ImageButton) findViewById(R.id.add_img_btn);
	//为点击图片按钮设置监听器
	add_img_btn.setOnClickListener(new View.OnClickListener() {
		@Override
		public void onClick(View view) {
			Log.d(TAG, "onClick: click add image button");
			//ACTION_GET_CONTENT: 允许用户选择特殊种类的数据,并返回(特殊种类的数据:照一张相片或录一段音)
			Intent loadImage = new Intent(Intent.ACTION_GET_CONTENT);
			//Category属性用于指定当前动作(Action)被执行的环境.
			//CATEGORY_OPENABLE; 用来指示一个ACTION_GET_CONTENT的intent
			loadImage.addCategory(Intent.CATEGORY_OPENABLE);
			loadImage.setType("image/*");
			startActivityForResult(loadImage, PHOTO_REQUEST);
		}
	});
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • convertToImage()方法(FilePath: MiNotes\app\src\main\java\net\micode\notes\ui\NoteEditActivity.java)
//路径字符串格式 转换为 图片image格式
private void convertToImage() {
	NoteEditText noteEditText = (NoteEditText) findViewById(R.id.note_edit_view); //获取当前的edit
	Editable editable = noteEditText.getText();//1.获取text
	String noteText = editable.toString(); //2.将note内容转换为字符串
	int length = editable.length(); //内容的长度
	//3.截取img片段 [local]+uri+[local],提取uri
	for(int i = 0; i < length; i++) {
		for(int j = i; j < length; j++) {
			String img_fragment = noteText.substring(i, j+1); //img_fragment:关于图片路径的片段
			if(img_fragment.length() > 15 && img_fragment.endsWith("[/local]") && img_fragment.startsWith("[local]")){
				int limit = 7;  //[local]为7个字符
				//[local][/local]共15个字符,剩下的为真正的path长度
				int len = img_fragment.length()-15;
				//从[local]之后的len个字符就是path
				String path = img_fragment.substring(limit,limit+len);//获取到了图片路径
				Bitmap bitmap = null;
				Log.d(TAG, "图片的路径是:"+path);
				try {
					bitmap = BitmapFactory.decodeFile(path);//将图片路径解码为图片格式
				} catch (Exception e) {
					e.printStackTrace();
				}
				if(bitmap!=null){  //若图片存在
					Log.d(TAG, "图片不为null");
					ImageSpan imageSpan = new ImageSpan(NoteEditActivity.this, bitmap);
					//4.创建一个SpannableString对象,以便插入用ImageSpan对象封装的图像
					String ss = "[local]" + path + "[/local]";
					SpannableString spannableString = new SpannableString(ss);
					//5.将指定的标记对象附加到文本的开始...结束范围
					spannableString.setSpan(imageSpan, 0, ss.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
					Log.d(TAG, "Create spannable string success!");
					Editable edit_text = noteEditText.getEditableText();
					edit_text.delete(i,i+len+15); //6.删掉图片路径的文字
					edit_text.insert(i, spannableString); //7.在路径的起始位置插入图片
				}
			}
		}
	}
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • onActivityResult()方法(FilePath: MiNotes\app\src\main\java\net\micode\notes\ui\NoteEditActivity.java)
//重写onActivityResult()来处理返回的数据
protected void onActivityResult(int requestCode, int resultCode, Intent intent) {
	super.onActivityResult(requestCode, resultCode, intent);
	ContentResolver resolver = getContentResolver();
	switch (requestCode) {
		case PHOTO_REQUEST:
			Uri originalUri = intent.getData(); //1.获得图片的真实路径
			Bitmap bitmap = null;
			try {
				bitmap = BitmapFactory.decodeStream(resolver.openInputStream(originalUri));//2.解码图片
			} catch (FileNotFoundException e) {
				Log.d(TAG, "onActivityResult: get file_exception");
				e.printStackTrace();
			}

			if(bitmap != null){
				//3.根据Bitmap对象创建ImageSpan对象
				Log.d(TAG, "onActivityResult: bitmap is not null");
				ImageSpan imageSpan = new ImageSpan(NoteEditActivity.this, bitmap);
				String path = getPath(this,originalUri);
				//4.使用[local][/local]将path括起来,用于之后方便识别图片路径在note中的位置
				String img_fragment= "[local]" + path + "[/local]";
				//创建一个SpannableString对象,以便插入用ImageSpan对象封装的图像
				SpannableString spannableString = new SpannableString(img_fragment);
				spannableString.setSpan(imageSpan, 0, img_fragment.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
				//5.将选择的图片追加到EditText中光标所在位置
				NoteEditText e = (NoteEditText) findViewById(R.id.note_edit_view);
				int index = e.getSelectionStart(); //获取光标所在位置
				Log.d(TAG, "Index是: " + index);
				Editable edit_text = e.getEditableText();
				edit_text.insert(index, spannableString); //将图片插入到光标所在位置

				mWorkingNote.mContent = e.getText().toString();
				//6.把改动提交到数据库中,两个数据库表都要改的
				ContentResolver contentResolver = getContentResolver();
				ContentValues contentValues = new ContentValues();
				final long id = mWorkingNote.getNoteId();
				contentValues.put("snippet",mWorkingNote.mContent);
				contentResolver.update(Uri.parse("content://micode_notes/note"), contentValues,"_id=?",new String[]{""+id});
				ContentValues contentValues1 = new ContentValues();
				contentValues1.put("content",mWorkingNote.mContent);
				contentResolver.update(Uri.parse("content://micode_notes/data"), contentValues1,"mime_type=? and note_id=?", new String[]{"vnd.android.cursor.item/text_note",""+id});

			}else{
				Toast.makeText(NoteEditActivity.this, "获取图片失败", Toast.LENGTH_SHORT).show();
			}
			break;
		default:
			break;
	}
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • getPath()方法(FilePath: MiNotes\app\src\main\java\net\micode\notes\ui\NoteEditActivity.java)
//获取文件的real path
public String getPath(final Context context, final Uri uri) {

    final boolean isKitKat = Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT;

    // DocumentProvider
    if (isKitKat && DocumentsContract.isDocumentUri(context, uri)) {
        // ExternalStorageProvider
//            if (isExternalStorageDocument(uri)) {
//                final String docId = DocumentsContract.getDocumentId(uri);
//                final String[] split = docId.split(":");
//                final String type = split[0];
//
//                if ("primary".equalsIgnoreCase(type)) {
//                    return Environment.getExternalStorageDirectory() + "/" + split[1];
//                }
//            }
//            // DownloadsProvider
//            else if (isDownloadsDocument(uri)) {
//                final String id = DocumentsContract.getDocumentId(uri);
//                final Uri contentUri = ContentUris.withAppendedId(Uri.parse("content://downloads/public_downloads"), Long.valueOf(id));
//                return getDataColumn(context, contentUri, null, null);
//            }
        // MediaProvider
//            else
            if (isMediaDocument(uri)) {
            final String docId = DocumentsContract.getDocumentId(uri);
            final String[] split = docId.split(":");
            final String type = split[0];

            Uri contentUri = null;
            if ("image".equals(type)) {
                contentUri = MediaStore.Images.Media.EXTERNAL_CONTENT_URI;
            }

            final String selection = "_id=?";
            final String[] selectionArgs = new String[]{split[1]};

            return getDataColumn(context, contentUri, selection, selectionArgs);
        }
    }
    // Media
    else if ("content".equalsIgnoreCase(uri.getScheme())) {
        return getDataColumn(context, uri, null, null);
    }
    // File
    else if ("file".equalsIgnoreCase(uri.getScheme())) {
        return uri.getPath();
    }
    return null;
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51

小米便签APP维护开发完整源代码地址:https://download.csdn.net/download/weixin_47936614/85436044

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/羊村懒王/article/detail/69401
推荐阅读
相关标签
  

闽ICP备14008679号