diff --git a/ShhShell.xcodeproj/project.pbxproj b/ShhShell.xcodeproj/project.pbxproj index 09052d8..46bc70c 100644 --- a/ShhShell.xcodeproj/project.pbxproj +++ b/ShhShell.xcodeproj/project.pbxproj @@ -72,6 +72,7 @@ A96C6B022E0C49E800F377FE /* CenteredLabel.swift in Sources */ = {isa = PBXBuildFile; fileRef = A96C6B012E0C49E800F377FE /* CenteredLabel.swift */; }; A96C90A12E12B87A00724253 /* TextBox.swift in Sources */ = {isa = PBXBuildFile; fileRef = A96C90A02E12B87900724253 /* TextBox.swift */; }; A96C90A32E12D53B00724253 /* KeyType.swift in Sources */ = {isa = PBXBuildFile; fileRef = A96C90A22E12D53900724253 /* KeyType.swift */; }; + A97AF1802E5D07BE00829443 /* CRTView.swift in Sources */ = {isa = PBXBuildFile; fileRef = A97AF17F2E5D07BE00829443 /* CRTView.swift */; }; A9835C3C2E17CCA500969508 /* TrafficLights.swift in Sources */ = {isa = PBXBuildFile; fileRef = A9835C3B2E17CCA500969508 /* TrafficLights.swift */; }; A98554552E05535F009051BD /* KeyManagerView.swift in Sources */ = {isa = PBXBuildFile; fileRef = A98554542E05535F009051BD /* KeyManagerView.swift */; }; A98554592E0553AA009051BD /* KeyManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = A98554582E0553AA009051BD /* KeyManager.swift */; }; @@ -212,6 +213,7 @@ A96C6B012E0C49E800F377FE /* CenteredLabel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CenteredLabel.swift; sourceTree = ""; }; A96C90A02E12B87900724253 /* TextBox.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TextBox.swift; sourceTree = ""; }; A96C90A22E12D53900724253 /* KeyType.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KeyType.swift; sourceTree = ""; }; + A97AF17F2E5D07BE00829443 /* CRTView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CRTView.swift; sourceTree = ""; }; A9835C3B2E17CCA500969508 /* TrafficLights.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TrafficLights.swift; sourceTree = ""; }; A98554542E05535F009051BD /* KeyManagerView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KeyManagerView.swift; sourceTree = ""; }; A98554582E0553AA009051BD /* KeyManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KeyManager.swift; sourceTree = ""; }; @@ -358,6 +360,7 @@ children = ( A923172E2E08851200ECE1E6 /* ShellView.swift */, A9FD37682E16A6BF005319A8 /* ShellTabView.swift */, + A97AF17F2E5D07BE00829443 /* CRTView.swift */, ); path = Terminal; sourceTree = ""; @@ -873,6 +876,7 @@ A98554592E0553AA009051BD /* KeyManager.swift in Sources */, A93F283D2E2A5DCB0092B8D5 /* SnippetManagerView.swift in Sources */, A9C060EB2E357FD300CA9374 /* Haptics.swift in Sources */, + A97AF1802E5D07BE00829443 /* CRTView.swift in Sources */, A9C897EF2DF1A9A400EF9A5F /* SSHHandler.swift in Sources */, A9D819312E102D8700442D38 /* HostkeysView.swift in Sources */, A98554552E05535F009051BD /* KeyManagerView.swift in Sources */, diff --git a/ShhShell/Terminal/CRT.metal b/ShhShell/Terminal/CRT.metal index 3f6a2f5..145384a 100644 --- a/ShhShell/Terminal/CRT.metal +++ b/ShhShell/Terminal/CRT.metal @@ -17,7 +17,8 @@ using namespace metal; //scanlines newCol *= 0.5 + 0.5 * sin(uv.y * 1250.0); - half4 output = half4(color.xyz*newCol, 1); +// half4 output = half4(layer.sample(pos).xyz*newCol, 1); + half4 output = half4(color.xyz*newCol*0.24, 0.25); return output; } diff --git a/ShhShell/Views/ContentView.swift b/ShhShell/Views/ContentView.swift index e6f498f..670c5d2 100644 --- a/ShhShell/Views/ContentView.swift +++ b/ShhShell/Views/ContentView.swift @@ -18,6 +18,13 @@ struct ContentView: View { hostsManager.selectedTheme.background.suiColor.opacity(0.7) .ignoresSafeArea(.all) List { + ForEach(0..<6) { + Color.red.frame(width: 60, height: 60, alignment: .center) + .brightness(Double($0) * 0.2) + .overlay(Text("\(Double($0) * 0.2 * 100, specifier: "%.0f")%"), + alignment: .bottom) + .border(Color.gray) + } SessionsListView( handler: handler, hostsManager: hostsManager, diff --git a/ShhShell/Views/Terminal/CRTView.swift b/ShhShell/Views/Terminal/CRTView.swift new file mode 100644 index 0000000..74702ac --- /dev/null +++ b/ShhShell/Views/Terminal/CRTView.swift @@ -0,0 +1,33 @@ +// +// CRTView.swift +// ShhShell +// +// Created by neon443 on 25/08/2025. +// + +import SwiftUI + +struct CRTView: View { + @State var startTime: Date = .now + + var body: some View { + TimelineView(.animation) { tl in + let time = tl.date.distance(to: startTime) + Rectangle() + .foregroundStyle(.white.opacity(0.1)) + .visualEffect { content, proxy in + content + .colorEffect( + ShaderLibrary.crt( + .float2(proxy.size), + .float(time) + ) + ) + } + } + } +} + +#Preview { + CRTView() +} diff --git a/ShhShell/Views/Terminal/ShellView.swift b/ShhShell/Views/Terminal/ShellView.swift index af84876..248c0bf 100644 --- a/ShhShell/Views/Terminal/ShellView.swift +++ b/ShhShell/Views/Terminal/ShellView.swift @@ -20,44 +20,47 @@ struct ShellView: View { var body: some View { NavigationStack { + let time = startTime.timeIntervalSinceNow ZStack { - TimelineView(.animation) { tl in - let time = tl.date.distance(to: startTime) - let shaderEnabled = hostsManager.settings.filter == .crt - hostsManager.selectedTheme.background.suiColor - .ignoresSafeArea(.all) - TerminalController(handler: handler, hostsManager: hostsManager) - - Group { - Color.gray.opacity(0.2) - .transition(.opacity) - Image(systemName: "bell.fill") - .foregroundStyle( - hostsManager.selectedTheme.background.luminance > 0.5 ? - .black : .white - ) - .font(.largeTitle) - .shadow(color: .black, radius: 5) - } - .opacity(handler.bell ? 1 : 0) - .onChange(of: handler.bell) { _ in - guard handler.bell else { return } - if hostsManager.settings.bellHaptic { - Haptic.warning.trigger() - } - if hostsManager.settings.bellSound { - AudioServicesPlaySystemSound(1103) + hostsManager.selectedTheme.background.suiColor + .ignoresSafeArea(.all) + + TerminalController(handler: handler, hostsManager: hostsManager) +// .visualEffect { content, proxy in +// content +// .layerEffect( +// ShaderLibrary.crt( +// .float2(proxy.size), +// .float(time) +// ), +// maxSampleOffset: .zero +// ) +// } + .overlay { + if hostsManager.settings.filter == .crt { + CRTView() } } - .visualEffect { content, proxy in - content - .colorEffect( - ShaderLibrary.crt( - .float2(proxy.size), - .float(time) - ), - isEnabled: shaderEnabled - ) + + Group { + Color.gray.opacity(0.2) + .transition(.opacity) + Image(systemName: "bell.fill") + .foregroundStyle( + hostsManager.selectedTheme.background.luminance > 0.5 ? + .black : .white + ) + .font(.largeTitle) + .shadow(color: .black, radius: 5) + } + .opacity(handler.bell ? 1 : 0) + .onChange(of: handler.bell) { _ in + guard handler.bell else { return } + if hostsManager.settings.bellHaptic { + Haptic.warning.trigger() + } + if hostsManager.settings.bellSound { + AudioServicesPlaySystemSound(1103) } } }