连续表情无法正常显示
[smile][smile][smile][smile][smile][smile][smile][smile][smile][smile]
无法显示正常
确实发现这个bug了
这个bug的问题,是因为下标计算错了 提供一下我修复好的算法
/**
- 解析字符串中url内容生成Run对象
- @param attributedString 内容
- @return TQRichTextRunURL对象数组 */
- (NSArray *)runsForAttributedString:(NSMutableAttributedString *)attributedString { NSString *markL = @"["; NSString *markR = @"]";
NSString *string = [NSString stringWithString:attributedString.string];
NSMutableArray *array = [NSMutableArray array]; NSMutableArray *stack = [[NSMutableArray alloc] init];
for (int i = 0, index = 0; i < string.length; i++, index++) { NSString *s = [string substringWithRange:NSMakeRange(i, 1)];
if (([s isEqualToString:markL]) || ((stack.count > 0) && [stack[0] isEqualToString:markL]))
{
if (([s isEqualToString:markL]) && ((stack.count > 0) && [stack[0] isEqualToString:markL]))
{
[stack removeAllObjects];
}
[stack addObject:s];
// 检测到表情结束符后,进行提取表情
if ([s isEqualToString:markR] || (i == string.length - 1))
{
NSMutableString *emojiStr = [[NSMutableString alloc] init];
for (NSString *c in stack)
{
[emojiStr appendString:c];
}
if ([[TQRichTextRunEmoji emojiStringArray] containsObject:emojiStr])
{
NSRange range = NSMakeRange(index + 1 - emojiStr.length, emojiStr.length);
[attributedString replaceCharactersInRange:range withString:@" "];
TQRichTextRunEmoji *run = [[TQRichTextRunEmoji alloc] init];
run.range = NSMakeRange(index + 1 - emojiStr.length, 1);
run.text = emojiStr;
run.drawSelf = YES;
[run decorateToAttributedString:attributedString range:run.range];
[array addObject:run];
}
index -= (stack.count - 1); // 此下标是计算表情被替换后的下标
[stack removeAllObjects];
}
}
}
return array; }
刚Checkout下来的代码,发现几个问题:
-
表情无法连续显示,解决方法: 在+ (NSArray *)runsForAttributedString:(NSMutableAttributedString *)attributedString方法中修改
if ([emojiTags containsObject:emojiStr]) { NSRange range = NSMakeRange(i + 1 - emojiStr.length, emojiStr.length); [attributedString replaceCharactersInRange:range withString:@" "]; TQRichTextRunEmoji *run = [[TQRichTextRunEmoji alloc] init]; run.range = NSMakeRange(i + 1 - emojiStr.length, 1); run.text = emojiImageNames[[emojiTags indexOfObject:emojiStr]]; run.drawSelf = YES; [run decorateToAttributedString:attributedString range:run.range]; [array addObject:run]; // 解决连续表情无法显示的问题 i = i - emojiStr.length + 1; } -
文字颜色设置无效的问题:在TQRichTextView的- (void)drawRect:(CGRect)rect方法中,添加
[attString addAttribute:(NSString *)kCTForegroundColorAttributeName value:(id)self.textColor.CGColor range:NSMakeRange(0,attString.length)]; -
如果一行中,只有表情或者只有英文+表情,会导致表情高度不对被压缩的问题(中文文字占用高度比小写英文多,所以表情会正常):
if (richTextRun.drawSelf) { CGFloat runAscent,runDescent; CGFloat runWidth = CTRunGetTypographicBounds(runRef, CFRangeMake(0,0), &runAscent, &runDescent, NULL); CGFloat runHeight = (lineAscent + lineDescent ); CGFloat runPointX = runRect.origin.x + lineOrigin.x; CGFloat runPointY = lineOrigin.y ; // 解决如果只有表情没有文字,表情高度被压缩的问题 CGRect runRectDraw = CGRectMake(runPointX, runPointY - 5, runWidth, runHeight); if (runRectDraw.size.height < runRectDraw.size.width) { runRectDraw.size.height = runRectDraw.size.width; } [richTextRun drawRunWithRect:runRectDraw]; [self.runRectDictionary setObject:richTextRun forKey:[NSValue valueWithCGRect:runRectDraw]]; } else { if (richTextRun) { [self.runRectDictionary setObject:richTextRun forKey:[NSValue valueWithCGRect:runRect]]; } }