How to replace layoutManager with textLayoutManager for a flexible dynamic height UITextView

In order to create a UITextView like that of the Messages app whose height grows to fits its contents (number of lines), I subclassed UITextView and customized the intrinsicContentSize like so:

override var intrinsicContentSize: CGSize {
    var size = super.intrinsicContentSize
    
    if size.height == UIView.noIntrinsicMetric {
        layoutManager.glyphRange(for: textContainer)
        size.height = layoutManager.usedRect(for: textContainer).height + textContainerInset.top + textContainerInset.bottom
    }
    
    return size
}

As noted at WWDC, accessing layoutManager will force TextKit 1, we should instead use textLayoutManager. How can this code be migrated to support TextKit 2?

Answered by DTS Engineer in 843613022

Does usageBoundsForTextContainer help? You can use the following code to retrieve the usage bounds for the text container:

textLayoutManager.ensureLayout(for: textLayoutManager.documentRange)        
let rect = textLayoutManager.usageBoundsForTextContainer

Best,
——
Ziqiao Chen
 Worldwide Developer Relations.

Does usageBoundsForTextContainer help? You can use the following code to retrieve the usage bounds for the text container:

textLayoutManager.ensureLayout(for: textLayoutManager.documentRange)        
let rect = textLayoutManager.usageBoundsForTextContainer

Best,
——
Ziqiao Chen
 Worldwide Developer Relations.

In testing, I removed this layoutManager code altogether, and it works as expected. It seems like the intrinsic content size height is never actually UIView.noIntrinsicMetric so that code was not executing in the first place 😄

Oh, yeah, I was wondering why you needed to override intrinsicContentSize before replying the post. Thanks for updating that you don't really need it.

Best,
——
Ziqiao Chen
 Worldwide Developer Relations.

How to replace layoutManager with textLayoutManager for a flexible dynamic height UITextView
 
 
Q