숫자가있는 텍스트가 포함 된 UITextField가 있는데 그보기에서 자동 레이아웃을 사용하는 데 끔찍한 시간이 있습니다. 숫자에 따라 때로는 너무 좁아서 모든 텍스트가 표시되지 않습니다. 이것은 monospacedDigitSystemFont를 사용할 때만 발생합니다. 또한 UITextField 대신 UILabel을 사용하면 발생하지 않습니다. 텍스트에 "좁은"자릿수 (예 : 1)가 여러 개 있고 숫자가 모두 "와이드"(예 : 5)가 아닌 경우 발생합니다. UITextField는 숫자를 모노 스페이스로 렌더링하지 않고 intrinsicContentSize
을 계산하는 것 같습니다. 이 문제를 해결하는 방법?monospacedDigitSystemFont를 사용하여 UITextField의 잘못된 intrinsicContentSize (너비)가 잘린 텍스트를 발생했습니다.
이 그래픽은 문제를 보여줍니다. 주황색 배경은 UILabel을, 노란색 배경은 UITextField를 보여줍니다. 문제는 상단의 노란색 상자 (좁은 숫자 "111111")에서만 나타납니다.
는 내가 해결 방법이 있습니다 대신의 UITextField에 직접 글꼴을 지정하는 AttributedString의 속성을 사용하지만 누군가가 더 나은 솔루션을 바라고 있어요. 그래픽의 놀이터 코드는 다음과 같습니다.
import UIKit
import PlaygroundSupport
func place(subview:UIView, on view:UIView, x:CGFloat, y:CGFloat) {
view.addSubview(subview)
subview.translatesAutoresizingMaskIntoConstraints = false
NSLayoutConstraint(item: subview, attribute: .left, relatedBy: .equal, toItem: view, attribute: .left, multiplier: 1, constant: x).isActive = true
NSLayoutConstraint(item: subview, attribute: .top, relatedBy: .equal, toItem: view, attribute: .top, multiplier: 1, constant: y).isActive = true
subview.setContentCompressionResistancePriority(.required, for: .horizontal)
}
let numericFont = UIFont.monospacedDigitSystemFont(ofSize: 18, weight: .regular)
let containerView = UIView(frame: CGRect(x: 0, y: 0, width: 300, height: 170))
containerView.backgroundColor = .lightGray
let textWithNarrowDigits = "111111 narrow digits"
let textWithWideDigits = "555555 wide digits"
func show(text:String, topOffset:CGFloat) {
// Using UILabel - works as expected
let label = UILabel()
label.font = numericFont
label.text = text
label.backgroundColor = .orange
print("Label intrinsicContentSize:\(label.intrinsicContentSize)") // width = 177 for narrow digits
place(subview: label, on:containerView, x: 20, y: topOffset)
// Using UITextField - width is too small (as if not monospaced)
let field = UITextField()
field.font = numericFont
field.text = text
field.backgroundColor = .yellow
print("Field intrinsicContentSize:\(field.intrinsicContentSize)") // width = 161 for narrow digits
place(subview: field, on:containerView, x: 20, y: topOffset + 30)
}
show(text: textWithNarrowDigits, topOffset: 10)
show(text: textWithWideDigits, topOffset: 100)
PlaygroundPage.current.liveView = containerView