From 4e00037a89da133a3579500593adf25fd7282613 Mon Sep 17 00:00:00 2001 From: enricobuehler Date: Mon, 29 Jun 2026 20:25:43 +0200 Subject: [PATCH] feat(apple): stage-2 default + pixel-perfect, decode robustness, UI/rumble polish MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Stream reliability - Default to the stage-2 presenter (VTDecompressionSession + CAMetalLayer): it detects and recovers a wedged decoder, where stage-1's AVSampleBufferDisplayLayer freezes hard on a lost HEVC reference frame with no app-side recovery (confirmed Apple limitation). Stage 1 is now a DEBUG-only presenter toggle, plus the automatic no-Metal fallback. - Stage-2 pixel-perfect: render the drawable at the decoded size (shader stays 1:1 = identity) and let the layer's contentsGravity scale via the system compositor — the same path stage-1's videoGravity used — instead of scaling in-shader. - Loss recovery in both pumps is now a persistent awaitingIDR want, retried until an IDR actually lands, so a keyframe request swallowed by the throttle can't strand a frozen frame; 100 ms keyframe throttle to match the Android path. - Fix "Publishing changes from within view updates": defer the HostStore writes out of the .onChange(of: model.phase) callback. - Move AVAudioSession setActive/setCategory off the main thread (async on a shared serial queue) to stop the UI-stall warning. Controllers - Rumble: capped-exponential backoff when the gamecontrollerd.haptics XPC breaks (-4811) so a transient server interruption self-heals instead of cascading; playsHapticsOnly so a controller engine doesn't join the always-active streaming audio session. - Host cards: iPad pointer "magnet" hover effect; iPhone press scale + light haptic. UI / design - Ship Geist (SIL OFL 1.1) as the app font (bundled OTFs + registration), with the license surfaced in Acknowledgements. - Restructure iOS/iPadOS Settings into a category NavigationSplitView; resolution wheel with custom-resolution entry; 10-bit HDR toggle in Display. - Industrial host-card redesign (left-aligned, bold, brand monogram tiles). Co-Authored-By: Claude Opus 4.8 (1M context) --- clients/apple/Package.swift | 3 + .../AcknowledgementsView.swift | 23 +- .../Sources/PunktfunkClient/BrandTheme.swift | 39 ++ .../Sources/PunktfunkClient/ContentView.swift | 19 +- .../PunktfunkClient/ControllerTestView.swift | 20 +- .../Sources/PunktfunkClient/HomeView.swift | 19 +- .../Sources/PunktfunkClient/HostCards.swift | 250 +++++++---- .../Sources/PunktfunkClient/LibraryView.swift | 6 +- .../Sources/PunktfunkClient/PairSheet.swift | 8 +- .../PunktfunkClient/PunktfunkClientApp.swift | 39 +- .../Screenshots/ScreenshotScenes.swift | 16 +- .../PunktfunkClient/SettingsView.swift | 409 ++++++++++++++++-- .../PunktfunkClient/SpeedTestSheet.swift | 8 +- .../PunktfunkClient/StreamHUDView.swift | 10 +- .../PunktfunkClient/TrustCardView.swift | 7 +- .../Sources/PunktfunkKit/BrandFont.swift | 101 +++++ .../Sources/PunktfunkKit/DefaultsKeys.swift | 3 + .../PunktfunkKit/GamepadFeedback.swift | 44 +- .../apple/Sources/PunktfunkKit/Licenses.swift | 11 + .../PunktfunkKit/MetalVideoPresenter.swift | 85 +++- .../Resources/Fonts/Geist-Bold.otf | Bin 0 -> 166516 bytes .../Resources/Fonts/Geist-Medium.otf | Bin 0 -> 162304 bytes .../Resources/Fonts/Geist-OFL.txt | 93 ++++ .../Resources/Fonts/Geist-Regular.otf | Bin 0 -> 157508 bytes .../Resources/Fonts/Geist-SemiBold.otf | Bin 0 -> 164780 bytes .../Sources/PunktfunkKit/SessionAudio.swift | 92 ++-- .../Sources/PunktfunkKit/Stage2Pipeline.swift | 38 +- .../Sources/PunktfunkKit/StreamPump.swift | 73 +++- .../Sources/PunktfunkKit/StreamView.swift | 36 +- .../Sources/PunktfunkKit/StreamViewIOS.swift | 45 +- .../MetalPresenterTests.swift | 21 + 31 files changed, 1221 insertions(+), 297 deletions(-) create mode 100644 clients/apple/Sources/PunktfunkClient/BrandTheme.swift create mode 100644 clients/apple/Sources/PunktfunkKit/BrandFont.swift create mode 100644 clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-Bold.otf create mode 100644 clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-Medium.otf create mode 100644 clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-OFL.txt create mode 100644 clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-Regular.otf create mode 100644 clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-SemiBold.otf create mode 100644 clients/apple/Tests/PunktfunkKitTests/MetalPresenterTests.swift diff --git a/clients/apple/Package.swift b/clients/apple/Package.swift index 7deaef3..3447872 100644 --- a/clients/apple/Package.swift +++ b/clients/apple/Package.swift @@ -24,6 +24,9 @@ let package = Package( .copy("Resources/THIRD-PARTY-NOTICES.txt"), .copy("Resources/LICENSE-MIT.txt"), .copy("Resources/LICENSE-APACHE.txt"), + // Geist (SIL OFL 1.1) — the brand typeface, shared with punktfunk-website. + // Registered with Core Text at first use; see BrandFont.swift. + .copy("Resources/Fonts"), ], linkerSettings: [ // Rust staticlib system deps. diff --git a/clients/apple/Sources/PunktfunkClient/AcknowledgementsView.swift b/clients/apple/Sources/PunktfunkClient/AcknowledgementsView.swift index cc19374..02b89af 100644 --- a/clients/apple/Sources/PunktfunkClient/AcknowledgementsView.swift +++ b/clients/apple/Sources/PunktfunkClient/AcknowledgementsView.swift @@ -17,10 +17,10 @@ struct AcknowledgementsView: View { LazyVStack(alignment: .leading, spacing: 0) { VStack(alignment: .leading, spacing: 18) { Text("punktfunk") - .font(.title2).bold() + .font(.geist(22, .bold, relativeTo: .title2)) if let version { Text("Version \(version)") - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) } Text(Licenses.appLicense) @@ -29,14 +29,29 @@ struct AcknowledgementsView: View { Divider() + Text("Bundled font") + .font(.geist(17, .semibold, relativeTo: .headline)) + Text("punktfunk ships the Geist typeface (Geist Sans), " + + "© The Geist Project Authors / Vercel, used under the SIL Open Font " + + "License 1.1.") + .font(.geist(12, relativeTo: .caption)) + .foregroundStyle(.secondary) + if !Licenses.fontLicense.isEmpty { + Text(Licenses.fontLicense) + .font(.caption2.monospaced()) + .modifier(SelectableText()) + } + + Divider() + Text("Third-party software") - .font(.headline) + .font(.geist(17, .semibold, relativeTo: .headline)) Text( "punktfunk uses the open-source components below, each under its own license. " + "On some platforms FFmpeg is additionally bundled under the LGPL v2.1+ " + "(dynamically linked, replaceable)." ) - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) } .frame(maxWidth: .infinity, alignment: .leading) diff --git a/clients/apple/Sources/PunktfunkClient/BrandTheme.swift b/clients/apple/Sources/PunktfunkClient/BrandTheme.swift new file mode 100644 index 0000000..7f7722d --- /dev/null +++ b/clients/apple/Sources/PunktfunkClient/BrandTheme.swift @@ -0,0 +1,39 @@ +// App-wide brand chrome. SwiftUI has no single switch to put a custom font on every navigation +// title, so the iOS large/inline nav titles are themed through UINavigationBar's appearance proxy +// (set once at launch). Backgrounds are left at the system defaults — transparent at the scroll +// edge (the large title floats on the content), blurred once scrolled — so only the typeface +// changes: Geist, matching the cards and the website. + +#if os(iOS) +import PunktfunkKit +import UIKit + +enum BrandTheme { + static func apply() { + BrandFont.registerIfNeeded() + + let scrollEdge = UINavigationBarAppearance() + scrollEdge.configureWithTransparentBackground() + applyFonts(to: scrollEdge) + + let standard = UINavigationBarAppearance() + standard.configureWithDefaultBackground() + applyFonts(to: standard) + + let proxy = UINavigationBar.appearance() + proxy.scrollEdgeAppearance = scrollEdge + proxy.standardAppearance = standard + proxy.compactAppearance = standard + } + + /// Override only the title fonts; leave colors/backgrounds at the configured defaults. + private static func applyFonts(to appearance: UINavigationBarAppearance) { + if let large = UIFont(name: "Geist-Bold", size: 34) { + appearance.largeTitleTextAttributes[.font] = large + } + if let inline = UIFont(name: "Geist-SemiBold", size: 17) { + appearance.titleTextAttributes[.font] = inline + } + } +} +#endif diff --git a/clients/apple/Sources/PunktfunkClient/ContentView.swift b/clients/apple/Sources/PunktfunkClient/ContentView.swift index 0a18ba6..c8d1319 100644 --- a/clients/apple/Sources/PunktfunkClient/ContentView.swift +++ b/clients/apple/Sources/PunktfunkClient/ContentView.swift @@ -28,6 +28,7 @@ struct ContentView: View { @AppStorage(DefaultsKey.gamepadType) private var gamepadType = 0 @AppStorage(DefaultsKey.bitrateKbps) private var bitrateKbps = 0 @AppStorage(DefaultsKey.audioChannels) private var audioChannels = 2 + @AppStorage(DefaultsKey.hdrEnabled) private var hdrEnabled = true @AppStorage(DefaultsKey.fullscreenWhileStreaming) private var fullscreenWhileStreaming = true @AppStorage(DefaultsKey.hudEnabled) private var hudEnabled = true @AppStorage(DefaultsKey.hudPlacement) private var hudPlacement = HUDPlacement.topTrailing.rawValue @@ -68,15 +69,19 @@ struct ContentView: View { // A session actually started — remember it on the card ("Connected … ago" // plus the accent ring on the most recent host). guard let host = model.activeHost else { break } - store.markConnected(host.id) // Delegated approval just succeeded: the operator let this device in, so pin the // host's observed fingerprint and remember it as paired — future connects are then // silent (rule 1), exactly like after a PIN/TOFU success. Dismisses the wait prompt. - if awaitingApproval?.host.id == host.id { - if let fp = model.connection?.hostFingerprint { - store.pin(host.id, fingerprint: fp) - } - awaitingApproval = nil + let approvedFingerprint = awaitingApproval?.host.id == host.id + ? model.connection?.hostFingerprint : nil + if awaitingApproval?.host.id == host.id { awaitingApproval = nil } + // Persist on the next runloop tick: HostStore is an ObservableObject, and mutating + // its @Published from inside .onChange (a view-update callback) trips SwiftUI's + // "Publishing changes from within view updates". A one-tick delay is imperceptible. + let store = store + DispatchQueue.main.async { + store.markConnected(host.id) + if let approvedFingerprint { store.pin(host.id, fingerprint: approvedFingerprint) } } case .idle: // The delegated-approval connect failed, timed out, or was cancelled — drop the @@ -333,6 +338,7 @@ struct ContentView: View { rawValue: UInt32(clamping: gamepadType)) ?? .auto), bitrateKbps: UInt32(clamping: bitrateKbps), audioChannels: UInt8(clamping: audioChannels), + hdrEnabled: hdrEnabled, launchID: launchID, allowTofu: allowTofu, requestAccess: requestAccess) @@ -475,6 +481,7 @@ struct ContentView: View { gamepad: pad, bitrateKbps: bitrate, audioChannels: UInt8(clamping: audioChannels), + hdrEnabled: hdrEnabled, autoTrust: true) } } diff --git a/clients/apple/Sources/PunktfunkClient/ControllerTestView.swift b/clients/apple/Sources/PunktfunkClient/ControllerTestView.swift index 0da3277..10bcaa6 100644 --- a/clients/apple/Sources/PunktfunkClient/ControllerTestView.swift +++ b/clients/apple/Sources/PunktfunkClient/ControllerTestView.swift @@ -54,7 +54,7 @@ struct ControllerTestView: View { var body: some View { VStack(spacing: 0) { HStack { - Text("Test Controller").font(.headline) + Text("Test Controller").font(.geist(17, .semibold, relativeTo: .headline)) Spacer() Button("Done") { dismiss() }.keyboardShortcut(.cancelAction) } @@ -99,8 +99,8 @@ struct ControllerTestView: View { .font(.title2) .foregroundStyle(.secondary) VStack(alignment: .leading, spacing: 2) { - Text(c.name).font(.headline) - Text(c.productCategory).font(.caption).foregroundStyle(.secondary) + Text(c.name).font(.geist(17, .semibold, relativeTo: .headline)) + Text(c.productCategory).font(.geist(12, relativeTo: .caption)).foregroundStyle(.secondary) } Spacer() } @@ -209,7 +209,7 @@ struct ControllerTestView: View { ) -> some View { VStack(alignment: .leading, spacing: 4) { Text("Touchpad\(tp.button.isPressed ? " — click" : "")") - .font(.caption2).foregroundStyle(.secondary) + .font(.geist(11, relativeTo: .caption2)).foregroundStyle(.secondary) ZStack { RoundedRectangle(cornerRadius: 8).stroke(Color.secondary.opacity(0.3)) fingerDot(tp.primary, color: .accentColor) @@ -230,7 +230,7 @@ struct ControllerTestView: View { private func motionReadout(_ m: GCMotion) -> some View { let a = Self.totalAccel(m) return VStack(alignment: .leading, spacing: 2) { - Text("Motion").font(.caption2).foregroundStyle(.secondary) + Text("Motion").font(.geist(11, relativeTo: .caption2)).foregroundStyle(.secondary) Text(String(format: "gyro %+.2f %+.2f %+.2f", m.rotationRate.x, m.rotationRate.y, m.rotationRate.z)) .font(.caption2.monospaced()) @@ -254,11 +254,11 @@ struct ControllerTestView: View { Toggle("Heavy motor (left)", isOn: $heavyOn) Toggle("Light motor (right)", isOn: $lightOn) Label("Backend: \(tester.rumbleBackend)", systemImage: "waveform") - .font(.caption).foregroundStyle(.secondary) + .font(.geist(12, relativeTo: .caption)).foregroundStyle(.secondary) Text("Toggle a motor to feel it. The host maps a game's low/high-frequency " + "rumble onto these two. A DualSense is driven over raw HID (CoreHaptics " + "can't reach its motors on macOS).") - .font(.caption).foregroundStyle(.secondary) + .font(.geist(12, relativeTo: .caption)).foregroundStyle(.secondary) } .onChange(of: heavyOn) { _, _ in applyRumble() } .onChange(of: lightOn) { _, _ in applyRumble() } @@ -289,11 +289,11 @@ struct ControllerTestView: View { } } Text("Pick an effect, then pull L2/R2 to feel the resistance.") - .font(.caption).foregroundStyle(.secondary) + .font(.geist(12, relativeTo: .caption)).foregroundStyle(.secondary) } } else { Text("Adaptive triggers need a DualSense.") - .font(.caption).foregroundStyle(.secondary) + .font(.geist(12, relativeTo: .caption)).foregroundStyle(.secondary) } } } @@ -348,7 +348,7 @@ struct ControllerTestView: View { _ title: String, @ViewBuilder _ content: () -> Content ) -> some View { VStack(alignment: .leading, spacing: 10) { - Text(title).font(.subheadline.weight(.semibold)) + Text(title).font(.geist(15, .semibold, relativeTo: .subheadline)) content() } .frame(maxWidth: .infinity, alignment: .leading) diff --git a/clients/apple/Sources/PunktfunkClient/HomeView.swift b/clients/apple/Sources/PunktfunkClient/HomeView.swift index aee5374..019949a 100644 --- a/clients/apple/Sources/PunktfunkClient/HomeView.swift +++ b/clients/apple/Sources/PunktfunkClient/HomeView.swift @@ -127,14 +127,13 @@ struct HomeView: View { AddHostSheet { store.add($0) } } #if os(iOS) + // SettingsView owns its own NavigationSplitView (sidebar + detail) and Done button, so it + // is presented directly — wrapping it in a NavigationStack here would nest a split view in + // a stack (double title bars). `settingsSheetSizing()` widens the sheet on iPad for the + // two-column layout. .sheet(isPresented: $showSettings) { - NavigationStack { - SettingsView() - .navigationTitle("Settings") - .toolbar { - Button("Done") { showSettings = false } - } - } + SettingsView() + .settingsSheetSizing() } #endif #endif @@ -172,7 +171,7 @@ struct HomeView: View { private var discoveredSection: some View { VStack(alignment: .leading, spacing: 10) { Label("On this network", systemImage: "antenna.radiowaves.left.and.right") - .font(.headline) + .font(.geist(15, .semibold, relativeTo: .headline)) .foregroundStyle(.secondary) .padding(.horizontal) LazyVGrid(columns: gridColumns, spacing: gridSpacing) { @@ -249,8 +248,10 @@ struct HomeView: View { /// the width so the cards stay edge-aligned with the title and bars — sized touch-first: one /// column on iPhone portrait, 3–4 generous cards on iPad. private var gridColumns: [GridItem] { + // Wider than before: the monogram card is a horizontal module (tile + address line), so + // it needs room for a monospaced "IP:port" without truncating. #if os(macOS) - [GridItem(.adaptive(minimum: 180, maximum: 240), spacing: 16)] + [GridItem(.adaptive(minimum: 250, maximum: 320), spacing: 16)] #elseif os(tvOS) [GridItem(.adaptive(minimum: 320), spacing: 48)] #else diff --git a/clients/apple/Sources/PunktfunkClient/HostCards.swift b/clients/apple/Sources/PunktfunkClient/HostCards.swift index 9ad1641..b2ebccb 100644 --- a/clients/apple/Sources/PunktfunkClient/HostCards.swift +++ b/clients/apple/Sources/PunktfunkClient/HostCards.swift @@ -1,26 +1,75 @@ // The host grid's cards: a saved host (tap to connect, context menu) and an mDNS-discovered -// host (tap to save + connect). Both share the same platform-tuned sizing. +// host (tap to save + connect). Both share the "monogram module" look — a squared brand-purple +// monogram tile + a left-aligned bold Geist name over monospaced technical metadata +// (address, status), framed by a hairline panel border. Industrial, not soft. import PunktfunkKit import SwiftUI -/// Shared host-card sizing — touch-first on iOS, compact on macOS/tvOS. +/// Shared host-card sizing — touch-first on iOS, compact on macOS, roomy on tvOS. private struct CardMetrics { - let iconSize: CGFloat - let iconBox: CGFloat - let cardPadding: CGFloat - let nameFont: Font + let tile: CGFloat // monogram tile side + let monogram: CGFloat // monogram letter point size + let name: CGFloat // host-name point size + let meta: CGFloat // address (mono) point size + let status: CGFloat // status-label (mono) point size + let padding: CGFloat + let spacing: CGFloat // tile ↔ text gap + let radius: CGFloat static var current: CardMetrics { #if os(iOS) - CardMetrics(iconSize: 56, iconBox: 76, cardPadding: 28, nameFont: .title3.weight(.semibold)) + CardMetrics(tile: 54, monogram: 26, name: 19, meta: 13, status: 11, + padding: 16, spacing: 14, radius: 12) + #elseif os(tvOS) + CardMetrics(tile: 64, monogram: 32, name: 24, meta: 16, status: 14, + padding: 18, spacing: 18, radius: 14) #else - CardMetrics(iconSize: 42, iconBox: 56, cardPadding: 18, nameFont: .headline) + CardMetrics(tile: 44, monogram: 21, name: 15, meta: 12, status: 10.5, + padding: 13, spacing: 12, radius: 10) #endif } } -/// A saved host. The accent ring marks the most-recently-connected one; the context menu +/// First letter of a host name, uppercased — the monogram glyph. Falls back to a bullet. +private func monogram(_ name: String) -> String { + guard let first = name.trimmingCharacters(in: .whitespacesAndNewlines).first else { return "•" } + return String(first).uppercased() +} + +/// The squared monogram tile. `filled` = a solid brand-purple chip (saved hosts); otherwise a +/// tinted outline (discovered hosts). Shows a spinner in place of the glyph while connecting. +private func monogramTile(_ letter: String, m: CardMetrics, connecting: Bool, filled: Bool) -> some View { + let shape = RoundedRectangle(cornerRadius: m.radius - 3, style: .continuous) + return ZStack { + shape.fill(filled + ? AnyShapeStyle(LinearGradient( + colors: [Color.brand, Color.brand.opacity(0.72)], + startPoint: .top, endPoint: .bottom)) + : AnyShapeStyle(Color.brand.opacity(0.14))) + if connecting { + ProgressView().tint(filled ? .white : Color.brand) + } else { + // Fixed size (not Dynamic Type): the glyph is pinned inside a fixed tile, so it must + // not scale up and spill out at large accessibility text sizes. minimumScaleFactor + + // the clip below are belt-and-suspenders for an unusually wide glyph. + Text(letter) + .font(.geistFixed(m.monogram, .bold)) + .minimumScaleFactor(0.5) + .lineLimit(1) + .foregroundStyle(filled ? Color.white : Color.brand) + } + } + .frame(width: m.tile, height: m.tile) + .clipShape(shape) + .overlay { + if !filled { + shape.strokeBorder(Color.brand.opacity(0.45), lineWidth: 1) + } + } +} + +/// A saved host. A left accent bar marks the most-recently-connected one; the context menu /// pairs / speed-tests / forgets / removes. Disabled while a session is busy. struct HostCardView: View { let host: StoredHost @@ -41,66 +90,44 @@ struct HostCardView: View { var body: some View { let m = CardMetrics.current return Button(action: onConnect) { - VStack(spacing: 10) { - ZStack { - Image(systemName: "play.display") - .font(.system(size: m.iconSize, weight: .light)) - .foregroundStyle(.tint) - .opacity(isConnecting ? 0.3 : 1) - if isConnecting { - ProgressView() - } + HStack(spacing: m.spacing) { + monogramTile(monogram(host.displayName), m: m, connecting: isConnecting, filled: true) + VStack(alignment: .leading, spacing: 4) { + Text(host.displayName) + .font(.geist(m.name, .bold, relativeTo: .title3)) + .foregroundStyle(.primary) + .lineLimit(1) + Text("\(host.address):\(String(host.port))") + .font(.geist(m.meta, relativeTo: .caption)) + .foregroundStyle(.secondary) + .lineLimit(1) + statusRow(m) } - .frame(height: m.iconBox) - VStack(spacing: 2) { - HStack(spacing: 6) { - // Presence dot: green = advertising on the LAN now; grey = not seen. - Circle() - .fill(isOnline ? Color.green : Color.secondary.opacity(0.35)) - .frame(width: 7, height: 7) - .accessibilityLabel(isOnline ? "Online" : "Offline") - Text(host.displayName) - .font(m.nameFont) - .lineLimit(1) - } - HStack(spacing: 4) { - if host.pinnedSHA256 != nil { - Image(systemName: "lock.fill") - .font(.system(size: 9)) - .foregroundStyle(.secondary) - } - Text("\(host.address):\(String(host.port))") - .font(.caption) - .foregroundStyle(.secondary) - .lineLimit(1) - } - if let last = host.lastConnected { - Text("Connected \(last, format: .relative(presentation: .named))") - .font(.caption2) - .foregroundStyle(.tertiary) - .lineLimit(1) - } + Spacer(minLength: 0) + } + .padding(m.padding) + .frame(maxWidth: .infinity, alignment: .leading) + #if !os(tvOS) + // tvOS: the .card button style owns platter + focus motion; extra chrome mutes it. + // Elsewhere: a flat material panel with a hairline border (industrial, not a soft blob), + // and a brand accent bar down the leading edge for the most-recent host. + .background(.regularMaterial) + .overlay(alignment: .leading) { + if isMostRecent { + Rectangle().fill(Color.brand).frame(width: 3) } } - .frame(maxWidth: .infinity) - .padding(.vertical, m.cardPadding) - .padding(.horizontal, 12) - #if !os(tvOS) - // tvOS: the .card button style owns platter + focus motion — extra chrome - // inside it mutes the grow/tilt. Material + accent ring are for pointer UIs. - // Deliberately .regularMaterial, not Liquid Glass: HIG keeps glass off content - // tiles (it flattens hierarchy over an opaque grid) — see GlassStyle.swift. - .background(.regularMaterial, in: RoundedRectangle(cornerRadius: 14)) + .clipShape(RoundedRectangle(cornerRadius: m.radius, style: .continuous)) .overlay { - if isMostRecent { - RoundedRectangle(cornerRadius: 14) - .strokeBorder(Color.accentColor.opacity(0.35), lineWidth: 1.5) - } + RoundedRectangle(cornerRadius: m.radius, style: .continuous) + .strokeBorder(.quaternary, lineWidth: 1) } #endif } #if os(tvOS) .buttonStyle(.card) + #elseif os(iOS) + .buttonStyle(HostCardButtonStyle(cornerRadius: m.radius)) #else .buttonStyle(.plain) #endif @@ -119,10 +146,31 @@ struct HostCardView: View { Button("Remove", role: .destructive, action: onRemove) } } + + /// Technical status line: a square presence pip + monospaced ONLINE/OFFLINE, and PAIRED when a + /// certificate is pinned (the lock state, spelled out). + @ViewBuilder private func statusRow(_ m: CardMetrics) -> some View { + HStack(spacing: 6) { + RoundedRectangle(cornerRadius: 1.5) + .fill(isOnline ? Color.green : Color.secondary.opacity(0.4)) + .frame(width: 6, height: 6) + // The state is spelled out in the adjacent text, so the pip is decorative — + // otherwise VoiceOver reads the status twice ("Online, ONLINE …"). + .accessibilityHidden(true) + Text(isOnline ? "ONLINE" : "OFFLINE") + if host.pinnedSHA256 != nil { + Text("· PAIRED") + } + } + .font(.geist(m.status, .medium, relativeTo: .caption2)) + .tracking(0.8) + .foregroundStyle(.secondary) + .lineLimit(1) + } } -/// A host found on the LAN but not yet saved. A dashed ring distinguishes it from saved cards; -/// tapping saves it and connects (or pairs, if the host requires it). +/// A host found on the LAN but not yet saved. A tinted-outline monogram + dashed panel border +/// distinguish it from saved cards; tapping saves it and connects (or pairs, if required). struct DiscoveredCardView: View { let discovered: DiscoveredHost let isBusy: Bool @@ -131,47 +179,77 @@ struct DiscoveredCardView: View { var body: some View { let m = CardMetrics.current return Button(action: onConnect) { - VStack(spacing: 10) { - Image(systemName: "play.display") - .font(.system(size: m.iconSize, weight: .light)) - .foregroundStyle(.tint) - .frame(height: m.iconBox) - VStack(spacing: 2) { + HStack(spacing: m.spacing) { + monogramTile(monogram(discovered.name), m: m, connecting: false, filled: false) + VStack(alignment: .leading, spacing: 4) { Text(discovered.name) - .font(m.nameFont) + .font(.geist(m.name, .bold, relativeTo: .title3)) + .foregroundStyle(.primary) .lineLimit(1) - HStack(spacing: 4) { - Image(systemName: discovered.requiresPairing ? "lock.fill" : "wifi") - .font(.system(size: 9)) - .foregroundStyle(.secondary) - Text("\(discovered.host):\(String(discovered.port))") - .font(.caption) - .foregroundStyle(.secondary) - .lineLimit(1) + Text("\(discovered.host):\(String(discovered.port))") + .font(.geist(m.meta, relativeTo: .caption)) + .foregroundStyle(.secondary) + .lineLimit(1) + HStack(spacing: 6) { + Image(systemName: discovered.requiresPairing + ? "lock.fill" : "antenna.radiowaves.left.and.right") + .font(.system(size: m.status)) + .accessibilityHidden(true) // decorative; the adjacent text says the state + Text(discovered.requiresPairing ? "PAIRING REQUIRED" : "DISCOVERED") } - Text(discovered.requiresPairing ? "Pairing required" : "Discovered") - .font(.caption2) - .foregroundStyle(.tertiary) + .font(.geist(m.status, .medium, relativeTo: .caption2)) + .tracking(0.8) + .foregroundStyle(.secondary) + .lineLimit(1) } + Spacer(minLength: 0) } - .frame(maxWidth: .infinity) - .padding(.vertical, m.cardPadding) - .padding(.horizontal, 12) + .padding(m.padding) + .frame(maxWidth: .infinity, alignment: .leading) #if !os(tvOS) - .background(.regularMaterial, in: RoundedRectangle(cornerRadius: 14)) + .background(.regularMaterial) + .clipShape(RoundedRectangle(cornerRadius: m.radius, style: .continuous)) .overlay { - RoundedRectangle(cornerRadius: 14) + RoundedRectangle(cornerRadius: m.radius, style: .continuous) .strokeBorder( - Color.secondary.opacity(0.25), + Color.secondary.opacity(0.3), style: StrokeStyle(lineWidth: 1, dash: [4, 3])) } #endif } #if os(tvOS) .buttonStyle(.card) + #elseif os(iOS) + .buttonStyle(HostCardButtonStyle(cornerRadius: m.radius)) #else .buttonStyle(.plain) #endif .disabled(isBusy) } } + +#if os(iOS) +/// The iOS host-card press/hover treatment, one style for both idioms: +/// - iPhone: a subtle scale-down on press + a light impact haptic on press-down. (`hoverEffect` is +/// inert without a pointer.) +/// - iPad: the system pointer "magnet" — the cursor morphs into a highlight that conforms to the +/// card's rounded rect on hover. (`sensoryFeedback` is inert without a Taptic Engine, and the +/// press scale doubles as click feedback.) +struct HostCardButtonStyle: ButtonStyle { + var cornerRadius: CGFloat + + func makeBody(configuration: Configuration) -> some View { + configuration.label + .scaleEffect(configuration.isPressed ? 0.96 : 1) + .animation(.spring(response: 0.3, dampingFraction: 0.65), value: configuration.isPressed) + // Conform the pointer highlight to the card's rounded rect, not its square bounds. + .contentShape(.hoverEffect, RoundedRectangle(cornerRadius: cornerRadius, style: .continuous)) + .hoverEffect(.highlight) + // Light tap on press-down (nil on release so it fires once, on touch). No haptic + // hardware on iPad → silently ignored there. + .sensoryFeedback(trigger: configuration.isPressed) { _, pressed in + pressed ? .impact(weight: .light) : nil + } + } +} +#endif diff --git a/clients/apple/Sources/PunktfunkClient/LibraryView.swift b/clients/apple/Sources/PunktfunkClient/LibraryView.swift index edf2b34..4de9833 100644 --- a/clients/apple/Sources/PunktfunkClient/LibraryView.swift +++ b/clients/apple/Sources/PunktfunkClient/LibraryView.swift @@ -146,7 +146,7 @@ private struct GameCard: View { .clipShape(RoundedRectangle(cornerRadius: 10, style: .continuous)) .overlay(alignment: .topLeading) { storeBadge } Text(game.title) - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .lineLimit(2) .foregroundStyle(.secondary) } @@ -154,7 +154,7 @@ private struct GameCard: View { private var storeBadge: some View { Text(game.isCustom ? "Custom" : "Steam") - .font(.caption2.weight(.semibold)) + .font(.geist(11, .semibold, relativeTo: .caption2)) .padding(.horizontal, 6) .padding(.vertical, 3) .background(.ultraThinMaterial, in: Capsule()) @@ -193,7 +193,7 @@ private struct PosterImage: View { ZStack { Rectangle().fill(.quaternary) Text(title) - .font(.headline) + .font(.geist(17, .semibold, relativeTo: .headline)) .multilineTextAlignment(.center) .foregroundStyle(.secondary) .padding(8) diff --git a/clients/apple/Sources/PunktfunkClient/PairSheet.swift b/clients/apple/Sources/PunktfunkClient/PairSheet.swift index e1f5755..9f46a18 100644 --- a/clients/apple/Sources/PunktfunkClient/PairSheet.swift +++ b/clients/apple/Sources/PunktfunkClient/PairSheet.swift @@ -48,7 +48,7 @@ struct PairSheet: View { + "(http://:3000 → Pairing). " + "Pairing verifies both sides at once — no fingerprint comparison " + "needed.") - .font(.callout) + .font(.geist(16, relativeTo: .callout)) .foregroundStyle(.secondary) .multilineTextAlignment(.center) TVFieldRow( @@ -59,7 +59,7 @@ struct PairSheet: View { ) { editing = .clientName } if let errorText { Text(errorText) - .font(.callout) + .font(.geist(16, relativeTo: .callout)) .foregroundStyle(.red) } HStack(spacing: 32) { @@ -121,13 +121,13 @@ struct PairSheet: View { + "(http://:3000 → Pairing). " + "Pairing verifies both sides at once — no fingerprint " + "comparison needed.") - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) } if let errorText { Section { Text(errorText) - .font(.callout) + .font(.geist(16, relativeTo: .callout)) .foregroundStyle(.red) } } diff --git a/clients/apple/Sources/PunktfunkClient/PunktfunkClientApp.swift b/clients/apple/Sources/PunktfunkClient/PunktfunkClientApp.swift index ce5ed76..a723b46 100644 --- a/clients/apple/Sources/PunktfunkClient/PunktfunkClientApp.swift +++ b/clients/apple/Sources/PunktfunkClient/PunktfunkClientApp.swift @@ -12,20 +12,36 @@ struct PunktfunkClientApp: App { @NSApplicationDelegateAdaptor(AppDelegate.self) private var appDelegate #endif + init() { + #if os(iOS) + // Put Geist on the navigation titles before any bar is built. + BrandTheme.apply() + #endif + } + var body: some Scene { WindowGroup("Punktfunk") { - #if DEBUG - // PUNKTFUNK_SHOT_SCENE= → show that single mock-populated screen full-bleed for - // the App Store screenshot capture (tools/screenshots.sh). Normal launch otherwise; - // the whole path is absent from Release builds. - if let scene = ScreenshotMode.requestedScene { - ScreenshotHostView(scene: scene) - } else { + // Pin the whole app's tint to the brand purple explicitly — the asset-catalog accent + // resolution is environment/timing-sensitive and can fall back to system blue. Wraps the + // screenshot harness too, so captured screens are on-brand. + Group { + #if DEBUG + // PUNKTFUNK_SHOT_SCENE= → show that single mock-populated screen full-bleed for + // the App Store screenshot capture (tools/screenshots.sh). Normal launch otherwise; + // the whole path is absent from Release builds. + if let scene = ScreenshotMode.requestedScene { + ScreenshotHostView(scene: scene) + } else { + ContentView() + } + #else ContentView() + #endif } - #else - ContentView() - #endif + .tint(.brand) + // Geist Sans is the app's typeface. This sets the default for unstyled text and the + // form row labels; views that pick an explicit size/weight use `.geist(…)` directly. + .font(.geist(17, relativeTo: .body)) } // The Stream menu (Disconnect ⌘D, Show/Hide Statistics ⌘⇧S) — a real menu bar on // macOS, hardware-keyboard shortcuts on iPad. tvOS has neither. @@ -34,7 +50,10 @@ struct PunktfunkClientApp: App { #endif #if os(macOS) Settings { + // A separate scene — `.tint` does not cross scene boundaries, so re-apply the brand + // tint here or the Preferences window falls back to the (unreliable) asset accent. SettingsView() + .tint(.brand) } #endif } diff --git a/clients/apple/Sources/PunktfunkClient/Screenshots/ScreenshotScenes.swift b/clients/apple/Sources/PunktfunkClient/Screenshots/ScreenshotScenes.swift index dec3cd8..f06e378 100644 --- a/clients/apple/Sources/PunktfunkClient/Screenshots/ScreenshotScenes.swift +++ b/clients/apple/Sources/PunktfunkClient/Screenshots/ScreenshotScenes.swift @@ -103,11 +103,11 @@ private struct ShotSettings: View { .shadow(radius: 40, y: 16) } #elseif os(iOS) - NavigationStack { - SettingsView() - .navigationTitle("Settings") - .navigationBarTitleDisplayMode(.inline) - } + // SettingsView owns its NavigationSplitView (sidebar + detail) and Done button, so it is + // rendered directly — a wrapping NavigationStack would nest a split view in a stack. Open + // on General so the shot lands on real controls (iPad: sidebar + General detail; iPhone: + // the General page) instead of the bare category list. + SettingsView(initialCategory: .general) #else NavigationStack { SettingsView() } #endif @@ -175,10 +175,10 @@ private struct ShotHUD: View { .foregroundStyle(.secondary) #if os(macOS) Text("⌘⎋ releases the mouse") - .font(.caption2).foregroundStyle(.secondary) + .font(.geist(11, relativeTo: .caption2)).foregroundStyle(.secondary) #elseif os(tvOS) Text("Press Menu to disconnect") - .font(.caption).foregroundStyle(.secondary) + .font(.geist(12, relativeTo: .caption)).foregroundStyle(.secondary) #endif } .padding(10) @@ -259,7 +259,7 @@ private struct ShotDesktopFrame: View { HStack(spacing: 8) { Image(systemName: "gamecontroller.fill") Text("Streaming from Battlestation") - .font(.system(.callout, weight: .semibold)) + .font(.geist(16, .semibold, relativeTo: .callout)) } .padding(.horizontal, 14).padding(.vertical, 9) .glassBackground(Capsule()) diff --git a/clients/apple/Sources/PunktfunkClient/SettingsView.swift b/clients/apple/Sources/PunktfunkClient/SettingsView.swift index 7123cb4..bf88fa1 100644 --- a/clients/apple/Sources/PunktfunkClient/SettingsView.swift +++ b/clients/apple/Sources/PunktfunkClient/SettingsView.swift @@ -1,10 +1,12 @@ // App settings. The host creates a native virtual output at exactly the chosen size/refresh — // there is no scaling anywhere in the pipeline. // -// Navigation differs per platform: macOS uses a tabbed preferences window (the sections had -// outgrown one scrolling pane); iOS uses a single grouped Form; tvOS uses a focus-native -// pushed-picker layout. The individual sections (`streamModeSection`, `audioSection`, …) are -// shared across all three so a setting is defined exactly once. +// Navigation differs per platform, but all three group the same categories (General, Display, +// Audio, Controllers, Advanced, About): macOS uses a tabbed preferences window; iOS/iPadOS uses +// an adaptive NavigationSplitView — a category sidebar + detail pane on iPad, auto-collapsing to +// a hierarchical push list on iPhone (the system Settings idiom on each); tvOS uses a +// focus-native pushed-picker layout. The individual sections (`streamModeSection`, +// `audioSection`, …) are shared across all three so a setting is defined exactly once. #if os(macOS) import AppKit @@ -21,7 +23,8 @@ struct SettingsView: View { @AppStorage(DefaultsKey.compositor) private var compositor = 0 @AppStorage(DefaultsKey.gamepadType) private var gamepadType = 0 @AppStorage(DefaultsKey.bitrateKbps) private var bitrateKbps = 0 - @AppStorage(DefaultsKey.presenter) private var presenter = "stage1" + @AppStorage(DefaultsKey.presenter) private var presenter = "stage2" + @AppStorage(DefaultsKey.hdrEnabled) private var hdrEnabled = true @AppStorage(DefaultsKey.libraryEnabled) private var libraryEnabled = false @AppStorage(DefaultsKey.fullscreenWhileStreaming) private var fullscreenWhileStreaming = true @AppStorage(DefaultsKey.micEnabled) private var micEnabled = true @@ -32,6 +35,21 @@ struct SettingsView: View { #if DEBUG && !os(tvOS) @State private var showControllerTest = false #endif + #if os(iOS) + // The sidebar selection drives the detail pane on iPad and the pushed sub-page on iPhone. + // Width class decides the initial value: nil on iPhone (show the category list first), + // General on iPad (a two-column layout should never open with an empty detail). + @Environment(\.horizontalSizeClass) private var horizontalSizeClass + @State private var settingsSelection: SettingsCategory? + // Tracked so the detail can show its own Done whenever the sidebar (and its Done) is off screen + // — not just on iPhone, but on any iPad layout that collapses the sidebar to an overlay. Starts + // .doubleColumn so iPad reliably opens with the sidebar (and its Done) visible. + @State private var columnVisibility: NavigationSplitViewVisibility = .doubleColumn + // Sticky once the wheel lands on "Custom…", so editing a width/height that briefly equals a + // preset doesn't snap the wheel back off Custom. A stored non-preset value reads as custom even + // when this is false (see `isCustomResolution`), so it survives relaunches without persisting. + @State private var customMode = false + #endif #if os(macOS) @AppStorage(DefaultsKey.speakerUID) private var speakerUID = "" @AppStorage(DefaultsKey.micUID) private var micUID = "" @@ -39,6 +57,15 @@ struct SettingsView: View { @State private var inputDevices: [AudioDevice] = [] #endif + #if os(iOS) + /// `initialCategory` is nil in the app (the list opens un-selected on iPhone; iPad lands on + /// General via `onAppear`). The screenshot harness passes an explicit category so the captured + /// shot opens on a real settings page (a populated detail) rather than the bare category list. + init(initialCategory: SettingsCategory? = nil) { + _settingsSelection = State(initialValue: initialCategory) + } + #endif + var body: some View { #if os(tvOS) // Native tv pattern: no inline text entry (typing numbers with a remote is @@ -66,6 +93,7 @@ struct SettingsView: View { Form { presenterSection + hdrSection windowSection statisticsSection } @@ -106,29 +134,115 @@ struct SettingsView: View { } #endif - // MARK: - iOS: one grouped Form + // MARK: - iOS / iPadOS: adaptive split view #if os(iOS) private var iosBody: some View { - Form { - streamModeSection - audioSection - compositorSection - presenterSection - statisticsSection - experimentalSection - controllersSection - Section { - NavigationLink("Acknowledgements") { AcknowledgementsView() } + NavigationSplitView(columnVisibility: $columnVisibility) { + List(selection: $settingsSelection) { + ForEach(SettingsCategory.allCases) { category in + // On iPhone the split view collapses to a push list, but a selection List + // draws no disclosure indicator of its own — add one in compact width for the + // expected drill-in affordance. On iPad the selected row highlights instead, so + // the chevron is omitted there. + HStack { + Label(category.title, systemImage: category.symbol) + if horizontalSizeClass == .compact { + Spacer() + Image(systemName: "chevron.forward") + .font(.footnote.weight(.semibold)) + .foregroundStyle(.tertiary) + // Purely a drill-in affordance — the row's button trait already + // conveys "opens"; keep it out of the VoiceOver announcement. + .accessibilityHidden(true) + } + } + .tag(category) + } } + .navigationTitle("Settings") + .toolbar { + ToolbarItem(placement: .confirmationAction) { + Button("Done") { dismiss() } + } + } + } detail: { + // NavigationSplitView hosts the detail in its own navigation context (its title bar), + // so no inner NavigationStack — that would double the bar on iPad. On iPhone the split + // view collapses to one stack and pushes this when a row is tapped. `?? .general` only + // backs the brief pre-selection window; the list never auto-pushes on a nil selection. + settingsDetail(settingsSelection ?? .general) + // Keep a Done on the detail whenever the sidebar (and its Done) isn't on screen: the + // iPhone push, or any iPad layout that collapsed the sidebar to an overlay. When the + // sidebar is showing, its Done is the only one — so this stays hidden to avoid two. + .toolbar { + if horizontalSizeClass == .compact || columnVisibility == .detailOnly { + ToolbarItem(placement: .confirmationAction) { + Button("Done") { dismiss() } + } + } + } } - .formStyle(.grouped) .onAppear { + if horizontalSizeClass == .regular, settingsSelection == nil { + settingsSelection = .general + } gamepads.refresh() gamepads.startDiscovery() } + // A regular→regular launch sets the default above; this catches a compact→regular change + // (e.g. an iPad leaving narrow split-screen multitasking) so the detail pane fills in. + .onChange(of: horizontalSizeClass) { _, newValue in + if newValue == .regular, settingsSelection == nil { + settingsSelection = .general + } + } .onDisappear { gamepads.stopDiscovery() } } + + @ViewBuilder + private func settingsDetail(_ category: SettingsCategory) -> some View { + switch category { + case .general: + Form { + streamModeSection + compositorSection + } + .formStyle(.grouped) + .navigationTitle("General") + .navigationBarTitleDisplayMode(.inline) + case .display: + Form { + presenterSection + hdrSection + statisticsSection + } + .formStyle(.grouped) + .navigationTitle("Display") + .navigationBarTitleDisplayMode(.inline) + case .audio: + Form { audioSection } + .formStyle(.grouped) + .navigationTitle("Audio") + .navigationBarTitleDisplayMode(.inline) + case .controllers: + Form { controllersSection } + .formStyle(.grouped) + .navigationTitle("Controllers") + .navigationBarTitleDisplayMode(.inline) + case .advanced: + Form { experimentalSection } + .formStyle(.grouped) + .navigationTitle("Advanced") + .navigationBarTitleDisplayMode(.inline) + case .about: + // Already a full scrollable view that sets its own "Acknowledgements" title; pin the + // display mode inline to match the five sibling detail pages (it would otherwise inherit + // the large title from the "Settings" sidebar root). + AcknowledgementsView() + .navigationBarTitleDisplayMode(.inline) + } + } #endif // MARK: - tvOS @@ -156,6 +270,10 @@ struct SettingsView: View { Binding(get: { hudEnabled ? "on" : "off" }, set: { hudEnabled = $0 == "on" }) } + private var hdrEnabledTag: Binding { + Binding(get: { hdrEnabled ? "on" : "off" }, set: { hdrEnabled = $0 == "on" }) + } + private var tvBody: some View { let currentTag = "\(width)x\(height)x\(hz)" let bounds = UIScreen.main.nativeBounds @@ -186,20 +304,25 @@ struct SettingsView: View { selection: $audioChannels) if bitrateKbps > 1_000_000 { Label(Self.gigabitWarning, systemImage: "exclamationmark.triangle.fill") - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.orange) .multilineTextAlignment(.center) } TVSelectionRow( title: "Compositor", options: compositors, selection: $compositor) + #if DEBUG TVSelectionRow( - title: "Presenter", - options: [("Stage 1 (default)", "stage1"), ("Stage 2 (experimental)", "stage2")], + title: "Presenter (debug)", + options: [("Stage 2 (default)", "stage2"), ("Stage 1 (debug)", "stage1")], selection: $presenter) + #endif + TVSelectionRow( + title: "10-bit HDR", + options: [("On", "on"), ("Off", "off")], selection: hdrEnabledTag) Text("The host creates a virtual output at exactly this mode — native " + "resolution, no scaling. \(Self.bitrateFooter) A specific compositor " + "is honored only if available on the host.") - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) .multilineTextAlignment(.center) .padding(.top, 8) @@ -219,7 +342,7 @@ struct SettingsView: View { TVSelectionRow( title: "Controller type", options: Self.padTypes, selection: $gamepadType) Text(Self.controllersFooter) - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) .multilineTextAlignment(.center) .padding(.top, 8) @@ -243,6 +366,63 @@ struct SettingsView: View { @ViewBuilder private var streamModeSection: some View { Section { + #if os(iOS) + // Touch-first: a rotating wheel of common resolutions (this device's own mode first) and + // a segmented refresh-rate control — the same family as the Clock/Timer pickers. The host + // renders a virtual output at exactly the chosen mode, so these are real pixel sizes. The + // last wheel row, "Custom…", reveals width/height/refresh fields for an arbitrary mode. + VStack(alignment: .leading, spacing: 4) { + Text("Resolution") + .font(.geist(15, relativeTo: .subheadline)) + .foregroundStyle(.secondary) + Picker("Resolution", selection: resolutionSelection) { + ForEach(resolutionChoices, id: \.tag) { choice in + Text(choice.label).tag(choice.tag) + } + } + .labelsHidden() + .pickerStyle(.wheel) + .frame(maxHeight: 140) + } + if isCustomResolution { + // Arbitrary entry: type the exact width × height (and refresh) the host should drive. + HStack { + TextField("Width", value: $width, format: .number.grouping(.never)) + .keyboardType(.numberPad) + Text("×") + TextField("Height", value: $height, format: .number.grouping(.never)) + .labelsHidden() + .keyboardType(.numberPad) + } + // A row built from an HStack of TextFields otherwise insets its bottom separator to + // the inner content, clipping the hairline under "Width"; pin it to the cell edge. + .alignmentGuide(.listRowSeparatorLeading) { _ in 0 } + LabeledContent("Refresh rate") { + TextField("Hz", value: $hz, format: .number.grouping(.never)) + .keyboardType(.numberPad) + .multilineTextAlignment(.trailing) + } + } else if refreshChoices.count > 1 { + VStack(alignment: .leading, spacing: 6) { + Text("Refresh rate") + .font(.geist(15, relativeTo: .subheadline)) + .foregroundStyle(.secondary) + Picker("Refresh rate", selection: $hz) { + ForEach(refreshChoices, id: \.self) { rate in + Text("\(rate) Hz").tag(rate) + } + } + .labelsHidden() + .pickerStyle(.segmented) + } + } else { + // A device with a single supported rate (e.g. 60 Hz) has nothing to pick. + LabeledContent("Refresh rate") { + Text("\(hz) Hz").foregroundStyle(.secondary) + } + } + Button("Use this display's mode") { fillFromMainScreen() } + #elseif os(macOS) HStack { TextField("Resolution", value: $width, format: .number.grouping(.never)) Text("×") @@ -253,6 +433,7 @@ struct SettingsView: View { LabeledContent("") { Button("Use this display's mode") { fillFromMainScreen() } } + #endif #if !os(tvOS) Toggle("Automatic bitrate", isOn: automaticBitrate) if bitrateKbps != 0 { @@ -267,7 +448,7 @@ struct SettingsView: View { } if bitrateKbps > 1_000_000 { Label(Self.gigabitWarning, systemImage: "exclamationmark.triangle.fill") - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.orange) } } @@ -277,11 +458,85 @@ struct SettingsView: View { } footer: { Text("The host creates a virtual output at exactly this mode — " + "native resolution, no scaling. \(Self.bitrateFooter)") - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) } } + #if os(iOS) + // MARK: - Stream mode (iOS wheel) + + /// Sentinel wheel tag for the "Custom…" row. Real tags are "WxH" (digits + "x"), so this can't + /// collide with a resolution. + private static let customResolutionTag = "custom" + + /// 16:9 then ultrawide presets; the device's native mode is prepended at runtime. + private static let resolutionPresets: [(name: String, w: Int, h: Int)] = [ + ("720p", 1280, 720), + ("1080p", 1920, 1080), + ("1440p", 2560, 1440), + ("4K", 3840, 2160), + ("Ultrawide 1080p", 2560, 1080), + ("Ultrawide 1440p", 3440, 1440), + ("Super ultrawide", 5120, 1440), + ] + + /// The non-custom wheel rows: this device's native mode first, then the presets, deduped by + /// dimensions (native wins a tie). + private var resolutionModes: [(name: String, w: Int, h: Int)] { + let bounds = UIScreen.main.nativeBounds // portrait-oriented pixels + let native = (w: Int(max(bounds.width, bounds.height)), h: Int(min(bounds.width, bounds.height))) + let all = [(name: "This device", w: native.w, h: native.h)] + Self.resolutionPresets + var seen = Set() + return all.filter { seen.insert("\($0.w)x\($0.h)").inserted } + } + + /// Wheel rows: the resolution modes, then a "Custom…" row that reveals the numeric fields. + private var resolutionChoices: [(label: String, tag: String)] { + resolutionModes.map { (label: "\($0.name) · \($0.w) × \($0.h)", tag: "\($0.w)x\($0.h)") } + + [(label: "Custom…", tag: Self.customResolutionTag)] + } + + private var presetResolutionTags: Set { + Set(resolutionModes.map { "\($0.w)x\($0.h)" }) + } + + /// True when the editable custom fields should show: the wheel is parked on "Custom…" (sticky), + /// or the stored size simply isn't one of the presets (e.g. a value synced from a Mac) — so a + /// non-preset mode stays editable across relaunches without a persisted flag. + private var isCustomResolution: Bool { + customMode || !presetResolutionTags.contains("\(width)x\(height)") + } + + /// The wheel works in "WxH" tags so one selection drives both width and height; the custom + /// sentinel toggles `customMode` instead of writing a size. + private var resolutionSelection: Binding { + Binding( + get: { isCustomResolution ? Self.customResolutionTag : "\(width)x\(height)" }, + set: { tag in + if tag == Self.customResolutionTag { + customMode = true + return + } + customMode = false + let parts = tag.split(separator: "x").compactMap { Int($0) } + guard parts.count == 2 else { return } + width = parts[0] + height = parts[1] + }) + } + + /// Refresh rates the device can actually display (no point asking the host to render frames the + /// screen can't show), plus any stored custom value so it stays selectable. + private var refreshChoices: [Int] { + let maxHz = UIScreen.main.maximumFramesPerSecond + var rates = [60, 120, 240].filter { $0 <= maxHz } + if rates.isEmpty { rates = [maxHz] } + if !rates.contains(hz) { rates.append(hz) } + return rates.sorted() + } + #endif + @ViewBuilder private var audioSection: some View { Section { Picker("Audio channels", selection: $audioChannels) { @@ -321,7 +576,7 @@ struct SettingsView: View { Text("Host audio plays through the speaker; the microphone feeds the " + "host's virtual mic. System default follows macOS device changes. " + "Applies from the next session.") - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) } } @@ -341,7 +596,7 @@ struct SettingsView: View { Text("Which compositor drives the virtual output on the host. A specific " + "choice is honored only if that backend is available there — " + "otherwise the host falls back to auto-detection.") - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) } } @@ -355,26 +610,47 @@ struct SettingsView: View { } footer: { Text("Take the window fullscreen when a session starts and restore it on the host " + "list, so only the stream is fullscreen — not the picker.") - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) } #endif } + // Stage-2 (Metal/VTDecompressionSession) is the default and only user-visible presenter — it + // recovers from a wedged decoder, where stage-1's AVSampleBufferDisplayLayer freezes hard on a + // lost HEVC reference. Stage-1 is kept reachable as a DEBUG-only override for diagnostics, like + // the controller test. Empty in release builds (no presenter UI; stage-2 always). @ViewBuilder private var presenterSection: some View { + #if DEBUG Section { Picker("Presenter", selection: $presenter) { - Text("Stage 1 (default)").tag("stage1") - Text("Stage 2 (experimental)").tag("stage2") + Text("Stage 2 (default)").tag("stage2") + Text("Stage 1 (debug)").tag("stage1") } } header: { - Text("Video presenter") + Text("Video presenter · debug") } footer: { - Text("Stage 1 feeds compressed video to the system display layer (known-good). " - + "Stage 2 decodes explicitly and presents through Metal with a display " - + "link — it adds a capture→present (glass-to-glass) latency line in the HUD " - + "and shortens the present tail. Applies from the next session.") - .font(.caption) + Text("Stage 2 (default) decodes explicitly and presents through Metal with a display " + + "link — it adds a capture→present (glass-to-glass) latency line in the HUD and " + + "self-recovers from decode stalls. Stage 1 feeds compressed video straight to the " + + "system display layer; it freezes on a lost HEVC reference frame, so it's a debug " + + "fallback only. Applies from the next session.") + .font(.geist(12, relativeTo: .caption)) + .foregroundStyle(.secondary) + } + #endif + } + + @ViewBuilder private var hdrSection: some View { + Section { + Toggle("10-bit HDR", isOn: $hdrEnabled) + } header: { + Text("HDR") + } footer: { + Text("Request a 10-bit BT.2020 PQ (HDR10) stream. It only engages when the host is " + + "sending HDR content AND this display supports HDR — otherwise the stream stays " + + "8-bit SDR. Applies from the next session.") + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) } } @@ -392,7 +668,7 @@ struct SettingsView: View { Text("Statistics") } footer: { Text(Self.statisticsFooter) - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) } } @@ -407,7 +683,7 @@ struct SettingsView: View { + "(Steam + custom) via the host's management API; tap a title to launch it. " + "The host must expose that API on the LAN with a token " + "(serve --mgmt-bind 0.0.0.0 --mgmt-token …).") - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) } } @@ -441,7 +717,7 @@ struct SettingsView: View { Text("Controllers") } footer: { Text(Self.controllersFooter) - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) } } @@ -593,13 +869,13 @@ struct SettingsView: View { } } } - .font(.caption2) + .font(.geist(11, relativeTo: .caption2)) .foregroundStyle(.secondary) } Spacer() if gamepads.active?.id == controller.id { Text("In use") - .font(.caption2.weight(.semibold)) + .font(.geist(11, .semibold, relativeTo: .caption2)) .padding(.horizontal, 8) .padding(.vertical, 3) .background(Capsule().fill(.green.opacity(0.2))) @@ -621,6 +897,10 @@ struct SettingsView: View { width = Int(max(bounds.width, bounds.height)) height = Int(min(bounds.width, bounds.height)) hz = UIScreen.main.maximumFramesPerSecond + #if os(iOS) + // The native mode is the "This device" wheel row, so leave Custom mode if it was on. + customMode = false + #endif #endif } } @@ -631,3 +911,52 @@ extension Double { Swift.min(Swift.max(self, lo), hi) } } + +#if os(iOS) +/// The settings groups, mirroring the macOS preference tabs. On iPad each is a sidebar row that +/// drives the detail pane; on iPhone the same list collapses to pushed sub-pages. Internal (not +/// private) so the screenshot harness can open SettingsView on a specific category. +enum SettingsCategory: String, CaseIterable, Identifiable { + case general, display, audio, controllers, advanced, about + + var id: Self { self } + + var title: String { + switch self { + case .general: return "General" + case .display: return "Display" + case .audio: return "Audio" + case .controllers: return "Controllers" + case .advanced: return "Advanced" + case .about: return "About" + } + } + + var symbol: String { + switch self { + case .general: return "gearshape" + case .display: return "display" + case .audio: return "speaker.wave.2" + case .controllers: return "gamecontroller" + case .advanced: return "slider.horizontal.3" + case .about: return "info.circle" + } + } +} + +extension View { + /// Present the settings sheet large on iPad so the NavigationSplitView has room for its + /// sidebar + detail — a default form sheet is too narrow and the split view would collapse to + /// the iPhone push list. No-op on iPhone (the standard sheet is already right) and on iOS 17 + /// (no `presentationSizing` — it falls back to the default sheet, which still degrades cleanly + /// to the push list). + @ViewBuilder + func settingsSheetSizing() -> some View { + if UIDevice.current.userInterfaceIdiom == .pad, #available(iOS 18, *) { + presentationSizing(.page) + } else { + self + } + } +} +#endif diff --git a/clients/apple/Sources/PunktfunkClient/SpeedTestSheet.swift b/clients/apple/Sources/PunktfunkClient/SpeedTestSheet.swift index 3fa2770..467b235 100644 --- a/clients/apple/Sources/PunktfunkClient/SpeedTestSheet.swift +++ b/clients/apple/Sources/PunktfunkClient/SpeedTestSheet.swift @@ -52,7 +52,7 @@ struct SpeedTestSheet: View { var body: some View { VStack(spacing: 20) { Label("Speed test — \(host.displayName)", systemImage: "gauge.with.needle") - .font(.headline) + .font(.geist(17, .semibold, relativeTo: .headline)) .foregroundStyle(.tint) switch phase { @@ -73,7 +73,7 @@ struct SpeedTestSheet: View { resultView(result) case .failed(let message): Text(message) - .font(.callout) + .font(.geist(16, relativeTo: .callout)) .foregroundStyle(.red) .multilineTextAlignment(.center) } @@ -149,13 +149,13 @@ struct SpeedTestSheet: View { if let rec = Self.recommendedKbps(result) { Text("Recommended bitrate: \(Self.mbpsLabel(kbps: rec)) " + "(~70% of measured, headroom for encoder bursts).") - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) .multilineTextAlignment(.center) } else { Text("Too little data made it through to recommend a bitrate — " + "check the network and retry.") - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) .multilineTextAlignment(.center) } diff --git a/clients/apple/Sources/PunktfunkClient/StreamHUDView.swift b/clients/apple/Sources/PunktfunkClient/StreamHUDView.swift index f59cd18..f561386 100644 --- a/clients/apple/Sources/PunktfunkClient/StreamHUDView.swift +++ b/clients/apple/Sources/PunktfunkClient/StreamHUDView.swift @@ -69,19 +69,19 @@ struct StreamHUDView: View { Text(model.mouseCaptured ? "⌘⎋ releases the mouse" : "Click the stream to capture input") - .font(.caption2) + .font(.geist(11, relativeTo: .caption2)) .foregroundStyle(.secondary) // The client-side cursor (⌘⇧C) draws the local cursor over the stream instead of // capturing it — the only accurate cursor for gamescope, whose capture has none. Text("⌘⇧C toggles the on-screen cursor") - .font(.caption2) + .font(.geist(11, relativeTo: .caption2)) .foregroundStyle(.secondary) #elseif os(iOS) // Touch always plays directly; ⌘⎋ (hardware keyboard) toggles kb/mouse. Text(model.mouseCaptured ? "⌘⎋ releases keyboard & mouse" : "⌘⎋ captures keyboard & mouse") - .font(.caption2) + .font(.geist(11, relativeTo: .caption2)) .foregroundStyle(.secondary) #endif #if os(tvOS) @@ -89,13 +89,13 @@ struct StreamHUDView: View { // A press (the focus engine consumes it before the host sees it). Disconnect is // the Siri Remote's Menu button (.onExitCommand on the stream) — just hint it. Text("Press Menu to disconnect") - .font(.caption) + .font(.geist(12, relativeTo: .caption)) .foregroundStyle(.secondary) #else // ⌘D lives on the app's Stream menu (so it still works when the HUD is hidden); // this button is the in-overlay, click-to-disconnect affordance. Button("Disconnect (⌘D)") { model.disconnect() } - .font(.caption) + .font(.geist(12, relativeTo: .caption)) #endif } .padding(10) diff --git a/clients/apple/Sources/PunktfunkClient/TrustCardView.swift b/clients/apple/Sources/PunktfunkClient/TrustCardView.swift index acb0dab..82ebf12 100644 --- a/clients/apple/Sources/PunktfunkClient/TrustCardView.swift +++ b/clients/apple/Sources/PunktfunkClient/TrustCardView.swift @@ -3,6 +3,7 @@ // or drops this and runs the PIN pairing ceremony instead. import Foundation +import PunktfunkKit import SwiftUI struct TrustCardView: View { @@ -18,11 +19,11 @@ struct TrustCardView: View { .font(.system(size: 36, weight: .light)) .foregroundStyle(.tint) Text("Verify \(hostName)") - .font(.title3.weight(.semibold)) + .font(.geist(20, .semibold, relativeTo: .title3)) Text("First connection. Compare this fingerprint with the one " + "punktfunk-host logged at startup (\u{201C}clients pin this " + "fingerprint\u{201D}):") - .font(.callout) + .font(.geist(16, relativeTo: .callout)) .foregroundStyle(.secondary) .multilineTextAlignment(.center) Text(Self.format(fingerprint: fingerprint)) @@ -58,7 +59,7 @@ struct TrustCardView: View { #else .buttonStyle(.borderless) #endif - .font(.callout) + .font(.geist(16, relativeTo: .callout)) } .padding(28) .frame(maxWidth: 440) diff --git a/clients/apple/Sources/PunktfunkKit/BrandFont.swift b/clients/apple/Sources/PunktfunkKit/BrandFont.swift new file mode 100644 index 0000000..27aeaa7 --- /dev/null +++ b/clients/apple/Sources/PunktfunkKit/BrandFont.swift @@ -0,0 +1,101 @@ +// Geist — the punktfunk brand typeface (the same family the website ships). Bundled as static +// OTF weights in this kit's resources and registered with Core Text at first use, so it works +// identically in the Xcode app and the `swift run` dev shell (Bundle.module resolves to the +// package resource bundle in both). Geist Sans carries titles/UI; Geist Mono carries the technical +// readouts — host addresses, status labels, the stream-stats HUD — for the industrial look. +// +// Licensed under the SIL Open Font License 1.1 (Resources/Fonts/Geist-OFL.txt). + +import CoreText +import SwiftUI +#if canImport(UIKit) +import UIKit +#elseif canImport(AppKit) +import AppKit +#endif + +public enum BrandFont { + public enum Weight { + case regular, medium, semibold, bold + } + + /// PostScript names of the bundled faces (verified from each OTF's name table). Geist Sans only + /// — Geist Mono is intentionally not shipped; the app's typeface is Geist Sans throughout. + private static let sansFaces = ["Geist-Regular", "Geist-Medium", "Geist-SemiBold", "Geist-Bold"] + + /// Registered exactly once per process — a static `let` initializer is run lazily and is + /// guaranteed thread-safe + run-at-most-once by the runtime. + private static let registered: Void = { + for face in sansFaces { + guard let url = Bundle.module.url( + forResource: face, withExtension: "otf", subdirectory: "Fonts") else { + #if DEBUG + print("BrandFont: bundled face \(face).otf not found — text will fall back to system") + #endif + continue + } + var error: Unmanaged? + if !CTFontManagerRegisterFontsForURL(url as CFURL, .process, &error) { + #if DEBUG + let message = error?.takeRetainedValue().localizedDescription ?? "unknown error" + print("BrandFont: failed to register \(face): \(message)") + #endif + } + } + }() + + /// Force registration before the first `Font.custom` lookup. Cheap to call repeatedly. + public static func registerIfNeeded() { _ = registered } + + fileprivate static func sansFace(_ weight: Weight) -> String { + switch weight { + case .regular: return "Geist-Regular" + case .medium: return "Geist-Medium" + case .semibold: return "Geist-SemiBold" + case .bold: return "Geist-Bold" + } + } +} + +public extension Color { + /// The punktfunk brand purple (the app-icon lens / website `--brand`). Defined explicitly, + /// independent of the asset-catalog accent — `Color.accentColor` resolution is environment- and + /// timing-sensitive (it can fall back to system blue), and the brand mark must never drift. + /// Light: #6656F2, Dark: #8678F5 (the lighter violet reads better on dark surfaces). + static let brand: Color = { + #if canImport(UIKit) + return Color(UIColor { traits in + traits.userInterfaceStyle == .dark + ? UIColor(red: 0x86 / 255, green: 0x78 / 255, blue: 0xF5 / 255, alpha: 1) + : UIColor(red: 0x66 / 255, green: 0x56 / 255, blue: 0xF2 / 255, alpha: 1) + }) + #elseif canImport(AppKit) + return Color(NSColor(name: nil) { appearance in + appearance.bestMatch(from: [.aqua, .darkAqua]) == .darkAqua + ? NSColor(red: 0x86 / 255, green: 0x78 / 255, blue: 0xF5 / 255, alpha: 1) + : NSColor(red: 0x66 / 255, green: 0x56 / 255, blue: 0xF2 / 255, alpha: 1) + }) + #else + // Non-Apple fallback: the light brand value, so all branches agree on a canonical color. + return Color(red: 0x66 / 255, green: 0x56 / 255, blue: 0xF2 / 255) + #endif + }() +} + +public extension Font { + /// Geist Sans at an explicit point size, scaling with Dynamic Type relative to `textStyle`. + static func geist( + _ size: CGFloat, _ weight: BrandFont.Weight = .regular, + relativeTo textStyle: TextStyle = .body + ) -> Font { + BrandFont.registerIfNeeded() + return .custom(BrandFont.sansFace(weight), size: size, relativeTo: textStyle) + } + + /// Geist Sans at a FIXED point size that does not scale with Dynamic Type — for glyphs pinned + /// inside a fixed-size container (e.g. the monogram tile), where a scaled letter would overflow. + static func geistFixed(_ size: CGFloat, _ weight: BrandFont.Weight = .regular) -> Font { + BrandFont.registerIfNeeded() + return .custom(BrandFont.sansFace(weight), fixedSize: size) + } +} diff --git a/clients/apple/Sources/PunktfunkKit/DefaultsKeys.swift b/clients/apple/Sources/PunktfunkKit/DefaultsKeys.swift index 1b9c281..4a4c9da 100644 --- a/clients/apple/Sources/PunktfunkKit/DefaultsKeys.swift +++ b/clients/apple/Sources/PunktfunkKit/DefaultsKeys.swift @@ -22,6 +22,9 @@ public enum DefaultsKey { public static let speakerUID = "punktfunk.speakerUID" public static let micUID = "punktfunk.micUID" public static let presenter = "punktfunk.presenter" + /// Request a 10-bit BT.2020 PQ (HDR10) stream. On by default; only takes effect when the host + /// has HDR content AND this display supports HDR — otherwise the stream stays 8-bit SDR. + public static let hdrEnabled = "punktfunk.hdrEnabled" public static let hosts = "punktfunk.hosts" /// Client-side cursor mode: "auto" (shown only in gamescope sessions), "always", "never". public static let cursorMode = "punktfunk.cursorMode" diff --git a/clients/apple/Sources/PunktfunkKit/GamepadFeedback.swift b/clients/apple/Sources/PunktfunkKit/GamepadFeedback.swift index 94a3cda..0397a38 100644 --- a/clients/apple/Sources/PunktfunkKit/GamepadFeedback.swift +++ b/clients/apple/Sources/PunktfunkKit/GamepadFeedback.swift @@ -68,6 +68,14 @@ private final class RumbleRenderer: @unchecked Sendable { private var broken = false /// Last logged active/silent state — for a one-line transition log, not per-event spam. private var wasActive = false + // Backoff after an engine failure. A broken `gamecontrollerd.haptics` XPC connection (CoreHaptics + // -4811 "server connection broke") fails EVERY rebuild until the service relaunches — and that + // break fires neither stoppedHandler nor resetHandler, so without a cooldown the next rumble + // update immediately rebuilds into the same dead connection, flooding the log and never + // recovering. Delay the next setup() — growing 0.5→1→2→4 s on repeated failure — and clear it + // the moment a player runs cleanly (or the controller changes). + private var retryAfter = Date.distantPast + private var consecutiveFailures = 0 /// CHHapticEvent sharpness = actuator frequency. A DualSense's voice-coil motors need a /// defined frequency to move at all — an intensity-only event (no sharpness) left them @@ -91,6 +99,8 @@ private final class RumbleRenderer: @unchecked Sendable { self.closeHID() self.controller = c self.broken = false + self.consecutiveFailures = 0 + self.retryAfter = .distantPast _ = self.openHIDIfDualSense(c) onBackend?(self.backendNote(for: c)) } @@ -108,7 +118,7 @@ private final class RumbleRenderer: @unchecked Sendable { // other pad (and for a DualSense whose HID device could not be opened). if self.hidRumble(low: lowAmp, high: highAmp) { return } guard !self.broken else { return } - if active, self.low == nil, self.high == nil { + if active, self.low == nil, self.high == nil, Date() >= self.retryAfter { self.setup() } let ok: Bool @@ -124,8 +134,15 @@ private final class RumbleRenderer: @unchecked Sendable { } // Rebuild on the next nonzero amplitude if an engine errored — and tear down OUTSIDE // the `inout` accesses above, so teardown() never mutates a motor that a `drive` call - // still holds an exclusive reference to. - if !ok { self.teardown() } + // still holds an exclusive reference to. Back off so a broken XPC isn't re-hit every + // update; once a player is actually running the path has recovered, so clear the backoff. + if !ok { + self.teardown() + self.scheduleRetryBackoff() + } else if self.low?.player != nil || self.high?.player != nil { + self.consecutiveFailures = 0 + self.retryAfter = .distantPast + } } } @@ -157,14 +174,29 @@ private final class RumbleRenderer: @unchecked Sendable { low = makeMotor(haptics, .default) } if low == nil, high == nil { - // Haptics present but no engine could be built right now (server busy / a transient - // error). Do NOT latch broken — the next nonzero amplitude retries setup(). - log.warning("rumble: haptics present but engine setup failed — will retry on next rumble") + // Haptics present but no engine could be built right now (server busy / XPC broken). Do + // NOT latch broken — back off and the next nonzero amplitude past the cooldown retries. + log.warning("rumble: haptics present but engine setup failed — backing off, will retry") + scheduleRetryBackoff() } } + /// Push the next engine-build attempt out after a failure (capped exponential backoff), so a + /// broken `gamecontrollerd.haptics` connection gets time to relaunch instead of being re-hit on + /// every rumble update. + private func scheduleRetryBackoff() { + consecutiveFailures += 1 + let shift = min(consecutiveFailures - 1, 4) + retryAfter = Date().addingTimeInterval(min(0.5 * Double(1 << shift), 4)) + } + private func makeMotor(_ haptics: GCDeviceHaptics, _ locality: GCHapticsLocality) -> Motor? { guard let engine = haptics.createEngine(withLocality: locality) else { return nil } + // A controller's motors carry no audio, so keep this engine OUT of the app's audio session + // (the default is to join it). Streaming keeps an AVAudioSession active the whole time; + // letting a haptics-only engine join it is a needless coupling that can get its + // gamecontrollerd XPC connection interrupted (the repeated -4811 server-connection breaks). + engine.playsHapticsOnly = true // The haptic server can stop or reset the engine out from under us — app backgrounding, an // audio-session interruption (a call, Siri, another audio app), or a server crash. Left // unhandled the players go dead and every later rumble throws, latching rumble off for the diff --git a/clients/apple/Sources/PunktfunkKit/Licenses.swift b/clients/apple/Sources/PunktfunkKit/Licenses.swift index a0b514a..f117415 100644 --- a/clients/apple/Sources/PunktfunkKit/Licenses.swift +++ b/clients/apple/Sources/PunktfunkKit/Licenses.swift @@ -27,6 +27,17 @@ public enum Licenses { + apache } + /// The bundled brand typeface (Geist Sans + Geist Mono) — SIL Open Font License 1.1. The + /// license file ships alongside the OTFs in `Resources/Fonts/`, satisfying the OFL's + /// distribution requirement; this surfaces it in the Acknowledgements screen too. + public static var fontLicense: String { + guard let url = Bundle.module.url( + forResource: "Geist-OFL", withExtension: "txt", subdirectory: "Fonts"), + let text = try? String(contentsOf: url, encoding: .utf8) + else { return "" } + return text + } + /// Third-party software notices for the linked Rust crates (generated by /// `scripts/gen-third-party-notices.sh`). public static var thirdPartyNotices: String { diff --git a/clients/apple/Sources/PunktfunkKit/MetalVideoPresenter.swift b/clients/apple/Sources/PunktfunkKit/MetalVideoPresenter.swift index bf9be22..529c391 100644 --- a/clients/apple/Sources/PunktfunkKit/MetalVideoPresenter.swift +++ b/clients/apple/Sources/PunktfunkKit/MetalVideoPresenter.swift @@ -11,6 +11,9 @@ import CoreGraphics import CoreVideo import Metal import QuartzCore +import os + +private let presenterLog = Logger(subsystem: "io.unom.punktfunk", category: "presenter") /// Runtime-compiled (no metallib build step needed in SwiftPM): a fullscreen triangle and a /// BT.709 limited-range NV12→RGB fragment shader. uv.y is flipped (1 - p.y) so the top-left- @@ -30,11 +33,44 @@ vertex VOut pf_vtx(uint vid [[vertex_id]]) { return o; } +// Bicubic (Catmull-Rom) sampling of the single-channel luma plane. When the drawable is larger +// than the decoded frame (a window/view bigger than the host's fixed mode), a bilinear upscale +// looks soft; Catmull-Rom keeps edges crisp — matching AVSampleBufferDisplayLayer's (stage-1) +// scaler — and reduces to the exact texel at 1:1, so a native-resolution present stays pixel-exact. +// Nine bilinear taps (TheRealMJP's optimisation of the 16-tap kernel); `s` MUST be a linear +// sampler. Luma carries the perceived detail, so only it gets bicubic; chroma stays bilinear. +float catmullRomLuma(texture2d tex, sampler s, float2 uv) { + float2 texSize = float2(tex.get_width(), tex.get_height()); + float2 samplePos = uv * texSize; + float2 tc1 = floor(samplePos - 0.5) + 0.5; + float2 f = samplePos - tc1; + float2 w0 = f * (-0.5 + f * (1.0 - 0.5 * f)); + float2 w1 = 1.0 + f * f * (-2.5 + 1.5 * f); + float2 w2 = f * (0.5 + f * (2.0 - 1.5 * f)); + float2 w3 = f * f * (-0.5 + 0.5 * f); + float2 w12 = w1 + w2; + float2 off12 = w2 / w12; + float2 tc0 = (tc1 - 1.0) / texSize; + float2 tc3 = (tc1 + 2.0) / texSize; + float2 tc12 = (tc1 + off12) / texSize; + float r = 0.0; + r += tex.sample(s, float2(tc0.x, tc0.y)).r * (w0.x * w0.y); + r += tex.sample(s, float2(tc12.x, tc0.y)).r * (w12.x * w0.y); + r += tex.sample(s, float2(tc3.x, tc0.y)).r * (w3.x * w0.y); + r += tex.sample(s, float2(tc0.x, tc12.y)).r * (w0.x * w12.y); + r += tex.sample(s, float2(tc12.x, tc12.y)).r * (w12.x * w12.y); + r += tex.sample(s, float2(tc3.x, tc12.y)).r * (w3.x * w12.y); + r += tex.sample(s, float2(tc0.x, tc3.y)).r * (w0.x * w3.y); + r += tex.sample(s, float2(tc12.x, tc3.y)).r * (w12.x * w3.y); + r += tex.sample(s, float2(tc3.x, tc3.y)).r * (w3.x * w3.y); + return r; +} + fragment float4 pf_frag(VOut in [[stage_in]], texture2d lumaTex [[texture(0)]], texture2d chromaTex [[texture(1)]]) { constexpr sampler s(filter::linear, address::clamp_to_edge); - float y = lumaTex.sample(s, in.uv).r; + float y = catmullRomLuma(lumaTex, s, in.uv); float2 c = chromaTex.sample(s, in.uv).rg; // BT.709, 8-bit limited (video) range → full-range RGB. y = (y - 16.0/255.0) * (255.0/219.0); @@ -55,7 +91,7 @@ fragment float4 pf_frag_hdr(VOut in [[stage_in]], texture2d lumaTex [[texture(0)]], texture2d chromaTex [[texture(1)]]) { constexpr sampler s(filter::linear, address::clamp_to_edge); - float y = lumaTex.sample(s, in.uv).r; + float y = catmullRomLuma(lumaTex, s, in.uv); float2 c = chromaTex.sample(s, in.uv).rg; // BT.2020 10-bit limited (video) range → full-range PQ R'G'B'. y = (y - 64.0/1023.0) * (1023.0/876.0); @@ -81,6 +117,11 @@ public final class MetalVideoPresenter { private var textureCache: CVMetalTextureCache? /// Current layer configuration — switched lazily in `configure(hdr:)` when a frame's mode differs. private var hdrActive = false + #if DEBUG + /// Last logged "decoded→drawable" signature, so the diagnostic logs only when a size changes + /// (on first frame, a resize, or a host Reconfigure) instead of every frame. + private var lastSizeSig = "" + #endif /// nil if Metal is unavailable (no GPU / a headless CI) — the caller falls back to stage-1. public init?() { @@ -113,6 +154,12 @@ public final class MetalVideoPresenter { layer.pixelFormat = .bgra8Unorm layer.framebufferOnly = true layer.isOpaque = true + // Render the drawable at the DECODED frame's resolution (set per-frame in `render`) and let + // the system compositor scale it to the layer's bounds — the same `.resizeAspect` path + // stage-1's AVSampleBufferDisplayLayer (videoGravity) uses, so stage-2 matches its sharpness. + // A native-resolution present is then pixel-exact (1:1, no shader scaling), and any display + // scaling uses the system's high-quality scaler rather than the in-shader bicubic. + layer.contentsGravity = .resizeAspect // Triple-buffer: more in-flight drawables before `nextDrawable()` (called on the // display-link / MAIN thread) has to block waiting for one to free. layer.maximumDrawableCount = 3 @@ -129,12 +176,6 @@ public final class MetalVideoPresenter { self.layer = layer } - /// Track the stream mode (the host can Reconfigure mid-stream). Size is in pixels. - public func setDrawableSize(_ size: CGSize) { - guard size.width > 0, size.height > 0 else { return } - if layer.drawableSize != size { layer.drawableSize = size } - } - /// Reconfigure the layer for SDR or HDR when the stream mode flips (HDR toggle). HDR uses an /// rgba16Float drawable + a BT.2020 PQ colour space + EDR, so the compositor PQ-maps to the /// display; SDR uses the plain 8-bit sRGB path. Main-thread only (called from `render`). @@ -171,13 +212,33 @@ public final class MetalVideoPresenter { let chroma = makeTexture(pixelBuffer, plane: 1, format: chromaFmt, cache: textureCache) else { return false } - // The hosting view owns drawableSize (aspect-fit to its bounds); skip until it's laid - // out. The fullscreen triangle scales the decoded texture to fill the drawable. - guard layer.drawableSize.width > 0, layer.drawableSize.height > 0, - let drawable = layer.nextDrawable(), + // Size the drawable to the decoded frame so the fullscreen triangle samples the texture 1:1 + // (pixel-exact); the layer's contentsGravity then scales it to the on-screen bounds via the + // system compositor (matching stage-1). Re-set only on a change (first frame / Reconfigure). + let decodedSize = CGSize( + width: CVPixelBufferGetWidth(pixelBuffer), height: CVPixelBufferGetHeight(pixelBuffer)) + if layer.drawableSize != decodedSize { layer.drawableSize = decodedSize } + guard let drawable = layer.nextDrawable(), let commandBuffer = queue.makeCommandBuffer() else { return false } + #if DEBUG + // Diagnose sharpness: decoded should equal the drawable (the shader is 1:1); the layer's + // bounds may differ (the system scales). Logged only when a size changes. + let decodedW = Int(decodedSize.width) + let decodedH = Int(decodedSize.height) + let sig = "\(decodedW)x\(decodedH)|\(Int(layer.drawableSize.width))x\(Int(layer.drawableSize.height))" + if sig != lastSizeSig { + lastSizeSig = sig + let msg = "stage2: decoded \(decodedW)x\(decodedH) → drawable " + + "\(Int(layer.drawableSize.width))x\(Int(layer.drawableSize.height)) " + + "(texture \(drawable.texture.width)x\(drawable.texture.height), " + + "contentsScale \(layer.contentsScale), " + + "layerBounds \(Int(layer.bounds.width))x\(Int(layer.bounds.height)))" + presenterLog.info("\(msg, privacy: .public)") + } + #endif + let pass = MTLRenderPassDescriptor() pass.colorAttachments[0].texture = drawable.texture pass.colorAttachments[0].loadAction = .clear diff --git a/clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-Bold.otf b/clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-Bold.otf new file mode 100644 index 0000000000000000000000000000000000000000..6ab5615f06c0e26cc8dcea4300f6e5af1a3e5955 GIT binary patch literal 166516 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 literal 0 HcmV?d00001 diff --git a/clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-Medium.otf b/clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-Medium.otf new file mode 100644 index 0000000000000000000000000000000000000000..99fb7c28266040b6097966ac3b371a7091259b66 GIT binary patch literal 162304 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®@SgQH_doQ+GA#D*iW$oB1f`nGQ$<$Kuku#>-mn%s@k zCol6*Y#uYilm_$TH>Gs+y8_DHu->-*rL4diAdf$LaOcT`gLXEV=V|CxW2R@EZtt8` z%h$TCHr%eQ>mC?#z|&w}i`5E+J7_q_z}CgmyE-e&bOy-WCy$5B-EH*v#RgWn;kPYc z>5OUzy#&nlu^q=Zdd{sb7}n=WkJBkjg@*ESp)u(3rU>^9FiuUUDwe4Y5Ojn8UjzQ% zAQzFa2Sm^rIZQ`29B!C^a{SkLcE^{>a80IY8wARl{kt zi?qu)PP;-I#tHD(Y1e7PF|A&&jnM9ezkrF}!u=j`|T(iMFM-1eW2M-)PkZZ>|HTbDnJFd|$qecwkn)Mygdmz_rP*49Mz`T*0 z#?9xdaJ9IfxE9>cTsN){H-ro1#&IFsuYk#f3G7e9xo}@0JjY#zbAsa`Oi=F+ZTBa( z`*Yjt+8#q_8J>}E50>@t~aT&JR(_ir8P(lr`$71Rr zFQhN>8?NoD zAcqAm721vK+v0f<@~48J#)82G{>C+5fz7xcEU+BD3kw{?b$NjZd^uOp6>;+xc!)1c z3oyw03ar6*eSw>})+!K->*j(+TwfRT!1bJhS3|)%1rGs!vx033b}ZPfV6TD$3N9`< zjN?m8Q~diD`O8}>^4F(+MLk%E(gVCD@3f5HUGI#aJ-+wdBCox5Wh)hVUG!`9hj;G7 zzYJd;AlqQ8u-IEsjq;WGAdhy4MZb20SE6vyYQ@8f`V_zBtt&c)(^T)n%2hp~Mg;dC zEIHso||D*0(HNW^C(;Eb;VN-rjq$rn65BhBYbE zlR>k=J%gunb{}i3b&>U^{Y|}F!`T<>^Q>R9zgZKqf64l8eeL*eeZqd~7wc;!H&5(& zv_58ev%Yi;Zwu*Ig5_4^-2TUKY29jn%X+t$JF}F`-+DVE)F&{Q5zg^JbbR^Pvo$fh zZ)W}3bCxxPH8$&e#+!@%3Aj^eg1y_Zh^J(@x9sZpXMM_2vA(gsas2wJXKR{O%7n~9 zXMM~0i}Lji!?QhqjycWz%ED#-DfJFou-<+@jm%K*Jt?)uV&sg)_ri157bug}dLz@v z`j=H=Z`QD!QnsE{LjtE1VNNTUWvPCPw+#HNVH~fFezX56`MidBN-dx-NC9S2tY@qb ztts}fXnB7!$kt?rHKm78+lU6eN0Rl0JzVy?^;Y&T>>XtTZa(&BFM};l$*e^vb#a&F z1Am$-b6LMwb7|EXTurWqk~dav9=XF0@As8(=s)n=XT5_jPf&}eK|L~_AF951O0k7g zFoUuv*vm-&an_c}!dmyKG4S-t9?k~CRx0abq;*Ek0iM#Ve=G4a>cyI7hoF3a4;Sy( zQf7YwXm3F+Z#fl=(R*%7QRi(z2(U5i2uKkF(dJLu=K8|KY%I zDD4>6XK)nlHrbj0j6FgbQ;^a_g_0QV-`L@+>8Wq_I!7#(vOn4%fJV?O0}}Gj`dd3C zAuUF6j9%YbQ&G+o>nl9Jk3*&0*}nsO?}tpvz>361B(%eKxUzP2&+fzS)(cAOdWEkV zRw5Q6>mTYM1>aQ)&G34^HZ#2Npwt^1!;mlQpXd>fFkjT(B5O28w?oQXf&py|h4I^; z^~WeH>tAMRvVM1bLyGUwyQBaA?D@SGfKq2td)Ab5?uXt_AMN42c4ZF*>bVSBIcL3z z)^P@DC9w3A-jLNU<73~#_mK61^)9e{&AJm*tdt*jjAtqwJ0`7*5IgBpqs% zQhPQI6nVJJdLi})EMG>QvVI7oNY--OLfp08;ct7oX{XnWFE(g^@YZ@BIeX41jFI7gYMqrzA=udf7ZX*NWeH9w0fmwu&QNq5Mp1Rh+J@K2N$?raTL-X3r+cHCO;*r`J81C$Z@uEOVD1N7Sp)C}%J zN%=BM0l58*(Jh`BuX9O(8^NyG{~Trq8D922&wghfpvV^rucPuq3N_%{Ip7w3o)Y3N zT2uz_om0EB*J38_5kDKZr}m4=7<~?L>{gEg$)3G7CW|A-=1BjL*&dQ>m2A#&b>wA@gR2c6iG9t3v==D^T0G4Ref^ ztS6NI4s?^XA8?5JUp-oHC_T_^z)fTTGJ0eM8rlciDB4F7S`njaHuBhJi?-xkY}e&uqe^o&^99{!v5o(;qozh<_!FOHf+giL6xm4m{-rD2R`eFW-L!6IgYETVO> zLUZc#V~lq@?QtF32aBPEj#lr8mtd#5_i>BVo+z^#meyy@krddNBdLGyORbdN+3x*C zcRQtiQKWw+v1~yW16xLG9((H#UwWv%U^~7uc*5VQ*u$l#Q2VdC2Jdwtp%|_BzZd98$ZV zZPdys*ayEk&J@%@pN7Up!kpzXA57-I@W`P(qfhu({yrhsL}^pNIXTERv*yB1_4cos ze4PEum)-3n<(I|!lF;v`kVA|85`h0z*qmC$rvbg6_fN%fte=d25E7zK#rsnK>@(so zjh{7q_Ss@qU;CR{Hv2k|{VVR@Iz0a?kMGY;vhvseT%wcX-u=AUJ{^sAxppn5_3mX0t5x>>V7~@-iQHDgV)pIr1J{Fd^6r9oh{@^H@ZN#m zW4tHfE!ca4_cZU>-V4341B7$3?d@UvdNkS%+RfPavqu|+wY>ND6=mNCq|t_ILlK_s z0OGk^-VMB);MdCgXQa(iN7@QTXsdOV%I0wW5anDgewMD2CfoZ4Y)dRKXDp_IfnRWP?k^aQPOI^;ykpu z;e1(2oIx`~Lo|CeziWd;{Kx`+@JzPvF{NZ`u-W5dS-WlpD-n;jeKcH2C9!GzN`<8-<-{ z1-M{M8BG~(w5F-1DK|#bPScJXtLd%j&5gqzv;o|Bjlag9o1ht~8Ocpl_L@xs2J>@X zkl1ltZLTh;f#u9u$(ai`m7B>GRB~1nIlF?rXxL!Nl~nRqiZ8$yLS9)eD=4|Fid+un zS}3_}tK_mBa+%0=((uS-7mZG%#5|}SIO}&IPTS(>!swi zkH!yq?W^RqzmnGh$g3A>@IT0FVXhMH^|OVfO#`G$L;$*cK}d#Nd@DapOol*3-YH=0_S zI-Eu0qw(Ranw}b8H0J zQ`p`^K9zsP|IOb;v(@m=HBK54dlB^-Jul&)oRLq*ZbVn!0=(wqt!z&s@LT|g=S1YG z3i4P@(-7Z451P`N=9<>Pc3b=^YT9c$XezN?ikhlym!hTyus&GRfbCM$G}2;!qUL9| zKT*?>?N8KnV*3*{KCB+tzDBJ(Yt5Vwq=meu5q2f;XkkWfU_p!eD^yDPiG}RH3WYxZ zrzvFriMCkALf*)w&r^-=ZE1Tc7j&(N}5hPnu4sRV}~F`T#hI(0YN>*YSC+Z}|ss z58)nJ-)j0<-)f72hY-=aT(Aq$g_{mH18yegf)?VUaf9=~J3^p8oCY@?ZU)>;>q(6c z&JE53?<~XLOel;CkXKbA)X+Y#ZgZxwKd1RHE6DxLUUUbn!B#-dVQzR z98qZQhC*{UL1P*|71XBVUntb}TJsgC?G32y8y+^CG-gm9Xdjg4u5su8W-S`@S4dL~ zbXo#brem!EJ<|`GdKy>FPnt#u&8W~#p~CzM6&BF^3@R+h+KQ&IrW<}m&|>;%yjc&R zDWw?%iYyI^9Ih#g-XH)FM}j&lvOTn#?-d%YsnBRGg+^;DG+IZY(YoAZuhSX7G_TM9 zUGVyx-)S2}HEeKG za4u+-Q$elM;HJaPfSbvE%a`Xo_zG|p;VN++pu2BDci)2UzSaDK_i@k8^R2I@Kn z>N*DMItJ=G#;wMvy9O>4E(~rh+&Z|caM$3jThD+3kAVV@fdY?d3gTN{#7aV}B*aQW ztR%!rLaZdjN+vPO zULIRN`3v#b{lVV=k71wn3-kEAUxdf!{p@A5=iV`gYL4vb+2Pr1YmBW%RBTPc+gxBw zg|k>GX9)5dfiHl`jo>U;OL_1Dp%o zS8ztS+;CsReFNtTXM+0{&J33a?muwf!R3Q*kaIN9mz_o>I2iG3%XSfb<9pO5``M`CB^M(5bt`}TyxIS=w z;kLkSh1&+V9c~BQPPkogyW#f0MZ!hFMZ?9w#lr1{+XuHF?l-sta0lT|!kvOU4Hpl0 z2JS4}6}SYrM7TR}cj4~A-AB(;6|NRsZMZsc_25uu4a%xP`83_&y2JH=8vqvo7YsKV zb;oKl4mBBvnv6qD#-S$TP?K?}$vD(x9BMKSH5rGRj6+Svp(f){lX0lYIMieuYBCNr z8HbvTLrun^CgV_(aj41vQ`?!qSy5d3zn0tgUKW{Qox4niVI0O`9FQGEQAA=;2@q6* zfCK>%2m*gVL_|Yeh$5mf#<+zbK}AGFL_|cRxHK^YQF(+ALI~~z4bS*^NL2pcbNb$y z0WtBPe{$<{PMxlYWn#ax9J#C?kx4+k$2hp z**%d<&&>JT(~-L-eSLbKy4$jy^Dcd7UaGANwOLHNF3xOBFO`;q7fUOoSEN^G%hKy8 z$t&qinH||Z={M5b<@)q4uI>@J^xJt!{Mw^hNyGPM2W3~)y7Yc=wa1z1$Ck7AWIxFa zKhk9vs9T$@ap?oKa%NoixyWUfWtOEsE1E7Yrc0%4|GTCc0r8!rTnN{QF9z)8XtopLSAETjYrGfOf{$YF_$Q)%VQ%FLQ*%w-PJBN=6x_1eStWi~Lv$}+nd zubVSlwb$;>yqnpVjb*-&K9>2Ivj>r5+I#CW=Gy5vEz9-ON{&0zgL>uq$L#D`*=uqA zIF=qYL|g5~>ciFqSOchHYk5%WP>VO1{9OZ4F_*=^aKgP`ik3t!-9K_g%hLUemKCimT2m9U zJ|}HTRn~Py8yI2Y_7-hS@2z!3n{)D=XbL7%{Giy?1k&8zDkv!F-)~s&kY|sz>^OxKuBp z)LE&1dNhcmL8&3B5xKKtBA?I+nGC(T#-*l+(|$}}PR$TX%}!lg6LMotDy1LO^N(U_Tqxb}h;~~7s^nZ=FVs-5MBI|v z_LMf1y3-QWh_aV!Dcc{JA31bQpUQ0AJAE7T_1n1q%wNwlW4)0+KfM|^lrc6kJyT}f z^e)^~W;N-%Gt)9tu45eBhLaI^C!vcOJ4PgsH4eb#>Rf8{Ay?Bi7|_a`RZ5pYLvQi{1O~1Gm@x#qD$Z-QU~+ z_rLB_cgTI_jSqZ%pYd7$4d0Tr`!ZkdTlU|dH#HVfgkL@ z>xcLY{ZK#5U&VS@8TnmrJbB(=;^aHmv>@*vndanwqbZ;aHD9?Oz z9A&zNs}{S(aLUHIC#7RacApdL#(uZoBq-rtbY@KRrjU8BsG!Ks}|QooL-K6UJ38pXy{HHPX5@ z)VdXXxo+-r_c>P`c895<)HA8|Y~~yI2Bs)i&thLpO{BIBe2M4XajkQMT%B9_R@5!3 z`SJdEWT}5Wt^aXa|3a;QR_os|x4!up>#mQ}w2#@qUW#>MJnQI}u%@}+-o`r2-|as8 zIqm@Kll57RxQ)4m$&1%6RYB-tX!VOx@2EgCp+ot~4{@W>#4T7b=p)2HFL`-bMb zIE$@h2&-lnn(rZxWR1+5E6hyfD{-C`v#XJ>G1nnqkF#nWDp2c7()`>k<{hM8;+pXO z{v)h9E@!2=h?V9w#1z|11M`A;g=@t^6F0BoJZo*6Ir|#UtF^|emC38kCdp?5|3I2M zaYbssX<&Ba#1{HzQrLq_szoQJRw-*f!>;34vrCz#Hf>9hTVdm|wgW4i%~{FohAh^q z7PhB7(*$a>a(0*l2R?5FlqQ)Lg?zZ3Gg{Q~?UDY)1Q>2eN>FFij%7K>Z~A6!hDVpq@ABLuq=h$r?$ z%P46KZ|a(wv|8;Ny5_EkI4PGRJdNE8TLr7e1&o?vLP}UYE?|ALCE=y6lyt-*=^005 z;3q~MLdvoDS;pH5U~HwUB%}(545ahHa`F$l2ZXG=bXHoIAsv z0lM~fy$L_loke(G*VlZ*o$by+7Q3f&{oJ>a`@8pDC?}Io*U!_5rX}T6vQ?f zU6YayvSWd$Ot!*tFYuDk9MP(DaN=llu+!dfg9(>F;k3p z<4IF&tPX_uK6y=a6A8IYzx=`aE+N=42$|}plB3u*t=I*LKf}!+otbVXajtY%QtMfc znaa&}j5zEa*O226+z*(oKpD8qUs;{MIxF6HSG@10c;7+szP;joR`I^8;{8dA_nj2) zvpRn@*7+-=^H*ahcweG;U#>`Btw>*~NZ-~SbO)I?WiD&1b6G~`vc`({C5rdu(y`3( zo}Vf6F&{&gIj*B(e;396#$K?$Lb3k@#r_J#{u31YTVjQ8Wl9zMTYAC%QpNt(f`g{1 z&HyLs4A4$zfRmZ+hcSD|JXi@DvX=myh=YhJ?AL;cjT93bgNdb}Mr1N610TKOV=KkS zL>+u=tN2(Se57xgGja7yA9FVHIk<#57ua4Is{qJ(}A9s zlgkWT0t~%^JZIKmXtO#PDz=%MK+JjO$K-W8)`u46F09%0>fmXC;%TAcX z`95(bvRfddsA?5elZvX%6;+dps#!(V094K6sRd7;C&w4;3#72YzKARq`@sGdY_*E5 z5vp26)uf_owhpSww|(9-E%}Dd`&|102pcHEW)xvhs6p7jnnv6|><3Q;XPeZ)*@WV3 zf#Pf<#aSo!7p8#w3yl3WILj1|{WQkN5wvZrXxl{5_P9D|TfqHDL-3ccw-Ud=6~GH! zA^0f!3yQHDHA8OhnuCljTno}EszG6=C=B|7zh3OH#K*!!{8I3@;3)hpCq$69P?5Jl z_bj*^^0swt$v2O`oj|D0ps-UE4zO393dZ#Wg{>3(Z4UB&6ZtIgw>kKG4st)&59AWG zZK`OSRGe)N&T?;|yCJM%s8tMgilH%Vz3dQjm%2;2Rxq@=qGyu(r%B{4xS3SMv>@g* z;>iA$2r;c9X0iq`XOYfqu+n`AD@zqCD-9OUbQzP54NL`U(vc;tbD2R z3zaWY{;cwwly6f0r1C43KO^@-<{6dOD}O=xDCKu5zfbvZBrjX6xj$}abJg9pJ|R!j zudR8*%HE~x?QMhl5K432=&J0PPd$U*I9YnUXl;5r4 zGbG&pUe7kvklw=04!&k(?N|-jA!p5ND&M26Cwu3tFEaA%d75y0Si;@Ug?o0xAy*4G z8-&|iG~}lmatn8u7HpI_&GqaPl7e|sL&`N|i1ZvgSVNA}kUq+LY4~*QQS((EAu@A^ zt^9uBZluahRQ4)&SN@{%j>_9B zXP2e4p~`9L;pS;=w*n0*QC^{O<|tpFXBAr*X;P93GYl?web(NjA#IdDpq!nar1_f4 zLt=b0&kl{1!H2{uh5NnAWpoUQwNUwC%72`W&_2pf*EpwpiF3NfIn5KtPSf%GfsWJp z8q#0mU#|QLz3K|R>I%K;3W>w>l#Klz%BL$oU->BI!!(^X$_Hr3|B1qtw^BY;d9mQI zE%EG3w#6PChJ(X!a2O5_+hRd%`=(%sJxO_m?}}XExfg(s67K$o_L-wG*X80!Iu)8u zg{D)XXEVy*lQ?FJ#_Z(S6>Q5iyi|E};iR^N@IozNp_Z*s%T}nVm1}sphL>x2xrWcz zG&9P}l>b6`bLB0R57D}xqr9E+Ta}-#{1WBQDxax*vhqUZrz$^NxO-dWpC~^?`2^)} zDUZ(fRrx~YTa^!1K2~{8&L7tXANP9=Pf#;k>GrSJ~E@3hND zP4gAgE}t^ZS5GHp);U*ki@GBEre?5FzNs18E#K4(Hp(|OgN^b{%^)M+)C?BLH#LLv z<(rzp0{Nz9uu;CL8En*6xAlhe{EY^ZeN0SzFMUq@Q^9rd^e@@QtoAb}g`P-uM$m)-#(>dpN%=s^IK1qJ_ za{h)WJjj(V7?O)e9KAjs`LX@Ea6XPZDYE41! zDp*I6)LO!|f2f}|-w5REuWi{sN-bGkk{zb<6>~E+=Vm*6j zZL+tl<0m_^XPm1J??!G<%h|+7>|V8rkIl*O1LR>7D`*v)xX_hiEtEKD9DioB4e0>V+{8S%>>3}y&S0C^%h4>ZbIC&Ed0S{T?+dwPirQai zZo<-X8AmNx1!8SlS5I8B8SfdnTuhs6Vq%F`6RQ$$B;F=wM{4}IS;d;poqh?&edsYS z@O1H_dC9!2wgH=5rbeP9fy3Iw71(%!LkVoTS7_ybtNUCh?+>2MN)UOh`uK zU}=bdl1oQJ;`@lRAQ!^=3FmhZ67@`jmRP?@jA_8ic6<=AqzBl<`5g5&wt@6YMHuOG ziD;DSgFZ)np=caRh)tj?`5d*DmwAaEqfb|LdQ6gD{?Gf&v97H5FJIZ_^9|;XljXlfI0Rd{&4DHyNuO# z7oSc1N9=O@C^PS4cBOsXuCh)JGZ_{;LNk7)*}{=!>yD&a{u>1R!*TP7dv#6+pkw9 zf<`s2Jhp<_a8I2)ld=7^E{Ml&XUZ>a(6+7t^yD>i_@ z3!8wF5Xdg~myFxCvDLA4vFBs21fyb`VsFH@2NPnuVsFRxQi=n?)YxY%?#>FX4U&|( zS&-qc#VUeo+M|1LTJUk)1h)qZgJr=QG`2a|5xg7B3;OVLvsNua~sXC zv4`g0Ja~=u`qz1P?M<_lckZ@f=jA;Kvjc1BPFCr6@h01D*1TWl{*e8yys7r8{f*tk z`uAr0n%!bww{O@t?N;oI+wAYKFaF-{$i11ci&gO5yiK+T>*Cw?9quZ{*4@QjC6*@c z8)bjR-&wQ#+;57r8s$m#Y;s&p)kMd;UJIwrlL++oSPfj0dj*+|a}CFXO`Mrb-TgBgOJ>mH@= zBB||KB_pzri-{^*Gmy zB}X-PAY8e^>GK))2;KPafga`*zD106A`$z4pg6f5`40$k4`;D`8T%nmfqSqd%&}Of z*>h7LJ7zDejIx3W4>w5;vLk!+{c~ETXx@;_v5f`OWmxy zPBkGqM-ysWsLz>zTEEYkz2>jf<-g4*%#a7LyA`VCr5Q1N-7Bz0ywANb_n%)5ReOT$ zh+toUiDO1w4!_$z3cts$fZu0V!hdcbhcC3)6qzTVfG@JE;fw7W z_%H2K@CWTW_(S#?_)@zb{;+)(zD)Nxw6U9!JF&09ad)?Yp4~yMM^`dmVi(3H?0gg7 z0^XDrXXl%Fo{4>Pp9W<9!d(3b{=Lk-FX7+My!$f#5@ufZi!fV1jeXD4hgc-XPX3zv zy<5k)eGqwz+u@#J1V4oQy8DA$&sbiH{02`X&oZhXMt;-%(LKlbUWUBY?c%-fC*32+ z|KwaRRr^?RGCP`X9x*{#*Aux0e33#4YA%Gf&e`gA)%p>49zOWs!#8GH;uA z%)912w71v%#q2X5nvc-of18iZ-_YU#!(YjnPi0ivQ|JZ9-sSe+)GF7jNc{qOgFG{| zG;MNkt>tqYW5$_DW`Vhtx76-851FOxt%>e^UZw;eNuJi)2K>Edp>1qS$hFe8u~oL6 zZBPDvZ9hB6PPNmpHQbaPr&u(ZI}hj6u03fV*P%|TxK4|UCl0{XRwt&%ag&a%#a(+-OQ1% z^8X<6e%`(G@z=4EZ^bQQHrYnI$Q-$tIdT^k^WA9YA=S&Hw9d!0*C)7@<^VJMQrH6{Wn%zi$#$Ci5{SIqI@A2OF_rRjv_JDiGy~i8bm42Zc<`?-z?hXF0 zWtn?ZzU1KkATyEMg?{8I-LjuR5cJ3%l}F2-IlRgt6-C=fi*l~<~Uzib?-9k18#17m$JYBP^ zhU2!m@DtS!e0AUE;(X}5BlK9Ot)!kc zb)xKb%Ov^6CYWZi$+T}5_F(*ni1oKBH`1KzI^iFSMiRbK<5anR_`Uu;WbZTG7$;R< zNmp@h0OcCMz1M)l9|EOkL+3`M$BlAf63%ujtSS6g1%3*DmupD;;=`ZSCG>QzyZG>j z;@eD)2G_`ezg+W^Jikm*_x}L--;l1f|3wgOZRb&*h)%`t#@^bhW6~(%-NW~Ggcjv| zWOokf{39C3`D4+su4&KzyY>7sp|g`*8`I(+Ql;tS>JZ=C(Kgq%J;k(k|4x!V`fnt5 zObk}~uKK-^8-8j0$yhmhEYP3ne|_nHA4I!@; z?+CUv(!Mi*cW5d(e?EllPG>LvHqw>6J2OVFMV4`W8PtvbBs7MwD>eSP(x0_%Q9Yva zNk5amMV-lqe#<)s(oa{Q-}h*v@8C;6y#rji-?ZnAh7)L`Q`o)Up8e{@>_I=p4M)bZ z<)+Y1Bbd9Hr@j`Er~ewH`98q-8$G`v%>m$Vb0b%~| zA^Q>csoP9BPsWW|ajIg6*I*&~bCnzm)m$&flFvN8QvarDWfya9AbOjR-wuB;*Ozgx zQ$`=X8UJSd@uW8%e=g^QuFKIle4%S|lsnck-b~o7To3W&uB2t?h0ca^PG~&g>*$l! zXCi=|;{O+c!?}0xjB7Ys_ypOu=A&<#W6OJKw zc0{os;S0u3BmQ;Z*4xku=z03x>tO9F@TiPT22;T6_40m9bmQ{{_RMR-ym^ literal 0 HcmV?d00001 diff --git a/clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-OFL.txt b/clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-OFL.txt new file mode 100644 index 0000000..04e95fc --- /dev/null +++ b/clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-OFL.txt @@ -0,0 +1,93 @@ +Copyright 2024 The Geist Project Authors (https://github.com/vercel/geist-font) + +This Font Software is licensed under the SIL Open Font License, Version 1.1. +This license is copied below, and is also available with a FAQ at: +https://openfontlicense.org + + +----------------------------------------------------------- +SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007 +----------------------------------------------------------- + +PREAMBLE +The goals of the Open Font License (OFL) are to stimulate worldwide +development of collaborative font projects, to support the font creation +efforts of academic and linguistic communities, and to provide a free and +open framework in which fonts may be shared and improved in partnership +with others. + +The OFL allows the licensed fonts to be used, studied, modified and +redistributed freely as long as they are not sold by themselves. The +fonts, including any derivative works, can be bundled, embedded, +redistributed and/or sold with any software provided that any reserved +names are not used by derivative works. The fonts and derivatives, +however, cannot be released under any other type of license. The +requirement for fonts to remain under this license does not apply +to any document created using the fonts or their derivatives. + +DEFINITIONS +"Font Software" refers to the set of files released by the Copyright +Holder(s) under this license and clearly marked as such. This may +include source files, build scripts and documentation. + +"Reserved Font Name" refers to any names specified as such after the +copyright statement(s). + +"Original Version" refers to the collection of Font Software components as +distributed by the Copyright Holder(s). + +"Modified Version" refers to any derivative made by adding to, deleting, +or substituting -- in part or in whole -- any of the components of the +Original Version, by changing formats or by porting the Font Software to a +new environment. + +"Author" refers to any designer, engineer, programmer, technical +writer or other person who contributed to the Font Software. + +PERMISSION & CONDITIONS +Permission is hereby granted, free of charge, to any person obtaining +a copy of the Font Software, to use, study, copy, merge, embed, modify, +redistribute, and sell modified and unmodified copies of the Font +Software, subject to the following conditions: + +1) Neither the Font Software nor any of its individual components, +in Original or Modified Versions, may be sold by itself. + +2) Original or Modified Versions of the Font Software may be bundled, +redistributed and/or sold with any software, provided that each copy +contains the above copyright notice and this license. These can be +included either as stand-alone text files, human-readable headers or +in the appropriate machine-readable metadata fields within text or +binary files as long as those fields can be easily viewed by the user. + +3) No Modified Version of the Font Software may use the Reserved Font +Name(s) unless explicit written permission is granted by the corresponding +Copyright Holder. This restriction only applies to the primary font name as +presented to the users. + +4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font +Software shall not be used to promote, endorse or advertise any +Modified Version, except to acknowledge the contribution(s) of the +Copyright Holder(s) and the Author(s) or with their explicit written +permission. + +5) The Font Software, modified or unmodified, in part or in whole, +must be distributed entirely under this license, and must not be +distributed under any other license. The requirement for fonts to +remain under this license does not apply to any document created +using the Font Software. + +TERMINATION +This license becomes null and void if any of the above conditions are +not met. + +DISCLAIMER +THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT +OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE +COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL +DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM +OTHER DEALINGS IN THE FONT SOFTWARE. \ No newline at end of file diff --git a/clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-Regular.otf b/clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-Regular.otf new file mode 100644 index 0000000000000000000000000000000000000000..82878335eb0faf730aa9932f5078f90869ae035c GIT binary patch literal 157508 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 UH+BJaczmQP)ECDt@m^H_1ycU@xc~qF literal 0 HcmV?d00001 diff --git a/clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-SemiBold.otf b/clients/apple/Sources/PunktfunkKit/Resources/Fonts/Geist-SemiBold.otf new file mode 100644 index 0000000000000000000000000000000000000000..277a521af67aa019c9191e902191eecd0929f81f GIT binary patch literal 164780 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 AI=QtTE8j_GrgTC~^mKqi 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 literal 0 HcmV?d00001 diff --git a/clients/apple/Sources/PunktfunkKit/SessionAudio.swift b/clients/apple/Sources/PunktfunkKit/SessionAudio.swift index 7e10459..c723fec 100644 --- a/clients/apple/Sources/PunktfunkKit/SessionAudio.swift +++ b/clients/apple/Sources/PunktfunkKit/SessionAudio.swift @@ -177,6 +177,16 @@ public final class SessionAudio { private var playbackEngine: AVAudioEngine? private var captureEngine: AVAudioEngine? private var drainStarted = false + #if !os(macOS) + /// AVAudioSession `setCategory`/`setActive` are synchronous and block on the audio server, so + /// they must not run on the main thread (UI stall — AVFoundation warns about it). PROCESS-WIDE + /// (static) so every SessionAudio shares one serial queue: the AVAudioSession is a process + /// singleton, and across a reconnect the old session's deactivate must be ordered before the + /// new session's activate (a per-instance queue would let them race and leave the new session's + /// audio deactivated). stop() enqueues its deactivate promptly so it lands before the next + /// session's activate. + private static let sessionQueue = DispatchQueue(label: "io.unom.punktfunk.audio.session") + #endif public init(connection: PunktfunkConnection) { self.connection = connection @@ -189,37 +199,60 @@ public final class SessionAudio { flag.stop() } - /// Start playback (and, if enabled+authorized, the mic uplink). Empty UIDs = system - /// default device; on iOS the UIDs are ignored entirely (routes are - /// AVAudioSession-managed). Main thread (engine setup); returns after the engines - /// start — the mic may start slightly later if the permission prompt is pending. + /// Start playback (and, if enabled+authorized, the mic uplink). Empty UIDs = system default + /// device; on iOS the UIDs are ignored entirely (routes are AVAudioSession-managed). On macOS + /// the engines start synchronously on the caller's (main) thread. On iOS/tvOS start() is + /// ASYNCHRONOUS: it activates the AVAudioSession off the main thread, then starts the engines on + /// a later main-queue hop (gated by `!flag.isStopped`) — so playback is live shortly after, not + /// on return. The mic may start later still if the permission prompt is pending. public func start(speakerUID: String, micUID: String, micEnabled: Bool) { - #if os(iOS) - // Route + policy live in the session, not per-engine: stereo playback, mic - // capture when enabled, Bluetooth allowed. Failure is non-fatal (defaults). + #if os(macOS) + // No AVAudioSession on macOS — start the engines directly (caller's thread, as before). + startEngines(speakerUID: speakerUID, micUID: micUID, micEnabled: micEnabled) + #else + // Configure + activate the session OFF the main thread (it blocks on the audio server), + // then start the engines back on the main thread once it's active — engine routing/format + // depend on the active session. A stop() racing in between is caught by the flag guard. + Self.sessionQueue.async { [weak self] in + guard let self else { return } + self.activateAudioSession(micEnabled: micEnabled) + DispatchQueue.main.async { [weak self] in + guard let self, !self.flag.isStopped else { return } + self.startEngines(speakerUID: speakerUID, micUID: micUID, micEnabled: micEnabled) + } + } + #endif + } + + #if !os(macOS) + /// Route + policy live in the session, not per-engine: stereo playback, mic capture when + /// enabled, Bluetooth allowed. Failure is non-fatal (defaults). Runs on `sessionQueue`. + private func activateAudioSession(micEnabled: Bool) { let session = AVAudioSession.sharedInstance() do { + #if os(iOS) if micEnabled { - // .defaultToSpeaker: .playAndRecord otherwise routes to the iPhone - // EARPIECE; only affects the built-in route (headphones/BT still win). + // .defaultToSpeaker: .playAndRecord otherwise routes to the iPhone EARPIECE; only + // affects the built-in route (headphones/BT still win). try session.setCategory( .playAndRecord, mode: .default, options: [.allowBluetoothA2DP, .defaultToSpeaker]) } else { try session.setCategory(.playback, mode: .default) } + #else // tvOS — no app-accessible mic + try session.setCategory(.playback, mode: .default) + #endif try session.setActive(true) } catch { log.warning("AVAudioSession setup failed: \(error.localizedDescription)") } - #elseif os(tvOS) - do { - try AVAudioSession.sharedInstance().setCategory(.playback, mode: .default) - try AVAudioSession.sharedInstance().setActive(true) - } catch { - log.warning("AVAudioSession setup failed: \(error.localizedDescription)") - } - #endif + } + #endif + + /// Build + start the playback engine (and the mic uplink when enabled + authorized). Main + /// thread (engine setup); on iOS/tvOS the session is already active by the time this runs. + private func startEngines(speakerUID: String, micUID: String, micEnabled: Bool) { startPlayback(speakerUID: speakerUID) #if os(tvOS) // No app-accessible microphone input on tvOS — playback only. @@ -258,19 +291,24 @@ public final class SessionAudio { capture.stop() } playback?.stop() + #if !os(macOS) + // Release the session so audio we interrupted (Music, podcasts) gets its resume cue. Like + // activation, setActive is synchronous/blocking — run it on the shared serial session queue + // (off the main thread). Enqueued HERE — engines already stopped, and BEFORE the drain wait + // below — so across a reconnect it lands ahead of the next session's activate on the shared + // queue (otherwise a deferred deactivate could deactivate the new session). Fire-and-forget. + Self.sessionQueue.async { + do { + try AVAudioSession.sharedInstance().setActive( + false, options: .notifyOthersOnDeactivation) + } catch { + log.warning("AVAudioSession deactivation failed: \(error.localizedDescription)") + } + } + #endif if wasDraining { _ = drainDone.wait(timeout: .now() + .milliseconds(400)) } - #if !os(macOS) - // Release the session so audio we interrupted (Music, podcasts) gets its - // resume cue. - do { - try AVAudioSession.sharedInstance().setActive( - false, options: .notifyOthersOnDeactivation) - } catch { - log.warning("AVAudioSession deactivation failed: \(error.localizedDescription)") - } - #endif } // MARK: - Playback (host → speaker) diff --git a/clients/apple/Sources/PunktfunkKit/Stage2Pipeline.swift b/clients/apple/Sources/PunktfunkKit/Stage2Pipeline.swift index 18ed298..2a65908 100644 --- a/clients/apple/Sources/PunktfunkKit/Stage2Pipeline.swift +++ b/clients/apple/Sources/PunktfunkKit/Stage2Pipeline.swift @@ -4,7 +4,7 @@ // capture→present. Mirrors StreamPump's lifecycle (one per start; cancel is permanent). // // Threading: the pump runs on its own thread; the decoder callback on a VT thread; `renderTick` -// + `setDrawableSize` + `start`/`stop` on the MAIN thread (the view's CADisplayLink fires there). +// + `start`/`stop` on the MAIN thread (the view's CADisplayLink fires there). // Only the ring + decoder cross threads and both are internally locked. #if canImport(Metal) && canImport(QuartzCore) @@ -60,7 +60,7 @@ private final class KeyframeRecovery: @unchecked Sendable { func request() { lock.lock() let now = DispatchTime.now().uptimeNanoseconds - let due = lastNs == 0 || now &- lastNs > 250_000_000 // ≥ 250 ms since the last request + let due = lastNs == 0 || now &- lastNs > 100_000_000 // ≥ 100 ms since the last request (matches Android) if due { lastNs = now } let conn = due ? connection : nil lock.unlock() @@ -114,20 +114,24 @@ public final class Stage2Pipeline { let thread = Thread { var format: CMVideoFormatDescription? var lastFramesDropped = connection.framesDropped() + // Persistent recovery WANT, not a one-shot edge (see StreamPump for the full rationale): + // the old code advanced lastFramesDropped on the same edge it called recovery.request(), + // so a request swallowed by the throttle (the lost recovery IDR being pruned within the + // window) was never re-sent and the picture stayed frozen. Keep asking until an IDR lands. + var awaitingIDR = false while token.isLive { do { - // Loss recovery (the primary recovery path). The reassembler drops unrecoverable - // AUs (framesDropped) and the decoder then conceals the reference-missing delta - // frames that follow — often rendering them WITHOUT an error callback — so the - // onDecodeError trigger rarely fires after a real network blip. Ask the host for - // a fresh IDR whenever the drop count climbs (throttled in KeyframeRecovery). - // Polled every iteration so a total-loss drought recovers the moment packets - // resume and the reassembler counts the gap. + // Loss recovery (the primary path). The reassembler drops unrecoverable AUs + // (framesDropped) and the decoder conceals the reference-missing deltas that + // follow — often WITHOUT an error callback — so key off the drop count climbing, + // then keep asking (awaitingIDR) until a fresh IDR re-anchors decode. Polled every + // iteration so a total-loss drought recovers the moment packets resume. let dropped = connection.framesDropped() if dropped > lastFramesDropped { lastFramesDropped = dropped - recovery.request() + awaitingIDR = true } + if awaitingIDR { recovery.request() } // Drain any HDR mastering-metadata update (0xCE) and hand it to the decoder, which // attaches it to subsequent HDR frames. Non-blocking; only HDR sessions emit these. if connection.isHDR, let meta = try? connection.nextHdrMeta(timeoutMs: 0) { @@ -136,15 +140,16 @@ public final class Stage2Pipeline { guard let au = try connection.nextAU(timeoutMs: 100) else { continue } onFrame?(au) if let f = AnnexB.formatDescription(fromIDR: au.data) { - format = f // refreshed on every IDR (mode changes included) + format = f // refreshed on every IDR (mode changes included) + awaitingIDR = false // a fresh IDR re-anchored decode — recovery complete } guard let f = format, token.isLive else { continue } if !decoder.decode(au: au, format: f) { // Submit/decoder error: drop the session and re-gate on the next IDR's - // in-band parameter sets (a delta frame can't recover) — stage-1's policy - // — and ask the host for that IDR now (infinite GOP; throttled). + // in-band parameter sets (a delta frame can't recover) — stage-1's policy — + // and keep asking for that IDR (infinite GOP) until one re-anchors decode. decoder.reset() - recovery.request() + awaitingIDR = true } } catch { if token.isLive { onSessionEnd?() } @@ -166,11 +171,6 @@ public final class Stage2Pipeline { presentMeter.record(ptsNs: frame.ptsNs, atNs: targetPresentNs, offsetNs: offsetNs) } - /// MAIN thread. Keep the drawable matched to the negotiated mode (host can Reconfigure). - public func setDrawableSize(_ size: CGSize) { - presenter.setDrawableSize(size) - } - /// Stop the pump (≤ one poll timeout) and drop the decode session. Does not close the /// connection. A restart needs a fresh Stage2Pipeline (cancel is permanent). public func stop() { diff --git a/clients/apple/Sources/PunktfunkKit/StreamPump.swift b/clients/apple/Sources/PunktfunkKit/StreamPump.swift index ca976e6..4b41c30 100644 --- a/clients/apple/Sources/PunktfunkKit/StreamPump.swift +++ b/clients/apple/Sources/PunktfunkKit/StreamPump.swift @@ -6,6 +6,9 @@ import AVFoundation import Foundation +import os + +private let pumpLog = Logger(subsystem: "io.unom.punktfunk", category: "video") /// Cancellation handle owned by exactly one pump thread — a restart hands the old pump /// its own token, so it can never be revived by a newer start(). @@ -47,44 +50,74 @@ final class StreamPump { var format: CMVideoFormatDescription? var lastKeyframeRequest = Date.distantPast var lastFramesDropped = connection.framesDropped() - // Coalesced host keyframe request: the decode stays wedged for several frames until - // the IDR lands, so requesting on every frame would flood the control stream. + // Recovery is a persistent WANT, not a one-shot edge: set it on detected loss (or a + // decoder reset), retry the throttled request EVERY iteration, and clear it only when a + // fresh IDR actually re-anchors decode. The old code advanced `lastFramesDropped` on the + // same edge it fired the throttled request — so a request swallowed by the throttle (a + // second drop within the window, e.g. the lost recovery IDR itself being pruned) was + // never re-sent: the counter went flat, the climb never re-fired, and the picture stayed + // frozen for good while audio kept playing. The iPhone's lossy Wi-Fi hits this where the + // Mac's Ethernet never does. + var awaitingIDR = false + var awaitingSince = Date.distantPast // when the current recovery began (for the resume log) + var wasFailed = false + // Coalesced host keyframe request. 100 ms throttle (matches the working Android path): + // fast enough that a lost recovery IDR is re-requested promptly, bounded so a sustained + // freeze can't flood the control stream. func requestKeyframeThrottled() { let now = Date() - if now.timeIntervalSince(lastKeyframeRequest) > 0.25 { + if now.timeIntervalSince(lastKeyframeRequest) > 0.1 { connection.requestKeyframe() lastKeyframeRequest = now } } while token.isLive { do { - // Loss recovery (the primary recovery path). Under the host's infinite GOP the - // only recovery keyframe is one we request. The reassembler drops unrecoverable - // AUs (framesDropped); the decoder then *conceals* the reference-missing delta - // frames that follow — a frozen / garbage picture, WITHOUT flipping the layer to - // .failed — so the .failed check below rarely fires after a real network blip. - // Ask the host for a fresh IDR whenever the drop count climbs. Polled every - // iteration (not just per AU) so a total-loss drought still recovers the moment - // packets resume and the reassembler counts the gap. + // Loss recovery (the primary path). Under the host's infinite GOP the only + // recovery keyframe is one we request. The reassembler drops unrecoverable AUs + // (framesDropped); the decoder then *conceals* the reference-missing deltas — a + // frozen / garbage picture that never flips the layer to .failed — so key off the + // drop count climbing, then keep asking (awaitingIDR) until an IDR lands. Polled + // every iteration so a total-loss drought still recovers when packets resume. let dropped = connection.framesDropped() if dropped > lastFramesDropped { + // Log only on the false→true transition (once per recovery cycle), not per + // dropped AU, so heavy loss doesn't spam the log. + if !awaitingIDR { + awaitingSince = Date() + pumpLog.notice( + "video: unrecoverable drop (framesDropped=\(dropped, privacy: .public)) — requesting recovery IDR") + } lastFramesDropped = dropped - requestKeyframeThrottled() + awaitingIDR = true } + if awaitingIDR { requestKeyframeThrottled() } + guard let au = try connection.nextAU(timeoutMs: 100) else { continue } onFrame?(au) - if let f = AnnexB.formatDescription(fromIDR: au.data) { - format = f // refreshed on every IDR (mode changes included) + let idrFormat = AnnexB.formatDescription(fromIDR: au.data) + if let f = idrFormat { + format = f // refreshed on every IDR (mode changes included) + if awaitingIDR { + let ms = Int(Date().timeIntervalSince(awaitingSince) * 1000) + pumpLog.notice("video: recovery IDR received — resumed after \(ms, privacy: .public) ms") + } + awaitingIDR = false // a fresh IDR re-anchored decode — recovery complete } - if layer.status == .failed { + let failed = layer.status == .failed + if failed { // Decode wedged hard (the cold-first-connect case — a lost/corrupt opening - // IDR): flush and re-gate on the next in-band parameter sets (resuming with - // a delta frame can't recover), AND ask the host for a fresh IDR. Throttled: - // the layer stays .failed across several polls until the IDR lands. + // IDR): flush and, unless THIS AU is the recovering IDR (re-anchored above), + // re-gate on the next in-band parameter sets and keep asking — enqueuing a + // delta into a failed layer can't recover it. + if !wasFailed { pumpLog.warning("video: display layer .failed — flushing + re-anchoring") } layer.flush() - format = AnnexB.formatDescription(fromIDR: au.data) - requestKeyframeThrottled() + if idrFormat == nil { + format = nil + awaitingIDR = true + } } + wasFailed = failed guard let f = format, let sample = AnnexB.sampleBuffer(au: au, format: f), token.isLive // don't enqueue a stale frame after a restart diff --git a/clients/apple/Sources/PunktfunkKit/StreamView.swift b/clients/apple/Sources/PunktfunkKit/StreamView.swift index 653afe9..8449984 100644 --- a/clients/apple/Sources/PunktfunkKit/StreamView.swift +++ b/clients/apple/Sources/PunktfunkKit/StreamView.swift @@ -245,6 +245,15 @@ public final class StreamLayerView: NSView { layoutMetalLayer() // keep the stage-2 sublayer aspect-fit to the view } + public override func setFrameSize(_ newSize: NSSize) { + super.setFrameSize(newSize) + // `layout()` isn't guaranteed on a manual-frame (no-Auto-Layout) live resize, so the + // stage-2 metal sublayer's drawableSize could stay at the old size while the view grows — + // the compositor then upscales a too-small drawable and the video turns blocky. Resize the + // drawable here too so it always tracks the window's pixel size (no stale upscale). + layoutMetalLayer() + } + // MARK: - Capture state machine /// Clicking into the video engages capture; that click is local (engagement), so @@ -549,10 +558,17 @@ public final class StreamLayerView: NSView { cursorVisible = false _ = connection.resolvedCompositor // (was: Auto → gamescope; kept to document intent) - // Presenter choice — default stage-1 (the known-good AVSampleBufferDisplayLayer). Stage-2 - // (`punktfunk.presenter == "stage2"`) takes explicit VTDecompressionSession decode + a - // CAMetalLayer/display-link present; it falls back here if Metal can't be set up. - if UserDefaults.standard.string(forKey: DefaultsKey.presenter) == "stage2", + // Presenter choice — stage-2 is the DEFAULT (explicit VTDecompressionSession decode + a + // CAMetalLayer/display-link present): it can detect + recover a wedged decoder where + // stage-1's AVSampleBufferDisplayLayer freezes hard on a lost HEVC reference. Stage-1 is + // reachable only via the DEBUG presenter toggle; release always takes stage-2 (the stage-1 + // pump below stays the automatic fallback if Metal is missing). + #if DEBUG + let forceStage1 = UserDefaults.standard.string(forKey: DefaultsKey.presenter) == "stage1" + #else + let forceStage1 = false + #endif + if !forceStage1, let meter = presentMeter, let pipeline = Stage2Pipeline(presentMeter: meter) { startStage2(pipeline, connection: connection, onFrame: onFrame, onSessionEnd: onSessionEnd) @@ -593,9 +609,11 @@ public final class StreamLayerView: NSView { targetPresentNs: Stage2Pipeline.realtimeNs(forDisplayLinkTimestamp: link.targetTimestamp)) } - /// Aspect-fit the metal sublayer in the view (the host streams at the client's native mode, - /// so this is usually the full bounds; it letterboxes a resized window). drawableSize is the - /// layer's pixel size — the fullscreen-triangle shader scales the decoded texture to fill it. + /// Position the metal sublayer aspect-fit in the view (the host streams at the client's native + /// mode, so this is usually the full bounds; it letterboxes a resized window). Only the layer + /// FRAME is set here — the presenter sizes the drawable to the decoded frame and the layer's + /// contentsGravity (.resizeAspect) scales it to this frame via the system compositor, so a + /// resized window rescales through the system's filter (matching stage-1) instead of the shader. private func layoutMetalLayer() { guard let metalLayer, let connection else { return } let mode = connection.currentMode() @@ -604,14 +622,12 @@ public final class StreamLayerView: NSView { aspectRatio: CGSize(width: Int(mode.width), height: Int(mode.height)), insideRect: bounds) : bounds - let scale = window?.backingScaleFactor ?? 1 // No implicit resize animation; refresh contentsScale on a retina↔non-retina move. CATransaction.begin() CATransaction.setDisableActions(true) - metalLayer.contentsScale = scale + metalLayer.contentsScale = window?.backingScaleFactor ?? 1 metalLayer.frame = fit CATransaction.commit() - stage2?.setDrawableSize(CGSize(width: fit.width * scale, height: fit.height * scale)) } public override func viewDidChangeBackingProperties() { diff --git a/clients/apple/Sources/PunktfunkKit/StreamViewIOS.swift b/clients/apple/Sources/PunktfunkKit/StreamViewIOS.swift index 5bea2c8..58a402c 100644 --- a/clients/apple/Sources/PunktfunkKit/StreamViewIOS.swift +++ b/clients/apple/Sources/PunktfunkKit/StreamViewIOS.swift @@ -136,6 +136,13 @@ public final class StreamViewController: UIViewController { public override func loadView() { view = StreamLayerUIView() + // Re-size the stage-2 drawable if the display scale changes without a bounds change (e.g. + // moving to an external display at a different scale) — the iOS analogue of macOS's + // viewDidChangeBackingProperties relayout. The handler takes the VC as its argument, so it + // doesn't capture self (no retain cycle with the registration). + registerForTraitChanges([UITraitDisplayScale.self]) { (vc: StreamViewController, _) in + vc.layoutMetalLayer() + } #if os(iOS) // Hide the iPadOS cursor while it hovers the video: the host renders its own // cursor from our deltas, so the local one only diverges from it. This hides the @@ -219,10 +226,17 @@ public final class StreamViewController: UIViewController { inputCapture = capture #endif - // Presenter choice — default stage-1 (the known-good AVSampleBufferDisplayLayer). Stage-2 - // (`punktfunk.presenter == "stage2"`) takes VTDecompressionSession decode + a - // CAMetalLayer/display-link present; falls back here if Metal can't be set up. - if UserDefaults.standard.string(forKey: DefaultsKey.presenter) == "stage2", + // Presenter choice — stage-2 is the DEFAULT (VTDecompressionSession decode + a + // CAMetalLayer/display-link present): it can detect + recover a wedged decoder, where + // stage-1's AVSampleBufferDisplayLayer freezes hard on a lost HEVC reference frame with no + // way to recover. Stage-1 is reachable only via the DEBUG presenter toggle; release always + // takes stage-2 (the stage-1 pump below stays the automatic fallback if Metal is missing). + #if DEBUG + let forceStage1 = UserDefaults.standard.string(forKey: DefaultsKey.presenter) == "stage1" + #else + let forceStage1 = false + #endif + if !forceStage1, let meter = presentMeter, let pipeline = Stage2Pipeline(presentMeter: meter) { startStage2(pipeline, connection: connection, onFrame: onFrame, onSessionEnd: onSessionEnd) @@ -300,8 +314,8 @@ public final class StreamViewController: UIViewController { onFrame: (@Sendable (AccessUnit) -> Void)?, onSessionEnd: (@Sendable () -> Void)? ) { let metal = pipeline.layer - metal.contentsScale = streamView.contentScaleFactor // Composites OVER the idle (un-enqueued in stage-2) AVSampleBufferDisplayLayer base. + // (contentsScale + frame + drawableSize are all set by layoutMetalLayer() just below.) streamView.layer.addSublayer(metal) metalLayer = metal stage2 = pipeline @@ -325,9 +339,20 @@ public final class StreamViewController: UIViewController { layoutMetalLayer() } - /// Aspect-fit the metal sublayer in the view (the host streams at the client's native mode, - /// so this is usually the full bounds). drawableSize is the layer's pixel size; the shader's - /// fullscreen triangle scales the decoded texture to fill it. + /// The display scale to render the metal drawable at. `traitCollection.displayScale` is the + /// canonical render scale and is reliable once the controller is in the hierarchy; + /// `view.contentScaleFactor` can read 1.0 before the view attaches to a window/screen, which + /// would size the drawable at point resolution → a pixelated, upscaled mess. Falls back to the + /// main screen scale if the trait is still unspecified. + private var renderScale: CGFloat { + let s = traitCollection.displayScale + return s > 0 ? s : UIScreen.main.scale + } + + /// Position the metal sublayer aspect-fit in the view (the host streams at the client's native + /// mode, so this is usually the full bounds). Only the layer FRAME is set here — the presenter + /// sizes the drawable to the decoded frame and the layer's contentsGravity (.resizeAspect) + /// scales it to this frame via the system compositor (matching stage-1's videoGravity). private func layoutMetalLayer() { guard let metalLayer, let connection else { return } let mode = connection.currentMode() @@ -337,13 +362,11 @@ public final class StreamViewController: UIViewController { aspectRatio: CGSize(width: Int(mode.width), height: Int(mode.height)), insideRect: bounds) : bounds - let scale = streamView.contentScaleFactor CATransaction.begin() CATransaction.setDisableActions(true) // don't animate the resize - metalLayer.contentsScale = scale + metalLayer.contentsScale = renderScale metalLayer.frame = fit CATransaction.commit() - stage2?.setDrawableSize(CGSize(width: fit.width * scale, height: fit.height * scale)) } private func teardownStage2() { diff --git a/clients/apple/Tests/PunktfunkKitTests/MetalPresenterTests.swift b/clients/apple/Tests/PunktfunkKitTests/MetalPresenterTests.swift new file mode 100644 index 0000000..3d4c71b --- /dev/null +++ b/clients/apple/Tests/PunktfunkKitTests/MetalPresenterTests.swift @@ -0,0 +1,21 @@ +import XCTest + +#if canImport(Metal) +import Metal +@testable import PunktfunkKit + +final class MetalPresenterTests: XCTestCase { + /// `MetalVideoPresenter.init?()` compiles the runtime Metal shaders (the BT.709/BT.2020 YUV→RGB + /// fragment shaders plus the Catmull-Rom luma sampler). A `nil` result on a GPU-equipped host + /// means a shader failed to compile — this catches a malformed shader before it silently + /// degrades stage-2 to a stage-1 fallback on device. + func testPresenterInitCompilesShaders() throws { + guard MTLCreateSystemDefaultDevice() != nil else { + throw XCTSkip("no Metal device available in this environment") + } + XCTAssertNotNil( + MetalVideoPresenter(), + "stage-2 Metal shaders failed to compile (presenter init returned nil)") + } +} +#endif