IM版接入说明

接入SDK,有以下必要步骤:

  1. 下载与安装
  2. 获取必要的接入信息
  3. 开始集成

第一步:下载与安装

目前有两种方式安装SDK:

  • 通过CocoaPods管理依赖。
  • 手动导入SDK并管理依赖。

1. 使用 CocoaPods 导入SDK

在终端中运行以下命令:

pod search BQMM

如果运行以上命令,没有搜到SDK,或者搜不到最新的 SDK 版本,您可以运行以下命令,更新您本地的 CocoaPods 源列表。

pod repo update

在您工程的 Podfile中添加最新版本的SDK(在此以1.2.1版本为例):

pod 'BQMM', '1.2.1'

然后在工程的根目录下运行以下命令:

pod install

2. 手动导入SDK

下载当前最新版本,解压缩后获得两个文件夹

  • BQMM
  • BQMM_EXT

BQMM中包含SDK所需的资源文件BQMM.bundle和库文件BQMM.frameworkBQMM_EXT提供了SDK的默认消息显示控件和消息默认格式的开源代码,开发者们导入后可按需修改。

3. 添加系统库依赖

您除了在工程中导入 SDK 之外,还需要添加libz动态链接库。

第二步:获取必要的接入信息

开发者将应用与SDK进行对接时,必要接入信息如下

  • appId - 应用的App ID
  • appSecret - 应用的App Secret

如您暂未获得以上接入信息,可以在此申请

第三步:开始集成

0. 注册AppId&AppSecret、设置SDK语言和区域

AppDelegate-application:didFinishLaunchingWithOptions: 中添加:

// 初始化SDK
[[MMEmotionCentre defaultCentre] setAppId:@“your app id” secret:@“your secret”]

//设置SDK语言和区域
[MMEmotionCentre defaultCentre].sdkLanguage = MMLanguageEnglish;
[MMEmotionCentre defaultCentre].sdkRegion = MMRegionChina;

1. 添加表情键盘

设置SDK代理

[MMEmotionCentre defaultCentre].delegate = self;

添加表情键盘

if (!_inputTextView.isFirstResponder) {
    [_inputTextView becomeFirstResponder];
}
[[MMEmotionCentre defaultCentre] attachEmotionKeyboardToInput:_inputTextView];

由表情键盘切换为普通键盘

[[MMEmotionCentre defaultCentre] switchToDefaultKeyboard];

2. 在App重新打开时清空session

AppDelegate- (void)applicationWillEnterForeground: 中添加:

[[MMEmotionCentre defaultCentre] clearSession];

3. 添加表情联想(deprecated

[[MMEmotionCentre defaultCentre] shouldShowShotcutPopoverAboveView:self.faceButton withInput:self.inputTextView];

4. 表情消息编辑控件 & 表情消息的解析

SDK提供UITextView+BQMM作为表情编辑控件的扩展实现。

/**
* UITextView的内容解析成的纯文字,例如:你好[厉害]。
*/
@property(nonatomic, assign, readonly, nonnull) NSString *characterMMText;
/**
* UITextView的内容解析出的MMEmoji对象 和 string的数组,例如:`@[@"你好", <Emoji*>]`
*/
@property(nonatomic, assign, readonly, nonnull) NSArray *textImgArray;

5. 实现表情发送代理方法

#pragma mark - *MMEmotionCentreDelegate

//点击键盘中大表情的代理
- (void)didSelectEmoji:(MMEmoji *)emoji
{
    if ([self.delegate respondsToSelector:@selector(didSendMMFace:)]) {
        [self.delegate didSendMMFace:emoji];
    }
}

//点击联想表情的代理
- (void)didSelectTipEmoji:(MMEmoji *)emoji
{
    if ([self.delegate respondsToSelector:@selector(didSendMMFace:)]) {
        [self.delegate didSendMMFace:emoji];
        self.inputTextView.text = @"";
    }
}

//点击表情小表情键盘上发送按钮的代理
- (void)didSendWithInput:(UIResponder<UITextInput> *)input
{
    if ([input isKindOfClass:[UITextView class]]) {
        UITextView *textView = (UITextView *)input;
        NSString *sendStr = textView.characterMMText;
        sendStr = [sendStr stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceCharacterSet]];
        if (![sendStr isEqualToString:@""]) {
            if ([self.delegate respondsToSelector:@selector(didSendTextMessageWithTextView:)]) {
                [self.delegate didSendTextMessageWithTextView:textView];
                self.inputTextView.text = @"";
                [self _willShowInputTextViewToHeight:[self _getTextViewContentH:_inputTextView]];
            }
        }
    }
}

//点击输入框切换表情按钮状态
- (void)tapOverlay
{
    self.faceButton.selected = NO;
}

实际发送消息的方法(环信Demo):

//发送图文混排消息
- (void)didSendTextMessageWithTextView:(UITextView *)textView {
    NSString *sendStr = textView.characterMMText;
    NSArray *textImgArray = textView.textImgArray;
    NSDictionary *mmExt = @{@"txt_msgType":@"emojitype",
                            @"msg_data":[MMTextParser extDataWithTextImageArray:textImgArray]};;
    [self sendTextMessage:sendStr withExt:mmExt];
}

//发送单条大表情的方法

-(void)sendMMFaceMessage:(MMEmoji *)emoji
{
    NSDictionary *ext = @{@"txt_msgType":@"facetype",
                          @"msg_data":[MMTextParser extDataWithEmoji:emoji]};
    EMMessage *tempMessage = [ChatSendHelper sendTextMessageWithString:[NSString stringWithFormat:@"[%@]", emoji.emojiName]
                                                            toUsername:_conversation.chatter
                                                           messageType:[self messageType]
                                                     requireEncryption:NO
                                                                   ext:ext];
    [self addMessage:tempMessage];
}

6. 图文混排消息各形态的转换

BQMM_EXT中提供了MMTextParser,可以实现textImgArraycharacterMMTextextData的互相转换。

+ (NSArray *)extDataWithTextImageArray:(NSArray *)textImageArray;
+ (NSArray *)extDataWithEmojiCode:(NSString *)emojiCode;
+ (NSString *)stringWithExtData:(NSArray *) extData;

说明:

extData是SDK推荐的用于解析的表情消息发送格式(在环信版Demo中作为消息扩展message.ext[@"msg_data"]发送),格式是一个二维数组,内容为拆分完成的textemojiCode,并且说明这段内容是否是一个emojiCode。例:

@[@[@"你好", @"0"], @[@"hhd", @"1"]], @[@"hhd", @"2"]]

0表示文本内容,1表示小表情emojiCode2表示大表情emojiCode

7. 根据Emoji Code下载表情

当APP收到大表情消息时,调用fetchEmojisByType方法,根据消息中的Emoji Code获取Emoji对象。

//大表情显示
self.canPress = NO;
self.imageView.image = [UIImage imageNamed:@"imageDownloadFail.png"];
self.backImageView.hidden = NO;
if ([model.message.ext[@"txt_msgType"] isEqualToString:@"facetype"]) {
    [[MMEmotionCentre defaultCentre] fetchEmojisByType:MMFetchTypeBig codes:@[model.message.ext[@"msg_data"][0][0]] completionHandler:^(NSArray *emojis) {
        if (emojis.count > 0) {
            MMEmoji *emoji = emojis[0];
            self.imageView.image = emoji.emojiImage;
            self.canPress = YES;
        }
        else {
            self.imageView.image = [UIImage imageNamed:@"mm_emoji_error.png"];
        }
    }];
    self.backImageView.hidden = YES;
    return;
}

下载表情时,需要指定表情类型,MMFetchType枚举类指定表情类型,定义如下:

typedef enum
{
    MMFetchTypeSmall    = 1 << 0,
    MMFetchTypeBig      = 1 << 1,
    MMFetchTypeAll      = 1 << 2  //只用于评论版
} MMFetchType;

8. 表情消息显示

SDK Demo提供MMTextView.hMMTextView.m作为显示表情消息的示例。使用方法:

_textView = [[MMTextView alloc] initWithFrame:CGRectZero];
_textView.mmFont = [UIFont systemFontOfSize:LABEL_FONT_SIZE];
_textView.mmTextColor = [UIColor blackColor];
_textView.backgroundColor = [UIColor clearColor];
_textView.userInteractionEnabled = NO;
_textView.multipleTouchEnabled = NO;
[self addSubview:_textView];

另外,开发者可参照MMTextView中的updateAttributeTextWithData:completionHandler:方法定义自己的表情消息显示方式。参数extData是拆分过的文本和emojiCode

- (void)updateAttributeTextWithData:(NSArray*)extData completionHandler:(void(^)(void))completionHandler {
    NSMutableArray *codes = [NSMutableArray array];
    __block NSMutableArray *textImgArray = [NSMutableArray array];
    for (NSArray *obj in extData) {
        NSString *str = obj[0];
        BOOL isEmoji = [obj[1] integerValue] == 0 ? NO : YES;
        if (isEmoji) {
            if (![codes containsObject:str]) {
                [codes addObject:str];
            }
        }
        [textImgArray addObject:str];
    }

    //
    [[MMEmotionCentre defaultCentre] fetchEmojisByType:MMFetchTypeAll codes:codes completionHandler:^(NSArray *emojis) {
        NSMutableAttributedString *mAStr = [[NSMutableAttributedString alloc] init];
        for (MMEmoji *emoji in emojis) {
            NSInteger objIndex = [textImgArray indexOfObject:emoji.emojiCode];
            while (objIndex != NSNotFound) {
                [textImgArray replaceObjectAtIndex:objIndex withObject:emoji];
                objIndex = [textImgArray indexOfObject:emoji.emojiCode];
            }
        }
        for (id obj in textImgArray) {
            if ([obj isKindOfClass:[MMEmoji class]]) {
                MMTextAttachment *attachment = [[MMTextAttachment alloc] init];
                attachment.emoji = obj;
                if ([attachment.image.images count] > 1) {
                    attachment.image = [attachment placeHolderImage];
                }
                [mAStr appendAttributedString:[NSAttributedString attributedStringWithAttachment:attachment]];
            } else {
                [mAStr appendAttributedString:[[NSAttributedString alloc] initWithString:obj]];
            }
        }
        if (self.mmFont) {
            [mAStr addAttribute:NSFontAttributeName value:self.mmFont range:NSMakeRange(0, mAStr.length)];
        }
        if (self.mmTextColor) {
            [mAStr addAttribute:NSForegroundColorAttributeName value:self.mmTextColor range:NSMakeRange(0, mAStr.length)];
        }
        self.attributedText = mAStr;
        if (completionHandler) {
            completionHandler();
        }
    }];
}

9. 添加表情详情页面

在点击大表情消息时添加单个表情详情页面,在详情页面可以查看和下载表情包信息。

UIViewController *emojiController = [[MMEmotionCentre defaultCentre] controllerForEmotionCode:model.message.ext[@"msg_data"][0][0]];
[self.navigationController pushViewController:emojiController animated:YES];

10. gif 搜索

MMEmotionCentre中有两个gif的数据接口,可以用于实现gif的搜索功能。

1.流行gif数据接口

- (void)trendingGifsAt:(int)page
          withPageSize:(int)pageSize
     completionHandler:(void (^ __nonnull)(NSArray<MMGif *> * __nullable gifs, NSError * __nullable error))completionHandler;

2.搜索gif数据接口

- (void)searchGifsWithKey:(NSString * _Nullable)key
                       At:(int)page
             withPageSize:(int)pageSize
        completionHandler:(void (^ __nonnull)(NSString * __nonnull searchKey, NSArray<MMGif *> * __nullable gifs, NSError * __nullable error))completionHandler;

点击表情键盘底栏的gif按钮代理, 在此代理方法中实现触发gif搜索功能

- (void)didClickGifTab;

说明:BQMM随SDK同时开放了一整套gif搜索的实现源码(BQMM_GIF目录),可用于参考实现gif搜索,及gif消息的发送解析。

11. UI定制

SDK通过MMTheme提供一定程度的UI定制。具体参考类说明MMTheme

创建一个MMTheme对象,设置相关属性, 然后[[MMEmotionCentre defaultCentre] setTheme:]即可修改商店和键盘样式。

12. 清除缓存

调用clearCache方法清除缓存,此操作会删除所有临时的表情缓存,已下载的表情包不会被删除。建议在- (void)applicationWillTerminate:(UIApplication *)application方法中调用。

13. 设置APP UserId

开发者可以用setUserId方法设置App UserId,以便在后台统计时跟踪追溯单个用户的表情使用情况。

results matching ""

    No results matching ""