Skip to content

Commit 132ea46

Browse files
committed
initial commit
0 parents  commit 132ea46

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

59 files changed

+3134
-0
lines changed

.gitignore

+3
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
.DS_Store
2+
Package.resolved
3+
*.xcuserdatad

README.md

+14
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
# Samra
2+
3+
A macOS Application to explore and edit Asset Catalog (.car) files on macOS, with a nicer native, modern-feeling UI that does not crash every couple of seconds.
4+
5+
## Why Samra?
6+
There are a few existing asset catalog viewer applications for macOS, however, none felt feature complete, Samra offers the following:
7+
- Browse through the Asset Catalog file
8+
- Show all types of objects (renditions) in it, not just images (colors, pdfs, image sets, etc)
9+
- Ability to edit icons/images & colors
10+
- Search in Asset Catalog for renditions by name
11+
- View detailed information about each rendition, such as lookup name, width, height, appearance (if it's meant for dark mode or light mode) and other type-specific information (ie, RGB values for colors).
12+
13+
## What versions does this support?
14+
macOS 10.15.1+

Samra.xcodeproj/project.pbxproj

+510
Large diffs are not rendered by default.

Samra.xcodeproj/project.xcworkspace/contents.xcworkspacedata

+7
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
3+
<plist version="1.0">
4+
<dict>
5+
<key>IDEDidComputeMac32BitWarning</key>
6+
<true/>
7+
</dict>
8+
</plist>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
{
2+
"pins" : [
3+
{
4+
"identity" : "santanderwrappers",
5+
"kind" : "remoteSourceControl",
6+
"location" : "https://github.com/SerenaKit/SantanderWrappers",
7+
"state" : {
8+
"branch" : "main",
9+
"revision" : "6400795b9b8ef256b842def850765833cca5c5ff"
10+
}
11+
}
12+
],
13+
"version" : 2
14+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,78 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<Scheme
3+
LastUpgradeVersion = "1420"
4+
version = "1.3">
5+
<BuildAction
6+
parallelizeBuildables = "YES"
7+
buildImplicitDependencies = "YES">
8+
<BuildActionEntries>
9+
<BuildActionEntry
10+
buildForTesting = "YES"
11+
buildForRunning = "YES"
12+
buildForProfiling = "YES"
13+
buildForArchiving = "YES"
14+
buildForAnalyzing = "YES">
15+
<BuildableReference
16+
BuildableIdentifier = "primary"
17+
BlueprintIdentifier = "CE3BC09329A0C625009823CF"
18+
BuildableName = "Samra.app"
19+
BlueprintName = "Samra"
20+
ReferencedContainer = "container:Samra.xcodeproj">
21+
</BuildableReference>
22+
</BuildActionEntry>
23+
</BuildActionEntries>
24+
</BuildAction>
25+
<TestAction
26+
buildConfiguration = "Debug"
27+
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
28+
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
29+
shouldUseLaunchSchemeArgsEnv = "YES">
30+
<Testables>
31+
</Testables>
32+
</TestAction>
33+
<LaunchAction
34+
buildConfiguration = "Debug"
35+
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
36+
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
37+
launchStyle = "0"
38+
useCustomWorkingDirectory = "NO"
39+
ignoresPersistentStateOnLaunch = "NO"
40+
debugDocumentVersioning = "YES"
41+
debugServiceExtension = "internal"
42+
allowLocationSimulation = "YES">
43+
<BuildableProductRunnable
44+
runnableDebuggingMode = "0">
45+
<BuildableReference
46+
BuildableIdentifier = "primary"
47+
BlueprintIdentifier = "CE3BC09329A0C625009823CF"
48+
BuildableName = "Samra.app"
49+
BlueprintName = "Samra"
50+
ReferencedContainer = "container:Samra.xcodeproj">
51+
</BuildableReference>
52+
</BuildableProductRunnable>
53+
</LaunchAction>
54+
<ProfileAction
55+
buildConfiguration = "Release"
56+
shouldUseLaunchSchemeArgsEnv = "YES"
57+
savedToolIdentifier = ""
58+
useCustomWorkingDirectory = "NO"
59+
debugDocumentVersioning = "YES">
60+
<BuildableProductRunnable
61+
runnableDebuggingMode = "0">
62+
<BuildableReference
63+
BuildableIdentifier = "primary"
64+
BlueprintIdentifier = "CE3BC09329A0C625009823CF"
65+
BuildableName = "Samra.app"
66+
BlueprintName = "Samra"
67+
ReferencedContainer = "container:Samra.xcodeproj">
68+
</BuildableReference>
69+
</BuildableProductRunnable>
70+
</ProfileAction>
71+
<AnalyzeAction
72+
buildConfiguration = "Debug">
73+
</AnalyzeAction>
74+
<ArchiveAction
75+
buildConfiguration = "Release"
76+
revealArchiveInOrganizer = "YES">
77+
</ArchiveAction>
78+
</Scheme>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<Bucket
3+
uuid = "126A8E73-CDAC-49E7-8DFD-674648E1C629"
4+
type = "1"
5+
version = "2.0">
6+
</Bucket>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
3+
<plist version="1.0">
4+
<dict>
5+
<key>SchemeUserState</key>
6+
<dict>
7+
<key>Samra.xcscheme_^#shared#^_</key>
8+
<dict>
9+
<key>orderHint</key>
10+
<integer>0</integer>
11+
</dict>
12+
</dict>
13+
<key>SuppressBuildableAutocreation</key>
14+
<dict>
15+
<key>CE3BC09329A0C625009823CF</key>
16+
<dict>
17+
<key>primary</key>
18+
<true/>
19+
</dict>
20+
</dict>
21+
</dict>
22+
</plist>

Samra/AppDelegate.swift

+195
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,195 @@
1+
//
2+
// AppDelegate.swift
3+
// Samra
4+
//
5+
// Created by Serena on 18/02/2023.
6+
//
7+
8+
import Cocoa
9+
import AssetCatalogWrapper
10+
11+
@main
12+
class AppDelegate: NSObject, NSApplicationDelegate {
13+
14+
static func main() {
15+
let instance = AppDelegate()
16+
NSApplication.shared.delegate = instance
17+
NSApplication.shared.run()
18+
}
19+
20+
func applicationWillFinishLaunching(_ notification: Notification) {}
21+
22+
@objc
23+
func openMenuItemClicked() {
24+
URLHandler.shared.presentArchiveChooserPanel(insertToRecentItems: true, senderView: nil)
25+
}
26+
27+
func applicationDidFinishLaunching(_ aNotification: Notification) {
28+
// Insert code here to initialize your application
29+
NSLog("I crash through glass ceilings, I break through closed doors.")
30+
31+
if Preferences.showWelcomeVCOnLaunch {
32+
WindowController(kind: .welcome).showWindow(self)
33+
}
34+
35+
let items = RenditionType.allCases.map { type in
36+
let item = NSMenuItem(title: type.description, action: #selector(TypesListViewController.goToSection(menuItemSender:)))
37+
item.tag = type.rawValue
38+
item.isEnabled = false
39+
return item
40+
}
41+
42+
NSApplication.shared.mainMenu = NSMenu(items: [
43+
NSMenuItem(submenuTitle: "App", items: [
44+
NSMenuItem(title: "About Samra",
45+
action: #selector(openAboutPanel),
46+
keyEquivalent: ""),
47+
NSMenuItem.separator(),
48+
NSMenuItem(title: "Hide Others", action: #selector(NSApplication.hideOtherApplications(_:)), keyEquivalent: "h", keyEquivalentModifierMask: [.command, .option]),
49+
NSMenuItem(title: "Show All", action: #selector(NSApplication.unhideAllApplications(_:))),
50+
NSMenuItem.separator(),
51+
NSMenuItem(title: "Quit Samra", action: #selector(NSApplication.terminate(_:)), keyEquivalent: "q"),
52+
]),
53+
NSMenuItem(submenuTitle: "File", items: [
54+
NSMenuItem(title: "Open...", action: #selector(openMenuItemClicked), keyEquivalent: "o"),
55+
NSMenuItem.separator(),
56+
NSMenuItem(title: "Close", action: #selector(NSWindow.performClose(_:)), keyEquivalent: "w")
57+
]),
58+
59+
NSMenuItem(submenuTitle: "Edit", items: [
60+
NSMenuItem(title: "Undo", action: Selector(("undo:")), keyEquivalent: "z"),
61+
NSMenuItem(title: "Redo", action: Selector(("redo:")), keyEquivalent: "Z"),
62+
NSMenuItem.separator(),
63+
NSMenuItem(title: "Cut", action: #selector(NSText.cut(_:)), keyEquivalent: "x"),
64+
NSMenuItem(title: "Copy", action: #selector(NSText.copy(_:)), keyEquivalent: "c"),
65+
NSMenuItem(title: "Paste", action: #selector(NSText.paste(_:)), keyEquivalent: "v"),
66+
NSMenuItem(title: "Paste and Match Style", action: #selector(NSText.paste(_:)), keyEquivalent: "V", keyEquivalentModifierMask: [.command, .option]),
67+
NSMenuItem(title: "Delete", action: #selector(NSText.delete(_:))),
68+
NSMenuItem(title: "Select All", action: #selector(NSText.selectAll(_:)), keyEquivalent: "a"),
69+
NSMenuItem.separator(),
70+
NSMenuItem(
71+
submenuTitle: "Find",
72+
items: [
73+
NSMenuItem(title: "Find…", action: #selector(NSResponder.performTextFinderAction(_:)), keyEquivalent: "f", tag: NSTextFinder.Action.showFindInterface.rawValue),
74+
NSMenuItem(title: "Find and Replace…", action: #selector(NSResponder.performTextFinderAction(_:)), keyEquivalent: "f", keyEquivalentModifierMask: [.command, .option], tag: NSTextFinder.Action.replaceAndFind.rawValue),
75+
NSMenuItem(title: "Find Next", action: #selector(NSResponder.performTextFinderAction(_:)), keyEquivalent: "g", tag: NSTextFinder.Action.nextMatch.rawValue),
76+
NSMenuItem(title: "Find Previous", action: #selector(NSResponder.performTextFinderAction(_:)), keyEquivalent: "G", tag: NSTextFinder.Action.previousMatch.rawValue),
77+
NSMenuItem(title: "Use Selection for Find", action: #selector(NSResponder.performTextFinderAction(_:)), keyEquivalent: "e", tag: NSTextFinder.Action.setSearchString.rawValue),
78+
NSMenuItem(title: "Jump to Selection", action: #selector(NSResponder.centerSelectionInVisibleArea(_:)), keyEquivalent: "j"),
79+
]),
80+
NSMenuItem(
81+
submenuTitle: "Spelling and Grammar",
82+
items: [
83+
NSMenuItem(title: "Show Spelling and Grammar", action: #selector(NSTextCheckingController.showGuessPanel(_:)), keyEquivalent: ":"),
84+
NSMenuItem(title: "Check Document Now", action: #selector(NSTextCheckingController.checkSpelling(_:)), keyEquivalent: ";"),
85+
NSMenuItem(title: "Check Spelling While Typing", action: #selector(NSTextView.toggleContinuousSpellChecking(_:))),
86+
NSMenuItem(title: "Correct Spelling Automatically", action: #selector(NSTextView.toggleAutomaticSpellingCorrection(_:))),
87+
]),
88+
NSMenuItem(
89+
submenuTitle: "Substitutions",
90+
items: [
91+
NSMenuItem(title: "Show Substitutions", action: #selector(NSTextCheckingController.orderFrontSubstitutionsPanel(_:))),
92+
NSMenuItem.separator(),
93+
NSMenuItem(title: "Smart Copy/Paste", action: #selector(NSTextView.toggleSmartInsertDelete(_:))),
94+
NSMenuItem(title: "Smart Quotes", action: #selector(NSTextView.toggleAutomaticQuoteSubstitution(_:))),
95+
NSMenuItem(title: "Smart Dashes", action: #selector(NSTextView.toggleAutomaticDashSubstitution(_:))),
96+
NSMenuItem(title: "Smart Links", action: #selector(NSTextView.toggleAutomaticLinkDetection(_:))),
97+
NSMenuItem(title: "Data Detectors", action: #selector(NSTextView.toggleAutomaticDataDetection(_:))),
98+
NSMenuItem(title: "Text Replacement", action: #selector(NSTextView.toggleAutomaticTextReplacement(_:))),
99+
]),
100+
NSMenuItem(
101+
submenuTitle: "Transformations",
102+
items: [
103+
NSMenuItem(title: "Make Upper Case", action: #selector(NSResponder.uppercaseWord(_:))),
104+
NSMenuItem(title: "Make Lower Case", action: #selector(NSResponder.lowercaseWord(_:))),
105+
NSMenuItem(title: "Capitalize", action: #selector(NSResponder.capitalizeWord(_:))),
106+
]),
107+
NSMenuItem(
108+
submenuTitle: "Speech",
109+
items: [
110+
NSMenuItem(title: "Start Speaking", action: #selector(NSSpeechSynthesizer.startSpeaking(_:))),
111+
NSMenuItem(title: "Stop Speaking", action: #selector(NSTextView.stopSpeaking(_:))),
112+
]),
113+
]),
114+
NSMenuItem(submenuTitle: "Sections", items: items),
115+
NSMenuItem(submenuTitle: "Help", items: [
116+
NSMenuItem(title: "Help", action: #selector(NSApplication.showHelp(_:)), keyEquivalent: "?")
117+
]),
118+
])
119+
}
120+
121+
func makeOpenMenuItem() -> NSMenu {
122+
let menu = NSMenu()
123+
menu.addItem(withTitle: "Title", action: nil, keyEquivalent: "O")
124+
return menu
125+
}
126+
127+
func applicationWillTerminate(_ aNotification: Notification) {
128+
// Insert code here to tear down your application
129+
}
130+
131+
func applicationSupportsSecureRestorableState(_ app: NSApplication) -> Bool {
132+
return true
133+
}
134+
135+
136+
func applicationShouldHandleReopen(_ sender: NSApplication, hasVisibleWindows flag: Bool) -> Bool {
137+
guard !flag else {
138+
return true
139+
}
140+
141+
if Preferences.showWelcomeVCOnLaunch {
142+
WindowController(kind: .welcome).showWindow(self)
143+
} else {
144+
URLHandler.shared.presentArchiveChooserPanel(insertToRecentItems: true, senderView: nil)
145+
}
146+
147+
return false
148+
}
149+
150+
@objc
151+
func openAboutPanel() {
152+
WindowController(kind: .aboutPanel).showWindow(self)
153+
}
154+
155+
func applicationDockMenu(_ sender: NSApplication) -> NSMenu? {
156+
let items = Preferences.recentlyOpenedFilePaths
157+
guard !items.isEmpty else {
158+
return nil
159+
}
160+
161+
let parentMenu = NSMenu()
162+
let submenu = NSMenu()
163+
let submenuItem = NSMenuItem()
164+
submenuItem.title = "Recents"
165+
submenuItem.submenu = submenu
166+
167+
for (index, item) in items.enumerated() {
168+
let menuItem = NSMenuItem(title: URL(fileURLWithPath: item).lastPathComponent,
169+
action: #selector(openItemFromDockMenu(sender:)),
170+
keyEquivalent: "")
171+
menuItem.tag = index
172+
submenu.addItem(menuItem)
173+
}
174+
175+
parentMenu.addItem(submenuItem)
176+
return parentMenu
177+
}
178+
179+
@objc
180+
func openItemFromDockMenu(sender: NSMenuItem) {
181+
let item = Preferences.recentlyOpenedFilePaths[sender.tag]
182+
URLHandler.shared.handleURLChosen(urlChosen: URL(fileURLWithPath: item),
183+
senderView: nil, insertToRecentItems: true)
184+
}
185+
186+
func application(_ application: NSApplication, open urls: [URL]) {
187+
for url in urls {
188+
URLHandler.shared.handleURLChosen(urlChosen: url,
189+
senderView: nil,
190+
insertToRecentItems: true,
191+
openWelcomeScreenUponError: true)
192+
}
193+
}
194+
}
195+

Samra/Assets.xcassets/.DS_Store

6 KB
Binary file not shown.
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
{
2+
"colors" : [
3+
{
4+
"idiom" : "universal"
5+
}
6+
],
7+
"info" : {
8+
"author" : "xcode",
9+
"version" : 1
10+
}
11+
}

0 commit comments

Comments
 (0)