mirror of
https://github.com/TencentCloud/TIMSDK.git
synced 2026-10-28 13:43:39 +08:00
186 lines
8.2 KiB
Objective-C
186 lines
8.2 KiB
Objective-C
//
|
|
// NSString+emoji.m
|
|
// TUIChat
|
|
//
|
|
// Created by harvy on 2021/11/15.
|
|
//
|
|
|
|
#import "NSString+emoji.h"
|
|
#import "TUIConfig.h"
|
|
|
|
@implementation NSString (emoji)
|
|
|
|
- (NSString *)getLocalizableStringWithFaceContent
|
|
{
|
|
NSString *content = self;
|
|
NSString *regex_emoji = @"\\[[a-zA-Z0-9\\/\\u4e00-\\u9fa5]+\\]"; //匹配表情
|
|
NSError *error = nil;
|
|
NSRegularExpression *re = [NSRegularExpression regularExpressionWithPattern:regex_emoji options:NSRegularExpressionCaseInsensitive error:&error];
|
|
if (re) {
|
|
NSArray *resultArray = [re matchesInString:content options:0 range:NSMakeRange(0, content.length)];
|
|
TUIFaceGroup *group = [TUIConfig defaultConfig].faceGroups[0];
|
|
NSMutableArray *waitingReplaceM = [NSMutableArray array];
|
|
for(NSTextCheckingResult *match in resultArray) {
|
|
NSRange range = [match range];
|
|
NSString *subStr = [content substringWithRange:range];
|
|
for (TUIFaceCellData *face in group.faces) {
|
|
if ([face.name isEqualToString:subStr]) {
|
|
[waitingReplaceM addObject:@{
|
|
@"range":NSStringFromRange(range),
|
|
@"localizableStr": face.localizableName.length?face.localizableName:face.name
|
|
}];
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (waitingReplaceM.count) {
|
|
// 从后往前替换,否则会引起位置问题
|
|
for (int i = (int)waitingReplaceM.count -1; i >= 0; i--) {
|
|
NSRange range = NSRangeFromString(waitingReplaceM[i][@"range"]);
|
|
NSString *localizableStr = waitingReplaceM[i][@"localizableStr"];
|
|
content = [content stringByReplacingCharactersInRange:range withString:localizableStr];
|
|
}
|
|
}
|
|
}
|
|
return content;
|
|
}
|
|
|
|
- (NSString *)getInternationalStringWithfaceContent
|
|
{
|
|
NSString *content = self;
|
|
NSString *regex_emoji = @"\\[[a-z\\s*A-Z\\s*0-9!-@\\/\\u4e00-\\u9fa5]+\\]"; //匹配表情
|
|
NSError *error = nil;
|
|
NSRegularExpression *re = [NSRegularExpression regularExpressionWithPattern:regex_emoji options:NSRegularExpressionCaseInsensitive error:&error];
|
|
if (re) {
|
|
NSMutableDictionary *faceDict = [NSMutableDictionary dictionary];
|
|
TUIFaceGroup *group = [TUIConfig defaultConfig].faceGroups[0];
|
|
for (TUIFaceCellData *face in group.faces) {
|
|
NSString *key = face.localizableName?:face.name;
|
|
NSString *value = face.name?:@"";
|
|
faceDict[key] = value;
|
|
}
|
|
|
|
NSArray *resultArray = [re matchesInString:content options:0 range:NSMakeRange(0, content.length)];
|
|
NSMutableArray *waitingReplaceM = [NSMutableArray array];
|
|
for(NSTextCheckingResult *match in resultArray) {
|
|
NSRange range = [match range];
|
|
NSString *subStr = [content substringWithRange:range];
|
|
[waitingReplaceM addObject:@{
|
|
@"range":NSStringFromRange(range),
|
|
@"localizableStr": faceDict[subStr]?:subStr
|
|
}];
|
|
}
|
|
|
|
if (waitingReplaceM.count != 0) {
|
|
// 从后往前替换,否则会引起位置问题
|
|
for (int i = (int)waitingReplaceM.count -1; i >= 0; i--) {
|
|
NSRange range = NSRangeFromString(waitingReplaceM[i][@"range"]);
|
|
NSString *localizableStr = waitingReplaceM[i][@"localizableStr"];
|
|
content = [content stringByReplacingCharactersInRange:range withString:localizableStr];
|
|
}
|
|
}
|
|
}
|
|
return content;
|
|
}
|
|
|
|
|
|
|
|
|
|
- (NSMutableAttributedString *)getFormatEmojiStringWithFont:(UIFont *)textFont emojiLocations:(nullable NSMutableArray<NSDictionary<NSValue *, NSAttributedString *> *> *)emojiLocations
|
|
{
|
|
//先判断text是否存在
|
|
if (self.length == 0) {
|
|
NSLog(@"getFormatEmojiStringWithFont failed , current text is nil");
|
|
return [[NSMutableAttributedString alloc] initWithString:@""];
|
|
}
|
|
//1、创建一个可变的属性字符串
|
|
NSMutableAttributedString *attributeString = [[NSMutableAttributedString alloc] initWithString:self];
|
|
if([TUIConfig defaultConfig].faceGroups.count == 0){
|
|
[attributeString addAttribute:NSFontAttributeName value:textFont range:NSMakeRange(0, attributeString.length)];
|
|
return attributeString;
|
|
}
|
|
|
|
//2、通过正则表达式来匹配字符串
|
|
NSString *regex_emoji = @"\\[[a-zA-Z0-9\\/\\u4e00-\\u9fa5]+\\]"; //匹配表情
|
|
|
|
NSError *error = nil;
|
|
NSRegularExpression *re = [NSRegularExpression regularExpressionWithPattern:regex_emoji options:NSRegularExpressionCaseInsensitive error:&error];
|
|
if (!re) {
|
|
NSLog(@"%@", [error localizedDescription]);
|
|
return attributeString;
|
|
}
|
|
|
|
NSArray *resultArray = [re matchesInString:self options:0 range:NSMakeRange(0, self.length)];
|
|
|
|
TUIFaceGroup *group = [TUIConfig defaultConfig].faceGroups[0];
|
|
|
|
//3、获取所有的表情以及位置
|
|
//用来存放字典,字典中存储的是图片和图片对应的位置
|
|
NSMutableArray *imageArray = [NSMutableArray arrayWithCapacity:resultArray.count];
|
|
//根据匹配范围来用图片进行相应的替换
|
|
for(NSTextCheckingResult *match in resultArray) {
|
|
//获取数组元素中得到range
|
|
NSRange range = [match range];
|
|
//获取原字符串中对应的值
|
|
NSString *subStr = [self substringWithRange:range];
|
|
|
|
for (TUIFaceCellData *face in group.faces) {
|
|
if ([face.name isEqualToString:subStr]) {
|
|
//face[i][@"png"]就是我们要加载的图片
|
|
//新建文字附件来存放我们的图片,iOS7才新加的对象
|
|
NSTextAttachment *textAttachment = [[NSTextAttachment alloc] init];
|
|
//给附件添加图片
|
|
textAttachment.image = [[TUIImageCache sharedInstance] getFaceFromCache:face.path];
|
|
//调整一下图片的位置,如果你的图片偏上或者偏下,调整一下bounds的y值即可
|
|
textAttachment.bounds = CGRectMake(0, -(textFont.lineHeight-textFont.pointSize)/2, textFont.pointSize, textFont.pointSize);
|
|
//把附件转换成可变字符串,用于替换掉源字符串中的表情文字
|
|
NSAttributedString *imageStr = [NSAttributedString attributedStringWithAttachment:textAttachment];
|
|
//把图片和图片对应的位置存入字典中
|
|
NSMutableDictionary *imageDic = [NSMutableDictionary dictionaryWithCapacity:2];
|
|
[imageDic setObject:imageStr forKey:@"image"];
|
|
[imageDic setObject:[NSValue valueWithRange:range] forKey:@"range"];
|
|
//把字典存入数组中
|
|
[imageArray addObject:imageDic];
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
//4、从后往前替换,否则会引起位置问题
|
|
NSMutableArray *locations = [NSMutableArray array];
|
|
for (int i = (int)imageArray.count -1; i >= 0; i--) {
|
|
NSRange originRange;
|
|
[imageArray[i][@"range"] getValue:&originRange];
|
|
|
|
//存储位置信息
|
|
NSAttributedString *originStr = [attributeString attributedSubstringFromRange:originRange];
|
|
NSAttributedString *currentStr = imageArray[i][@"image"];
|
|
[locations insertObject:@[[NSValue valueWithRange:originRange], originStr, currentStr] atIndex:0];
|
|
|
|
//进行替换
|
|
[attributeString replaceCharactersInRange:originRange withAttributedString:currentStr];
|
|
}
|
|
|
|
//5、获取 emoji 转换后字符串的位置信息
|
|
NSInteger offsetLocation = 0;
|
|
for (NSArray *obj in locations) {
|
|
NSArray *location = (NSArray *)obj;
|
|
NSRange originRange = [(NSValue *)location[0] rangeValue];
|
|
NSAttributedString *originStr = location[1];
|
|
NSAttributedString *currentStr = location[2];
|
|
NSRange currentRange;
|
|
currentRange.location = originRange.location + offsetLocation;
|
|
currentRange.length = currentStr.length;
|
|
offsetLocation += currentStr.length - originStr.length;
|
|
[emojiLocations addObject:@{[NSValue valueWithRange:currentRange] : originStr}];
|
|
}
|
|
|
|
[attributeString addAttribute:NSFontAttributeName value:textFont range:NSMakeRange(0, attributeString.length)];
|
|
|
|
return attributeString;
|
|
}
|
|
|
|
|
|
@end
|