I am new to swift. I am trying to build a command line wrapper around ScreenCaptureKit. The idea is that when i run the command, it starts capturing the main screen and then stops the capturing when user sends the kill signal to the command (ctrl+c). The program also writes the captured video to a file.
I could not figure out how to wait for user's input (the kill signal) while the video stream is being captured.
struct ScreenCaptureKitCLI: AsyncParsableCommand {
mutating func run() async throws {
// Create a screen recording
do {
// Check for screen recording permission, make sure your terminal has screen recording permission
guard CGPreflightScreenCaptureAccess() else {
throw RecordingError("No screen capture permission")
}
let url = URL(filePath: FileManager.default.currentDirectoryPath).appending(path: "recording \(Date()).mov")
// let cropRect = CGRect(x: 0, y: 0, width: 960, height: 540)
let screenRecorder = try await ScreenRecorder(url: url, displayID: CGMainDisplayID(), cropRect: nil)
print("Starting screen recording of main display")
try await screenRecorder.start()
// This await only waits for the recording to start. After that ScreenCaptureKit keeps sending the frames to the stream we provide it.
// TODO: Need some way to keep the program running until the user sends a kill signal
} catch {
print("Error during recording:", error)
}
}
}
I am using the ArgumentParser library for building the CLI program.
Here's the link to what i have written so far - https://github.com/mukeshsoni/screencapturekit-cli/blob/main/Sources/screencapturekit-cli/ScreenCaptureKitCli.swift
Any help or pointers would be really appreciated.
I tried using Dispatch
but was not able to use it inside an async function. None of the solutions from the 'Trapping signals in a swift command line application' questions worked inside the mutating func run() async throws {
needed to implement AsyncParsableCommand
protocol.