web-dev-qa-db-fra.com

Hauteur (ou largeur) proportionnelle dans SwiftUI

J'ai commencé à explorer SwiftUI et je ne trouve pas de moyen d'obtenir une chose simple: je voudrais qu'une vue ait une hauteur proportionnelle (essentiellement un pourcentage de la hauteur de son parent). Disons que j'ai 3 vues empilées verticalement. Je voudrais:

  • Le premier mesure 43% (de la taille de ses parents)
  • Le deuxième mesure 37% (de la taille de ses parents)
  • Le dernier mesure 20% (de la taille de ses parents)

J'ai regardé cette vidéo intéressante de la WWDC19 sur les vues personnalisées dans SwiftUI ( https://developer.Apple.com/videos/play/wwdc2019/237/ ) et j'ai compris (corrigez-moi si je suis mal) que, fondamentalement, une vue n'a jamais de taille en soi, la taille est la taille de ses enfants. Ainsi, la vue des parents demande à ses enfants de quelle taille ils sont. Ils répondent à quelque chose comme: "la moitié de votre taille!" et maintenant quoi? Comment le système de mise en page (qui est différent du système de mise en page que nous utilisions auparavant) gère-t-il cette situation?

Si vous écrivez le code ci-dessous:

struct ContentView : View {
    var body: some View {
        VStack(spacing: 0) {
            Rectangle()
                .fill(Color.red)
            Rectangle()
                .fill(Color.green)
            Rectangle()
                .fill(Color.yellow)
        }
    }
}

Le système de mise en page SwiftUI dimensionne chaque vue pour qu'elle soit 1/3 de haut et cela correspond à la vidéo que j'ai publiée ci-dessus. Vous pouvez envelopper les rectangles dans un cadre de cette façon:

struct ContentView : View {
    var body: some View {
        VStack(spacing: 0) {
            Rectangle()
                .fill(Color.red)
                .frame(height: 200)
            Rectangle()
                .fill(Color.green)
                .frame(height: 400)
            Rectangle()
                .fill(Color.yellow)
        }
    }
}

De cette façon, le système de mise en page dimensionne le premier rectangle à 200 de haut, le second à 400 de haut et le troisième à tout l'espace gauche. Et encore une fois, ça va. Ce que vous ne pouvez pas faire (de cette façon), c'est spécifier une hauteur proportionnelle.

9
superpuccio

Vous pouvez utiliser GeometryReader. Enveloppez le lecteur autour de toutes les autres vues et utilisez sa valeur de fermeture metrics pour calculer les hauteurs:

let propHeight = metrics.size.height * 0.43

Utilisez-le comme suit:

import SwiftUI

struct ContentView: View {
    var body: some View {
        GeometryReader { metrics in
            VStack(spacing: 0) {
                Color.red.frame(height: metrics.size.height * 0.43)
                Color.green.frame(height: metrics.size.height * 0.37)
                Color.yellow
            }
        }
    }
}

import PlaygroundSupport

PlaygroundPage.current.liveView = UIHostingController(rootView: ContentView())
18
rob mayoff