web-dev-qa-db-fra.com

Est-il possible d'obtenir une hauteur d'en-tête de section de vue dynamique sous forme de tableau à l'aide de la disposition automatique?

Nouveauté dans iOS 8, vous pouvez obtenir des cellules d’affichage de tableau dynamiques à 100% en définissant simplement la hauteur estimée des lignes, puis en disposant vos éléments dans la cellule à l’aide de la disposition automatique. Si le contenu augmente en hauteur, la cellule augmentera également en hauteur. Ceci est extrêmement utile et je me demande si le même exploit peut être accompli pour les en-têtes de section dans une vue sous forme de tableau. 

Peut-on, par exemple, créer une UIView dans tableView:viewForHeaderInSection:, ajouter une sous-vue UILabel, spécifier des contraintes de mise en page automatique pour l’étiquette par rapport à la vue, et augmenter la hauteur de la vue pour s’adapter au contenu de l’étiquette, sans avoir à implémenter tableView:heightForHeaderInSection:?

La documentation de viewForHeaderInSection indique: "Cette méthode ne fonctionne correctement que lorsque tableView: heightForHeaderInSection: est également implémenté." Je n'ai pas entendu dire si quelque chose a changé pour iOS 8.

Si on ne peut pas faire ça, quel est le meilleur moyen d'imiter ce comportement?

87
Jordan H

C'est possible. C'est une nouveauté juste à côté des hauteurs de cellules dynamiques implémentées dans iOS 8.

C'est très simple. Ajoutez simplement ceci dans viewDidLoad:

self.tableView.sectionHeaderHeight = UITableViewAutomaticDimension;
self.tableView.estimatedSectionHeaderHeight = 25;

Remplacez ensuite viewForHeaderInSection et utilisez la mise en page automatique pour contraindre les éléments de votre vue comme il convient. C'est tout! Pas besoin d'implémenter heightForHeaderInSection. Et en fait, la variable sectionHeaderHeight n'a pas besoin d'être déclarée non plus, je l'ai simplement ajoutée pour plus de clarté.

Notez que dans iOS 11, les vues de cellules et d'en-tête/pied de page utilisent les hauteurs estimées par défaut. La seule chose à faire est de fournir une hauteur estimée afin de mieux informer le système de ce à quoi il doit s’attendre. La valeur par défaut est UITableViewAutomaticDimension, mais vous devriez fournir une meilleure estimation, c'est-à-dire la hauteur moyenne, si possible.

228
Jordan H

Cela peut être accompli en définissant (ou en retournant) la estimatedSectionHeaderHeight sur votre vue de table. 

Si l'en-tête de votre section chevauche vos cellules après avoir défini estimatedSectionHeaderHeight, assurez-vous que vous utilisez également une estimatedRowHeight

(J'ajoute cette réponse parce que le deuxième paragraphe contient une réponse à un problème qui peut être trouvé après avoir lu tous les commentaires que certains pourraient manquer.) 

22
Clay Ellis

J'ai essayé

self.tableView.sectionHeaderHeight = UITableViewAutomaticDimension;
self.tableView.estimatedSectionHeaderHeight = 25;

mais il n'a pas dimensionné correctement l'en-tête avec le libellé multiligne . J'ai ajouté ceci pour résoudre mon problème:

override func viewWillAppear(_ animated: Bool) {
    super.viewWillAppear(animated)

    // Recalculates height
    tableView.beginUpdates()
    tableView.endUpdates()
}
6
iuriimoz

Swift 4 +

fonctionne (testé à 100%)

Si vous avez besoin des deux sections ainsi que des lignes avec une hauteur dynamique basée sur le contenu, vous pouvez utiliser le code ci-dessous:

Sur viewDidLoad (), écrivez ces lignes:

    self.globalTableView.estimatedRowHeight = 20
    self.globalTableView.rowHeight = UITableView.automaticDimension

    self.globalTableView.sectionHeaderHeight =  UITableView.automaticDimension
    self.globalTableView.estimatedSectionHeaderHeight = 25;

Maintenant, nous avons défini la hauteur des lignes et des sections à l'aide des méthodes UITableView Delegate:

func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat
   {
       return UITableView.automaticDimension
   }
   func tableView(_ tableView: UITableView, heightForHeaderInSection section: Int) -> CGFloat {

       return UITableView.automaticDimension

   }
2
Mr.Javed Multani

Dans mon cas:

  1. définir par programme ne fonctionne pas .

self.tableView.sectionHeaderHeight = UITableViewAutomaticDimension.

  1. mis en storyboard pas travailler .

  2. remplacer heightForHeaderInSection travaillé .

override func tableView(_ tableView: UITableView, heightForHeaderInSection section: Int) -> CGFloat {
    return UITableViewAutomaticDimension
}

environnement de test:

  • Mac OS 10.13.4 
  • XCode version 9.4.1
  • Simulateur iPhone 8 Plus
0
Codus

Oui, ça marche pour moi. Je dois faire plus de changements comme ci-dessous:

override func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
    let label = UILabel()

    label.numberOfLines = 0
    label.text          = my own text

    return label
}
0
arg_vn

Je me suis retrouvé coincé dans le même problème où l'en-tête n'atteignait aucune hauteur et à moins que je spécifie une hauteur fixe dans le délégué pour heighForHeaderInSection.

Essayé beaucoup de solutions qui comprend 

self.tableView.sectionHeaderHeight = UITableViewAutomaticDimension;
self.tableView.estimatedSectionHeaderHeight = 73`

Mais rien n'a fonctionné. Ma cellule utilisait aussi les autolayouts appropriés. Les lignes changeaient dynamiquement leur hauteur en utilisant le code suivant, mais les en-têtes de section ne l'étaient pas.

self.tableView.estimatedRowHeight = 135
self.tableView.rowHeight = UITableViewAutomaticDimension`

Le correctif est extrêmement simple et étrange aussi, mais je devais implémenter les méthodes de délégation au lieu du code à une ligne pour les variables estimatedSectionHeaderHeight et sectionHeaderHeight, comme suit pour mon cas.

func tableView(_ tableView: UITableView, heightForHeaderInSection section: Int) -> CGFloat {
    return UITableViewAutomaticDimension
}

func tableView(_ tableView: UITableView, estimatedHeightForHeaderInSection section: Int) -> CGFloat {
    return 73
}
0
Ahsan Ebrahim