1.为什么要实现自定义消息
正如我们自己的app,要实现在分享功能,并且分享的类型也不是固定的传统的分享,同时还可以点击跳转,用传统的融云分享格式是满足不了需求,这就用到了融云自定义消息
2. 怎么去实现自定义分享
-
首先我们应该自定义一个消息类继承融云MessageContent这个类,重写其中的encode方法,将json串转换为byte数组,其中shareTittle等都是在需要在分享中使用的字段,这个地方的键值要与IOS统一,否则会产生无法同步现象
@Override public byte[] encode() { JSONObject jsonObject = new JSONObject(); try { jsonObject.put("shareTitle",shareTitle); jsonObject.put("shareDescription",shareDescription); jsonObject.put("shareImageStr",shareImageStr); jsonObject.put("shareId",shareId); jsonObject.put("shareUrl",shareUrl); jsonObject.put("extra",extra); jsonObject.put("shareType",shareType); }catch (JSONException e){ e.printStackTrace(); } try { return jsonObject.toString().getBytes("UTF-8"); }catch (UnsupportedEncodingException e){ e.printStackTrace(); } return null; }
-
重写父类的构造器,其中参数是byte[],将相应的byte[] 转换为json字符串,并将json中的数据赋给该类的字段
public ShareMessageContent(byte[] data) { String jsonStr = null; try { jsonStr = new String(data, "UTF-8"); } catch (UnsupportedEncodingException e1) { } try { JSONObject jsonObj = new JSONObject(jsonStr); if(jsonObj.has("shareTitle")) shareTitle = jsonObj.optString("shareTitle"); if(jsonObj.has("shareDescription")) shareDescription = jsonObj.optString("shareDescription"); if(jsonObj.has("shareImageStr")) shareImageStr = jsonObj.optString("shareImageStr"); if(jsonObj.has("shareId")) shareId = jsonObj.optString("shareId"); if(jsonObj.has("shareUrl")) shareUrl = jsonObj.optString("shareUrl"); if(jsonObj.has("extra")) extra = jsonObj.optString("extra"); if(jsonObj.has("shareType")) shareType = jsonObj.optString("shareType"); } catch (JSONException e) { e.printStackTrace(); } }
- 建立以parcel为参数的构造器,并重写writeToParcel方法,这里面用到融云的工具类ParcelUtils,这两个方法必须一一对应,否则会使数据错乱
/** * 以下两个方法必须顺序必须一一对应否则会出现数据混乱 * @param in */ public ShareMessageContent(Parcel in){ setShareTitle(ParcelUtils.readFromParcel(in)); //该类为工具了,消息属性 setShareDescription(ParcelUtils.readFromParcel(in)); setShareImageStr(ParcelUtils.readFromParcel(in)); setShareId(ParcelUtils.readFromParcel(in)); setShareUrl(ParcelUtils.readFromParcel(in)); setExtra(ParcelUtils.readFromParcel(in)); setShareType(ParcelUtils.readFromParcel(in)); } /** * 将类的数据写入外部提供的parcel中 * @param dest 对象被写入Parcel * @param flags 对象如何被写入的附加标志 */ @Override public void writeToParcel(Parcel dest, int flags) { ParcelUtils.writeToParcel(dest,getShareTitle()); ParcelUtils.writeToParcel(dest,getShareDescription()); ParcelUtils.writeToParcel(dest,getShareImageStr()); ParcelUtils.writeToParcel(dest,getShareId()); ParcelUtils.writeToParcel(dest,getShareUrl()); ParcelUtils.writeToParcel(dest,getExtra()); ParcelUtils.writeToParcel(dest,getShareType()); }
-
实现 Parcelable中的方法Creator方法,同时重写相应的describeContents()方法
/** * 读取接口,目的要从Parcel中构造一个实现了Parcelable的类的实例处理 */ public static final Creator<ShareMessageContent> CREATOR = new Creator<ShareMessageContent>() { @Override public ShareMessageContent createFromParcel(Parcel source) { return new ShareMessageContent(source); } @Override public ShareMessageContent[] newArray(int size) { return new ShareMessageContent[size]; } }; /** * 描述了包含在 Parcelable 对象排列信息中的特殊对象的类型。 * * @return 一个标志位,表明Parcelable对象特殊对象类型集合的排列。 */ public int describeContents() { return 0; }
-
在该model上添加注解信息,以便于融云识别,其中注意属性value1必须是唯一不可重复的标识,同时也是应该和ios定义的城一个字段。
@MessageTag(value = "app:custom", flag = MessageTag.ISCOUNTED | MessageTag.ISPERSISTED) public class CustomizeMessage extends MessageContent { ... }
-
注册自定义消息,注册在application中进行注册:
RongIM.registerMessageType(CustomizeMessage.class);
-
消息展示创建一个消息提供者,继承IContainerProvider.MessageProvider类,实现其中的5个方法newView (),bingView(),getContentSummary(),onItemClick(),onItemLongClick(),代码如下
/** * desc新建一个消息类继承IContainerItemProvider.MessageProvider类,实现对应接口的方法 * 1.注意开头的注解 * 2.注意泛型 */ @ProviderTag(messageContent = ShareMessageContent.class, showReadState = true) public class ShareMessageContentItemProvider extends IContainerItemProvider.MessageProvider<ShareMessageContent> { public ShareMessageContentItemProvider() { } @Override public View newView(Context context, ViewGroup viewGroup) { View view = LayoutInflater.from(context).inflate(R.layout.item_share_message_rongyun, null); ViewHolder holder = new ViewHolder(); //控件id //类型1 holder.rl_item1 = (RelativeLayout) view.findViewById(R.id.rl_item1); holder.tv_item1_title = (TextView) view.findViewById(R.id.tv_item1_title); holder.tv_item1_description = (TextView) view.findViewById(R.id.tv_item1_description); holder.iv_item1_img = (ImageView) view.findViewById(R.id.iv_item1_img); //类型二 holder.rl_item2 = (RelativeLayout) view.findViewById(R.id.rl_item2); holder.iv_item2_img = (ImageView) view.findViewById(R.id.iv_item2_img); holder.tv_item2_title = (TextView) view.findViewById(R.id.tv_item2_title); //类型三 // holder.rl_item3 = (RelativeLayout) view.findViewById(R.id.rl_item3); // holder.iv_item3_img = (ImageView) view.findViewById(R.id.iv_item3_img); view.setTag(holder); return view; } @Override public void bindView(View view, int i, ShareMessageContent content, UIMessage message) { ViewHolder holder = (ViewHolder) view.getTag(); // if(message.getMessageDirection() == Message.MessageDirection.SEND){ // view.setBackgroundResource(io.rong.imkit.R.drawable.rc_ic_bubble_right); // // }else { // view.setBackgroundResource(io.rong.imkit.R.drawable.rc_ic_bubble_left); // } if (content != null) { //item1 //资讯,活动,成果转化 if (content.getShareType().equals(ShareTypeModel.SHARETYPENEWS) || content.getShareType().equals(ShareTypeModel.SHARETYPEACTIVE) || content.getShareType().equals(ShareTypeModel.SHARETYPESCIENCERESULIT) ||content.getShareType().equals(ShareTypeModel.SHARETYPECOMPANYNEED)) { holder.rl_item1.setVisibility(View.VISIBLE); holder.rl_item2.setVisibility(View.GONE); // holder.rl_item3.setVisibility(View.GONE); holder.tv_item1_title.setText(content.getShareTitle()); holder.tv_item1_description.setText(content.getShareDescription()); if(!TextUtils.isEmpty(content.getShareImageStr())){ ImageLoader.loadpic2(view.getContext(), content.getShareImageStr(), holder.iv_item1_img); } else{ holder.iv_item1_img.setBackgroundResource(R.mipmap.zhanweitu); } // ImageLoader.loadpic2(view.getContext(), content.getShareImageStr(), holder.iv_item1_img); } else if (content.getShareType().equals(ShareTypeModel.SHARETYPELEARNSOCIETY) || content.getShareType().equals(ShareTypeModel.SHARETYPETRIBE) || content.getShareType().equals(ShareTypeModel.SHARETYPETOPIC) || content.getShareType().equals(ShareTypeModel.SHARETYPEVIDEO) || content.getShareType().equals(ShareTypeModel.SHARETYPEMETTING) || content.getShareType().equals(ShareTypeModel.SHARETYPECIRCLE) || content.getShareType().equals(ShareTypeModel.SHARETYPEWARNING) || content.getShareType().equals(ShareTypeModel.SHARETYPEWEBLINK)) { //item2 holder.rl_item1.setVisibility(View.GONE); holder.rl_item2.setVisibility(View.VISIBLE); // holder.rl_item3.setVisibility(View.GONE); holder.tv_item2_title.setText(content.getShareTitle()); if(!TextUtils.isEmpty(content.getShareImageStr())){ ImageLoader.loadpic2(view.getContext(), content.getShareImageStr(), holder.iv_item2_img); } else{ holder.iv_item2_img.setBackgroundResource(R.mipmap.zhanweitu); } // ImageLoader.loadpic2(view.getContext(), content.getShareImageStr(), holder.iv_item2_img); } // else if(content.getShareType().equals(ShareTypeModel.SHARETYPESCREENPIC)){ // holder.rl_item3.setVisibility(View.VISIBLE); // holder.rl_item1.setVisibility(View.GONE); // holder.rl_item2.setVisibility(View.GONE); // String shareImageStr = content.getShareImageStr(); // if(!TextUtils.isEmpty(shareImageStr)){ // ImageLoader.loadpic(view.getContext(),content.getShareImageStr(),holder.iv_item3_img); // } // } } } @Override public Spannable getContentSummary(ShareMessageContent content) { return new SpannableString("<链接>"+content.getShareTitle()); } //点击监听 @Override public void onItemClick(View view, int i, ShareMessageContent shareMessageContent, UIMessage uiMessage) { LogUtils.d("---->>", "---->> shareMessageContent = " + shareMessageContent.toString()); //这里处理相应的跳转 if (shareMessageContent != null && !TextUtils.isEmpty(shareMessageContent.getShareType())) { String type = shareMessageContent.getShareType(); if (type.equals(ShareTypeModel.SHARETYPENEWS)) { //这是跳转到咨询 Intent intent = new Intent(view.getContext(), NewsDetailActivity.class); intent.putExtra("id", shareMessageContent.getShareId()); view.getContext().startActivity(intent); } else if (type.equals(ShareTypeModel.SHARETYPELEARNSOCIETY)) { //这是跳转到协会 Intent intent = new Intent(view.getContext(), AssociationMainPageActivity.class); intent.putExtra("id", shareMessageContent.getShareId()); view.getContext().startActivity(intent); } else if (type.equals(ShareTypeModel.SHARETYPETRIBE)) { //兴趣部落 view.getContext().startActivity(new Intent(view.getContext(), InterestClubHomeActivity.class).putExtra("gid", shareMessageContent.getShareId())); } else if (type.equals(ShareTypeModel.SHARETYPETOPIC)) { //话题 Intent intent = new Intent(view.getContext(), TopicActivity.class); intent.putExtra("topic_id", shareMessageContent.getShareId()); intent.putExtra("topic_name", "#" + shareMessageContent.getShareTitle() + "#"); view.getContext().startActivity(intent); } else if (type.equals(ShareTypeModel.SHARETYPEACTIVE)) { //视频活动 Intent intent = new Intent(view.getContext(), Intent_Activity.class); intent.putExtra("url", shareMessageContent.getShareUrl()); view.getContext().startActivity(intent); } else if (type.equals(ShareTypeModel.SHARETYPECIRCLE)) { //科猫圈 Intent intent = new Intent(view.getContext(), WeiboDetailActivity3.class); intent.putExtra("id", shareMessageContent.getShareId()); view.getContext().startActivity(intent); } else if (type.equals(ShareTypeModel.SHARETYPESCIENCERESULIT)) { //科技成果 Intent intent = new Intent(view.getContext(), TransformKejiDetailActivity.class); intent.putExtra("id", shareMessageContent.getShareId()); view.getContext().startActivity(intent); } else if (type.equals(ShareTypeModel.SHARETYPEVIDEO)) { //视频 Intent intent = new Intent(view.getContext(), VideosDetailActivity.class); intent.putExtra("videoid", shareMessageContent.getShareId()); intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); view.getContext().startActivity(intent); } else if (type.equals(ShareTypeModel.SHARETYPEMETTING)) { //会议 Intent intent = new Intent(view.getContext(), MeetingDetailActivity.class); intent.putExtra("id", shareMessageContent.getShareId()); view.getContext().startActivity(intent); } else if (type.equals(ShareTypeModel.SHARETYPEWARNING)) { } else if (type.equals(ShareTypeModel.SHARETYPECOMPANYNEED)) { Intent intent = new Intent(view.getContext(), TransformBusinessDetailActivity.class); intent.putExtra("id", shareMessageContent.getShareId()); view.getContext().startActivity(intent); } else if (type.equals(ShareTypeModel.SHARETYPEWEBLINK)) { Intent intent = new Intent(view.getContext(), Intent_Activity.class); intent.putExtra("url", shareMessageContent.getShareUrl()); view.getContext().startActivity(intent); } } } //长按监听 @Override public void onItemLongClick(final View view, int i, final ShareMessageContent content, final UIMessage uiMessage) { //实现长按删除等功能,直接复制融云其他provider的实现 String[] items; // 复制,删除 items = new String[]{view.getContext().getResources().getString(R.string.rc_dialog_item_message_copy), view.getResources().getString(R.string.rc_dialog_item_message_delete)}; OptionsPopupDialog.newInstance(view.getContext(), items).setOptionsPopupDialogListener(new OptionsPopupDialog.OnOptionsItemClickedListener() { @Override public void onOptionsItemClicked(int i) { switch (i) { case 0: ClipboardManager clipboard = (ClipboardManager) view.getContext().getSystemService(Context.CLIPBOARD_SERVICE); clipboard.setText(TextUtils.isEmpty(content.getShareUrl()) ? content.getShareTitle() : content.getShareUrl()); break; case 1: RongIM.getInstance().deleteMessages(new int[]{uiMessage.getMessageId()}, (RongIMClient.ResultCallback) null); break; } } }).show(); } class ViewHolder { RelativeLayout rl_item1, rl_item2; TextView tv_item1_title, tv_item1_description, tv_item2_title; ImageView iv_item1_img, iv_item2_img; } }
-
发送,通过初始化model类将,将该model放在Message中的content中,通过RongIM.getInstance().sendMesssage发出去。
//开始发送消息 //进行分享的操作 Gson gson = new Gson(); String s = gson.toJson(shareModel); //将一个model转化为json字符串 byte[] data = s.getBytes(); //将string转换为byte ShareMessageContent shareMessageContent = new ShareMessageContent(data); io.rong.imlib.model.Message message = new io.rong.imlib.model.Message(); message.setContent(shareMessageContent); message.setTargetId(bean.getUid() + ""); message.setConversationType(Conversation.ConversationType.PRIVATE); message.setMessageDirection(io.rong.imlib.model.Message.MessageDirection.SEND); final String inputContent = input_et.getText().toString(); LogUtils.d("---->>", "---->> inputContent == " + input_et.getText().toString()); final String text = TextUtils.isEmpty(inputContent) ? "" : inputContent; number_tv.setVisibility(View.GONE); LogUtils.d("---->>", "---->> text == " + text); RongIM.getInstance().sendMessage(message, text, text, new IRongCallback.ISendMediaMessageCallback() { @Override public void onProgress(io.rong.imlib.model.Message message, int i) { } @Override public void onCanceled(io.rong.imlib.model.Message message) { pop.dismiss(); } @Override public void onAttached(io.rong.imlib.model.Message message) { } @Override public void onSuccess(io.rong.imlib.model.Message message) { if (!TextUtils.isEmpty(text)) { TextMessage txtMsg = TextMessage.obtain(text); io.rong.imlib.model.Message message1 = io.rong.imlib.model.Message.obtain(bean.getUid() + "", Conversation.ConversationType.PRIVATE, txtMsg); RongIM.getInstance().sendMessage(message1, null, null, new IRongCallback.ISendMediaMessageCallback() { @Override public void onProgress(io.rong.imlib.model.Message message, int i) { } @Override public void onCanceled(io.rong.imlib.model.Message message) { } @Override public void onAttached(io.rong.imlib.model.Message message) { } @Override public void onSuccess(io.rong.imlib.model.Message message) { ToastUtil.show(context, "分享成功"); pop.dismiss(); finish(); } @Override public void onError(io.rong.imlib.model.Message message, RongIMClient.ErrorCode errorCode) { pop.dismiss(); } }); } else { ToastUtil.show(context, "分享成功"); pop.dismiss(); finish(); } } @Override public void onError(io.rong.imlib.model.Message message, RongIMClient.ErrorCode errorCode) { pop.dismiss(); } }); } });
9.融云传送门
-
-
-