diff --git a/assets/tray-icon/generated/tray-icon-template.png b/assets/tray-icon/generated/tray-icon-template.png index ce93621..cd5f613 100644 Binary files a/assets/tray-icon/generated/tray-icon-template.png and b/assets/tray-icon/generated/tray-icon-template.png differ diff --git a/assets/tray-icon/source/tray-icon-design.md b/assets/tray-icon/source/tray-icon-design.md index 16a414b..1716040 100644 --- a/assets/tray-icon/source/tray-icon-design.md +++ b/assets/tray-icon/source/tray-icon-design.md @@ -3,8 +3,12 @@ Purpose: Source notes for the generated Decodex App menu bar template image. The menu bar icon uses the same cloud-wrapped prompt-lightning mark as the app icon, -but removes the tile and color. It is generated as a single-color macOS template image -with a moderate 22pt display size so the system can tint it correctly in light, dark, -and selected menu bar states. +but removes the tile and color. The template variant keeps the cloud slightly smaller +and nudges the lightning mark down and right so the forms stay separated at the 22pt +menu bar size. The lightning uses a small-template polygon to avoid a blocky vertical +edge when the cloud masks it. The internal prompt mark is also reduced slightly and +nudged inward so it does not overpower or hollow out the cloud silhouette. It is +generated as a single-color macOS template image so the system can tint it correctly +in light, dark, and selected menu bar states. Generator: `scripts/assets/render_decodex_app_icons.swift`. diff --git a/scripts/assets/render_decodex_app_icons.swift b/scripts/assets/render_decodex_app_icons.swift index 339b9d1..5486595 100755 --- a/scripts/assets/render_decodex_app_icons.swift +++ b/scripts/assets/render_decodex_app_icons.swift @@ -32,6 +32,16 @@ enum Palette { static let black = NSColor(calibratedWhite: 0.0, alpha: 1) } +enum TemplateMark { + static let canvasScale: CGFloat = 1.06 + static let cloudScale: CGFloat = 0.97 + static let boltCenter = NSPoint(x: 766, y: 378) + static let boltScale: CGFloat = 1.82 + static let promptCenter = NSPoint(x: 456, y: 504) + static let promptOffset = NSSize(width: 18, height: 0) + static let promptScale: CGFloat = 0.88 +} + func bitmap(size: Int = canvasSize, drawing: (CGContext) -> Void) throws -> NSBitmapImageRep { guard let rep = NSBitmapImageRep( bitmapDataPlanes: nil, @@ -112,6 +122,17 @@ func boltPoints(center: NSPoint, scale: CGFloat) -> [NSPoint] { ] } +func templateBoltPoints(center: NSPoint, scale: CGFloat) -> [NSPoint] { + [ + NSPoint(x: center.x + 48 * scale, y: center.y + 130 * scale), + NSPoint(x: center.x - 88 * scale, y: center.y + 18 * scale), + NSPoint(x: center.x - 16 * scale, y: center.y + 18 * scale), + NSPoint(x: center.x - 56 * scale, y: center.y - 128 * scale), + NSPoint(x: center.x + 96 * scale, y: center.y - 8 * scale), + NSPoint(x: center.x + 20 * scale, y: center.y - 8 * scale), + ] +} + func appBoltPoints(offsetX: CGFloat = 0, offsetY: CGFloat = 0) -> [NSPoint] { [ NSPoint(x: 850 + offsetX, y: 592 + offsetY), @@ -195,18 +216,28 @@ func drawAppMark() { } func drawTemplateBolt() { - fillPolygon(boltPoints(center: NSPoint(x: 762, y: 386), scale: 2.04), color: .black) + fillPolygon(templateBoltPoints(center: TemplateMark.boltCenter, scale: TemplateMark.boltScale), color: .black) } func drawTemplateCloud() { + let context = NSGraphicsContext.current!.cgContext + context.saveGState() + context.translateBy(x: 512, y: 512) + context.scaleBy(x: TemplateMark.cloudScale, y: TemplateMark.cloudScale) + context.translateBy(x: -512, y: -512) Palette.black.setFill() cloudPath().fill() + context.restoreGState() } func clearTemplatePrompt() { let context = NSGraphicsContext.current!.cgContext context.saveGState() context.setBlendMode(.clear) + context.translateBy(x: TemplateMark.promptOffset.width, y: TemplateMark.promptOffset.height) + context.translateBy(x: TemplateMark.promptCenter.x, y: TemplateMark.promptCenter.y) + context.scaleBy(x: TemplateMark.promptScale, y: TemplateMark.promptScale) + context.translateBy(x: -TemplateMark.promptCenter.x, y: -TemplateMark.promptCenter.y) drawPromptMark(color: .clear, width: 108) context.restoreGState() } @@ -215,7 +246,7 @@ func drawTemplateMark() { let context = NSGraphicsContext.current!.cgContext context.saveGState() context.translateBy(x: 512, y: 512) - context.scaleBy(x: 1.10, y: 1.10) + context.scaleBy(x: TemplateMark.canvasScale, y: TemplateMark.canvasScale) context.translateBy(x: -512, y: -512) drawTemplateBolt() drawTemplateCloud()