Closed 112292454 closed 2 years ago
如果希望在simbot3中发送转发消息,以一个群消息事件为例:
@Listener
public void onGroupMessageEvent(MiraiGroupMessageEvent event) {
// 得到此事件的所在群,并得到这个群原生的mirai contact对象。
// 其他Mirai组件特供的对象也都有类似的功能,例如 MiraiMember.getOriginalContact
// 可以通过此方式来得到mirai原生的对象类型。
final Group groupContact = event.getGroup().getOriginalContact();
// 事件也是一样的。你可以在simbot所包装的Mirai事件中直接得到mirai原生事件。
// 这里的 GroupMessageEvent是mirai的事件类型,而不是simbot的。
final GroupMessageEvent originalEvent = event.getOriginalEvent();
// 同理,消息也是。除了部分simbot标准消息类型以外(例如simbot中的At、Text),
// 所有由mirai组件特殊实现的消息类型都会实现 MiraiSimbotMessage 接口。
// 所有从接收的事件中得到的、由mirai组件特殊实现的消息类型都会实现 OriginalMiraiComputableSimbotMessage 接口。
// 但是,如果你更希望直接操作原本的mirai消息链,则可能会更加方便。上文中我们已经得到了mirai的原生消息类型,
// 因此你可以直接得到此事件的最原始的消息链。
// mirai原生的消息链对象
final MessageChain messageChain = originalEvent.getMessage();
final ForwardMessageBuilder builder = new ForwardMessageBuilder(groupContact);
// 转发当前这条消息。
// 使用一开始说到的方式,得到当前消息事件的发送者,然后把消息链放进去。
builder.add(event.getAuthor().getOriginalContact(), messageChain);
// 构建转发消息
final ForwardMessage forwardMessage = builder.build();
// 发送消息
// 两种方式。第一种,通过simbot的 send/sendBlocking 发送。将ForwardMessage转化为simbot的消息对象即可。
// 第二种,你上面得到了mirai原生的群对象,那么你可以直接通过mirai本身的api发送。
// 这里以第一种为例。
event.sendBlocking(MiraiMessageParserUtil.asSimbotMessage(forwardMessage));
}
其中需要注意的地方:
MiraiGroupMessageEvent
,这代表你监听的是一个mirai组件专门提供/实现的消息事件。如果你监听的是simbot标准api中的 GroupMessageEvent
,那么你需要提前判断类型再进行操作,例如:if(event instanceof MiraiGroupMessageEvent) {...}
好家伙九点 这效率 太强了
看了您的代码和这里面一些类具体的关系
我理解是 现在3.0消息类型(Text这种simbot.message下的)还没有实现转发消息,因此只能用mirai的api。这其中simbot提供了一个过渡对接的封装,比如MiraiGroupMessageEvent;而上面与之前那个issue的转发方式相仿,在getOriginalxxxx()
之后就整个是使用mirai的内容来构建消息,最后再转换成simbot的消息对象或者直接发送 这样子吗?
我目前想实现的功能类似于一个比较通用的public Messages buileForwardMsgByList (ArrayList<Messages> messagesList)
(参考上面的代码似乎还需要传入一个event来得到contact才能构建?),通过已有的数个messages得到转发消息(为了避免刷屏)。
如果是上面的情况,想法就是解析传入的Messages,然后用mirai的api来重新构建消息内容、再构建成转发形式、返回。发现这第一步的功能MiraiMessageParserUtil.toOriginalMiraiMessage()
看名字似乎已经实现了;但它最后一个参数的Continuation不是很理解是什么,怎么得到;contact生搬硬套用前面的不知道是否可行
发现这第一步的功能MiraiMessageParserUtil.toOriginalMiraiMessage()看名字似乎已经实现了;但它最后一个参数的Continuation不是很理解是什么,怎么得到;
toOriginalMiraiMessage
实际上应当是一个不应暴露给Java的Kotlin API。
如果希望合并多个消息 ,参考:
@Listener
public void onGroupMessageEvent(MiraiGroupMessageEvent event) {
// 得到此事件的所在群,并得到这个群原生的mirai contact对象。
// 其他Mirai组件特供的对象也都有类似的功能,例如 MiraiMember.getOriginalContact
// 可以通过此方式来得到mirai原生的对象类型。
final Group groupContact = event.getGroup().getOriginalContact();
// 准备转发消息
final ForwardMessageBuilder builder = new ForwardMessageBuilder(groupContact);
// 假设这里有多个消息。
// 在构建转发消息的过程中,对于一个完整的消息,使用 MessageContent 会更简单。
// 如果执意要使用Messages而不是MessageContent,那么你需要再遍历Messages中的每一个消息元素,并分别单独的判断并处理。
List<MessageContent> messageContentList = new ArrayList<>();
//
for (MessageContent messageContent : messageContentList) {
// 如果 messageContent 来自于mirai组件事件,那么他就会是 MiraiReceivedMessageContent 类型。
if (messageContent instanceof MiraiReceivedMessageContent) {
// 得到原始的消息链
final MessageChain originalMessageChain = ((MiraiReceivedMessageContent) messageContent).getOriginalMessageChain();
// 拼接到转发消息中
// 这里假设转发消息中的'发送人'都是当前事件的人。
final Member originalAuthor = event.getAuthor().getOriginalContact();
builder.add(originalAuthor, originalMessageChain);
}
}
// 构建转发消息
final ForwardMessage forwardMessage = builder.build();
// 发送消息
// 两种方式。第一种,通过simbot的 send/sendBlocking 发送。将ForwardMessage转化为simbot的消息对象即可。
// 第二种,你上面得到了mirai原生的群对象,那么你可以直接通过mirai本身的api发送。
// 第一种:
event.sendBlocking(MiraiMessageParserUtil.asSimbotMessage(forwardMessage));
// 第二种:
// groupContact.sendMessage(forwardMessage);
}
其他方面:可以追踪 https://github.com/simple-robot/simbot-component-mirai/issues/56 来关注对转发消息内容封装的进度、提供贡献或参与讨论。
此issue已经在「等待反馈」状态下5日未应答。如果在「陈旧」状态下逾期2日将会被视为无效过期并关闭。
此issue已经在「陈旧」状态下逾期2日未应答, 视为无效过期并关闭。
版本号
v3.0
疑问描述
我看了issue#169里面您说明的,使用mirai的MiraiMessageContentBuilder构建forwardMessage来实现转发消息的方式。 但是现在我将消息整个使用3.0的messages来发送,而mirai的组件似乎自然地,并不支持直接使用messages或者element来构建;之后我去
看了说明文档,也没有在里面发现类似转发消息的类。 是否我在这过程中忽略了什么地方;或者有什么比较方便的,由新的message转换到最开始那个构建转发的办法?