web-dev-qa-db-fra.com

Comment utiliser UIScrollView dans Storyboard

J'ai une vue par défilement avec un contenu de 1 000 pixels de haut et j'aimerais pouvoir le disposer pour une conception facile sur le storyboard.
Je sais que cela peut être fait par programme, mais je veux vraiment pouvoir le voir visuellement. Chaque fois que je mets une vue défilante sur un contrôleur de vue, elle ne défilera pas. Est-il possible de le faire fonctionner comme je le souhaite ou dois-je le faire dans le code?

118
Alex Reynolds

Je réponds à ma propre question car je viens de passer 2 heures à trouver la solution et StackOverflow permet ce style QA.

Voici comment le faire fonctionner dans le storyboard.

1: allez voir le contrôleur et cliquez sur Attribute Inspector.

2: changez Size en Freeform au lieu de Inféré.

3: Accédez à la vue principale de ce scénario, pas à votre vue défilement, mais à la vue de niveau supérieur.

4: Cliquez sur Size Inspector et réglez cette vue sur la taille souhaitée. J'ai changé ma taille à 1000. 

Maintenant, vous verrez que votre storyboard a la configuration de votre vue afin que vous puissiez voir toute la hauteur de votre défilement pour une conception facile.

5: déposez une vue à défiler et étirez-la pour qu’elle occupe toute la vue. Vous devriez maintenant avoir une vue de défilement de taille 320,1000 assise sur une vue dans votre contrôleur de vue.

Maintenant, nous devons le faire défiler et le faire afficher correctement le contenu.

6: Cliquez sur votre scrollview et cliquez sur Identity Inspector.

7: Ajoutez un User Defined runtime attribute avec KeyPath de contentSize puis tapez SIZE et entrez la taille de votre contenu. Pour moi c'est (320, 1000).

Puisque nous voulons voir notre vue de défilement complète sur le scénarimage, nous l'avons étiré et il a un cadre de 320,1000 mais pour que cela fonctionne dans notre application, nous devons modifier le cadre afin qu'il soit ce que la vue de défilement visible sera.

8: Ajoutez un runtime attribute avec KeyPath frame avec le type RECT et 0,0,320,416.

Maintenant, lorsque nous exécutons notre application, une scrollview visible a un cadre de 0,0 320, 416 et peut défiler jusqu'à 1000. Nous sommes en mesure de mettre en page nos sous-vues et images, ainsi que tout ce que nous souhaitons dans Storyboard, exactement comme nous le souhaiterions. Ensuite, nos attributs d’exécution s’assurent de l’afficher correctement. Tout cela sans 1 ligne de code.

149
Alex Reynolds

Voici les étapes avec Auto Layout qui ont fonctionné pour moi sur XCode 8.2.1.

  1. Sélectionnez Size Inspector of View Controller et remplacez Simulated Size par Freeform avec height 1000 au lieu de Fixed.
  2. Renommez la vue de View Controller en RootView.
  3. Faites glisser un Scroll View en tant que sous-vue de RootView et renommez-le en ScrollView.
  4. Ajouter des contraintes pour ScrollView:
    • ScrollView [Haut, Bas, Début, Fin] = RootView [Haut, Bas, Début, Fin]
  5. Faites glisser un Vertical Stack View en tant que sous-vue de ScrollView et renommez-le en ContentView.
  6. Ajouter des contraintes pour ContentView:
    • ContentView .height = 1000
    • ContentView [Haut, Bas, Début, Fin, Largeur] = ScrollView [Haut, Bas, Début, Fin, Largeur]
  7. Sélectionnez Attributes Inspector de ContentView et remplacez Distribution par Fill Equally au lieu de Fill.
  8. Faites glisser une View en tant que sous-vue de ContentView et renommez-la en tant que RedView.
  9. Définissez Red comme arrière-plan de RedView.
  10. Faites glisser une View en tant que sous-vue de ContentView et renommez-la en tant que BlueView.
  11. Définissez Blue comme arrière-plan de BlueView.
  12. Sélectionnez RootView, puis cliquez sur le bouton Update Frames .
    • Update Frames est un nouveau bouton dans Xcode8, au lieu du bouton Resolve Auto Layout Issues. Cela ressemble à un bouton de rafraîchissement, situé dans la barre de contrôle sous le Storyboard:  Update Frames Button

Afficher la hiérarchie:

  • RootView
    • ScrollView
      • ContentView
        • RedView
        • BlueView

Voir la scène du contrôleur (hauteur: 1000):

scene

Courir sur iPhone7 (Hauteur: 1334/2):

demo

48
jqgsninimo

Voici les étapes qui ont fonctionné pour moi sur iOS 7 et XCode 5.

  1. Faites glisser un ViewController (il est livré avec UIView "View").

    1.1 Sélectionnez "View Controller", sélectionnez "File Inspector" et décochez "Auto layout".

  2. Faites glisser une ScrollView (en tant qu'enfant de la vue "View" d'UIView de ViewController)
  3. Sélectionnez ScrollView et ouvrez "Inspecteur d'identité".
  4. Entrez "contentSize" pour keyPath. Sélectionnez "Taille" pour le type. Et entrez {320, 1000} pour la valeur. 

    Remarque: l'étape 4 indique simplement que la liste de défilement contient du contenu de taille 320x1000 unités. Donc, définir contentSize fera fonctionner le scroller.

  5. Sélectionnez View Controller, sélectionnez "Attributes Inspector" puis sélectionnez Freeform from Size.

    Remarque: l'étape 5 nous permettra de changer la taille de "View" fournie avec le contrôleur de vue.

  6. Sélectionnez "Affichage" puis sélectionnez "Inspecteur de taille". 

  7. Définissez Largeur sur 320 et Hauteur sur 1000.

Remarque: 5, 6 et 7 servent uniquement à voir une vue agrandie ou entièrement agrandie dans StoryBoard .

Votre hiérarchie de vues doit ressembler à: hierarchy

43
Raja Rao

Après des heures d’essais et d’erreurs, j’ai trouvé un moyen très simple d’ajouter du contenu dans des vues de défilement «hors écran». Testé avec XCode 5 et iOS 7. Vous pouvez le faire presque entièrement dans Storyboard, en utilisant 2 petites astuces/solutions de contournement:

  1. Faites glisser un contrôleur de vue sur votre story-board.
  2. Faites glisser un scrollView sur ce viewController. Pour la démo, vous pouvez laisser sa taille par défaut, , Couvrant l’ensemble de l’écran.
  3. Maintenant vient astuce 1 : avant d’ajouter un élément à scrollView, faites-le glisser dans une "vue" normale (Cette vue sera agrandie par rapport à l’écran et contiendra tous les sous-éléments tels que des boutons, des libellés, ... appelons cela la ' vue englobante ').
  4. Laissez cette taille englobant la taille Y de la vue dans l'inspecteur de taille, par exemple, 800.
  5. Déposez une étiquette sur la vue englobante, quelque part en Y, position 200, appelez-la 'étiquette 1'.
  6. Trick 2 : assurez-vous que la vue qui entoure est sélectionnée ( pas la scrollView! ), et réglez sa position Y sur -250, par exemple, pour pouvoir ajouter un élément «extérieur». ' l'écran 
  7. Déposez une étiquette, quelque part au bas de l'écran, nommez-la 'étiquette 2'. Cette étiquette est en fait "hors écran".
  8. Réinitialisez la position Y de la vue englobante à 0, vous ne verrez plus l'étiquette 2, car elle était positionnée hors écran.

Jusqu'ici, pour le travail du storyboard, vous devez maintenant ajouter une seule ligne de code à la méthode 'viewDidLoad' de viewController pour définir le contenu de scrollViews afin qu'il contienne la totalité de la 'vue englobante'. Je n'ai pas trouvé le moyen de faire cela dans Storyboard:

- (void)viewDidLoad
{
    [super viewDidLoad];

    self.scrollView.contentSize = CGSizeMake(320, 800);
}

Vous pouvez essayer cela en ajoutant un contentSize keyPath en tant que size à scrollView dans l'inspecteur d'identité et en le définissant sur (320, 1000).

Je pense qu'Apple devrait faciliter cela dans le storyboard, dans un TableViewController, vous pouvez simplement faire défiler hors de l'écran dans Storyboard (ajoutez 20 cellules et vous verrez que vous pouvez simplement faire défiler), cela devrait également être possible avec un ScrollViewController. 

13
Ronny Webers

Faire fonctionner le défilement avec iOS7 et la mise en page automatique sous iOS 7 et XCode 5.

En plus de cela: https://stackoverflow.com/a/22489795/1553014

Apparemment, tout ce que nous avons à faire, c'est:

  1. Définir toutes les contraintes sur la vue défilement (c.-à-d. Réparer la vue défilement en premier)

  2. Définissez ensuite la contrainte distance-from-scrollView sur l'élément le plus en bas pour faire défiler la vue (la super vue). 

Remarque: l'étape 2 indiquera au storyboard où se trouve le dernier élément de contenu dans la vue Défilement.

8
Raja Rao

Pour cet exemple, j'ai décoché la fonctionnalité Autolayout du générateur d'interface. Et j'utilise toujours (sans aucune raison) la version 4.6.1 relativement ancienne de Xcode.

Commencez avec un contrôleur de vue doté d'une vue de défilement (vue principale).

1: Ajoutez une vue de conteneur, à partir de la bibliothèque d'objets, à la vue de défilement. Notez qu'un nouveau contrôleur de vue est ajouté au storyboard et qu'il est lié au contrôleur de vue avec la vue de défilement.

2: sélectionnez la vue conteneur et, dans l'inspecteur de taille, fixez-la en haut et en gauche sans redimensionnement automatique.

enter image description here

3: modifiez sa hauteur en 1000. (1000 est utilisé pour cet exemple. Vous devez appliquer la valeur requise.)

4: sélectionnez le nouveau contrôleur de vue et, dans l'inspecteur d'attributs, définissez Taille sur forme libre.

enter image description here

5: Sélectionnez la vue du nouveau contrôleur de vue et, dans l'inspecteur de taille, définissez la hauteur sur 1000 (ce qui correspond à la hauteur de la vue du conteneur).

6: Pour votre test ultérieur, tout en restant sur la vue du nouveau contrôleur de vue, ajoutez une étiquette en haut et en bas de la vue.

7: Sélectionnez la vue de défilement à partir du contrôleur de vue d'origine. Dans l'inspecteur Identité, ajoutez un attribut avec keyPath défini sur contentSize, le type défini sur Size et la valeur définie sur {320, 1000} (ou la taille de votre vue conteneur).

enter image description here

8: Exécuter sur le simulateur iPhone 4 pouces. Vous devriez pouvoir faire défiler l'étiquette du haut vers le bas.

9: Exécuter sur le simulateur iPhone 3,5 pouces. Vous devriez pouvoir faire défiler l'étiquette du haut vers le bas.

Rappelez-vous que Xcode 4.6.1 ne peut être construit que pour iOS6 et inférieur. En utilisant cette approche et en construisant pour iOS6, je suis toujours capable d’obtenir les mêmes résultats lorsque l’application est exécutée sur iOS7.

7
yoninja

Notez que dans une UITableView, vous pouvez réellement faire défiler la vue tableau en sélectionnant une cellule ou un élément de celle-ci et en le faisant défiler vers le haut ou le bas avec votre trackpad.

Pour une UIScrollView, j'aime bien la suggestion d'Alex, mais je recommanderais temporairement de changer le contrôleur de vue en forme libre, d'augmenter la hauteur de la vue racine, de construire votre interface utilisateur (étapes 1 à 5), puis de revenir au standard déduit taille lorsque vous avez terminé afin que vous n'ayez pas à coder en dur les tailles de contenu sous forme d'attributs d'exécution. Si vous faites cela, vous vous exposez à de nombreux problèmes de maintenance en essayant de prendre en charge les périphériques 3,5 "et 4", ainsi qu’à la possibilité d’une résolution accrue de l’écran à l’avenir.

5
Kyle Clegg

Dans iOS7, j'ai découvert que, si j'avais une vue dans UIScrollView sur un ViewController de taille FreeForm, elle ne défilerait pas dans l'application, peu importe ce que j'ai fait. J'ai joué et j'ai trouvé ce qui suit semblait fonctionner, qui n'utilise pas de FreeForm:

  1. Insérer un UIScrollView dans la vue principale d'un ViewController

  2. Définissez les contraintes de report automatique sur ScrollView comme il convient. Pour moi, j'ai utilisé 0 to Top Guide de mise en page et 0 to Bottom Guide

  3. Dans ScrollView, placez une vue de conteneur. Définissez sa hauteur sur ce que vous voulez (par exemple 1000)

  4. Ajoutez une contrainte de hauteur (1000) au conteneur afin qu’il ne soit pas redimensionné. Le fond sera passé la fin du formulaire.

  5. Ajoutez la ligne [self.scrollView setContentSize: CGSizeMake (320, 1000)]; au ViewController qui contient le scrollView (que vous avez connecté en tant qu'IBOutlet)

Le ViewController (ajouté automatiquement) associé au conteneur aura la hauteur souhaitée (1 000) dans Interface Builder et défilera également correctement dans le contrôleur de vue d'origine. Vous pouvez maintenant utiliser ViewController du conteneur pour organiser vos contrôles.

4
nh32rg

Vous devez uniquement définir la propriété contentSize sur le viewDidAppear, comme dans l'exemple suivant:

- (void)viewDidAppear:(BOOL)animated{

     [super viewDidAppear:animated];
     self.scrollView.contentSize=CGSizeMake(306,400.0);

}

Il résout les problèmes d'autolayout et fonctionne très bien sur iOS7.

4
Lucio Fonseca

Clause de non-responsabilité: - Uniquement pour iOS 9 et versions ultérieures (Stack View).

Si vous déployez votre application sur des appareils ios 9, utilisez une vue pile . Voici les étapes à suivre: -

  1. Ajouter une vue de défilement avec des contraintes - épingler à gauche, à droite, en bas et en haut (sans marges) pour une vue d'ensemble (vue)
  2. Ajoutez une vue de pile avec les mêmes contraintes pour faire défiler la vue.
  3. Autres contraintes de la vue de pile: - stackView.bottom = view.bottom et stackView.width = scrollView.width
  4. Commencez à ajouter vos vues. La vue de défilement décidera de faire défiler en fonction de la taille de la vue de pile (qui est essentiellement votre vue de contenu)
3
DharinS

je veux mettre mes 5 cents en réponse acceptée:

montez jusqu'au point 4 de la réponse acceptée et oubliez d'ajouter des attributs de cadres et de tailles de contenu, etc.

pour que tout soit automatique, il suffit d'utiliser la solution de ce lien

tout est clair, facile, élégant et fonctionne comme un charme sur ios 7. Je suis plutôt content de tout ça lol

3
jungle_mole

Voici une solution simple.

  1. Définissez l'attribut de taille de votre contrôleur de vue dans le storyboard sur "Freeform" et définissez la taille souhaitée. Assurez-vous qu'il est assez grand pour contenir tout le contenu de votre vue défilement.

  2. Ajoutez votre vue de défilement et définissez les contraintes comme vous le feriez normalement. c'est-à-dire si vous voulez que la vue de défilement ait la taille de votre vue, puis attachez vos marges supérieure, inférieure, principale et inférieure à la vue supérieure comme vous le feriez normalement.

  3. Maintenant, assurez-vous qu'il existe des contraintes dans les sous-vues de la vue de défilement qui relient le haut et le bas de la vue de défilement. Idem pour gauche et droite si vous avez le défilement horizontal.

 enter image description here

3
Hulk_SMASH

Voici une réponse un peu dégoûtante qui aboutit à la même solution pour les vues de défilement vertical, mais qui (contrairement à la philosophie de stackoverflow) ne répond pas à la question. Au lieu d'utiliser un scrollView, utilisez simplement un UITableView, faites glisser un UIView normal dans l'en-tête et faites-le grand comme vous le souhaitez, vous pouvez maintenant faire défiler le contenu dans le storyboard.

2
TimWhiting

La clé est la taille du contenu.

Cela manque souvent et n'est pas indiqué lors de l'ajout d'un UIScrollView.

Sélectionnez UIScrollView et sélectionnez l'inspecteur d'identité.

Ajoutez un chemin contentSize en tant que size à la vue de la vue de l'inspecteur d'identité et définissez-le sur (320, 1000).

Faites défiler.

0
Alex Zavatone

Apparemment, vous vous n'avez pas besoin de spécifier la hauteur! Ce qui est bien si cela change pour une raison quelconque (vous redimensionnez des composants ou changez la taille des polices).

Je viens de suivre ce tutoriel et tout a fonctionné: http://natashatherobot.com/ios-autolayout-scrollview/

(Remarque: il n'est pas nécessaire d'implémenter viewDidLayoutSubviews sauf si vous souhaitez centrer la vue, la liste des étapes est encore plus courte).

J'espère que cela pourra aider!

0
Lukasz Czerwinski

Si vous utilisez la mise en page automatique, la meilleure approche consiste à utiliser UITableViewController avec des cellules statiques dans le storyboard.

J'ai également rencontré le problème une fois avec une vue nécessitant beaucoup plus de défilement. Changez donc UIScrollView avec la technique susmentionnée.

0
Usman Awan