浅析NSTextContainer

简介:

浅析NSTextContainer

TextKit中的NSTextContainer有点晦涩难懂,如果想用TextKit实现文本分页的效果,你是必须要使用NSTextContainer的......

他们的关系是这样子的:

NSTextStorage  ---> NSLayoutManager ---> 多个NSTextContainer

当你添加了几个NSTextContainer的时候,对应的那个NSTextContainer实际上已经分页好了,下面用例子来验证结论:

- (void)viewDidLoad
{
    [super viewDidLoad];
    
    // 数据源
    NSString *string = [NSString stringWithContentsOfURL:[NSBundle.mainBundle URLForResource:@"bubizhidaowoshishui" withExtension:@"txt"] usedEncoding:nil
                                                   error:nil];
    
    // 文本容器
    NSTextStorage *storage = [[NSTextStorage alloc] initWithString:string];
    
    // 文本容器的布局管理器
    NSLayoutManager *layoutManager = [NSLayoutManager new];
    [storage addLayoutManager:layoutManager];
    
    // 分段显示文本容器中的内容
    CGSize size = CGSizeMake(300, 540);
    NSTextContainer *textContainer1 = [[NSTextContainer alloc] initWithSize:size];
    [layoutManager addTextContainer:textContainer1];
    NSTextContainer *textContainer2 = [[NSTextContainer alloc] initWithSize:size];
    [layoutManager addTextContainer:textContainer2];
    NSTextContainer *textContainer3 = [[NSTextContainer alloc] initWithSize:size];
    [layoutManager addTextContainer:textContainer3];
    NSTextContainer *textContainer4 = [[NSTextContainer alloc] initWithSize:size];
    [layoutManager addTextContainer:textContainer4];
    
    // 给TextView添加带有内容和布局的容器
    UITextView *textView = [[UITextView alloc] initWithFrame:CGRectMake(10, 20,
                                                                        size.width, size.height)
                                               textContainer:textContainer1];
    textView.layer.borderWidth = 1;
    textView.scrollEnabled     = NO;
    textView.editable          = NO;
    [self.view addSubview:textView];
    
    // 验证
    if (textView.textStorage == storage)
    {
        NSLog(@"textView.textStorage == storage");
    }
    
    if (textView.layoutManager == layoutManager)
    {
        NSLog(@"textView.layoutManager == layoutManager");
    }
    
    NSLog(@"计算的页码数:%f", [textView sizeThatFits:CGSizeMake(300, FLT_MAX)].height / 540.f);
}

注意看下面的关系:

修改一下源码后,如下打印(注意将容器换成了textContainer2了):

你会发现,textContainer2显示了第二页的内容,但是呢,你会发现整个UITextView的页码变成了119了.

其实,看到这里,结论已经相当明显了.

NSLayoutManager就像一个队列一样,它会将添加到NSLayoutManager中的NSTextContainer自动按照进入队列的顺序来给NSTextContainer赋值,最先进入队列的NSTextContainer将会有着最多显示的内容,往后进入队列的NSTextContainer会依次递减(发现这个花了我半天时间-_-!!).

 

还有一点内容相当重要哦:)

看起来,你可能觉得UITextView仅仅持有了一个NSTextContainer,其实,他还接管了你在上面定义的那个NSTextStorage以及layoutManager,这一点很容易被忽视掉得.

也就是说(个人观点):

       UITextView在获取到了NSTextContainer后,会自动的接管了与这个NSTextContainer相关的所有配置,UITextView将自身包含的textStorage以及layoutManager替换成了NSTextContainer相关配置.

 

 

附录:

解析1.3M的txt文本.

花了将近3.3s......

 

拖动时占用内存的情况:

这内存长的有点恐怖哦:)

目录
相关文章
|
JSON 自然语言处理 编译器
Alibaba.com瘦包40MB——业界最全的iOS包大小技术总结
前言包大小是衡量APP性能的一项重要指标,它直接影响用户的下载点击率(包太大不想下)、下载安装成功率(下载慢不用了)、APP卸载率(太占空间先删掉)。包大小的计算逻辑很简单,它是各种类型的文件占用磁盘大小相加。APP瘦身的技术却很复杂,代码文件的复杂度和编译器策略决定了可执行文件的大小,业务功能和工程架构决定了代码文件的复杂度。iOS APP瘦身,需要掌握的技能有XCode构建技术、LLVM编译器
3882 0
Alibaba.com瘦包40MB——业界最全的iOS包大小技术总结
|
8月前
|
iOS开发 开发者
iOS 上架报错:无法添加以供审核
iOS 上架报错:无法添加以供审核
|
8月前
|
数据采集 监控 供应链
shopee商品列表数据接口丨关键词搜索shopee商品数据采集
shopee商品列表数据接口丨关键词搜索shopee商品数据采集
|
8月前
|
安全 JavaScript 前端开发
escape, encodeURI, encodeURIComponent 有什么区别以及作用?
escape, encodeURI, encodeURIComponent 有什么区别以及作用?
342 0
|
前端开发 JavaScript Java
springboot+vue考研资料分享系统
本考研资料分享系统设计目标是实现考研资料的信息化管理,提高管理效率,使得考研资料交流工作规范化、科学化、高效化。本文研究的考研资料分享系统基于Springboot架构,采用JSP技术、JAVA编程语言和MYSQL数据库设计开发。通过本系统,实现了管理员和用户两个角色的功能,能够有效提高考研资料交流诊断效率。本系统经过测试,运行效果稳定,操作方便、快捷,是一个功能全面、实用性好、安全性高,并具有良好的可扩展性、可维护性的考研资料分享系统。论文首先阐述了考研资料分享系统的开发,并对该系统进行了较详细的需求分析,探讨了考研资料分享系统的功能需求、业务流程、系统结构和数据库设计等方面的问题。望能利用先
325 0
|
程序员 开发工具 iOS开发
UIVisualEffectView 毛玻璃效果
UIVisualEffectView 毛玻璃效果
608 0
|
iOS开发
iOS下载文件保存到手机文件指定目录
iOS下载文件保存到手机文件指定目录
1170 0
|
编译器 Swift iOS开发
Xcode中那些让人焕然一新的特殊注释#pragma mark、TODO、FIXME、MARK
Xcode中那些让人焕然一新的特殊注释#pragma mark、TODO、FIXME、MARK
586 0
Xcode中那些让人焕然一新的特殊注释#pragma mark、TODO、FIXME、MARK
|
iOS开发 容器 API
iOS文本布局探讨之一——文本布局框架TextKit浅析
在iOS开发中,使用TextKit框架进行富文本布局。TextKit有一组高级的类和协议组成,其中使用比较上层的API来完成复杂的富文本布局,功能十分强大。
5005 0
|
iOS开发
iOS 统计Xcode项目代码行数
iOS 统计Xcode项目代码行数
317 0