HStack
Definition
HStack ist ein SwiftUI Container, der seine Child-Views horizontal von links nach rechts anordnet. Es ist das horizontale Gegenstück zu VStack und essentiell für die Erstellung von horizontalen Layouts.
Basic Syntax
HStack {
Text("First")
Text("Second")
Text("Third")
}
HStack mit Spacing
// Standard Spacing
HStack {
Text("Item 1")
Text("Item 2")
Text("Item 3")
}
// Custom Spacing
HStack(spacing: 20) {
Text("Item 1")
Text("Item 2")
Text("Item 3")
}
// Kein Spacing
HStack(spacing: 0) {
Text("A")
Text("B")
Text("C")
}
HStack mit Alignment
// Top Alignment
HStack(alignment: .top) {
Text("Short")
Text("Medium\nText")
Text("Very\nLong\nText")
}
// Center Alignment (Standard)
HStack(alignment: .center) {
Text("Short")
Text("Medium\nText")
Text("Very\nLong\nText")
}
// Bottom Alignment
HStack(alignment: .bottom) {
Text("Short")
Text("Medium\nText")
Text("Very\nLong\nText")
}
Spacing und Alignment kombiniert
HStack(alignment: .top, spacing: 15) {
Image(systemName: "star.fill")
.font(.largeTitle)
VStack(alignment: .leading) {
Text("Title")
.font(.headline)
Text("Subtitle")
.font(.subheadline)
}
}
Mit Spacer
// Links ausrichten
HStack {
Text("Left")
Spacer()
}
// Rechts ausrichten
HStack {
Spacer()
Text("Right")
}
// Zentrieren
HStack {
Spacer()
Text("Center")
Spacer()
}
// Verteilen
HStack {
Text("Left")
Spacer()
Text("Center")
Spacer()
Text("Right")
}
Verschiedene View-Typen
HStack(spacing: 15) {
Image(systemName: "person.fill")
.foregroundColor(.blue)
Text("John Doe")
.font(.headline)
Button("Follow") {
print("Followed")
}
.buttonStyle(.borderedProminent)
}
Mit ForEach
let items = ["Home", "Search", "Profile"]
HStack(spacing: 20) {
ForEach(items, id: \.self) { item in
VStack {
Image(systemName: "star")
Text(item)
.font(.caption)
}
}
}
Nested HStacks
VStack {
HStack {
Text("Row 1 - Item 1")
Text("Row 1 - Item 2")
}
HStack {
Text("Row 2 - Item 1")
Text("Row 2 - Item 2")
}
}
Mit Divider
HStack(spacing: 0) {
Text("Left")
.padding()
Divider()
Text("Middle")
.padding()
Divider()
Text("Right")
.padding()
}
Praktische Beispiele
Navigation Bar
HStack {
Button(action: { /* back */ }) {
Image(systemName: "chevron.left")
}
Spacer()
Text("Title")
.font(.headline)
Spacer()
Button(action: { /* more */ }) {
Image(systemName: "ellipsis")
}
}
.padding()
User Profile Row
HStack(spacing: 12) {
Image(systemName: "person.circle.fill")
.resizable()
.frame(width: 50, height: 50)
.foregroundColor(.blue)
VStack(alignment: .leading, spacing: 4) {
Text("John Doe")
.font(.headline)
Text("iOS Developer")
.font(.subheadline)
.foregroundColor(.secondary)
}
Spacer()
Image(systemName: "chevron.right")
.foregroundColor(.gray)
}
.padding()
Icon mit Label
HStack(spacing: 8) {
Image(systemName: "star.fill")
.foregroundColor(.yellow)
Text("4.5")
Text("(1.2k reviews)")
.foregroundColor(.secondary)
}
Button Row
HStack(spacing: 15) {
Button("Cancel") {
// Cancel action
}
.buttonStyle(.bordered)
Button("Save") {
// Save action
}
.buttonStyle(.borderedProminent)
}
Stats Row
HStack(spacing: 30) {
VStack {
Text("1.2K")
.font(.title)
.bold()
Text("Posts")
.font(.caption)
.foregroundColor(.secondary)
}
VStack {
Text("15.3K")
.font(.title)
.bold()
Text("Followers")
.font(.caption)
.foregroundColor(.secondary)
}
VStack {
Text("842")
.font(.title)
.bold()
Text("Following")
.font(.caption)
.foregroundColor(.secondary)
}
}
Tag List
ScrollView(.horizontal, showsIndicators: false) {
HStack(spacing: 10) {
ForEach(["Swift", "SwiftUI", "iOS", "Xcode"], id: \.self) { tag in
Text(tag)
.padding(.horizontal, 15)
.padding(.vertical, 8)
.background(Color.blue.opacity(0.2))
.cornerRadius(20)
}
}
.padding()
}
Toolbar Actions
HStack(spacing: 20) {
Button(action: {}) {
Image(systemName: "square.and.arrow.up")
}
Button(action: {}) {
Image(systemName: "heart")
}
Button(action: {}) {
Image(systemName: "bookmark")
}
Spacer()
Button(action: {}) {
Image(systemName: "ellipsis")
}
}
.font(.title2)
.padding()
Price Display
HStack(alignment: .firstTextBaseline, spacing: 4) {
Text("$")
.font(.headline)
Text("99")
.font(.largeTitle)
.bold()
Text(".99")
.font(.title3)
Spacer()
Text("per month")
.font(.caption)
.foregroundColor(.secondary)
}
Form Field
HStack {
Text("Email:")
.frame(width: 80, alignment: .leading)
TextField("Enter email", text: $email)
.textFieldStyle(.roundedBorder)
}
.padding()
Badge
HStack(spacing: 4) {
Text("New")
.font(.caption2)
.fontWeight(.bold)
.padding(.horizontal, 8)
.padding(.vertical, 4)
.background(Color.red)
.foregroundColor(.white)
.cornerRadius(4)
Text("Product Name")
.font(.headline)
}
Mit ScrollView
// Horizontal scrolling
ScrollView(.horizontal, showsIndicators: false) {
HStack(spacing: 15) {
ForEach(0..<10) { index in
RoundedRectangle(cornerRadius: 10)
.fill(Color.blue)
.frame(width: 150, height: 100)
.overlay(
Text("Item \(index)")
.foregroundColor(.white)
)
}
}
.padding()
}
Layout Priority
HStack {
Text("Fixed Width Text")
.frame(width: 100)
.background(Color.blue)
Text("This text will take remaining space")
.layoutPriority(1)
.background(Color.green)
Image(systemName: "star")
.background(Color.yellow)
}
Custom Alignment Guide
HStack(alignment: .customAlignment) {
VStack {
Text("Top")
Text("Custom")
.alignmentGuide(.customAlignment) { d in d[.bottom] }
Text("Bottom")
}
VStack {
Text("Item 1")
Text("Item 2")
.alignmentGuide(.customAlignment) { d in d[.bottom] }
}
}
extension VerticalAlignment {
private enum CustomAlignment: AlignmentID {
static func defaultValue(in context: ViewDimensions) -> CGFloat {
context[.bottom]
}
}
static let customAlignment = VerticalAlignment(CustomAlignment.self)
}
HStack vs LazyHStack
// Regular HStack - lädt alle Views sofort
ScrollView(.horizontal) {
HStack {
ForEach(0..<100) { index in
Text("Item \(index)")
.frame(width: 100)
}
}
}
// LazyHStack - lädt Views on-demand (bessere Performance)
ScrollView(.horizontal) {
LazyHStack {
ForEach(0..<100) { index in
Text("Item \(index)")
.frame(width: 100)
}
}
}
Conditional Content
HStack {
Text("Title")
if isVerified {
Image(systemName: "checkmark.seal.fill")
.foregroundColor(.blue)
}
Spacer()
if isPremium {
Text("PRO")
.font(.caption)
.padding(4)
.background(Color.yellow)
.cornerRadius(4)
}
}
Best Practices
- Verwende Spacer für Verteilung: Kontrolle über horizontale Verteilung
HStack {
Text("Left")
Spacer()
Text("Right")
}
- Alignment für mehrzeilige Inhalte: Richtige Ausrichtung bei unterschiedlichen Höhen
HStack(alignment: .top) {
Image(systemName: "star")
Text("Long multiline text...")
}
- LazyHStack für lange Listen: Bessere Performance
ScrollView(.horizontal) {
LazyHStack {
ForEach(items) { item in
ItemView(item: item)
}
}
}
- Fixed Width für gleichmäßige Abstände
HStack {
ForEach(items) { item in
Text(item)
.frame(width: 100)
}
}
Common Use Cases
- Navigation Bars: Title mit Buttons
- Toolbar: Icon-Buttons nebeneinander
- Profile Rows: Avatar + Info + Actions
- Tab Bars: Horizontal angeordnete Tabs
- Tag Clouds: Horizontale Tag-Listen
- Button Groups: Mehrere Buttons nebeneinander
- Form Labels: Label + Input nebeneinander
- Stats Display: Mehrere Statistiken horizontal
Related Views
- VStack: Vertikales Layout
- ZStack: Übereinander liegendes Layout
- LazyHStack: Lazy-loading horizontal stack
- ScrollView: Für scrollbare Inhalte
- Spacer: Für Abstände und Verteilung