swift - 具有自动布局和滚动功能的奇怪 TextView 行为
问题描述
我正在尝试构建一个与 iMessage/WhatsApp 类似的 TextView,即随着内容的增长而高度增长的 textView,但一旦达到特定高度,它也允许滚动。
我将 textView 设置为 [8,0,8,0] 的 textContainerInsent 和 38 的高度,并且能够随着内容的增加使用自动布局轻松调整 TextView 的大小。
当我尝试启用滚动时,问题就来了。每当我的 textView 有一个新的文本行时,我的 textContainerInsent 就会感到困惑并向上“推”我的文本(这意味着第一行文本被剪切为 TextView 之外的一半)。出于某种更奇怪的原因,这种情况只发生在每隔一行(所以在第 2、第 4、第 6 等)。
这也只发生在新行的第一个字符处,并在后续字符处重新定位(参见图片)。
我能够通过将我的顶部 textContainerInsent 强制为偶数行的 16 ([16,0,8,0]) 并将其保持为奇数行的 [8,0,8,0] 来破解一些东西。
然而,这远非理想,因为:
- 当我关闭我的 textView 时,我在其中注入的占位符文本再次被向上推,我找不到解决该问题的方法
- 即使尝试将 textContainerInsent 强制为 [16,0,8,0],仍然存在一个像素左右的微小移动。
知道是什么原因造成的吗?我对 textContainerInsents/TextView 或 ContentSize 有误解吗?您对此根本原因的任何想法将不胜感激(并且不要过多地关注我的黑客行为......无论如何我都想摆脱它)。
我找到了以下有用的线程,但我尝试了建议的答案,但它们对我不起作用(因为我不想删除所有填充并希望保持滚动启用):
// Called by textViewDidChange delegate
@objc func handleTextViewSearch() {
let maxTextViewHeight : CGFloat = 180
textView.isScrollEnabled = true
textView.showsVerticalScrollIndicator = true
textView.textContainerInset = UIEdgeInsetsMake(8, 0, 8, 0)
let sizeHeight = min(maxTextViewHeight, textView.contentSize.height )
// This is my textView Height Constraint
viewHeightConstraint.constant = sizeHeight
textView.contentOffset = CGPoint(x: 0, y: 0)
// This my hack to manually "push" my text back when it jumps by increasing my textContainerInsent to [16,0,8,0]... It almost fixes the issue but doesn't address the root cause for the weird TextView behavior...
if textView.contentSize.height > textView.frame.height && textView.contentSize.height <= (maxTextViewHeight - 10) {
// Weird micro readjustment: When line goes from 1 to 2, need to increase insent by another 8 points but only when going from odd to even lines (go figure)...
var insentAdjustment : CGFloat = 0
let linesNumber = numberOfLines(textView: textView)
if linesNumber % 2 == 0 {
print("Is even number")
insentAdjustment = 8
} else if linesNumber == 1 {
insentAdjustment = 8
}
textView.frame.size.height = textView.contentSize.height
textView.textContainerInset = UIEdgeInsetsMake(8 + insentAdjustment, 0, 8, 0)
print("Post update TextView: ", textView)
}
}
解决方案
推荐阅读
- linux - 如何释放linux服务器上的cashed memory
- python - 在 unicode 和 text 上使用 re 拆分 python 字符串
- c++ - c++ 11 如何获取系统时间?
- django - 编写使用主数据库的 django 测试
- perl - 如何在方法调用时传递参数中创建的哈希引用?
- jquery - 在输入类型号中设置 plus 和 int 值
- c - openMP 程序中的嵌套 for 循环耗时过长
- ios - 在 ios swift3 中使用自定义相机捕捉视频
- php - 使用php从mysql的html数据中下拉列表
- javascript - 带有 npm / 代码更改的 Kotlin2JS 未反映