feat: Add VS Code launch/task configurations and refactor app icon and resource management.
3
.gitignore
vendored
@@ -11,8 +11,9 @@ Thumbs.db
|
||||
*~
|
||||
*.swp
|
||||
*.swo
|
||||
.vscode/
|
||||
.idea/
|
||||
.vscode/*.code-workspace
|
||||
.vscode/settings.json
|
||||
|
||||
# Logs
|
||||
*.log
|
||||
|
||||
44
.vscode/launch.json
vendored
Normal file
@@ -0,0 +1,44 @@
|
||||
{
|
||||
"configurations": [
|
||||
{
|
||||
"type": "swift",
|
||||
"request": "launch",
|
||||
"name": "Debug Mole",
|
||||
"args": [],
|
||||
"cwd": "${workspaceFolder}/app",
|
||||
"target": "Mole",
|
||||
"configuration": "debug",
|
||||
"preLaunchTask": "swift: Build Debug Mole (app)"
|
||||
},
|
||||
{
|
||||
"type": "swift",
|
||||
"request": "launch",
|
||||
"name": "Release Mole",
|
||||
"args": [],
|
||||
"cwd": "${workspaceFolder}/app",
|
||||
"target": "Mole",
|
||||
"configuration": "release",
|
||||
"preLaunchTask": "swift: Build Release Mole (app)"
|
||||
},
|
||||
{
|
||||
"type": "swift",
|
||||
"request": "launch",
|
||||
"args": [],
|
||||
"cwd": "${workspaceFolder:Mole}/app",
|
||||
"name": "Debug Mole (app)",
|
||||
"target": "Mole",
|
||||
"configuration": "debug",
|
||||
"preLaunchTask": "swift: Build Debug Mole (app)"
|
||||
},
|
||||
{
|
||||
"type": "swift",
|
||||
"request": "launch",
|
||||
"args": [],
|
||||
"cwd": "${workspaceFolder:Mole}/app",
|
||||
"name": "Release Mole (app)",
|
||||
"target": "Mole",
|
||||
"configuration": "release",
|
||||
"preLaunchTask": "swift: Build Release Mole (app)"
|
||||
}
|
||||
]
|
||||
}
|
||||
38
.vscode/tasks.json
vendored
Normal file
@@ -0,0 +1,38 @@
|
||||
{
|
||||
"version": "2.0.0",
|
||||
"tasks": [
|
||||
{
|
||||
"label": "swift: Build Debug Mole (app)",
|
||||
"type": "shell",
|
||||
"command": "swift",
|
||||
"args": ["build", "-c", "debug"],
|
||||
"options": {
|
||||
"cwd": "${workspaceFolder}/app"
|
||||
},
|
||||
"group": {
|
||||
"kind": "build",
|
||||
"isDefault": true
|
||||
},
|
||||
"presentation": {
|
||||
"reveal": "always",
|
||||
"panel": "shared"
|
||||
},
|
||||
"problemMatcher": ["$swiftc"]
|
||||
},
|
||||
{
|
||||
"label": "swift: Build Release Mole (app)",
|
||||
"type": "shell",
|
||||
"command": "swift",
|
||||
"args": ["build", "-c", "release"],
|
||||
"options": {
|
||||
"cwd": "${workspaceFolder}/app"
|
||||
},
|
||||
"group": "build",
|
||||
"presentation": {
|
||||
"reveal": "always",
|
||||
"panel": "shared"
|
||||
},
|
||||
"problemMatcher": ["$swiftc"]
|
||||
}
|
||||
]
|
||||
}
|
||||
19
app/Extensions.swift
Normal file
@@ -0,0 +1,19 @@
|
||||
import AppKit
|
||||
|
||||
extension Bundle {
|
||||
/// Loads an image from the bundle's resources by name.
|
||||
///
|
||||
/// This method attempts to load an image with the given name by trying
|
||||
/// common image file extensions in order: PNG, JPG, and ICNS.
|
||||
///
|
||||
/// - Parameter name: The name of the image resource without extension.
|
||||
/// - Returns: An NSImage if found, nil otherwise.
|
||||
///
|
||||
/// - Note: Supported formats: PNG, JPG, ICNS
|
||||
func image(forResource name: String) -> NSImage? {
|
||||
if let url = url(forResource: name, withExtension: "png") { return NSImage(contentsOf: url) }
|
||||
if let url = url(forResource: name, withExtension: "jpg") { return NSImage(contentsOf: url) }
|
||||
if let url = url(forResource: name, withExtension: "icns") { return NSImage(contentsOf: url) }
|
||||
return nil
|
||||
}
|
||||
}
|
||||
@@ -119,12 +119,7 @@ struct MoleSceneView: NSViewRepresentable {
|
||||
}
|
||||
|
||||
// Load Texture (Support PNG and JPG)
|
||||
var finalImage: NSImage?
|
||||
if let url = Bundle.module.url(forResource: textureName, withExtension: "png") {
|
||||
finalImage = NSImage(contentsOf: url)
|
||||
} else if let url = Bundle.module.url(forResource: textureName, withExtension: "jpg") {
|
||||
finalImage = NSImage(contentsOf: url)
|
||||
}
|
||||
let finalImage = Bundle.module.image(forResource: textureName)
|
||||
|
||||
if let image = finalImage {
|
||||
material.diffuse.contents = image
|
||||
@@ -12,6 +12,8 @@ let package = Package(
|
||||
targets: [
|
||||
.executableTarget(
|
||||
name: "Mole",
|
||||
path: ".",
|
||||
exclude: ["Package.swift", "package.sh"],
|
||||
resources: [
|
||||
.process("Resources")
|
||||
]
|
||||
|
||||
@@ -42,10 +42,8 @@ struct PasswordSheetView: View {
|
||||
VStack(alignment: .leading, spacing: 14) {
|
||||
// Icon
|
||||
ZStack(alignment: .bottomTrailing) {
|
||||
if let url = Bundle.module.url(forResource: "mole", withExtension: "png"),
|
||||
let customIcon = NSImage(contentsOf: url)
|
||||
{
|
||||
Image(nsImage: customIcon)
|
||||
if let icon = Bundle.module.image(forResource: "mole") {
|
||||
Image(nsImage: icon)
|
||||
.resizable()
|
||||
.interpolation(.high)
|
||||
.aspectRatio(contentMode: .fit)
|
||||
|
Before Width: | Height: | Size: 452 KiB After Width: | Height: | Size: 452 KiB |
|
Before Width: | Height: | Size: 869 KiB After Width: | Height: | Size: 869 KiB |
|
Before Width: | Height: | Size: 1014 KiB After Width: | Height: | Size: 1014 KiB |
BIN
app/Resources/mole.icns
Normal file
|
Before Width: | Height: | Size: 2.8 MiB |
|
Before Width: | Height: | Size: 600 KiB |
@@ -6,7 +6,7 @@ APP_NAME="Mole"
|
||||
# Get the actual build path dynamically
|
||||
BUILD_PATH="$(swift build -c release --show-bin-path)/$APP_NAME"
|
||||
APP_BUNDLE="$APP_NAME.app"
|
||||
ICON_SOURCE="Sources/Mole/Resources/mole.png"
|
||||
ICON_SOURCE="Resources/mole.icns"
|
||||
|
||||
echo "🚀 Building Release Binary..."
|
||||
swift build -c release
|
||||
@@ -46,29 +46,8 @@ cat <<EOF > "$APP_BUNDLE/Contents/Info.plist"
|
||||
EOF
|
||||
|
||||
if [ -f "$ICON_SOURCE" ]; then
|
||||
echo "🎨 Generating App Icon from $ICON_SOURCE..."
|
||||
ICONSET="Mole.iconset"
|
||||
mkdir -p "$ICONSET"
|
||||
|
||||
# Resize images for standard icon sizes
|
||||
sips -z 16 16 "$ICON_SOURCE" --out "$ICONSET/icon_16x16.png" > /dev/null
|
||||
sips -z 32 32 "$ICON_SOURCE" --out "$ICONSET/icon_16x16@2x.png" > /dev/null
|
||||
sips -z 32 32 "$ICON_SOURCE" --out "$ICONSET/icon_32x32.png" > /dev/null
|
||||
sips -z 64 64 "$ICON_SOURCE" --out "$ICONSET/icon_32x32@2x.png" > /dev/null
|
||||
sips -z 128 128 "$ICON_SOURCE" --out "$ICONSET/icon_128x128.png" > /dev/null
|
||||
sips -z 256 256 "$ICON_SOURCE" --out "$ICONSET/icon_128x128@2x.png" > /dev/null
|
||||
sips -z 256 256 "$ICON_SOURCE" --out "$ICONSET/icon_256x256.png" > /dev/null
|
||||
sips -z 512 512 "$ICON_SOURCE" --out "$ICONSET/icon_256x256@2x.png" > /dev/null
|
||||
sips -z 512 512 "$ICON_SOURCE" --out "$ICONSET/icon_512x512.png" > /dev/null
|
||||
sips -z 1024 1024 "$ICON_SOURCE" --out "$ICONSET/icon_512x512@2x.png" > /dev/null
|
||||
|
||||
# Convert to icns
|
||||
iconutil -c icns "$ICONSET"
|
||||
mv "Mole.icns" "$APP_BUNDLE/Contents/Resources/AppIcon.icns"
|
||||
|
||||
# Clean up
|
||||
rm -rf "$ICONSET"
|
||||
|
||||
echo "🎨 Copying App Icon from $ICON_SOURCE..."
|
||||
cp "$ICON_SOURCE" "$APP_BUNDLE/Contents/Resources/AppIcon.icns"
|
||||
echo "✅ App Icon set successfully."
|
||||
else
|
||||
echo "⚠️ Icon file not found at $ICON_SOURCE. App will use default icon."
|
||||
|
||||