UIPageViewController / TextKit在分页上回stream文本

我正在使用TextKit支持的多页阅读应用程序,该应用程序基于WWDC 2013的“高级文本布局和与文本工具箱的效果”会话(但是其中一些代码是从不完整的示例中重新构build的)。 基本的结构是计算你的文本所需的页面数量,然后为每个页面创build一个NSTextContainer,并将其添加到NSLayoutManager。 每当UIPageViewController请求下一页或上一页时,您将创build一个新的UITextView,并通过从NLayoutManger的NSTextContainers数组中select正确的一个来设置其后备文本容器。

不幸的是,我有一个问题,在第一页,第一次,我回到任何给定的页面文本得到重新stream转。 这是它的样子:

回流文本的动画

这不是最明显的效果(如果你错过了,当回页时注意屏幕的顶部),但有点迷惑,我想尽可能消除它。 鉴于文本容器应该在前面计算,我不明白为什么它回stream的文本,或如何防止它。 有谁知道问题是什么?

编辑 :添加一个代码示例。

@interface ReaderViewController () <UIPageViewControllerDataSource> @property (nonatomic, assign) NSUInteger numberOfPages; @property (nonatomic, retain) UIPageViewController *pageViewController; @property (nonatomic, retain) NSTextStorage *currentDocument; @property (nonatomic, retain) NSLayoutManager *layoutManager; @end @implementation ReaderViewController - (instancetype)initWithDocument:(NSTextStorage *)document { if ((self = [super init])) { _currentDocument = document; } return self; } - (void)viewDidLoad { [super viewDidLoad]; _layoutManager = [[NSLayoutManager alloc] init]; [self.layoutManager setTextStorage:self.currentDocument]; self.layoutManager.delegate = self; _pageViewController = [[UIPageViewController alloc] initWithTransitionStyle:UIPageViewControllerTransitionStyleScroll navigationOrientation:UIPageViewControllerNavigationOrientationHorizontal options:nil]; self.pageViewController.view.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; self.pageViewController.dataSource = self; [self addChildViewController:self.pageViewController]; [self.view addSubview:self.pageViewController.view]; // the numberOfPages accessor lazily calculates the number of pages needed to contain the document for (int i = 0; i < self.numberOfPages; ++i) { NSTextContainer *container = [[NSTextContainer alloc] init]; container.size = [self _textFrame].size; [self.layoutManager addTextContainer:container]; } [self.pageViewController setViewControllers:@[[self viewControllerForPageNumber:0]] direction:UIPageViewControllerNavigationDirectionForward animated:NO completion:nil]; } - (UIViewController *)viewControllerForPageNumber:(NSUInteger)pageNumber { if (pageNumber >= self.numberOfPages) { return nil; } // SinglePageViewController is a lightweight view controller that has a UITextView and a page number SinglePageViewController *vc = [[SinglePageViewController alloc] init]; UITextView *textView = [[UITextView alloc] initWithFrame:[self _textFrame] textContainer:[self.layoutManager.textContainers objectAtIndex:pageNumber]]; textView.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; textView.scrollEnabled = NO; textView.editable = NO; [textView setFont:[UIFont fontWithName:@"IowanOldStyle-Roman" size:20.f]]; [vc.view addSubview:textView]; vc.textView = textView; vc.pageNumber = pageNumber; return vc; } #pragma mark - UIPageViewControllerDataSource - (UIViewController *)pageViewController:(UIPageViewController *)pageViewController viewControllerAfterViewController:(UIViewController *)viewController { NSUInteger currentPage = [(SinglePageViewController *)viewController pageNumber]; if (currentPage >= self.numberOfPages) { return nil; } return [self viewControllerForPageNumber:currentPage + 1]; } - (UIViewController *)pageViewController:(UIPageViewController *)pageViewController viewControllerBeforeViewController:(UIViewController *)viewController { NSUInteger currentPage = [(SinglePageViewController *)viewController pageNumber]; if (currentPage == 0) { return nil; } return [self viewControllerForPageNumber:currentPage - 1]; } #pragma mark - Private - (CGRect)_textFrame { return CGRectInset(self.view.bounds, 5., 0.); } @end 

我面临同样的问题。 我的解决方法是在addSubview之后放置scrollEnabled将强制textContainer重新计算大小。 看下面的代码:

  vc.view.addSubview(textView) textView.scrollEnabled = false; 

更新:最后,我想我find了正确的答案…我们需要重置didChangeGeometryFromSize事件中的容器大小。 如果不是这样,请纠正我。 🙂

 func layoutManager(layoutManager: NSLayoutManager, textContainer: NSTextContainer, didChangeGeometryFromSize oldSize: CGSize) { textContainer.size = self.textFrame().size; println(textContainer.size.width) println(textContainer.size.height) } 

尝试automaticallyAdjustsScrollViewInsets设置您的视图控制器的调整NONO