Files
Screens/Packages/VNCUI/Sources/VNCUI/List/ConnectionListView.swift
Claude 2cff17fa0d Phase 0: scaffold
Two SPM packages (VNCCore, VNCUI) + thin iOS app target wired via
xcodegen. Builds for iPhone 17 simulator, unit tests pass.

- VNCCore: SessionState, SessionController stub, Transport protocol
  with DirectTransport (NWConnection), DiscoveryService (Bonjour on
  _rfb._tcp and _workstation._tcp), SavedConnection @Model,
  ConnectionStore, KeychainService, ClipboardBridge
- VNCUI: ConnectionListView, AddConnectionView, SessionView,
  FramebufferView/FramebufferUIView (UIKit CALayer), InputMapper,
  SettingsView; UIKit bits guarded with #if canImport(UIKit) so
  swift test runs on macOS
- App: @main VNCApp, AppStateController state machine, RootView
- RoyalVNCKit dependency pinned to main (transitive CryptoSwift
  constraint blocks tagged releases)
- xcodegen Project.yml + README + .gitignore

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-16 19:29:47 -05:00

70 lines
2.4 KiB
Swift

import SwiftUI
import SwiftData
import VNCCore
public struct ConnectionListView: View {
@Environment(\.modelContext) private var modelContext
@Query(sort: \SavedConnection.displayName) private var connections: [SavedConnection]
@State private var discovery = DiscoveryService()
@State private var showingAdd = false
@State private var selectedConnection: SavedConnection?
public init() {}
public var body: some View {
NavigationStack {
List {
if !discovery.hosts.isEmpty {
Section("Discovered on this network") {
ForEach(discovery.hosts) { host in
Button {
// Phase 1: resolve host to SavedConnection draft
} label: {
Label(host.displayName, systemImage: "bonjour")
}
}
}
}
Section("Saved") {
if connections.isEmpty {
ContentUnavailableView(
"No saved connections",
systemImage: "display",
description: Text("Tap + to add a computer to connect to.")
)
} else {
ForEach(connections) { connection in
ConnectionCard(connection: connection)
.onTapGesture {
selectedConnection = connection
}
}
}
}
}
.navigationTitle("Screens")
.toolbar {
ToolbarItem(placement: .primaryAction) {
Button {
showingAdd = true
} label: {
Image(systemName: "plus")
}
}
}
.sheet(isPresented: $showingAdd) {
AddConnectionView()
}
.navigationDestination(item: $selectedConnection) { connection in
SessionView(connection: connection)
}
.task {
discovery.start()
}
.onDisappear {
discovery.stop()
}
}
}
}