当前位置:   article > 正文

手把手教你用鸿蒙HarmonyOS实现微信聊天界面(二)_鸿蒙系统可以按照message吗

鸿蒙系统可以按照message吗

简介

        本系列文章记录作者大三开学第一个月中学习HarmonyOS移动应用开发学习经历,此篇为《微信聊天界面》项目,实现功能有

1、聊天信息功能,包括图片、文字

2、发送定位功能

3、选择发送本机图片功能

4、拍照并发送图片功能

        如果在真机调试请将config文件中包名换成自己的应用包名即可,申请权限有文件读写、位置获取、相机调用、麦克风调用。

之前文章


手把手教你用鸿蒙HarmonyOS实现微信聊天界面(一)_hys1124388788的博客-CSDN博客

聊天界面效果如图

图片选择效果如图

图片获取 

        本篇讲关于图片的获取。一种方式是在项目中放置静态资源,另一种则是从本机中获取图片。

第一种

        第一种方式使用很简单,只需要在Image组件添加src属性即可。

  1. <Image
  2. ohos:id="$+id:image_message"
  3. ohos:width="match_content"
  4. ohos:image_src="$media:rick_c137"
  5. ohos:height="match_content"
  6. ohos:scale_mode="zoom_center"
  7. ohos:background_element="$graphic:message_background"
  8. ohos:left_margin="15vp"
  9. ohos:left_padding="15vp"
  10. ohos:right_padding="15vp"
  11. ohos:right_margin="15vp"
  12. ohos:top_margin="15vp"
  13. ohos:top_padding="15vp"
  14. ohos:bottom_margin="15vp"
  15. ohos:bottom_padding="15vp"
  16. ohos:margin="5vp"/>

第二种

        第二种的使用场景更加普遍,是根据图片文件的uri来访问媒体资源转换为PixelMap对象传给Image组件实现的。

  1. Component container = LayoutScatter.getInstance(context).parse(ResourceTable.Layout_image_message_list_item, null, false);
  2. Image image = (Image) container.findComponentById(ResourceTable.Id_image_message);
  3. DataAbilityHelper helper=DataAbilityHelper.creator(context);
  4. ImageSource imageSource;
  5. Uri uri = Uri.parse(aMessage.getMessage());
  6. FileDescriptor fd = null;
  7. try {
  8. fd = helper.openFile(uri, "r");
  9. } catch (DataAbilityRemoteException | FileNotFoundException e) {
  10. e.printStackTrace();
  11. }
  12. imageSource = ImageSource.create(fd, null);
  13. //创建位图
  14. PixelMap pixelMap = imageSource.createPixelmap(null);
  15. image.setPixelMap(pixelMap);
  16. imageSource.release();
  17. helper.release();
  18. return container;

获取Uri

        如何获取图片的Uri呢?是通过DataAbilityHelper这个类查询本机的资源(参考官方文档文档中心),媒体存储相关类AVStorage类中AVStorage.Images.Media.EXTERNAL_DATA_ABILITY_URI是获取用于处理图像媒体信息的Uri,视频资源也类似,根据查询结果获取到的资源id拼接处Uri

Uri.appendEncodedPathToUri(AVStorage.Images.Media.EXTERNAL_DATA_ABILITY_URI, String.valueOf(id));

项目中获取图片URI资源的类

  1. public class PictureManager {
  2. private static final String TAG = PictureManager.class.getSimpleName();
  3. private List<Uri> imagePathElements = new ArrayList<>();
  4. private Context context;
  5. /**
  6. * The construction method of this class
  7. *
  8. * @param context Context
  9. */
  10. public PictureManager(Context context) {
  11. this.context = context;
  12. loadFromMediaLibrary(context);
  13. }
  14. private void loadFromMediaLibrary(Context context) {
  15. Uri remoteUri = AVStorage.Images.Media.EXTERNAL_DATA_ABILITY_URI;
  16. DataAbilityHelper helper = DataAbilityHelper.creator(context, remoteUri, false);
  17. try {
  18. ResultSet resultSet = helper.query(remoteUri, null, null);
  19. LogUtil.info(TAG, "The result size: " + resultSet.getRowCount());
  20. processResult(resultSet);
  21. resultSet.close();
  22. } catch (DataAbilityRemoteException e) {
  23. LogUtil.error(TAG, "Query system media failed.");
  24. } finally {
  25. helper.release();
  26. }
  27. }
  28. private void processResult(ResultSet resultSet) {
  29. while (resultSet.goToNextRow()) {
  30. String path = resultSet.getString(resultSet.getColumnIndexForName(AVStorage.AVBaseColumns.DATA));
  31. String title = resultSet.getString(resultSet.getColumnIndexForName(AVStorage.AVBaseColumns.TITLE));
  32. String id = resultSet.getString(resultSet.getColumnIndexForName(AVStorage.Images.Media.ID));
  33. Uri uri = Uri.appendEncodedPathToUri(AVStorage.Images.Media.EXTERNAL_DATA_ABILITY_URI, String.valueOf(id));
  34. LogUtil.info(TAG, "The title is: " + title);
  35. LogUtil.info(TAG, "The path is: " + path);
  36. LogUtil.info(TAG, "The id is: " + id);
  37. LogUtil.info(TAG, "The uri is: " + uri);
  38. imagePathElements.add(uri);
  39. }
  40. }
  41. public List<Uri> getimageElements() {
  42. LogUtil.info(TAG, "The size is: " + imagePathElements.size());
  43. return imagePathElements;
  44. }
  45. }

Uri转图片

         ​​​​​​具体怎么选择图片是通过ListContiner组件将图片按行展示在手机上,通过添加图片的点击方法调用发送消息方法将图片发出。

        如何将Uri显示为图片?在鸿蒙中Image组件可通过调用setPixelMap方法设置,参数是PixMap对象。可以通过ImageSource根据FileDescriptor 创建位图

  1. DataAbilityHelper helper=DataAbilityHelper.creator(slice.getContext());
  2. ImageSource imageSource;
  3. FileDescriptor fd = null;
  4. fd = helper.openFile(uri, "r");
  5. imageSource = ImageSource.create(fd, null);
  6. PixelMap pixelMap = imageSource.createPixelmap(null);
  7. image.setPixelMap(pixelMap);

        以下是在项目中将图片一行三张展示所以Uri采用数组存储,如果只想显示一张将数组换为单个对象即可。

  1. DataAbilityHelper helper=DataAbilityHelper.creator(slice.getContext());
  2. //定义图片来源对象
  3. ImageSource imageSource;
  4. Uri[] uris = imageLineItem.getUris();
  5. FileDescriptor fd = null;
  6. image1.setClickedListener(component1 -> {
  7. mainAbilitySlice.addAndUpdateMessage(mainAbilitySlice.getMessageDataSize(), String.valueOf(uris[0]),"image");
  8. mainAbilitySlice.getDialog().destroy();
  9. });
  10. try {
  11. fd = helper.openFile(uris[0], "r");
  12. } catch (DataAbilityRemoteException | FileNotFoundException e) {
  13. e.printStackTrace();
  14. }
  15. imageSource = ImageSource.create(fd, null);
  16. //创建位图
  17. PixelMap pixelMap = imageSource.createPixelmap(null);
  18. image1.setPixelMap(pixelMap);
  19. imageSource.release();
  20. helper.release();

ListContiner的内容实体类

  1. public class ImageLineItem {
  2. private int index;
  3. private Uri[] uris;
  4. public ImageLineItem(int index) {
  5. this.index = index;
  6. }
  7. public int getIndex() {
  8. return index;
  9. }
  10. public void setIndex(int index) {
  11. this.index = index;
  12. }
  13. public Uri[] getUris() {
  14. return uris;
  15. }
  16. public void setUris(Uri[] uris) {
  17. this.uris = uris;
  18. }
  19. }

Provider类

  1. public class ImageLineProvider extends BaseItemProvider {
  2. private static final String TAG = ImageLineProvider.class.getSimpleName();
  3. private List<ImageLineItem> list;
  4. private AbilitySlice slice;
  5. private MainAbilitySlice mainAbilitySlice;
  6. public void setMainAbilitySlice(MainAbilitySlice mainAbilitySlice){
  7. this.mainAbilitySlice = mainAbilitySlice;
  8. }
  9. public ImageLineProvider(List<ImageLineItem> list, AbilitySlice slice) {
  10. LogUtil.info(TAG,"list.size() : "+list.size());
  11. this.list = list;
  12. this.slice = slice;
  13. }
  14. @Override
  15. public int getCount() {
  16. return list == null ? 0 : list.size();
  17. }
  18. @Override
  19. public Object getItem(int position) {
  20. if (list != null && position >= 0 && position < list.size()){
  21. return list.get(position);
  22. }
  23. return null;
  24. }
  25. @Override
  26. public long getItemId(int position) {
  27. return position;
  28. }
  29. private Component getItemComponent(int position) {
  30. return getComponent(position);
  31. }
  32. private Component getComponent(int position) {
  33. LogUtil.info(TAG,"list.size()"+list.size());
  34. final Component cpt;
  35. cpt = LayoutScatter.getInstance(slice).parse(ResourceTable.Layout_images_line, null, false);
  36. ImageLineItem imageLineItem = list.get(position);
  37. Image image1,image2,image3;
  38. image1 = (Image) cpt.findComponentById(ResourceTable.Id_image1);
  39. image2 = (Image) cpt.findComponentById(ResourceTable.Id_image2);
  40. image3 = (Image) cpt.findComponentById(ResourceTable.Id_image3);
  41. DataAbilityHelper helper=DataAbilityHelper.creator(slice.getContext());
  42. //定义图片来源对象
  43. ImageSource imageSource;
  44. Uri[] uris = imageLineItem.getUris();
  45. FileDescriptor fd = null;
  46. image1.setClickedListener(component1 -> {
  47. mainAbilitySlice.addAndUpdateMessage(mainAbilitySlice.getMessageDataSize(), String.valueOf(uris[0]),"image");
  48. mainAbilitySlice.getDialog().destroy();
  49. });
  50. image2.setClickedListener(component1 -> {
  51. mainAbilitySlice.addAndUpdateMessage(mainAbilitySlice.getMessageDataSize(), String.valueOf(uris[1]),"image");
  52. mainAbilitySlice.getDialog().destroy();
  53. });
  54. image3.setClickedListener(component1 -> {
  55. mainAbilitySlice.addAndUpdateMessage(mainAbilitySlice.getMessageDataSize(), String.valueOf(uris[2]),"image");
  56. mainAbilitySlice.getDialog().destroy();
  57. });
  58. try {
  59. fd = helper.openFile(uris[0], "r");
  60. } catch (DataAbilityRemoteException | FileNotFoundException e) {
  61. e.printStackTrace();
  62. }
  63. imageSource = ImageSource.create(fd, null);
  64. //创建位图
  65. PixelMap pixelMap = imageSource.createPixelmap(null);
  66. image1.setPixelMap(pixelMap);
  67. imageSource.release();
  68. helper.release();
  69. try {
  70. fd = helper.openFile(uris[1], "r");
  71. } catch (DataAbilityRemoteException | FileNotFoundException e) {
  72. e.printStackTrace();
  73. }
  74. imageSource = ImageSource.create(fd, null);
  75. //创建位图
  76. pixelMap = imageSource.createPixelmap(null);
  77. image2.setPixelMap(pixelMap);
  78. imageSource.release();
  79. helper.release();
  80. try {
  81. fd = helper.openFile(uris[2], "r");
  82. } catch (DataAbilityRemoteException | FileNotFoundException e) {
  83. e.printStackTrace();
  84. }
  85. imageSource = ImageSource.create(fd, null);
  86. //创建位图
  87. pixelMap = imageSource.createPixelmap(null);
  88. image3.setPixelMap(pixelMap);
  89. imageSource.release();
  90. helper.release();
  91. return cpt;
  92. }
  93. @Override
  94. public Component getComponent(int position, Component convertComponent, ComponentContainer componentContainer) {
  95. return getItemComponent(position);
  96. }
  97. }

        到此图片获取的方式讲完了,下篇讲前边图片中展示的效果怎么实现。

Gitee链接
WeChatPage: 鸿蒙版微信界面

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

闽ICP备14008679号