mirror of
https://github.com/phranck/TUIkit.git
synced 2026-06-20 09:54:37 +00:00
Implement SwiftUI-style structural identity so @State values survive full view-tree reconstruction on every render pass. State is keyed by ViewIdentity (path-based) and property index in a central StateStorage. - Add ViewIdentity (path-based structural identity for views) - Add StateStorage with GC and branch invalidation - Refactor @State to self-hydrate from StateStorage during init - Set root hydration context in RenderLoop before app.body evaluation - Extend RenderContext with identity propagation helpers - Add ConditionalView branch invalidation on switch - Remove scene cache from RenderLoop (app.body evaluated fresh per frame) - Enhance Example App pages with @State (ButtonsPage, OverlaysPage, ContainersPage) - Update DocC articles (StateManagement, RenderCycle) - Add 12 tests for state storage identity
86 lines
2.7 KiB
Swift
86 lines
2.7 KiB
Swift
//
|
|
// OverlaysPage.swift
|
|
// TUIkitExample
|
|
//
|
|
// Demonstrates overlay and modal capabilities.
|
|
//
|
|
|
|
import TUIkit
|
|
|
|
/// Overlays and modals demo page.
|
|
///
|
|
/// Shows the overlay system including:
|
|
/// - `.overlay()` modifier with `@State`-controlled visibility
|
|
/// - `.dimmed()` modifier
|
|
/// - `.modal()` helper
|
|
/// - Note: The status bar is NOT dimmed by modals!
|
|
struct OverlaysPage: View {
|
|
@State var showModal: Bool = true
|
|
|
|
var body: some View {
|
|
if showModal {
|
|
backgroundContent
|
|
.dimmed()
|
|
.overlay {
|
|
HStack {
|
|
Spacer()
|
|
Alert(
|
|
title: "Alert",
|
|
message: "This alert overlays dimmed content!",
|
|
borderColor: .palette.border,
|
|
titleColor: .palette.accent
|
|
) {
|
|
VStack(spacing: 1) {
|
|
Button("Dismiss", style: .primary) {
|
|
showModal = false
|
|
}
|
|
}
|
|
}
|
|
.frame(width: 55)
|
|
Spacer()
|
|
}
|
|
}
|
|
} else {
|
|
backgroundContent
|
|
}
|
|
}
|
|
|
|
var backgroundContent: some View {
|
|
VStack(spacing: 1) {
|
|
HeaderView(title: "Overlays & Modals Demo")
|
|
|
|
DemoSection("Overlay System Features") {
|
|
Text(" .overlay() modifier - layer content on top")
|
|
Text(" .dimmed() modifier - reduce visual emphasis")
|
|
Text(" .modal() helper - combines dimmed + centered overlay")
|
|
}
|
|
|
|
DemoSection("Modal Toggle (@State)") {
|
|
HStack(spacing: 2) {
|
|
if showModal {
|
|
Text("Modal is visible")
|
|
.foregroundColor(.palette.accent)
|
|
} else {
|
|
Text("Modal dismissed")
|
|
.foregroundColor(.palette.foregroundSecondary)
|
|
Button("Show Again", style: .primary) {
|
|
showModal = true
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
DemoSection("How It Works") {
|
|
Text("The modal visibility is controlled by @State var showModal")
|
|
Text("Pressing 'Dismiss' sets showModal = false")
|
|
.foregroundColor(.palette.foregroundSecondary)
|
|
Text("Note: The status bar is NOT dimmed!")
|
|
.bold()
|
|
.foregroundColor(.palette.accent)
|
|
}
|
|
|
|
Spacer()
|
|
}
|
|
}
|
|
}
|