Create Wristivo iPhone and Apple Watch foundation

This commit is contained in:
2026-09-17 17:59:08 +04:00
commit a92698e1e6
48 changed files with 2492 additions and 0 deletions
+35
View File
@@ -0,0 +1,35 @@
import RemoteCore
extension RemoteCommand {
var title: String {
switch self {
case .up: "Up"
case .down: "Down"
case .left: "Left"
case .right: "Right"
case .select: "Select"
case .back: "Back"
case .home: "Home"
case .playPause: "Play / pause"
case .volumeUp: "Volume up"
case .volumeDown: "Volume down"
case .mute: "Mute"
}
}
var symbol: String {
switch self {
case .up: "chevron.up"
case .down: "chevron.down"
case .left: "chevron.left"
case .right: "chevron.right"
case .select: "checkmark"
case .back: "arrow.uturn.backward"
case .home: "house"
case .playPause: "playpause"
case .volumeUp: "speaker.plus"
case .volumeDown: "speaker.minus"
case .mute: "speaker.slash"
}
}
}
+37
View File
@@ -0,0 +1,37 @@
import SwiftUI
import RemoteCore
struct WatchRemoteDemoView: View {
@State private var lastCommand = "No TV connected"
var body: some View {
ScrollView {
VStack(spacing: 8) {
Text("Wristivo").font(.headline)
Text("DEMO").font(.caption2).foregroundStyle(.secondary)
commandButton(.up)
HStack(spacing: 4) {
commandButton(.left)
commandButton(.select)
commandButton(.right)
}
commandButton(.down)
Text(lastCommand).font(.caption2)
HStack(spacing: 4) {
commandButton(.back)
commandButton(.home)
}
Text("Wrist gestures are coming in the hardware prototype.")
.font(.footnote).foregroundStyle(.secondary)
}.padding(.horizontal, 4)
}.tint(.teal)
}
private func commandButton(_ command: RemoteCommand) -> some View {
Button { lastCommand = "Demo: \(command.title)" } label: {
Image(systemName: command.symbol).frame(minWidth: 24, minHeight: 30)
}
.buttonStyle(.bordered)
.accessibilityLabel(command.title)
}
}
+8
View File
@@ -0,0 +1,8 @@
import SwiftUI
@main
struct WristivoWatchApp: App {
var body: some Scene {
WindowGroup { WatchRemoteDemoView() }
}
}
+67
View File
@@ -0,0 +1,67 @@
import SwiftUI
import RemoteCore
/// Foundation UI: intentionally never opens a TV connection.
struct RemoteDemoView: View {
@State private var lastCommand = "Try a button below"
var body: some View {
NavigationStack {
ScrollView {
VStack(spacing: 24) {
VStack(alignment: .leading, spacing: 8) {
Label("Demo mode", systemImage: "play.rectangle")
.font(.headline)
Text("Explore your remote. No television is connected.")
Text("Pairing and wrist movement recognition are still in development.")
.font(.footnote).foregroundStyle(.secondary)
}
.frame(maxWidth: .infinity, alignment: .leading)
.padding().background(.thinMaterial, in: RoundedRectangle(cornerRadius: 20))
VStack(spacing: 12) {
commandButton(.up)
HStack(spacing: 16) {
commandButton(.left)
commandButton(.select)
commandButton(.right)
}
commandButton(.down)
}
Text(lastCommand).font(.callout).accessibilityIdentifier("demo.lastCommand")
LazyVGrid(columns: [GridItem(.flexible()), GridItem(.flexible())], spacing: 12) {
ForEach([RemoteCommand.back, .home, .volumeDown, .volumeUp, .mute, .playPause], id: \.rawValue) { command in
Button { record(command) } label: {
Label(command.title, systemImage: command.symbol)
.frame(maxWidth: .infinity, minHeight: 44)
}.buttonStyle(.bordered)
}
}
VStack(alignment: .leading, spacing: 8) {
Text("Made for a lighter touch").font(.headline)
Text("The planned watch remote translates deliberate wrist movements into directional presses. Your iPhone will relay commands to a paired TV on your home network.")
Text("Gesture control will require an active watch session and a reachable iPhone.")
.foregroundStyle(.secondary)
}.frame(maxWidth: .infinity, alignment: .leading)
}
.padding().frame(maxWidth: 560)
.frame(maxWidth: .infinity)
}
.navigationTitle("Wristivo")
.tint(.teal)
}
}
private func commandButton(_ command: RemoteCommand) -> some View {
Button { record(command) } label: {
Image(systemName: command.symbol)
.font(.title2).frame(width: 64, height: 56)
}
.buttonStyle(.borderedProminent)
.accessibilityLabel(command.title)
}
private func record(_ command: RemoteCommand) {
lastCommand = "Demo: \(command.title)"
}
}
+8
View File
@@ -0,0 +1,8 @@
import SwiftUI
@main
struct WristivoApp: App {
var body: some Scene {
WindowGroup { RemoteDemoView() }
}
}