// // Copyright 2026 Aarav Ravindra Kharade // import CSystem /// A custom widget node tree for SwiftCrossUI over ArkGraphics IPC public class ArkGraphicsWidget { public var children: [ArkGraphicsWidget] = [] public var x: Int = 0 public var y: Int = 0 public var width: Int = 0 public var height: Int = 0 public init() {} } public class ArkGraphicsWindow { public var rootWidget: ArkGraphicsWidget? public var title: String = "" public init() {} } /// The Backend bridging SwiftCrossUI to ArkGraphics IPC public class ArkGraphicsBackend: BackendFeatures.BaseStubs { public struct Widget { var node: ArkGraphicsWidget } public struct Window { var node: ArkGraphicsWindow } public required init() {} public var deviceClass: DeviceClass { .desktop } public static func earlySetup() {} public func runMainLoop(_ callback: @escaping @MainActor () -> Void) { // Setup ArkGraphics IPC let graphics = ArkGraphics() if !graphics.isConnected { print("ArkGraphicsBackend: FATAL - Cannot connect to display daemon") return } callback() // Main run loop while true { usleep(16000) // ~60fps // Poll for inputs, trigger UI redraws, etc } } public nonisolated func runInMainThread(action: @escaping @MainActor () -> Void) { // Run on the single main thread Task { @MainActor in action() } } public func computeRootEnvironment(defaultEnvironment: EnvironmentValues) -> EnvironmentValues { return defaultEnvironment } public func setRootEnvironmentChangeHandler(to action: @escaping @Sendable @MainActor () -> Void) {} // - CoreWindowing - public func createWindow(withDefaultSize defaultSize: SIMD2?, id: String) -> Window { return Window(node: ArkGraphicsWindow()) } public func updateWindow(_ window: Window, title: String) { window.node.title = title } public func updateWindow(_ window: Window, resizability: WindowResizability) {} public func setChild(ofWindow window: Window, to child: Widget) { window.node.rootWidget = child.node } public func showWindow(_ window: Window) {} // - GenericContainers - public func createContainer() -> Widget { return Widget(node: ArkGraphicsWidget()) } public func addChild(_ child: Widget, to container: Widget) { container.node.children.append(child.node) } public func setChildren(_ children: [Widget], of container: Widget) { container.node.children = children.map { $0.node } } public func removeChild(_ child: Widget, from container: Widget) { container.node.children.removeAll(where: { $0 === child.node }) } public func removeAllChildren(of container: Widget) { container.node.children.removeAll() } public func insert(_ child: Widget, into container: Widget, at index: Int) { container.node.children.insert(child.node, at: index) } public func swap(childAt firstIndex: Int, withChildAt secondIndex: Int, in container: Widget) { container.node.children.swapAt(firstIndex, secondIndex) } public func setPosition(ofChildAt index: Int, in container: Widget, to position: SIMD2) { container.node.children[index].x = position.x container.node.children[index].y = position.y } public func remove(childAt index: Int, from container: Widget) { container.node.children.remove(at: index) } // - TextViews - public func createTextView() -> Widget { return Widget(node: ArkGraphicsWidget()) } public func updateTextView(_ textView: Widget, content: String, environment: EnvironmentValues) {} public func size(of text: String, whenDisplayedIn widget: Widget, proposedWidth: Int?, proposedHeight: Int?, environment: EnvironmentValues) -> SIMD2 { return SIMD2(text.count * 8, 16) } // - Buttons - public func createSimpleButton() -> Widget { return Widget(node: ArkGraphicsWidget()) } public func updateSimpleButton(_ button: Widget, label: String, environment: EnvironmentValues, action: @escaping () -> Void) {} public func createButton(wrapping: Widget) -> Widget { return Widget(node: ArkGraphicsWidget()) } public func updateButton(_ button: Widget, environment: EnvironmentValues, action: @escaping () -> Void) {} public func buttonPadding(in environment: EnvironmentValues) -> SIMD2 { return SIMD2(8, 8) } public func defaultButtonStyle() -> ButtonStyle { return .bordered } public var scrollBarWidth: Int { return 10 } public var requiresImageUpdateOnScaleFactorChange: Bool { return false } public var requiresToggleSwitchSpacer: Bool { return false } public var supportedPickerStyles: [BackendPickerStyle] { return [] } // Windowing extra methods public func show(window: Window) {} public func setTitle(ofWindow window: Window, to title: String) {} public func updateWindow(_ window: Window, environment: EnvironmentValues) {} public func size(ofWindow window: Window) -> SIMD2 { return SIMD2(1024, 768) } public func setSize(ofWindow window: Window, to newSize: SIMD2) {} public func setSizeLimits(ofWindow window: Window, minimum minimumSize: SIMD2, maximum maximumSize: SIMD2?) {} public func isWindowProgrammaticallyResizable(_ window: Window) -> Bool { return false } public func setResizeHandler(ofWindow window: Window, to action: @escaping (SIMD2) -> Void) {} public func activate(window: Window) {} public func computeWindowEnvironment(window: Window, rootEnvironment: EnvironmentValues) -> EnvironmentValues { return rootEnvironment } public func setWindowEnvironmentChangeHandler(of window: Window, to action: @escaping @Sendable @MainActor () -> Void) {} public var defaultPaddingAmount: Int { return 10 } public func naturalSize(of widget: Widget) -> SIMD2 { return SIMD2(0, 0) } public func setSize(of widget: Widget, to size: SIMD2) { widget.node.width = size.x widget.node.height = size.y } public func show(widget: Widget) {} public var supportsMultipleWindows: Bool { return false } public var canOverrideWindowColorScheme: Bool { return false } public var restoresWindowFrames: Bool { return false } }