原文:http://www.cnblogs.com/lujianwenance/p/5716804.html

本文的目的是希望能帮助到我们更快的熟悉和学习YYText的结构和实现的思路,如有不正确或者不准确的地方请指正,谢谢。  
一、特点与用法
关于YYText的特点和用法请看@ibireme大神的github:
https://github.com/ibireme/YYText
二、使用到的组件
1、介绍YYLabel之前先说一下YYTextAttribute,因为后面会大量的使用到它。
YYTextAttribute:
1)定义的一些Enum,YYTextAttributeType:attribute的类型,有None、UIKit、CoreText和YYText四种类型;YYTextLineStyle:line的样式;YYTextVerticalAlignment:垂直方向text的位置;YYTextDirection:text的位置;YYTextTruncationType:text截断的位置。
2)YYText中定义的Attribute Name。主要是独有的一些类型。
3)YYTextBackedString:可以将一些表情图片映射成纯文本。
4)YYTextBinding:使一些特定的字符串绑定在一起,YYTextView在选择和编辑他们的时候把他们当成一个单独的字符。
5)YYTextShadow:用处和NSShadow一样,只是比NSShadow多了一些功能,比如说可以使用blendMode(图形混合模式)、可以在shadow上再加一层shadow。关于blendMode的学习,可以参见喵神的博客:https://onevcat.com/2013/04/using-blending-in-ios/
6)YYTextDecoration:实现下划线(underline)和中间截线(strikethrough)时使用,线条的形式给出了几种样式,可以通过YYTextLineStyle枚举查看。具体是underline还是strikethrough是在NSAttributedString+YYText中NSMutableAttributeString(YYText)中实现的方法。
7)YYTextBorder:实现在文本周围画一个border,也可以是填充一个背景色。
8)YYTextAttachment:封装需要放入text中的对象。在说明文档中提到,如果attachment是UIImage,就绘制到CGContext,如果是UIView或者CALayer就加入到text container的view或者layer中。
9)YYTextHightlight:当YYLabel或者YYTextView中的text可以被用户按下时,被按下的text会有一个highlighted 状态,这时候就需要是用YYTextHighlight来修改原来的text。所以这个对象和YYText一样,只是是在highlight状态下的YYText,而且添加了点击和长按事件。
2、再来说一下NSAttributedString+YYText文件
在这个分类中主要是实现了几类的操作:
1)一些操作当前attributed string的方法
比如说归档和反归档当前字符串、获得某个位置的attributes、字间距、色值、背景色、shadow等等。具体的参见文件,基本上是作者封装的方便获得各种数据的方法。(和Foundation中比强大太多了)。
2)为YYText创建attachment的方法
3)为YYText添加YYText特有的attribute的方法
4)添加像设置属性一样的设置character attribute的font、color、backgroundColor等等的方法。
5)添加像设置属性一样的设置paragraph attribute的方法。
6)添加像设置属性一样的设置YYText attribute的方法。 
7)使用range设置不连续的attribute的方法
8)设置text highlight 的便捷方法
9)和其他的工具型的方法。
3、NSParagraphStyle+YYText文件

提供了CoreText中的CTParagraphStyleRef和NSParagraphStyle之间的转化。
4、YYTextParser
这是一个protocol,声明了一个-(BOOL)parseText:(NSMutableAttributedString *)string selectedRange:(NSRangePointer)selectedRange;方法。这个方式是遵守这个协议必须实现的方法,当YYTextView或者YYLabel中的text改变时被调用。返回YES说明修改了这个text。
作者简单的实现了MarkdownParser和EmotionParser,两个原理都差不多一样,在这里只对EmotionParser做一下简单的介绍,希望能有所启发:

这段代码就是生成正则表达式_regex和映射的字典_mapper,第一层for是获得你要匹配的key,第二层是如果有这些特殊的字符需要转译一下,然后将这些需要比配的key 用“|”连接起来。
这个就是修改text之后会被调用的方法,在这个方法里对输入的text进行匹配,如果匹配到之前_mapper中需要替换的字符,就将这个字符串替换为需要替换的表情符。
替换成表情符之后就需要重新计算这个表情符所占的range了,这个方法就是拿到替换之后的的range。
5、YYTextLayout
先看一下文档中的说明,如下图:
是不是很眼熟?好像在哪见过?是的,就是NSLayoutManager和NSTextContainer。他们的作用都是相似的。
1)YYTextContainer
支持矩形(CGSize)和图形(UIBezierPath)来初始化YYTextContainer;
在这里重点说一下YYTextLinePositionModifier,它是 一个协议,定义了一个必须实现的方法,这个方法将会在layout完成的时候被调用,三个参数分别是存放YYTextLine的数组、完整的text和layout container。
YYTextLine:它是封装了CTLineRef的对象,封装了每一行text的具体展示位置、range、这一行拥有的attachments等等,只有一个类方法的初始化方法。如果不了解一些自行描述集的内容,对textLine中的一些属性和操作会不是很清晰,看下图:
边框(Bounding Box):一个假想的边框,尽可能地容纳整个字形。
基线(Baseline):一条假想的参照线,以此为基础进行字形的渲染。一般来说是一条横线。
基础原点(Origin):基线上最左侧的点。
行间距(Leading):行与行之间的间距。
字间距(Kerning):字与字之间的距离,为了排版的美观,并不是所有的字形之间的距离都是一致的,但是这个基本步影响到我们的文字排版。
上行高度(Ascent)和下行高度(Decent):一个字形最高点和最低点到基线的距离,所以行高就是ascent + decent。
看完上面的简单介绍你就能明白,在YYTextLine的setCTLine中的代码逻辑是从CTLineRef中取出对应的行宽、上行高度、下行高度、行间距、rangge和第一个字型符的位置(这个在垂直布局会用到)。之后调用reloadBounds方法,重新计算当前行的bounds、attachments所在的range和rect。
2)YYTextLayout
这个真的是核心内容了,这个文件一共3300多行的代码,从代码量上就能看出它的地位。这个类中存储着text的layout结果,所有的property都是readonly的。实现的接口有:
1、通过一些类方法初始化的方法(YYTextContainer、CGSize和text)
2、layout之后的attributes,都是只读的
3、从layout中读取信息(位置、range等等)
4、绘制text layout
这个类主要是使用上面讲过的所有的数据来绘制text,这部分的代码还是需要一点一点的去读的,如果是新手每一行都会有收获(比如说我),如果是老司机就没有必要一行行的读了,了解他的解题思路和解决这个问题的办法就可以。下面说一下生成layout的那个500行代码的情况,就按照代码的顺序从上往下大概的说明一下干了什么。
1)、初始化一系列使用到的变量
2)、安全判断,text和container
3)、判断是否需要修复emoji的bug(iOS8.3中)
4)、判断是否设置了path属性和exclusionPaths数组,做相应的计算拿到cgpath,如果cgpath为空则goto fail 返回nil(如果设置了path,size和insets就没有用了)
5)、判断是不是奇偶填充,判断pathWidth是否为0,判断是否是垂直展示
6)、使用text创建CTFramesetterRef,创建失败goto fail
7)、使用上一步中创建的frameSetter创建CTFrameRef
8)、从CTFrameRef的对象中获得每一行、ctRun数组,计算每一行的frame,判断是否实现了linePositionModifier这个协议,有的话调用协议方法。
9)、计算bounding size
10)、判断是否需要truncation,和按那种方式处理
11)、判断是否垂直布局text,需要的话,旋转布局
12)、判断得到的visibleRange长度,有效的话遍历text中的attributes,配置对应的layout属性
13)、配置layout中的attachments
14)、配置结束,返回layout
绘制时就是根据layout中的配置情况绘制相应的特征,这段代码在此就不做分析了。
6、YYAsyncLayer文件
YYAsyncLayerDispalyTask是在YYAsyncLayer去background queue 渲染是调用的对象,它有三个回调,一个willDisplay在渲染之前、一个didDisplay在渲染之后和渲染时被调用的display。
YYAsyncLayer是CAlayer的子类,当这个layer更新contents时就会调用delegate方法去调用async display task 去background queue 渲染。这个delegate方法是YYAsyncLayerDelegate的方法。
YYAsyncLayer在刷新时调用_displayAsync:方法,然后调用遵守YYAsyncLayerDelegate的对象实现的newAsyncDisplayTask方法,获取到需要绘制的前后和绘制时的task,根据是够需要异步来判断直接在主线程执行绘制代码还是异步执行绘制代码。
在异步绘制过程中用到了一个异步队列,获取方法是YYAsyncLayerGetDisplayQueue,在这个方法中有一个关于QOS的概念,NSQualityOfService(QOS)ios8之后提供的新功能,这个枚举值是要告诉操作系统我们在进行什么样的工作,让系统能通过合理的资源控制来最高效的执行任务代码,主要涉及CPU调度、IO优先级、任务运行在哪个线程以及运行的顺序等等。

枚举值的含义如下:
NSQualityOfServiceUserInteractive
与用户交互的任务,这些任务通常跟UI级别的刷新相关,比如动画,这些任务需要在一瞬间完成
NSQualityOfServiceUserInitiated
由用户发起的并且需要立即得到结果的任务,比如滑动scroll view时去加载数据用于后续cell的显示,这些任务通常跟后续的用户交互相关,在几秒或者更短的时间内完成
NSQualityOfServiceUtility
一些可能需要花点时间的任务,这些任务不需要马上返回结果,比如下载的任务,这些任务可能花费几秒或者几分钟的时间

            NSQualityOfServiceBackground
            这些任务对用户不可见,比如后台进行备份的操作,这些任务可能需要较长的时间,几分钟甚至几个小时

            NSQualityOfServiceDefault

            优先级介于user-initiated 和 utility,当没有 QoS信息时默认使用,开发者不应该使用这个值来设置自己的任务

Qos和GCD queue的对照图:
看详细的分析请到这里:http://www.jianshu.com/p/f9e01c69a46f

收获到的小知识点:
1、iOS7 and later,UIFont 和CTFontRef是 toll-free bridged的,在iOS6,UIFont是对CTFontRref的封装,所以在CoreText中是可以使用UIFont的,但是在UILabel和UITextView中不能使用CTFontRef。
2、NSParagraphStype不是toll-free bridged 到CTParagraphStypeRef,CoreText可以同时使用两者,但UILabel和UITextView只能使用NSParagraphStyle。
3、查看.a静态文件支持哪种iOS处理器

转载于:https://www.cnblogs.com/mkai/p/7295542.html

YYKit之YYText相关推荐

  1. iOS开发学习之YYKit中YYText的深入解析,YYTextShadow的代码解析

    上面的阴影效果是用这样的代码实现的: 可以看到先生成了 YYTextShadow, 然后赋值给了 attributedString 的 yy_textShadow,然后再把 attributedStr ...

  2. yytextview多种格式_iOS YYText的使用笔记一(YYTextView图文编辑器)

    YYText是强大的YYKit的一部分可以单独下载 Powerful text framework for iOS to display and edit rich text. (It's a com ...

  3. 专访 YYKit 作者 ibireme: 开源大牛是怎样炼成的

    前言 第一次听到 ibireme 这个名字,是看到他在 微博上分享 了 YYText 开源库.当时我第一眼见到 YYText 的功能示意 GIF 图时(下图所示),就被它丰富的功能吸引了.YYText ...

  4. iOS YYText的使用笔记一(YYTextView图文编辑器)

    YYText是强大的YYKit的一部分可以单独下载 Github地址 :    https://github.com/ibireme/YYText Powerful text framework fo ...

  5. YYText使用遇到的问题--文本无法点击

    突然想学学YYKit,一开始现将self.titleLb赋值了,然后再设置 yy_setTextHighlightRange ,发现点击了没有任何的反应,最后才发现,得先设置yy_setTextHig ...

  6. 一组功能丰富的iOS组件:YYKit

    YYKit 是一组庞大.功能丰富的 iOS 组件. 为了尽量复用代码,这个项目中的某些组件之间有比较强的依赖关系.为了方便其他开发者使用,我从中拆分出以下独立组件: -YYModel - 高性能的 i ...

  7. iOS tableView性能优化之异步排版和绘制渲染----YYText框架学习(YYTextAsyncLayer)

    YYWebImage源码分析 YYImage源码 YYModel源码解析 前言 这段时间针对设计架构,解耦以及性能优化相关的知识点看了不少,前两者可以看MVVM和AOP编程思路,最后一个是昨天看的,Y ...

  8. layer 同步调用_YYText源码解读-YYText同步/异步渲染流程(一)—UIView与CALayer

    一.CALayer官方文档 Layers are often used to provide the backing store for views but can also be used with ...

  9. YYKit学习系列 ---- 开篇

    准备花半年时间系统学习YYKit,  学习过程会放入"YYKit学习系列"这个分类, 喜欢YYKit的可以随时留意我的文章, 一起学习!!! 转载于:https://www.cnb ...

  10. yytextview多种格式_YYKit之YYText

    原文:http://www.cnblogs.com/lujianwenance/p/5716804.html 本文的目的是希望能帮助到我们更快的熟悉和学习YYText的结构和实现的思路,如有不正确或者 ...

最新文章

  1. CQOI2015 任务查询系统
  2. 多路I/O转接服务器——epoll
  3. thymeleaf 获取yml中的值_SpringBoot引入Thymeleaf
  4. ipv6链路本地地址ping不通
  5. 前端学习(1339):mongodb更新数据文档
  6. hibernate基本类型映射
  7. Nginx: error while loading shared libraries: libpcre.so.1解决
  8. 7、监控和管理Linux进程
  9. php利用mht导出word,解析掌握PHP导出Word文档原理
  10. c语言编译器pellc,单片机C语言程序的设计实训100例_基于8051+PROTEUS仿真1
  11. pip下载更新及采用镜像安装numpy、matplotlib等包
  12. 个人制作:AD库、元件库、封装库及3D模型,免费
  13. 你有必要不沾计算机一段时间英语,八年级英语下册unit 1必背词组及句子(新人教版).docx...
  14. 瑞禧PLGA-PEG-Val-Thr-Cys-Gly 聚乙二醇
  15. @value 读取yml没有读到
  16. 数据库(oracle)服务器的cpu大于80%
  17. Cause: java.sql.SQLException: SQL String cannot be empty 解决方案
  18. 我的第一篇 实习报告
  19. sql server 2008 R2 数据库文件大小限制
  20. 如何使用React创建视频和动画

热门文章

  1. 费曼纪念日,霍金和蚁人下了一盘的“量子象棋”
  2. 在Windows10上安装3Ds Max完整教程
  3. 单片机技术与c语言编程教学大纲,《单片机原理及应用》课程教学大纲
  4. 微型计算机原理及应用课程复习与考研指导,微机原理及应用课程复习.doc
  5. 新萝卜家园 Ghost XP SP3 电脑城装机专用版 10.5
  6. 天超级计算机,2、天啦,古老的超级计算机!
  7. Windows系统安装adb/fastboot驱动教程
  8. Win10 Android Fastboot驱动问题
  9. 千里达v1000时速_《美骑评测》第10期 千里达V1000山地车 评测
  10. 发送邮件服务器错误怎么更改,怎么解决SMTP服务器发送邮件失败