I'm not aware of any utility which does this, but you can easily write your own with the help of https://github.com/apple/swift-argument-parser package and NSWorkspace
:
The following sample code utilizes the first method.
Sample project
- Xcode - New project
- Select macOS & Command line utility
- Add
https://github.com/apple/swift-argument-parser
Swift package
- Copy & paste the code below
import AppKit
import ArgumentParser
final class StderrOutputStream: TextOutputStream {
func write(_ string: String) {
FileHandle.standardError.write(Data(string.utf8))
}
}
struct Icon: ParsableCommand {
static var configuration = CommandConfiguration(
commandName: "icon",
abstract: "Get the workspace icon and save it as a PNG image.",
version: "0.0.1"
)
@Argument(help: "Path to a file.")
var input: String
@Argument(help: "Output file.")
var output: String
@Option(name: .shortAndLong, help: "Icon size.")
var size: Int = 512
mutating func run() throws {
if !FileManager.default.fileExists(atPath: input) {
var stderr = StderrOutputStream()
print("File not found: \(input)", to: &stderr)
throw ExitCode(-1)
}
// Get NSImage with multiple representations (sizes)
let icon = NSWorkspace.shared.icon(forFile: input)
// Propose some size to get as accurate as possible representation size
var proposedRect = NSRect(x: 0, y: 0, width: size, height: size)
guard let cgRef = icon.cgImage(forProposedRect: &proposedRect, context: nil, hints: nil) else {
var stderr = StderrOutputStream()
print("Internal error: unable to get CGImage from NSImage", to: &stderr)
throw ExitCode(-2)
}
do {
// Get PNG representation
let data = NSBitmapImageRep(cgImage: cgRef).representation(using: .png, properties: [:])
// Save it to a file
try data?.write(to: URL(fileURLWithPath: output), options: .atomic)
}
catch {
var stderr = StderrOutputStream()
print("Failed to save icon: \(error)", to: &stderr)
throw ExitCode(-3)
}
print("Icon (\(size)x\(size)) saved to: \(output)")
}
}
Icon.main()