TD;DR
Parece que, en algunos casos, systemLayoutSizeFitting no devuelve la altura correcta para mostrar/posicionar correctamente todas las subvistas de una vista. ¿Estoy usando systemLayoutSizeFitting mal o hay alguna otra forma de evitar esto?
Larga historia:
El archivo XIB de un UIViewController no solo contiene la vista principal, sino también una serie de otras vistas que se agregan a la vista de los controladores de vista en tiempo de ejecución. Todas estas vistas adicionales deben tener la misma altura cuando se agregan a la vista de controladores de vista.
Las vistas podrían verse así: una vista de contenedor simple que contiene algunas subvistas que se apilan una encima de la otra.
Dado que la altura de la vista del contenedor debe ser flexible, el espacio vertical entre el botón inferior y la etiqueta que se encuentra encima utiliza una restricción mayor que .
Para dar a todas las vistas la misma altura, traté de medir la altura necesaria de cada vista usando systemLayoutSizeFitting :
@IBOutlet var pageViews: [UIView]! override func viewDidLoad() { super.viewDidLoad() var maxHeight: CGFloat = 0 for pageView in pageViews { // Add pageView somewhere on view and give it leading, trailing and top // constraint, but no height constraint yet. addToView(pageView) maxHeight = max(maxHeight, pageView.systemLayoutSizeFitting(CGSize(width: view.frame.width, height: UIView.layoutFittingCompressedSize.height), withHorizontalFittingPriority: .required, verticalFittingPriority: .fittingSizeLevel).height) } for pageView in pageViews { // Give all pageViews the same height pageView.heightAnchor.constraint(equalToConstant: maxHeight).isActive = true } }Esto no funciona cuando el texto de la etiqueta se vuelve demasiado largo:
En el ejemplo de la derecha, la altura no es lo suficientemente grande y, por lo tanto, se aprieta el botón. Puedo contrarrestar esto elevando la resistencia de compresión vertical del botón, sin embargo, en este caso, los otros controles (por ejemplo, la etiqueta del título) se aprietan...
¿Por qué es esto? ¿Por qué systemLayoutSizeFitting no devuelve una altura suficiente para mostrar todos los controles sin apretarlos?
Si desea que su vista resista la compresión, debe usar la prioridad defaultHigh como verticalFittingPriority en lugar de fittingSizeLevel .
En realidad button's height aplastar cuando el texto de la etiqueta se hace más grande. Está configurando restricciones superiores e inferiores, pero la altura del botón no se declara, por lo que cuando la etiqueta se hace más grande, la vista básicamente dice "Puedo reducir la altura del botón antes de actualizar mi altura, tengo espacio. Las restricciones inferiores y superiores siguen siendo las mismas, no afectó. "
Dar las restricciones de constant height del botón podría solucionar su problema.