J’essaie de créer une vue de conteneur, avec un contrôleur à hauteur dynamic, à l’intérieur d’un UIScrollView et de la dimensionner automatiquement à l’aide de la mise en page automatique.
View Controller A est la vue de défilement, qui contient la vue du conteneur, avec plus de contenu ci-dessous.
View Controller B est le contrôleur de vue que je souhaite avoir une taille dynamic et pour que tout le contenu soit affiché en pleine hauteur dans la vue de défilement de View Controller A.
J’ai du mal à obtenir la taille dynamic de B pour définir automatiquement la taille de la vue de conteneur dans A. Toutefois, si je définis une contrainte de hauteur sur la vue de conteneur dans A ,
Ce serait la sortie attendue si View Controller B aurait également 250 hauteurs. Cela fonctionne également très bien pour la hauteur 1000, donc pour autant que je sache, toutes les contraintes de mise en page automatique sont correctement configurées. Malheureusement, comme la hauteur doit être dynamic, je voudrais éviter de créer une contrainte de hauteur.
Je ne sais pas s’il existe des parameters pour le contrôleur de vue que BI peut définir pour qu’il mette automatiquement à jour sa taille en fonction de son contenu ou s’il existe d’autres astuces que j’ai manquées. Toute aide serait très appréciée!
Existe-t-il un moyen de dimensionner la vue Conteneur dans A en fonction de la taille de View Controller B sans définir de contrainte de hauteur?
Yup, il y a. J’ai réussi à adopter ce type de comportement dans l’un de mes propres projets.
Tout ce que vous devez faire, c’est dire au système qu’il ne doit pas append de contraintes qui imitent le cadre fixe défini pour votre vue racine dans Interface Builder. Le meilleur endroit pour cela est dans votre contrôleur de vue de conteneur lorsque votre connexion intégrée est déclenchée:
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender { // You might want to check if this is your embed segue here // in case there are other segues sortingggered from this view controller. segue.destinationViewController.view.translatesAutoresizingMaskIntoConstraints = NO; }
Vous devez vous assurer que la vue que vous chargez dans le conteneur est contrainte de haut en bas et que vous devez définir la priorité d’une des contraintes verticales sur une valeur inférieure à 1000. (Il est conseillé de toujours utiliser la contrainte inférieure pour cela.) Cela est nécessaire car sinon Interface Builder se plaindra – avec une bonne raison:
Au moment de la conception, votre vue racine a une taille fixe (hauteur). Maintenant, si toutes vos sous-vues ont une hauteur fixe et sont connectées avec des contraintes fixes qui ont toutes la même priorité, il est impossible de satisfaire toutes ces exigences, sauf si la hauteur de votre vue racine correspond exactement à la hauteur totale de vos sous-vues et aux contraintes verticales. Si vous réduisez la priorité de l’une des contraintes, 999 Interface Builder sait quelle contrainte doit être interrompue. Lors de l’exécution, lorsque la propriété translatesAutoresizingMaskIntoConstraints
est définie comme indiqué ci-dessus, il n’y a plus de cadre fixe pour votre vue racine et le système utilisera votre contrainte de priorité 999 à la place.
De la réponse de @Mischa, j’ai été capable de rendre la hauteur d’un conteneurView dynamic en fonction de son contenu:
Dans le viewController du containerView écrivez:
override func loadView() { super.loadView() view.translatesAutoresizingMaskIntoConstraints = false }
Et en prenant soin que les contraintes verticales dans IB soient toutes définies. Pour ce faire, vous n’avez pas besoin de définir view.translatesAutoresizingMaskIntoConstraints = false en dehors du contrôleur de vue.
Dans mon cas, j’essayais de redimensionner le conteneur à une tableView à l’intérieur du viewController. Comme la tableView a une hauteur flexible en fonction de sa superview (donc tout est OK pour IB), j’ai complété les contraintes verticales du code en procédant comme suit:
@IBOutlet private var tableView: UITableView! { didSet { tableView.addConstraint(tableViewHeight) } } private lazy var tableViewHeight: NSLayoutConstraint = NSLayoutConstraint(item: self.tableView, atsortingbute: NSLayoutAtsortingbute.Height, relatedBy: .Equal, toItem: nil, atsortingbute: .NotAnAtsortingbute, multiplier: 1, constant: 0)
Ensuite, observez la hauteur contentSize de la tableview et ajustez la constante de la contrainte tableViewHeight par programmation si nécessaire.
Swift 4, Xcode 9
La réponse acceptée seule n’a pas résolu le problème pour moi.
Ma hiérarchie: ScrollView -> Vue du contenu (UIView) -> Vues | Vue du conteneur | Autres vues.
J’ai dû append les contraintes suivantes pour que les options ScrollView et Container soient ajustées dynamicment:
view.translatesAutoresizingMaskIntoConstraints = false
dans prepareForSegue()
ou dans loadView()
comme indiqué dans les autres réponses. J’ai maintenant une vue de conteneur réglable dynamicment dans une vue de défilement à redimensionnement automatique.