El layout automático no es válido después de presentar el controller de vista (y muchas situaciones)

Fondo:

Tengo un controller de contenedor personalizado, que al igual que UITabBarController, pero con animation de conmutador. Y uso el layout automático para lograrlo.
Debido a que el cambio entre controlleres secundarios es dynamic, las restricciones correctas se agregan al controller de vista secundaria cuando la vista de su contenido se agrega a la vista del contenedor, no se configura previamente en IB. (Las restricciones se agregan a la supervisión por supuesto)

http://d.pr/i/q6NF Configuración de la pestaña del controller de contenedor

PS: el detalle de las restricciones
H: | [Child] (Cambia la constante de la restricción a la animation de izquierda / derecha a derecha / izquierda)
H: [Child (== Super)]
V: | [Niño] |

Dónde está el problema:

Uno de los controlleres secundarios es un controller de navigation, las cosas salen mal cuando el controller de navigation presenta un controller de vistas modal (usando presentViewController:animated:completion: , y lo descarta (usando dismissViewControllerAnimated:completion: , después de present / dismiss the frame of el controller de navigation se convierte en (x, y, 0, 0), parece que el layout automático no es válido, tal vez se eliminaron las restricciones.

http://d.pr/i/VmvL El process de presente / rechazo

Investigación

No utilizo el código para verificar qué suceden con estas restricciones todavía, pero con Spark Inspector veo que la presentación de vistas cambia durante el process de presente / rechazo. Cuando Mi controller de navigation presenta un controller de vista modal, iOS simplemente cambia la vista del controller de navigation completo a la vista del controller de vista modal. Y cuando vuelve la vista del controller de navigation, el layout automático ya no funciona.

Solución posible

Una de las soluciones que se me ocurrió es dejar que mi controller de contenedor presente el controller modal.

O simplemente cambio mi controller de contenedor a ningún layout automático.

El hecho es que desde que comencé a usar el layout automático, los problemas que esta técnica causa solo dominan los beneficios. Además de este problema , cada vez que cambia la orientación de la interfaz, las vistas dentro de mi controller de contenedor no pueden ser autoajustadas a la derecha, parece que las subvistas siempre usan el marco de supervisión antes del cambio de orientación. Comprobé dos veces las restricciones que configuré, no hay conflictos ni ambigüedades.

Mi conjetura es que mi controller de contenedor personalizado no es compatible con la presentación del controller de vista modal y el cambio de orientación de la interfaz en el sistema de layout automático, incluso con la configuration de restricciones.

Ambiente de Xcode

Xcode 5 beta, iOS 7SDK, objective iOS6.1 Quizás ¿Algo no está bien con el entorno SDK?

Entonces publiqué esta pregunta, ¡ayúdeme!

Esta es mi primera pregunta, por lo que no tengo suficiente reputación para publicar imágenes, pero proporciono enlaces para las capturas de pantalla. ¡Lo siento por eso!

Tuve un problema similar . Estuve estableciendo translatesAutoresizingMaskIntoConstraints = NO; en mi raíz UIView. Aparece la UIView "más externa": la vista de supervisión en la raíz de su jerarquía debe usar la translatesAutoresizingMaskIntoConstraints = YES pnetworkingeterminadaAutoresizingMaskIntoConstraints translatesAutoresizingMaskIntoConstraints = YES . Una vez que he eliminado esto, todo funcionó como se esperaba.

Probablemente sea causada por restricciones ambiguas. Recomiendo pausar una aplicación en ejecución y escriba un command siguiente para la console:

 po [[UIWindow keyWindow] _autolayoutTrace] 

También tengo el mismo problema y cuando probé este controller de navigation funcionaba bien pero no con el viewcontroller actual. Utilice este método de controller de vista a continuación junto con traduceAutorizarMascar aConstructuras para resolver este problema.

 -(void) viewWillLayoutSubviews { [super viewWillLayoutSubviews]; self.view.translatesAutoresizingMaskIntoConstraints = NO; } 

Por favor, déjame ahora que tienes alguna preocupación al respecto. Gracias

Si utiliza el layout automático entre UIWindow y su vista raíz (para configurar la vista raíz para que ocupe todo el UIWindow ), estas restricciones se borrarán con una presentación a pantalla completa de otro controller de vista.

Lo que sucede es que toda la jerarquía de la presentación a pantalla completa reemplaza todo lo que está debajo de UIWindow : se elimina la vista original (eliminando las restricciones) y se sustituye la nueva jerarquía de vista. Luego, cuando se reemplaza su reseña, estas restricciones se pierden. Tendría que volver a viewWillAppear: algún lugar como viewWillAppear: o simplemente asegúrese de que su vista raíz tenga self.view.translatesAutoresizingMaskIntoConstraints = NO;

Tuve un problema similar con las celdas de vista de tabla que estaba presentando con autolayout. Al regresar de una vista modal, las celdas tenían un layout no válido. Podría volver a diseñar cada celda después de viewDidAppear, pero se veía terrible. Gracias a la sugerencia de @ palimondo, comencé a husmear en traduçãoAutoresizingMaskIntoConstraints. Resulta que estaba configurando la vista de contenido de la celda de vista de tabla para translatesAutoresizingMaskIntoConstraints = NO cuando no debería haber estado.

Tuve el mismo problema, con un contenedor de la barra de búsqueda como el elemento fuera de lugar (dentro de un UIViewController, dentro de un UITabBarController). Ninguna de las otras soluciones que he visto funcionó, pero finalmente logré evitarlo volviendo a agregar la restricción de layout en la vista WillAppear:

 [self.view addConstraint:[NSLayoutConstraint constraintWithItem: self.searchBar.superview attribute: NSLayoutAttributeTop relatedBy: NSLayoutRelationEqual toItem: self.view attribute: NSLayoutAttributeTop multiplier: 1 constant: 0]];