Foundation implementation
This commit is contained in:
commit
145d0a710d
27 changed files with 739 additions and 0 deletions
42
Tests/PorticoTests/MountTests.swift
Normal file
42
Tests/PorticoTests/MountTests.swift
Normal file
|
|
@ -0,0 +1,42 @@
|
|||
import Testing
|
||||
import Gtk
|
||||
@_spi(Portico) import Portico
|
||||
|
||||
@MainActor @Suite(.serialized) struct MountTests {
|
||||
private func childCount(_ w: Gtk.Widget) -> Int {
|
||||
var n = 0
|
||||
var cur = w.getFirstChild()
|
||||
while let c = cur { n += 1; cur = c.getNextSibling() }
|
||||
return n
|
||||
}
|
||||
|
||||
@Test func vstackAppendsChildrenInOrder() {
|
||||
guard Gtk.initCheck() else { return }
|
||||
let widget = AnyView(VStack(spacing: 0) {
|
||||
Label("a")
|
||||
Button("b") {}
|
||||
}).makeWidget(MountContext())
|
||||
#expect(childCount(widget) == 2)
|
||||
}
|
||||
|
||||
@Test func hstackMountsLabelAndText() {
|
||||
guard Gtk.initCheck() else { return }
|
||||
let widget = AnyView(HStack(spacing: 0) {
|
||||
Label("a")
|
||||
Text("b")
|
||||
}).makeWidget(MountContext())
|
||||
#expect(childCount(widget) == 2)
|
||||
}
|
||||
|
||||
@Test func buttonStoresAction() {
|
||||
// Validates Portico-level contract: Button stores its action
|
||||
// closure, and it is callable synchronously. The connectClicked
|
||||
// signal wiring cannot be tested synchronously in P0 — GTK's
|
||||
// activate→clicked chain requires a realized widget and main-loop
|
||||
// iteration (~250ms timer), out of scope for unit tests.
|
||||
var fired = false
|
||||
let button = Button("x") { fired = true }
|
||||
button.action()
|
||||
#expect(fired)
|
||||
}
|
||||
}
|
||||
31
Tests/PorticoTests/ViewBuilderTests.swift
Normal file
31
Tests/PorticoTests/ViewBuilderTests.swift
Normal file
|
|
@ -0,0 +1,31 @@
|
|||
import Testing
|
||||
@_spi(Portico) import Portico
|
||||
|
||||
@Suite struct ViewBuilderTests {
|
||||
@ViewBuilder private func mixed(_ flag: Bool) -> [AnyView] {
|
||||
Label("a")
|
||||
if flag { Label("b") }
|
||||
}
|
||||
|
||||
@ViewBuilder private func either(_ flag: Bool) -> [AnyView] {
|
||||
if flag { Label("a") } else { Label("b"); Label("c") }
|
||||
}
|
||||
|
||||
@ViewBuilder private func loop() -> [AnyView] {
|
||||
for _ in 0..<3 { Label("x") }
|
||||
}
|
||||
|
||||
@Test func mixedPlainAndConditional() {
|
||||
#expect(mixed(true).count == 2)
|
||||
#expect(mixed(false).count == 1)
|
||||
}
|
||||
|
||||
@Test func eitherBranches() {
|
||||
#expect(either(true).count == 1)
|
||||
#expect(either(false).count == 2)
|
||||
}
|
||||
|
||||
@Test func forLoopFlattens() {
|
||||
#expect(loop().count == 3)
|
||||
}
|
||||
}
|
||||
25
Tests/PorticoTests/WindowConfigTests.swift
Normal file
25
Tests/PorticoTests/WindowConfigTests.swift
Normal file
|
|
@ -0,0 +1,25 @@
|
|||
import Testing
|
||||
@_spi(Portico) import Portico
|
||||
|
||||
@Suite struct WindowConfigTests {
|
||||
@Test func modifiersAccumulate() {
|
||||
let w = Window { _ in Label("x") }
|
||||
.title("T")
|
||||
.defaultSize(width: 100, height: 200)
|
||||
.resizable(false)
|
||||
.fullscreen()
|
||||
#expect(w.config.title == "T")
|
||||
#expect(w.config.defaultSize?.width == 100)
|
||||
#expect(w.config.defaultSize?.height == 200)
|
||||
#expect(w.config.resizable == false)
|
||||
#expect(w.config.fullscreen == true)
|
||||
}
|
||||
|
||||
@Test func defaultConfigIsEmpty() {
|
||||
let w = Window { _ in Label("x") }
|
||||
#expect(w.config.title == nil)
|
||||
#expect(w.config.defaultSize == nil)
|
||||
#expect(w.config.resizable == nil)
|
||||
#expect(w.config.fullscreen == false)
|
||||
}
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue