├── .assets
├── installation.png
└── usage.gif
├── .github
├── FUNDING.yml
└── workflows
│ ├── build.yml
│ └── homebrew.yml
├── .gitignore
├── .swift-version
├── .swiftformat
├── ActionExtension
├── ActionExtension.entitlements
├── ActionRequestHandler.swift
├── Info.plist
└── Media.xcassets
│ ├── Contents.json
│ ├── Symbol.symbolset
│ ├── Contents.json
│ └── doc.badge.gearshape.svg
│ └── TouchBarBezel.colorset
│ └── Contents.json
├── CHANGELOG.md
├── LICENSE
├── README.md
├── SourceEditorExtension
├── GenDiagramInBrowser.swift
├── Info.plist
├── PreferencesCommand.swift
├── SourceEditorExtension.entitlements
└── SourceEditorExtension.swift
├── SwiftPlantUMLApp.xcodeproj
├── project.pbxproj
├── project.xcworkspace
│ ├── contents.xcworkspacedata
│ └── xcshareddata
│ │ ├── IDEWorkspaceChecks.plist
│ │ └── swiftpm
│ │ └── Package.resolved
└── xcshareddata
│ └── xcschemes
│ ├── SourceEditorExtension.xcscheme
│ └── SwiftPlantUMLApp.xcscheme
├── SwiftPlantUMLApp
├── AppDelegate.swift
├── Assets.xcassets
│ ├── AccentColor.colorset
│ │ └── Contents.json
│ ├── AppIcon.appiconset
│ │ ├── 1024.png
│ │ ├── 128.png
│ │ ├── 16.png
│ │ ├── 256.png
│ │ ├── 32.png
│ │ ├── 512.png
│ │ ├── 64.png
│ │ └── Contents.json
│ ├── Color.colorset
│ │ └── Contents.json
│ ├── Contents.json
│ ├── Logo.imageset
│ │ ├── 128.png
│ │ ├── 256.png
│ │ ├── 64.png
│ │ └── Contents.json
│ └── appstore.png
├── Base.lproj
│ └── Main.storyboard
├── ContentView.swift
├── Info.plist
├── Preview Content
│ └── Preview Assets.xcassets
│ │ └── Contents.json
├── SettingsView.swift
├── Shared
│ ├── SettingsModel.swift
│ └── Utils.swift
├── SwiftPlantUMLApp.entitlements
├── SwiftPlantUMLAppApp.swift
├── ThemeView.swift
└── ViewController.swift
└── XPCService
├── Info.plist
├── XPCService.entitlements
├── XPCService.swift
├── XPCServiceProtocol.swift
└── main.swift
/.assets/installation.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/29539e2bd6a45f2e399bb2bcfa0c6f5899481895/.assets/installation.png
--------------------------------------------------------------------------------
/.assets/usage.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/29539e2bd6a45f2e399bb2bcfa0c6f5899481895/.assets/usage.gif
--------------------------------------------------------------------------------
/.github/FUNDING.yml:
--------------------------------------------------------------------------------
1 | github: [marcoeidinger]
2 |
--------------------------------------------------------------------------------
/.github/workflows/build.yml:
--------------------------------------------------------------------------------
1 | name: Build
2 |
3 | on:
4 | push:
5 | branches:
6 | - main
7 | - dev
8 | pull_request:
9 | branches:
10 | - '*'
11 |
12 | jobs:
13 | build:
14 |
15 | runs-on: macos-latest
16 |
17 | steps:
18 | - uses: actions/checkout@v2
19 | - name: Build
20 | run: xcodebuild -scheme SwiftPlantUMLApp -sdk macosx CODE_SIGN_IDENTITY="" clean build
21 |
--------------------------------------------------------------------------------
/.github/workflows/homebrew.yml:
--------------------------------------------------------------------------------
1 | name: Homebrew Bump Formula
2 | on:
3 | release:
4 | types: [published]
5 | workflow_dispatch:
6 |
7 | jobs:
8 | homebrew:
9 | runs-on: macos-latest
10 | steps:
11 | - uses: macauley/action-homebrew-bump-cask@v1
12 | with:
13 | token: ${{ secrets.HOMEBREW_GITHUB_API_TOKEN }}
14 | cask: swiftplantumlapp
15 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # Xcode
2 | #
3 | # gitignore contributors: remember to update Global/Xcode.gitignore, Objective-C.gitignore & Swift.gitignore
4 |
5 | ## User settings
6 | xcuserdata/
7 |
8 | ## compatibility with Xcode 8 and earlier (ignoring not required starting Xcode 9)
9 | *.xcscmblueprint
10 | *.xccheckout
11 |
12 | ## compatibility with Xcode 3 and earlier (ignoring not required starting Xcode 4)
13 | build/
14 | DerivedData/
15 | *.moved-aside
16 | *.pbxuser
17 | !default.pbxuser
18 | *.mode1v3
19 | !default.mode1v3
20 | *.mode2v3
21 | !default.mode2v3
22 | *.perspectivev3
23 | !default.perspectivev3
24 |
25 | ## Obj-C/Swift specific
26 | *.hmap
27 |
28 | ## App packaging
29 | *.ipa
30 | *.dSYM.zip
31 | *.dSYM
32 |
33 | ## Playgrounds
34 | timeline.xctimeline
35 | playground.xcworkspace
36 |
37 | # Swift Package Manager
38 | #
39 | # Add this line if you want to avoid checking in source code from Swift Package Manager dependencies.
40 | # Packages/
41 | # Package.pins
42 | # Package.resolved
43 | # *.xcodeproj
44 | #
45 | # Xcode automatically generates this directory with a .xcworkspacedata file and xcuserdata
46 | # hence it is not needed unless you have added a package configuration file to your project
47 | # .swiftpm
48 |
49 | .build/
50 |
51 | # CocoaPods
52 | #
53 | # We recommend against adding the Pods directory to your .gitignore. However
54 | # you should judge for yourself, the pros and cons are mentioned at:
55 | # https://guides.cocoapods.org/using/using-cocoapods.html#should-i-check-the-pods-directory-into-source-control
56 | #
57 | # Pods/
58 | #
59 | # Add this line if you want to avoid checking in source code from the Xcode workspace
60 | # *.xcworkspace
61 |
62 | # Carthage
63 | #
64 | # Add this line if you want to avoid checking in source code from Carthage dependencies.
65 | # Carthage/Checkouts
66 |
67 | Carthage/Build/
68 |
69 | # Accio dependency management
70 | Dependencies/
71 | .accio/
72 |
73 | # fastlane
74 | #
75 | # It is recommended to not store the screenshots in the git repo.
76 | # Instead, use fastlane to re-generate the screenshots whenever they are needed.
77 | # For more information about the recommended setup visit:
78 | # https://docs.fastlane.tools/best-practices/source-control/#source-control
79 |
80 | fastlane/report.xml
81 | fastlane/Preview.html
82 | fastlane/screenshots/**/*.png
83 | fastlane/test_output
84 |
85 | # Code Injection
86 | #
87 | # After new code Injection tools there's a generated folder /iOSInjectionProject
88 | # https://github.com/johnno1962/injectionforxcode
89 |
90 | iOSInjectionProject/
91 |
--------------------------------------------------------------------------------
/.swift-version:
--------------------------------------------------------------------------------
1 | 5.3
2 |
--------------------------------------------------------------------------------
/.swiftformat:
--------------------------------------------------------------------------------
1 | --header strip
--------------------------------------------------------------------------------
/ActionExtension/ActionExtension.entitlements:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | com.apple.security.app-sandbox
6 |
7 | com.apple.security.files.user-selected.read-only
8 |
9 |
10 |
11 |
--------------------------------------------------------------------------------
/ActionExtension/ActionRequestHandler.swift:
--------------------------------------------------------------------------------
1 | import Foundation
2 | import XPCService
3 |
4 | class ActionRequestHandler: NSObject, NSExtensionRequestHandling {
5 | lazy var connection: NSXPCConnection = {
6 | let connection = NSXPCConnection(serviceName: "us.eidinger.SwiftPlantUMLXPCService")
7 | connection.remoteObjectInterface = NSXPCInterface(with: XPCServiceProtocol.self)
8 | connection.resume()
9 | return connection
10 | }()
11 |
12 | deinit {
13 | connection.invalidate()
14 | }
15 |
16 | func beginRequest(with context: NSExtensionContext) {
17 | // For an Action Extension there will only ever be one extension item.
18 | precondition(context.inputItems.count == 1)
19 | guard let inputItem = context.inputItems[0] as? NSExtensionItem
20 | else { preconditionFailure("Expected an extension item") }
21 |
22 | // The extension item's attachments hold the set of files to process.
23 | guard let inputAttachments = inputItem.attachments
24 | else { preconditionFailure("Expected a valid array of attachments") }
25 | precondition(inputAttachments.isEmpty == false, "Expected at least one attachment")
26 |
27 | // The output of this extension is the existing swift files
28 | guard let inputAttachments = inputItem.attachments
29 | else { preconditionFailure("Expected a valid array of attachments") }
30 |
31 | let handler: (Error) -> Void = { error in
32 | print("remote proxy error: \(error)")
33 | }
34 | let service = connection.remoteObjectProxyWithErrorHandler(handler) as! XPCServiceProtocol
35 | var paths: [String] = []
36 |
37 | // Use a dispatch group to synchronise asynchronous calls to loadInPlaceFileRepresentation.
38 | let dispatchGroup = DispatchGroup()
39 |
40 | for attachment in inputAttachments {
41 | dispatchGroup.enter()
42 |
43 | attachment.loadInPlaceFileRepresentation(forTypeIdentifier: "public.swift-source") { url, _, _ in
44 | if let url = url {
45 | paths.append(url.path)
46 | }
47 |
48 | dispatchGroup.leave()
49 | }
50 | }
51 |
52 | dispatchGroup.notify(queue: DispatchQueue.main) {
53 | service.generateDiagram(for: paths) {
54 | context.completeRequest(returningItems: [inputItem], completionHandler: nil)
55 | }
56 | }
57 | }
58 | }
59 |
--------------------------------------------------------------------------------
/ActionExtension/Info.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | CFBundleIconFile
6 |
7 | NSExtension
8 |
9 | NSExtensionAttributes
10 |
11 | NSExtensionActivationRule
12 | SUBQUERY (
13 | extensionItems,
14 | $extensionItem,
15 | SUBQUERY (
16 | $extensionItem.attachments,
17 | $attachment,
18 | ANY $attachment.registeredTypeIdentifiers UTI-CONFORMS-TO "public.swift-source"
19 | ).@count == $extensionItem.attachments.@count
20 | ).@count == 1
21 | NSExtensionServiceAllowsFinderPreviewItem
22 |
23 | NSExtensionServiceAllowsTouchBarItem
24 |
25 | NSExtensionServiceFinderPreviewIconName
26 | Symbol
27 | NSExtensionServiceRoleType
28 | NSExtensionServiceRoleTypeEditor
29 | NSExtensionServiceTouchBarBezelColorName
30 | TouchBarBezel
31 | NSExtensionServiceTouchBarIconName
32 | Symbol
33 |
34 | NSExtensionPointIdentifier
35 | com.apple.services
36 | NSExtensionPrincipalClass
37 | $(PRODUCT_MODULE_NAME).ActionRequestHandler
38 |
39 |
40 |
41 |
--------------------------------------------------------------------------------
/ActionExtension/Media.xcassets/Contents.json:
--------------------------------------------------------------------------------
1 | {
2 | "info" : {
3 | "author" : "xcode",
4 | "version" : 1
5 | }
6 | }
7 |
--------------------------------------------------------------------------------
/ActionExtension/Media.xcassets/Symbol.symbolset/Contents.json:
--------------------------------------------------------------------------------
1 | {
2 | "info" : {
3 | "author" : "xcode",
4 | "version" : 1
5 | },
6 | "symbols" : [
7 | {
8 | "filename" : "doc.badge.gearshape.svg",
9 | "idiom" : "universal"
10 | },
11 | {
12 | "appearances" : [
13 | {
14 | "appearance" : "luminosity",
15 | "value" : "light"
16 | }
17 | ],
18 | "idiom" : "universal"
19 | },
20 | {
21 | "appearances" : [
22 | {
23 | "appearance" : "luminosity",
24 | "value" : "dark"
25 | }
26 | ],
27 | "idiom" : "universal"
28 | }
29 | ]
30 | }
31 |
--------------------------------------------------------------------------------
/ActionExtension/Media.xcassets/Symbol.symbolset/doc.badge.gearshape.svg:
--------------------------------------------------------------------------------
1 |
2 |
3 |
6 |
103 |
--------------------------------------------------------------------------------
/ActionExtension/Media.xcassets/TouchBarBezel.colorset/Contents.json:
--------------------------------------------------------------------------------
1 | {
2 | "info" : {
3 | "version" : 1,
4 | "author" : "xcode"
5 | },
6 | "colors" : [
7 | {
8 | "idiom" : "universal",
9 | "color" : {
10 | "reference" : "systemPurpleColor"
11 | }
12 | }
13 | ]
14 | }
--------------------------------------------------------------------------------
/CHANGELOG.md:
--------------------------------------------------------------------------------
1 | # [1.6.0](https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/releases/tag/1.6.0)
2 |
3 | ## Features
4 |
5 | - support `package` access level ([SE-0386](https://github.com/apple/swift-evolution/blob/main/proposals/0386-package-access-modifier.md)) introduced in Swift 5.9
6 |
7 | ## Internal Dependencies
8 |
9 | uses [SwiftPlantUML@0.8.0](https://github.com/MarcoEidinger/SwiftPlantUML/releases/tag/0.8.0)
10 |
11 | # [1.5.1](https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/releases/tag/1.5.1)
12 |
13 | ## Bug Fixes
14 |
15 | - Cannot define nested types in extensions and cannot extend nested types ([Issue #26](https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/issues/26))
16 |
17 | # [1.5.0](https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/releases/tag/1.5.0)
18 |
19 | ## Features
20 |
21 | - Select one or more Swift files in your finder and then use a quick action to view a class diagram in your browser.
22 |
23 |
24 |
25 |
26 | # [1.4.1](https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/releases/tag/1.4.1)
27 |
28 | ## Bug Fixes
29 |
30 | - Fix previous installation error `“SwiftPlantUMLApp” is damaged and can’t be opened. You should move it to the Bin.` ([Issue #20](https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/issues/20))
31 |
32 | # [1.4.0](https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/releases/tag/1.4.0)
33 |
34 | ## Features
35 |
36 | - [X] Able to merge extensions into main type.
37 |
38 |
39 |
40 | - [X] Able to choose a theme
41 |
42 |
43 |
44 | ## Improvements
45 |
46 | - [X] Show Nested Types
47 |
48 |
49 | - [X] Several Bug Fixes
50 |
51 | ## Internal Dependencies
52 |
53 | uses [SwiftPlantUML@0.7.0](https://github.com/MarcoEidinger/SwiftPlantUML/releases/tag/0.7.0)
54 |
55 | # [1.3.0](https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/releases/tag/1.3.0)
56 |
57 | ## Features
58 |
59 | - [X] Able to set preferences to influence which code shall be considered for diagram generation.
60 |
61 |
62 |
63 |
64 |
65 |
66 |
67 | ## Improvements
68 |
69 | - [X] New Look & Feel (incl. logo)
70 |
71 |
72 |
73 | ## Internal Dependencies
74 |
75 | uses [SwiftPlantUML@0.6.0](https://github.com/MarcoEidinger/SwiftPlantUML/releases/tag/0.6.0)
76 |
77 | # [1.2.2](https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/releases/tag/1.2.2)
78 |
79 | ## Improvements
80 |
81 | - [X] Faster launch of diagram in browser (also no longer that pesky leading `.` in the diagram textual description).
82 |
83 | ## Internal Dependencies
84 |
85 | uses [SwiftPlantUML@0.6.0](https://github.com/MarcoEidinger/SwiftPlantUML/releases/tag/0.6.0)
86 |
87 | # [1.2.1](https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/releases/tag/1.2.1)
88 |
89 | ## Bug Fixes
90 |
91 | - [X] Diagram in browser will open correctly as invalid prefix `type=png&plantuml=` in script was removed.
92 |
93 | ## Internal Dependencies
94 |
95 | uses [SwiftPlantUML@0.5.2](https://github.com/MarcoEidinger/SwiftPlantUML/releases/tag/0.5.2)
96 |
97 | # [1.2.0](https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/releases/tag/1.2.0)
98 |
99 | ## Features
100 |
101 | - [X] 👀 `Open` elements and members will now be rendered while this was
102 | previously not the case.
103 | - [X] ⬆️ Change of order for elements and their inheritance/extensions relationships.
104 | - before: subclass points down to superclass
105 | - now: superclass on top and subclass points up to superclass
106 |
107 | ## Internal Dependencies
108 |
109 | uses [SwiftPlantUML@0.5.0](https://github.com/MarcoEidinger/SwiftPlantUML/releases/tag/0.5.0)
110 |
111 | # [1.1.0](https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/releases/tag/1.1.0)
112 |
113 | ## Features
114 |
115 | - [X] 🖥️ Use on macOS 10.15.7 and not only on macOS 11
116 |
117 | ## Internal Dependencies
118 |
119 | uses [SwiftPlantUML@0.4.0](https://github.com/MarcoEidinger/SwiftPlantUML/releases/tag/0.4.0)
120 |
121 | # [1.0.0](https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/releases/tag/1.0.0)
122 |
123 | ## Features
124 |
125 | - [X] 📊 Create class diagram from Swift file
126 | - [X] 🔦 Create class diagram from selected Swift code
127 |
128 | ## Internal Dependencies
129 |
130 | uses [SwiftPlantUML@0.2.0](https://github.com/MarcoEidinger/SwiftPlantUML/releases/tag/0.2.0)
131 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2021 MarcoEidinger
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | 
6 | [](#)
7 | [](http://twitter.com/MarcoEidinger)
8 | # SwiftPlantUML.app
9 |
10 | Generate and view a class diagram for Swift code in Xcode or from the Finder.
11 |
12 | Use the hosting macOS application to configure the diagram visualization.
13 |
14 | The Source Editor Extension (as well as the Action extension) makes use of [`SwiftPlantUML`](https://github.com/MarcoEidinger/SwiftPlantUML) Swift package.
15 |
16 | To generate a large diagram from a project with Swift files across folders then I recommend using `SwiftPlantUML` as a command-line tool.
17 |
18 | ## Features
19 |
20 | ### Xcode
21 | - [X] 📊 Create class diagram from Swift file
22 | - [X] 🔦 Create class diagram from selected Swift code
23 |
24 | 
25 |
26 | ### Finder
27 | - [X] 📊 Create class diagram from selected Swift file(s)
28 |
29 | https://user-images.githubusercontent.com/4176826/218329052-b03ec650-d845-46a2-a31b-6d3817add52a.mp4
30 |
31 | ## Example
32 |
33 | 
34 |
35 | ## Install
36 |
37 | Homebrew
38 |
39 | ```bash
40 | brew install swiftplantumlapp
41 | ```
42 |
43 |
44 |
45 | *Alternative*
46 | - Download latest *SwiftPlantUML* package from the [Releases](https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/releases).
47 | - Copy *SwiftPlantUML* to your *Applications* folder.
48 |
49 | ## Enable Extension
50 | - Launch *SwiftPlantUML*.
51 |
52 |
53 |
54 | - To use in **Xcode**: enable extension in System Preferences > Extensions > Xcode Source Editor > select SwiftPlantUML
55 |
56 | 
57 |
58 | - To use in **Finder**: enable extension in System Preferences > Extensions > Finder > select Open Swift Class Diagram
59 |
60 | 
61 |
62 | ## Configure
63 |
64 | *Optional*:
65 |
66 |
67 |
68 |
69 |
70 |
71 |
72 | ## Troubleshooting
73 |
74 | ### The command "Open editable diagram in browser" is still busy
75 |
76 | Xcode Source Code Extension initialization might take up ~ 30 seconds on initial launch.
77 |
78 | If the prompt does not appear within 60 seconds
79 |
80 | 
81 |
82 | then check for a crash report related to XPC service in Console app of your MacOS.
83 |
84 |
85 |
86 | If you see such crash report related to `fatal error: Loading sourcekitd.framework/Versions/A/sourcekitd failed` please check the installation path of Xcode. If it's installed under `/Applications/Xcode.app`, please run:
87 |
88 | ```
89 | sudo xcode-select -s /Applications/Xcode.app/Contents/Developer
90 | ```
91 |
92 | If it's installed elsewhere, please replace the `/Applications/Xcode.app` path in the command above with the location where you've installed Xcode.
93 |
94 |
95 | ## Technical Details
96 |
97 | This Source Editor Extension makes use of XPC service to run the app sandboxed and use `SwiftPlantUML` (and its dependency `SourceKitten`). Source Editor Extensions using `SourceKitten` (either directly or indirectly) have to either run in a non-sandboxed app (and could not be distributed via the App Store) or use XPC service to outsource the use of `SourceKitten` to a different process.
98 |
99 | # Acknowledgements
100 |
101 | These awesome blog posts helped me to dive into Xcode Source Editor Extensions and XPC services
102 |
103 | - https://www.vadimbulavin.com/xcode-source-editor-extension-tutorial/
104 | - https://nshipster.com/xcode-source-extensions/
105 | - https://ilya.puchka.me/xcode-source-editor-extension-superpowered-with-sourcekitten/
106 | - https://www.objc.io/issues/14-mac/xpc/
107 |
--------------------------------------------------------------------------------
/SourceEditorExtension/GenDiagramInBrowser.swift:
--------------------------------------------------------------------------------
1 | import ApplicationServices
2 | import Foundation
3 | import XcodeKit
4 |
5 | class GenDiagramInBrowser: NSObject, XCSourceEditorCommand {
6 | lazy var connection: NSXPCConnection = {
7 | let connection = NSXPCConnection(serviceName: "us.eidinger.SwiftPlantUMLXPCService")
8 | connection.remoteObjectInterface = NSXPCInterface(with: XPCServiceProtocol.self)
9 | connection.resume()
10 | return connection
11 | }()
12 |
13 | deinit {
14 | connection.invalidate()
15 | }
16 |
17 | func perform(with invocation: XCSourceEditorCommandInvocation, completionHandler: @escaping (Error?) -> Void) {
18 | let handler: (Error) -> Void = { error in
19 | print("remote proxy error: \(error)")
20 | }
21 | let service = connection.remoteObjectProxyWithErrorHandler(handler) as! XPCServiceProtocol
22 |
23 | let code = determineRelevantCodeForDiagram(invocation: invocation)
24 |
25 | service.generateDiagram(from: code) {
26 | completionHandler(nil)
27 | }
28 | }
29 |
30 | func determineRelevantCodeForDiagram(invocation: XCSourceEditorCommandInvocation) -> String {
31 | // 1. all lines of current source file in editor
32 | var code = invocation.buffer.completeBuffer
33 | // 2. check if specific lines were selected
34 | var selectedCode = ""
35 | if invocation.buffer.selections.count > 0 {
36 | for sel in invocation.buffer.selections {
37 | guard let selection = sel as? XCSourceTextRange else { continue }
38 | guard selection.start.line != selection.end.line else { continue }
39 | let selectedText = (selection.start.line ..< selection.end.line).map { invocation.buffer.lines[$0] as? String }.compactMap { $0 }.joined()
40 | if selectedText.count > 0 {
41 | selectedCode += selectedText
42 | }
43 | }
44 | if selectedCode.count > 0 {
45 | code = selectedCode
46 | }
47 | }
48 | return code
49 | }
50 | }
51 |
--------------------------------------------------------------------------------
/SourceEditorExtension/Info.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | CFBundleDevelopmentRegion
6 | $(DEVELOPMENT_LANGUAGE)
7 | CFBundleDisplayName
8 | SwiftPlantUML
9 | CFBundleExecutable
10 | $(EXECUTABLE_NAME)
11 | CFBundleIdentifier
12 | $(PRODUCT_BUNDLE_IDENTIFIER)
13 | CFBundleInfoDictionaryVersion
14 | 6.0
15 | CFBundleName
16 | SwiftPlantUML
17 | CFBundlePackageType
18 | XPC!
19 | CFBundleShortVersionString
20 | $(MARKETING_VERSION)
21 | CFBundleVersion
22 | $(CURRENT_PROJECT_VERSION)
23 | LSMinimumSystemVersion
24 | $(MACOSX_DEPLOYMENT_TARGET)
25 | NSExtension
26 |
27 | NSExtensionAttributes
28 |
29 | XCSourceEditorCommandDefinitions
30 |
31 |
32 | XCSourceEditorCommandClassName
33 | $(PRODUCT_MODULE_NAME).GenDiagramInBrowser
34 | XCSourceEditorCommandIdentifier
35 | $(PRODUCT_BUNDLE_IDENTIFIER).GenDiagramInBrowser
36 | XCSourceEditorCommandName
37 | Open editable diagram in browser
38 |
39 |
40 | XCSourceEditorCommandClassName
41 | $(PRODUCT_MODULE_NAME).PreferencesCommand
42 | XCSourceEditorCommandIdentifier
43 | $(PRODUCT_MODULE_NAME).PreferencesCommand
44 | XCSourceEditorCommandName
45 | Preferences
46 |
47 |
48 | XCSourceEditorExtensionPrincipalClass
49 | $(PRODUCT_MODULE_NAME).SourceEditorExtension
50 |
51 | NSExtensionPointIdentifier
52 | com.apple.dt.Xcode.extension.source-editor
53 |
54 | NSHumanReadableCopyright
55 | Copyright © 2021-2024 Marco Eidinger. All rights reserved.
56 |
57 |
58 |
--------------------------------------------------------------------------------
/SourceEditorExtension/PreferencesCommand.swift:
--------------------------------------------------------------------------------
1 | import AppKit
2 | import XcodeKit
3 |
4 | class PreferencesCommand: NSObject, XCSourceEditorCommand {
5 | func perform(with _: XCSourceEditorCommandInvocation, completionHandler: @escaping (Error?) -> Void) {
6 | NSWorkspace.shared.open(URL(string: "swiftplantumlapp://preferences")!)
7 | completionHandler(nil)
8 | }
9 | }
10 |
--------------------------------------------------------------------------------
/SourceEditorExtension/SourceEditorExtension.entitlements:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | com.apple.security.app-sandbox
6 |
7 | com.apple.security.files.user-selected.read-only
8 |
9 |
10 |
11 |
--------------------------------------------------------------------------------
/SourceEditorExtension/SourceEditorExtension.swift:
--------------------------------------------------------------------------------
1 | import Foundation
2 | import XcodeKit
3 |
4 | class SourceEditorExtension: NSObject, XCSourceEditorExtension {
5 | /*
6 | func extensionDidFinishLaunching() {
7 | // If your extension needs to do any work at launch, implement this optional method.
8 | }
9 | */
10 |
11 | /*
12 | var commandDefinitions: [[XCSourceEditorCommandDefinitionKey: Any]] {
13 | // If your extension needs to return a collection of command definitions that differs from those in its Info.plist, implement this optional property getter.
14 | return []
15 | }
16 | */
17 | }
18 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp.xcodeproj/project.pbxproj:
--------------------------------------------------------------------------------
1 | // !$*UTF8*$!
2 | {
3 | archiveVersion = 1;
4 | classes = {
5 | };
6 | objectVersion = 53;
7 | objects = {
8 |
9 | /* Begin PBXBuildFile section */
10 | 1919C9C8296B48EA00804361 /* SwiftPlantUMLFramework in Frameworks */ = {isa = PBXBuildFile; productRef = 1919C9C7296B48EA00804361 /* SwiftPlantUMLFramework */; };
11 | 1919C9CA296B48FC00804361 /* SwiftPlantUMLFramework in Frameworks */ = {isa = PBXBuildFile; productRef = 1919C9C9296B48FC00804361 /* SwiftPlantUMLFramework */; };
12 | 192CDFCF2971F5F400CF914F /* Cocoa.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 8A73D8E225CAE9AA008DDEA3 /* Cocoa.framework */; };
13 | 192CDFD22971F5F400CF914F /* Media.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 192CDFD12971F5F400CF914F /* Media.xcassets */; };
14 | 192CDFD62971F5F400CF914F /* ActionRequestHandler.swift in Sources */ = {isa = PBXBuildFile; fileRef = 192CDFD52971F5F400CF914F /* ActionRequestHandler.swift */; };
15 | 192CDFDB2971F5F400CF914F /* ActionExtension.appex in Embed Foundation Extensions */ = {isa = PBXBuildFile; fileRef = 192CDFCE2971F5F400CF914F /* ActionExtension.appex */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
16 | 192CDFE02971F60B00CF914F /* XPCService.xpc in CopyFiles */ = {isa = PBXBuildFile; fileRef = 8A73D8FA25CAE9DD008DDEA3 /* XPCService.xpc */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
17 | 192CDFE52971F6DB00CF914F /* XPCServiceProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A73D91825CAEA8F008DDEA3 /* XPCServiceProtocol.swift */; };
18 | 19E902A029737244002212BA /* SwiftPlantUMLFramework in Frameworks */ = {isa = PBXBuildFile; productRef = 19E9029F29737244002212BA /* SwiftPlantUMLFramework */; };
19 | 8A1EFEF42735DEC000BD6F69 /* Utils.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A1EFEF32735DEC000BD6F69 /* Utils.swift */; };
20 | 8A30356F279BA55700042D19 /* PreferencesCommand.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A30356E279BA55700042D19 /* PreferencesCommand.swift */; };
21 | 8A319170261911B900540446 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A31916F261911B900540446 /* AppDelegate.swift */; };
22 | 8A3191742619123F00540446 /* ViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A3191732619123F00540446 /* ViewController.swift */; };
23 | 8A3191792619124B00540446 /* Main.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 8A3191772619124B00540446 /* Main.storyboard */; };
24 | 8A42F198279B6B95003BCDB4 /* SettingsView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A42F197279B6B95003BCDB4 /* SettingsView.swift */; };
25 | 8A73D8CC25CAE974008DDEA3 /* SwiftPlantUMLAppApp.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A73D8CB25CAE974008DDEA3 /* SwiftPlantUMLAppApp.swift */; };
26 | 8A73D8CE25CAE974008DDEA3 /* ContentView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A73D8CD25CAE974008DDEA3 /* ContentView.swift */; };
27 | 8A73D8D025CAE978008DDEA3 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 8A73D8CF25CAE978008DDEA3 /* Assets.xcassets */; };
28 | 8A73D8D325CAE978008DDEA3 /* Preview Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 8A73D8D225CAE978008DDEA3 /* Preview Assets.xcassets */; };
29 | 8A73D8E325CAE9AA008DDEA3 /* Cocoa.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 8A73D8E225CAE9AA008DDEA3 /* Cocoa.framework */; };
30 | 8A73D8E825CAE9AA008DDEA3 /* SourceEditorExtension.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A73D8E725CAE9AA008DDEA3 /* SourceEditorExtension.swift */; };
31 | 8A73D8EA25CAE9AA008DDEA3 /* GenDiagramInBrowser.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A73D8E925CAE9AA008DDEA3 /* GenDiagramInBrowser.swift */; };
32 | 8A73D8EF25CAE9AA008DDEA3 /* SourceEditorExtension.appex in Embed Foundation Extensions */ = {isa = PBXBuildFile; fileRef = 8A73D8E025CAE9AA008DDEA3 /* SourceEditorExtension.appex */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
33 | 8A73D90525CAE9DD008DDEA3 /* XPCService.xpc in Embed XPC Services */ = {isa = PBXBuildFile; fileRef = 8A73D8FA25CAE9DD008DDEA3 /* XPCService.xpc */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
34 | 8A73D91425CAEA78008DDEA3 /* main.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A73D91325CAEA78008DDEA3 /* main.swift */; };
35 | 8A73D91925CAEA8F008DDEA3 /* XPCServiceProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A73D91825CAEA8F008DDEA3 /* XPCServiceProtocol.swift */; };
36 | 8A73D91E25CAEA9E008DDEA3 /* XPCService.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A73D91D25CAEA9E008DDEA3 /* XPCService.swift */; };
37 | 8A73D92825CAEB4F008DDEA3 /* XPCService.xpc in CopyFiles */ = {isa = PBXBuildFile; fileRef = 8A73D8FA25CAE9DD008DDEA3 /* XPCService.xpc */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
38 | 8A9E73BF25CAEBAF00327AD1 /* XPCServiceProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A73D91825CAEA8F008DDEA3 /* XPCServiceProtocol.swift */; };
39 | 8A9E73CA25CAEE2B00327AD1 /* XcodeKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 8A73D8E425CAE9AA008DDEA3 /* XcodeKit.framework */; };
40 | 8A9E73CB25CAEE2B00327AD1 /* XcodeKit.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = 8A73D8E425CAE9AA008DDEA3 /* XcodeKit.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; };
41 | 8A9F8E68273ED22700D29025 /* Utils.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A1EFEF32735DEC000BD6F69 /* Utils.swift */; };
42 | 8A9F8E6E273EECF300D29025 /* SettingsModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A9F8E6D273EECF300D29025 /* SettingsModel.swift */; };
43 | 8A9F8E6F273EECF300D29025 /* SettingsModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 8A9F8E6D273EECF300D29025 /* SettingsModel.swift */; };
44 | /* End PBXBuildFile section */
45 |
46 | /* Begin PBXContainerItemProxy section */
47 | 192CDFD92971F5F400CF914F /* PBXContainerItemProxy */ = {
48 | isa = PBXContainerItemProxy;
49 | containerPortal = 8A73D8C025CAE974008DDEA3 /* Project object */;
50 | proxyType = 1;
51 | remoteGlobalIDString = 192CDFCD2971F5F400CF914F;
52 | remoteInfo = ActionExtension;
53 | };
54 | 192CDFE32971F68700CF914F /* PBXContainerItemProxy */ = {
55 | isa = PBXContainerItemProxy;
56 | containerPortal = 8A73D8C025CAE974008DDEA3 /* Project object */;
57 | proxyType = 1;
58 | remoteGlobalIDString = 8A73D8F925CAE9DD008DDEA3;
59 | remoteInfo = XPCService;
60 | };
61 | 8A73D8ED25CAE9AA008DDEA3 /* PBXContainerItemProxy */ = {
62 | isa = PBXContainerItemProxy;
63 | containerPortal = 8A73D8C025CAE974008DDEA3 /* Project object */;
64 | proxyType = 1;
65 | remoteGlobalIDString = 8A73D8DF25CAE9AA008DDEA3;
66 | remoteInfo = SourceEditorExtension;
67 | };
68 | 8A73D90325CAE9DD008DDEA3 /* PBXContainerItemProxy */ = {
69 | isa = PBXContainerItemProxy;
70 | containerPortal = 8A73D8C025CAE974008DDEA3 /* Project object */;
71 | proxyType = 1;
72 | remoteGlobalIDString = 8A73D8F925CAE9DD008DDEA3;
73 | remoteInfo = XPCService;
74 | };
75 | 8A73D92525CAEB2B008DDEA3 /* PBXContainerItemProxy */ = {
76 | isa = PBXContainerItemProxy;
77 | containerPortal = 8A73D8C025CAE974008DDEA3 /* Project object */;
78 | proxyType = 1;
79 | remoteGlobalIDString = 8A73D8F925CAE9DD008DDEA3;
80 | remoteInfo = XPCService;
81 | };
82 | /* End PBXContainerItemProxy section */
83 |
84 | /* Begin PBXCopyFilesBuildPhase section */
85 | 192CDFDF2971F5FF00CF914F /* CopyFiles */ = {
86 | isa = PBXCopyFilesBuildPhase;
87 | buildActionMask = 2147483647;
88 | dstPath = "$(CONTENTS_FOLDER_PATH)/XPCServices";
89 | dstSubfolderSpec = 16;
90 | files = (
91 | 192CDFE02971F60B00CF914F /* XPCService.xpc in CopyFiles */,
92 | );
93 | runOnlyForDeploymentPostprocessing = 0;
94 | };
95 | 8A73D8F325CAE9AA008DDEA3 /* Embed Foundation Extensions */ = {
96 | isa = PBXCopyFilesBuildPhase;
97 | buildActionMask = 2147483647;
98 | dstPath = "";
99 | dstSubfolderSpec = 13;
100 | files = (
101 | 192CDFDB2971F5F400CF914F /* ActionExtension.appex in Embed Foundation Extensions */,
102 | 8A73D8EF25CAE9AA008DDEA3 /* SourceEditorExtension.appex in Embed Foundation Extensions */,
103 | );
104 | name = "Embed Foundation Extensions";
105 | runOnlyForDeploymentPostprocessing = 0;
106 | };
107 | 8A73D90925CAE9DD008DDEA3 /* Embed XPC Services */ = {
108 | isa = PBXCopyFilesBuildPhase;
109 | buildActionMask = 2147483647;
110 | dstPath = "$(CONTENTS_FOLDER_PATH)/XPCServices";
111 | dstSubfolderSpec = 16;
112 | files = (
113 | 8A73D90525CAE9DD008DDEA3 /* XPCService.xpc in Embed XPC Services */,
114 | );
115 | name = "Embed XPC Services";
116 | runOnlyForDeploymentPostprocessing = 0;
117 | };
118 | 8A73D92725CAEB3B008DDEA3 /* CopyFiles */ = {
119 | isa = PBXCopyFilesBuildPhase;
120 | buildActionMask = 2147483647;
121 | dstPath = "$(CONTENTS_FOLDER_PATH)/XPCServices";
122 | dstSubfolderSpec = 16;
123 | files = (
124 | 8A73D92825CAEB4F008DDEA3 /* XPCService.xpc in CopyFiles */,
125 | );
126 | runOnlyForDeploymentPostprocessing = 0;
127 | };
128 | 8A9E73CC25CAEE2B00327AD1 /* Embed Frameworks */ = {
129 | isa = PBXCopyFilesBuildPhase;
130 | buildActionMask = 2147483647;
131 | dstPath = "";
132 | dstSubfolderSpec = 10;
133 | files = (
134 | 8A9E73CB25CAEE2B00327AD1 /* XcodeKit.framework in Embed Frameworks */,
135 | );
136 | name = "Embed Frameworks";
137 | runOnlyForDeploymentPostprocessing = 0;
138 | };
139 | /* End PBXCopyFilesBuildPhase section */
140 |
141 | /* Begin PBXFileReference section */
142 | 192CDFCE2971F5F400CF914F /* ActionExtension.appex */ = {isa = PBXFileReference; explicitFileType = "wrapper.app-extension"; includeInIndex = 0; path = ActionExtension.appex; sourceTree = BUILT_PRODUCTS_DIR; };
143 | 192CDFD12971F5F400CF914F /* Media.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Media.xcassets; sourceTree = ""; };
144 | 192CDFD52971F5F400CF914F /* ActionRequestHandler.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ActionRequestHandler.swift; sourceTree = ""; };
145 | 192CDFD72971F5F400CF914F /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; };
146 | 192CDFD82971F5F400CF914F /* ActionExtension.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = ActionExtension.entitlements; sourceTree = ""; };
147 | 8A1EFEF32735DEC000BD6F69 /* Utils.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Utils.swift; sourceTree = ""; };
148 | 8A30356E279BA55700042D19 /* PreferencesCommand.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = PreferencesCommand.swift; sourceTree = ""; };
149 | 8A31916F261911B900540446 /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = ""; };
150 | 8A3191732619123F00540446 /* ViewController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ViewController.swift; sourceTree = ""; };
151 | 8A3191782619124B00540446 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/Main.storyboard; sourceTree = ""; };
152 | 8A42F197279B6B95003BCDB4 /* SettingsView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SettingsView.swift; sourceTree = ""; };
153 | 8A73D8C825CAE974008DDEA3 /* SwiftPlantUMLApp.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = SwiftPlantUMLApp.app; sourceTree = BUILT_PRODUCTS_DIR; };
154 | 8A73D8CB25CAE974008DDEA3 /* SwiftPlantUMLAppApp.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SwiftPlantUMLAppApp.swift; sourceTree = ""; };
155 | 8A73D8CD25CAE974008DDEA3 /* ContentView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ContentView.swift; sourceTree = ""; };
156 | 8A73D8CF25CAE978008DDEA3 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = ""; };
157 | 8A73D8D225CAE978008DDEA3 /* Preview Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = "Preview Assets.xcassets"; sourceTree = ""; };
158 | 8A73D8D425CAE978008DDEA3 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; };
159 | 8A73D8D525CAE978008DDEA3 /* SwiftPlantUMLApp.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = SwiftPlantUMLApp.entitlements; sourceTree = ""; };
160 | 8A73D8E025CAE9AA008DDEA3 /* SourceEditorExtension.appex */ = {isa = PBXFileReference; explicitFileType = "wrapper.app-extension"; includeInIndex = 0; path = SourceEditorExtension.appex; sourceTree = BUILT_PRODUCTS_DIR; };
161 | 8A73D8E225CAE9AA008DDEA3 /* Cocoa.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Cocoa.framework; path = System/Library/Frameworks/Cocoa.framework; sourceTree = SDKROOT; };
162 | 8A73D8E425CAE9AA008DDEA3 /* XcodeKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = XcodeKit.framework; path = Library/Frameworks/XcodeKit.framework; sourceTree = DEVELOPER_DIR; };
163 | 8A73D8E725CAE9AA008DDEA3 /* SourceEditorExtension.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SourceEditorExtension.swift; sourceTree = ""; };
164 | 8A73D8E925CAE9AA008DDEA3 /* GenDiagramInBrowser.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = GenDiagramInBrowser.swift; sourceTree = ""; };
165 | 8A73D8EB25CAE9AA008DDEA3 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; };
166 | 8A73D8EC25CAE9AA008DDEA3 /* SourceEditorExtension.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = SourceEditorExtension.entitlements; sourceTree = ""; };
167 | 8A73D8FA25CAE9DD008DDEA3 /* XPCService.xpc */ = {isa = PBXFileReference; explicitFileType = "wrapper.xpc-service"; includeInIndex = 0; path = XPCService.xpc; sourceTree = BUILT_PRODUCTS_DIR; };
168 | 8A73D90225CAE9DD008DDEA3 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; };
169 | 8A73D91325CAEA78008DDEA3 /* main.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = main.swift; sourceTree = ""; };
170 | 8A73D91825CAEA8F008DDEA3 /* XPCServiceProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = XPCServiceProtocol.swift; sourceTree = ""; };
171 | 8A73D91D25CAEA9E008DDEA3 /* XPCService.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = XPCService.swift; sourceTree = ""; };
172 | 8A9F8E69273ED6D300D29025 /* XPCService.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = XPCService.entitlements; sourceTree = ""; };
173 | 8A9F8E6D273EECF300D29025 /* SettingsModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SettingsModel.swift; sourceTree = ""; };
174 | /* End PBXFileReference section */
175 |
176 | /* Begin PBXFrameworksBuildPhase section */
177 | 192CDFCB2971F5F400CF914F /* Frameworks */ = {
178 | isa = PBXFrameworksBuildPhase;
179 | buildActionMask = 2147483647;
180 | files = (
181 | 19E902A029737244002212BA /* SwiftPlantUMLFramework in Frameworks */,
182 | 192CDFCF2971F5F400CF914F /* Cocoa.framework in Frameworks */,
183 | );
184 | runOnlyForDeploymentPostprocessing = 0;
185 | };
186 | 8A73D8C525CAE974008DDEA3 /* Frameworks */ = {
187 | isa = PBXFrameworksBuildPhase;
188 | buildActionMask = 2147483647;
189 | files = (
190 | 1919C9C8296B48EA00804361 /* SwiftPlantUMLFramework in Frameworks */,
191 | );
192 | runOnlyForDeploymentPostprocessing = 0;
193 | };
194 | 8A73D8DD25CAE9AA008DDEA3 /* Frameworks */ = {
195 | isa = PBXFrameworksBuildPhase;
196 | buildActionMask = 2147483647;
197 | files = (
198 | 8A73D8E325CAE9AA008DDEA3 /* Cocoa.framework in Frameworks */,
199 | 8A9E73CA25CAEE2B00327AD1 /* XcodeKit.framework in Frameworks */,
200 | );
201 | runOnlyForDeploymentPostprocessing = 0;
202 | };
203 | 8A73D8F725CAE9DD008DDEA3 /* Frameworks */ = {
204 | isa = PBXFrameworksBuildPhase;
205 | buildActionMask = 2147483647;
206 | files = (
207 | 1919C9CA296B48FC00804361 /* SwiftPlantUMLFramework in Frameworks */,
208 | );
209 | runOnlyForDeploymentPostprocessing = 0;
210 | };
211 | /* End PBXFrameworksBuildPhase section */
212 |
213 | /* Begin PBXGroup section */
214 | 192CDFD02971F5F400CF914F /* ActionExtension */ = {
215 | isa = PBXGroup;
216 | children = (
217 | 192CDFD12971F5F400CF914F /* Media.xcassets */,
218 | 192CDFD52971F5F400CF914F /* ActionRequestHandler.swift */,
219 | 192CDFD72971F5F400CF914F /* Info.plist */,
220 | 192CDFD82971F5F400CF914F /* ActionExtension.entitlements */,
221 | );
222 | path = ActionExtension;
223 | sourceTree = "";
224 | };
225 | 8A73D8BF25CAE974008DDEA3 = {
226 | isa = PBXGroup;
227 | children = (
228 | 8A73D8CA25CAE974008DDEA3 /* SwiftPlantUMLApp */,
229 | 8A73D8E625CAE9AA008DDEA3 /* SourceEditorExtension */,
230 | 8A73D8FB25CAE9DD008DDEA3 /* XPCService */,
231 | 192CDFD02971F5F400CF914F /* ActionExtension */,
232 | 8A73D8E125CAE9AA008DDEA3 /* Frameworks */,
233 | 8A73D8C925CAE974008DDEA3 /* Products */,
234 | );
235 | sourceTree = "";
236 | };
237 | 8A73D8C925CAE974008DDEA3 /* Products */ = {
238 | isa = PBXGroup;
239 | children = (
240 | 8A73D8C825CAE974008DDEA3 /* SwiftPlantUMLApp.app */,
241 | 8A73D8E025CAE9AA008DDEA3 /* SourceEditorExtension.appex */,
242 | 8A73D8FA25CAE9DD008DDEA3 /* XPCService.xpc */,
243 | 192CDFCE2971F5F400CF914F /* ActionExtension.appex */,
244 | );
245 | name = Products;
246 | sourceTree = "";
247 | };
248 | 8A73D8CA25CAE974008DDEA3 /* SwiftPlantUMLApp */ = {
249 | isa = PBXGroup;
250 | children = (
251 | 8A31916F261911B900540446 /* AppDelegate.swift */,
252 | 8A3191732619123F00540446 /* ViewController.swift */,
253 | 8A3191772619124B00540446 /* Main.storyboard */,
254 | 8A73D8CB25CAE974008DDEA3 /* SwiftPlantUMLAppApp.swift */,
255 | 8A73D8CD25CAE974008DDEA3 /* ContentView.swift */,
256 | 8A42F197279B6B95003BCDB4 /* SettingsView.swift */,
257 | 8A9F8E6A273EECBC00D29025 /* Shared */,
258 | 8A73D8CF25CAE978008DDEA3 /* Assets.xcassets */,
259 | 8A73D8D425CAE978008DDEA3 /* Info.plist */,
260 | 8A73D8D525CAE978008DDEA3 /* SwiftPlantUMLApp.entitlements */,
261 | 8A73D8D125CAE978008DDEA3 /* Preview Content */,
262 | );
263 | path = SwiftPlantUMLApp;
264 | sourceTree = "";
265 | };
266 | 8A73D8D125CAE978008DDEA3 /* Preview Content */ = {
267 | isa = PBXGroup;
268 | children = (
269 | 8A73D8D225CAE978008DDEA3 /* Preview Assets.xcassets */,
270 | );
271 | path = "Preview Content";
272 | sourceTree = "";
273 | };
274 | 8A73D8E125CAE9AA008DDEA3 /* Frameworks */ = {
275 | isa = PBXGroup;
276 | children = (
277 | 8A73D8E225CAE9AA008DDEA3 /* Cocoa.framework */,
278 | 8A73D8E425CAE9AA008DDEA3 /* XcodeKit.framework */,
279 | );
280 | name = Frameworks;
281 | sourceTree = "";
282 | };
283 | 8A73D8E625CAE9AA008DDEA3 /* SourceEditorExtension */ = {
284 | isa = PBXGroup;
285 | children = (
286 | 8A73D8E725CAE9AA008DDEA3 /* SourceEditorExtension.swift */,
287 | 8A73D8E925CAE9AA008DDEA3 /* GenDiagramInBrowser.swift */,
288 | 8A73D8EB25CAE9AA008DDEA3 /* Info.plist */,
289 | 8A73D8EC25CAE9AA008DDEA3 /* SourceEditorExtension.entitlements */,
290 | 8A30356E279BA55700042D19 /* PreferencesCommand.swift */,
291 | );
292 | path = SourceEditorExtension;
293 | sourceTree = "";
294 | };
295 | 8A73D8FB25CAE9DD008DDEA3 /* XPCService */ = {
296 | isa = PBXGroup;
297 | children = (
298 | 8A9F8E69273ED6D300D29025 /* XPCService.entitlements */,
299 | 8A73D90225CAE9DD008DDEA3 /* Info.plist */,
300 | 8A73D91325CAEA78008DDEA3 /* main.swift */,
301 | 8A73D91825CAEA8F008DDEA3 /* XPCServiceProtocol.swift */,
302 | 8A73D91D25CAEA9E008DDEA3 /* XPCService.swift */,
303 | );
304 | path = XPCService;
305 | sourceTree = "";
306 | };
307 | 8A9F8E6A273EECBC00D29025 /* Shared */ = {
308 | isa = PBXGroup;
309 | children = (
310 | 8A9F8E6D273EECF300D29025 /* SettingsModel.swift */,
311 | 8A1EFEF32735DEC000BD6F69 /* Utils.swift */,
312 | );
313 | path = Shared;
314 | sourceTree = "";
315 | };
316 | /* End PBXGroup section */
317 |
318 | /* Begin PBXNativeTarget section */
319 | 192CDFCD2971F5F400CF914F /* ActionExtension */ = {
320 | isa = PBXNativeTarget;
321 | buildConfigurationList = 192CDFDE2971F5F400CF914F /* Build configuration list for PBXNativeTarget "ActionExtension" */;
322 | buildPhases = (
323 | 192CDFCA2971F5F400CF914F /* Sources */,
324 | 192CDFCB2971F5F400CF914F /* Frameworks */,
325 | 192CDFCC2971F5F400CF914F /* Resources */,
326 | 192CDFDF2971F5FF00CF914F /* CopyFiles */,
327 | );
328 | buildRules = (
329 | );
330 | dependencies = (
331 | 192CDFE42971F68700CF914F /* PBXTargetDependency */,
332 | );
333 | name = ActionExtension;
334 | packageProductDependencies = (
335 | 19E9029F29737244002212BA /* SwiftPlantUMLFramework */,
336 | );
337 | productName = ActionExtension;
338 | productReference = 192CDFCE2971F5F400CF914F /* ActionExtension.appex */;
339 | productType = "com.apple.product-type.app-extension";
340 | };
341 | 8A73D8C725CAE974008DDEA3 /* SwiftPlantUMLApp */ = {
342 | isa = PBXNativeTarget;
343 | buildConfigurationList = 8A73D8D825CAE978008DDEA3 /* Build configuration list for PBXNativeTarget "SwiftPlantUMLApp" */;
344 | buildPhases = (
345 | 8A73D8C425CAE974008DDEA3 /* Sources */,
346 | 8A73D8C525CAE974008DDEA3 /* Frameworks */,
347 | 8A73D8C625CAE974008DDEA3 /* Resources */,
348 | 8A73D8F325CAE9AA008DDEA3 /* Embed Foundation Extensions */,
349 | 8A73D90925CAE9DD008DDEA3 /* Embed XPC Services */,
350 | );
351 | buildRules = (
352 | );
353 | dependencies = (
354 | 8A73D8EE25CAE9AA008DDEA3 /* PBXTargetDependency */,
355 | 8A73D90425CAE9DD008DDEA3 /* PBXTargetDependency */,
356 | 192CDFDA2971F5F400CF914F /* PBXTargetDependency */,
357 | );
358 | name = SwiftPlantUMLApp;
359 | packageProductDependencies = (
360 | 1919C9C7296B48EA00804361 /* SwiftPlantUMLFramework */,
361 | );
362 | productName = SwiftPlantUMLApp;
363 | productReference = 8A73D8C825CAE974008DDEA3 /* SwiftPlantUMLApp.app */;
364 | productType = "com.apple.product-type.application";
365 | };
366 | 8A73D8DF25CAE9AA008DDEA3 /* SourceEditorExtension */ = {
367 | isa = PBXNativeTarget;
368 | buildConfigurationList = 8A73D8F025CAE9AA008DDEA3 /* Build configuration list for PBXNativeTarget "SourceEditorExtension" */;
369 | buildPhases = (
370 | 8A73D8DC25CAE9AA008DDEA3 /* Sources */,
371 | 8A73D8DD25CAE9AA008DDEA3 /* Frameworks */,
372 | 8A73D8DE25CAE9AA008DDEA3 /* Resources */,
373 | 8A9E73CC25CAEE2B00327AD1 /* Embed Frameworks */,
374 | 8A73D92725CAEB3B008DDEA3 /* CopyFiles */,
375 | );
376 | buildRules = (
377 | );
378 | dependencies = (
379 | 8A73D92625CAEB2B008DDEA3 /* PBXTargetDependency */,
380 | );
381 | name = SourceEditorExtension;
382 | packageProductDependencies = (
383 | );
384 | productName = SourceEditorExtension;
385 | productReference = 8A73D8E025CAE9AA008DDEA3 /* SourceEditorExtension.appex */;
386 | productType = "com.apple.product-type.xcode-extension";
387 | };
388 | 8A73D8F925CAE9DD008DDEA3 /* XPCService */ = {
389 | isa = PBXNativeTarget;
390 | buildConfigurationList = 8A73D90625CAE9DD008DDEA3 /* Build configuration list for PBXNativeTarget "XPCService" */;
391 | buildPhases = (
392 | 8A73D8F625CAE9DD008DDEA3 /* Sources */,
393 | 8A73D8F725CAE9DD008DDEA3 /* Frameworks */,
394 | 8A73D8F825CAE9DD008DDEA3 /* Resources */,
395 | );
396 | buildRules = (
397 | );
398 | dependencies = (
399 | );
400 | name = XPCService;
401 | packageProductDependencies = (
402 | 1919C9C9296B48FC00804361 /* SwiftPlantUMLFramework */,
403 | );
404 | productName = XPCService;
405 | productReference = 8A73D8FA25CAE9DD008DDEA3 /* XPCService.xpc */;
406 | productType = "com.apple.product-type.xpc-service";
407 | };
408 | /* End PBXNativeTarget section */
409 |
410 | /* Begin PBXProject section */
411 | 8A73D8C025CAE974008DDEA3 /* Project object */ = {
412 | isa = PBXProject;
413 | attributes = {
414 | BuildIndependentTargetsInParallel = YES;
415 | LastSwiftUpdateCheck = 1420;
416 | LastUpgradeCheck = 1500;
417 | TargetAttributes = {
418 | 192CDFCD2971F5F400CF914F = {
419 | CreatedOnToolsVersion = 14.2;
420 | };
421 | 8A73D8C725CAE974008DDEA3 = {
422 | CreatedOnToolsVersion = 12.4;
423 | };
424 | 8A73D8DF25CAE9AA008DDEA3 = {
425 | CreatedOnToolsVersion = 12.4;
426 | };
427 | 8A73D8F925CAE9DD008DDEA3 = {
428 | CreatedOnToolsVersion = 12.4;
429 | LastSwiftMigration = 1240;
430 | };
431 | };
432 | };
433 | buildConfigurationList = 8A73D8C325CAE974008DDEA3 /* Build configuration list for PBXProject "SwiftPlantUMLApp" */;
434 | compatibilityVersion = "Xcode 9.3";
435 | developmentRegion = en;
436 | hasScannedForEncodings = 0;
437 | knownRegions = (
438 | en,
439 | Base,
440 | );
441 | mainGroup = 8A73D8BF25CAE974008DDEA3;
442 | packageReferences = (
443 | 1919C9C6296B48EA00804361 /* XCRemoteSwiftPackageReference "SwiftPlantUML" */,
444 | );
445 | productRefGroup = 8A73D8C925CAE974008DDEA3 /* Products */;
446 | projectDirPath = "";
447 | projectRoot = "";
448 | targets = (
449 | 8A73D8C725CAE974008DDEA3 /* SwiftPlantUMLApp */,
450 | 8A73D8DF25CAE9AA008DDEA3 /* SourceEditorExtension */,
451 | 192CDFCD2971F5F400CF914F /* ActionExtension */,
452 | 8A73D8F925CAE9DD008DDEA3 /* XPCService */,
453 | );
454 | };
455 | /* End PBXProject section */
456 |
457 | /* Begin PBXResourcesBuildPhase section */
458 | 192CDFCC2971F5F400CF914F /* Resources */ = {
459 | isa = PBXResourcesBuildPhase;
460 | buildActionMask = 2147483647;
461 | files = (
462 | 192CDFD22971F5F400CF914F /* Media.xcassets in Resources */,
463 | );
464 | runOnlyForDeploymentPostprocessing = 0;
465 | };
466 | 8A73D8C625CAE974008DDEA3 /* Resources */ = {
467 | isa = PBXResourcesBuildPhase;
468 | buildActionMask = 2147483647;
469 | files = (
470 | 8A3191792619124B00540446 /* Main.storyboard in Resources */,
471 | 8A73D8D325CAE978008DDEA3 /* Preview Assets.xcassets in Resources */,
472 | 8A73D8D025CAE978008DDEA3 /* Assets.xcassets in Resources */,
473 | );
474 | runOnlyForDeploymentPostprocessing = 0;
475 | };
476 | 8A73D8DE25CAE9AA008DDEA3 /* Resources */ = {
477 | isa = PBXResourcesBuildPhase;
478 | buildActionMask = 2147483647;
479 | files = (
480 | );
481 | runOnlyForDeploymentPostprocessing = 0;
482 | };
483 | 8A73D8F825CAE9DD008DDEA3 /* Resources */ = {
484 | isa = PBXResourcesBuildPhase;
485 | buildActionMask = 2147483647;
486 | files = (
487 | );
488 | runOnlyForDeploymentPostprocessing = 0;
489 | };
490 | /* End PBXResourcesBuildPhase section */
491 |
492 | /* Begin PBXSourcesBuildPhase section */
493 | 192CDFCA2971F5F400CF914F /* Sources */ = {
494 | isa = PBXSourcesBuildPhase;
495 | buildActionMask = 2147483647;
496 | files = (
497 | 192CDFD62971F5F400CF914F /* ActionRequestHandler.swift in Sources */,
498 | 192CDFE52971F6DB00CF914F /* XPCServiceProtocol.swift in Sources */,
499 | );
500 | runOnlyForDeploymentPostprocessing = 0;
501 | };
502 | 8A73D8C425CAE974008DDEA3 /* Sources */ = {
503 | isa = PBXSourcesBuildPhase;
504 | buildActionMask = 2147483647;
505 | files = (
506 | 8A42F198279B6B95003BCDB4 /* SettingsView.swift in Sources */,
507 | 8A319170261911B900540446 /* AppDelegate.swift in Sources */,
508 | 8A73D8CE25CAE974008DDEA3 /* ContentView.swift in Sources */,
509 | 8A3191742619123F00540446 /* ViewController.swift in Sources */,
510 | 8A73D8CC25CAE974008DDEA3 /* SwiftPlantUMLAppApp.swift in Sources */,
511 | 8A9F8E6E273EECF300D29025 /* SettingsModel.swift in Sources */,
512 | 8A1EFEF42735DEC000BD6F69 /* Utils.swift in Sources */,
513 | );
514 | runOnlyForDeploymentPostprocessing = 0;
515 | };
516 | 8A73D8DC25CAE9AA008DDEA3 /* Sources */ = {
517 | isa = PBXSourcesBuildPhase;
518 | buildActionMask = 2147483647;
519 | files = (
520 | 8A30356F279BA55700042D19 /* PreferencesCommand.swift in Sources */,
521 | 8A73D8E825CAE9AA008DDEA3 /* SourceEditorExtension.swift in Sources */,
522 | 8A9E73BF25CAEBAF00327AD1 /* XPCServiceProtocol.swift in Sources */,
523 | 8A73D8EA25CAE9AA008DDEA3 /* GenDiagramInBrowser.swift in Sources */,
524 | );
525 | runOnlyForDeploymentPostprocessing = 0;
526 | };
527 | 8A73D8F625CAE9DD008DDEA3 /* Sources */ = {
528 | isa = PBXSourcesBuildPhase;
529 | buildActionMask = 2147483647;
530 | files = (
531 | 8A73D91925CAEA8F008DDEA3 /* XPCServiceProtocol.swift in Sources */,
532 | 8A9F8E6F273EECF300D29025 /* SettingsModel.swift in Sources */,
533 | 8A73D91E25CAEA9E008DDEA3 /* XPCService.swift in Sources */,
534 | 8A73D91425CAEA78008DDEA3 /* main.swift in Sources */,
535 | 8A9F8E68273ED22700D29025 /* Utils.swift in Sources */,
536 | );
537 | runOnlyForDeploymentPostprocessing = 0;
538 | };
539 | /* End PBXSourcesBuildPhase section */
540 |
541 | /* Begin PBXTargetDependency section */
542 | 192CDFDA2971F5F400CF914F /* PBXTargetDependency */ = {
543 | isa = PBXTargetDependency;
544 | target = 192CDFCD2971F5F400CF914F /* ActionExtension */;
545 | targetProxy = 192CDFD92971F5F400CF914F /* PBXContainerItemProxy */;
546 | };
547 | 192CDFE42971F68700CF914F /* PBXTargetDependency */ = {
548 | isa = PBXTargetDependency;
549 | target = 8A73D8F925CAE9DD008DDEA3 /* XPCService */;
550 | targetProxy = 192CDFE32971F68700CF914F /* PBXContainerItemProxy */;
551 | };
552 | 8A73D8EE25CAE9AA008DDEA3 /* PBXTargetDependency */ = {
553 | isa = PBXTargetDependency;
554 | target = 8A73D8DF25CAE9AA008DDEA3 /* SourceEditorExtension */;
555 | targetProxy = 8A73D8ED25CAE9AA008DDEA3 /* PBXContainerItemProxy */;
556 | };
557 | 8A73D90425CAE9DD008DDEA3 /* PBXTargetDependency */ = {
558 | isa = PBXTargetDependency;
559 | target = 8A73D8F925CAE9DD008DDEA3 /* XPCService */;
560 | targetProxy = 8A73D90325CAE9DD008DDEA3 /* PBXContainerItemProxy */;
561 | };
562 | 8A73D92625CAEB2B008DDEA3 /* PBXTargetDependency */ = {
563 | isa = PBXTargetDependency;
564 | target = 8A73D8F925CAE9DD008DDEA3 /* XPCService */;
565 | targetProxy = 8A73D92525CAEB2B008DDEA3 /* PBXContainerItemProxy */;
566 | };
567 | /* End PBXTargetDependency section */
568 |
569 | /* Begin PBXVariantGroup section */
570 | 8A3191772619124B00540446 /* Main.storyboard */ = {
571 | isa = PBXVariantGroup;
572 | children = (
573 | 8A3191782619124B00540446 /* Base */,
574 | );
575 | name = Main.storyboard;
576 | sourceTree = "";
577 | };
578 | /* End PBXVariantGroup section */
579 |
580 | /* Begin XCBuildConfiguration section */
581 | 192CDFDC2971F5F400CF914F /* Debug */ = {
582 | isa = XCBuildConfiguration;
583 | buildSettings = {
584 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++20";
585 | CODE_SIGN_ENTITLEMENTS = ActionExtension/ActionExtension.entitlements;
586 | CODE_SIGN_IDENTITY = "Apple Development";
587 | CODE_SIGN_STYLE = Automatic;
588 | COMBINE_HIDPI_IMAGES = YES;
589 | CURRENT_PROJECT_VERSION = 3;
590 | DEAD_CODE_STRIPPING = YES;
591 | DEVELOPMENT_TEAM = 6V66CC3AN6;
592 | ENABLE_HARDENED_RUNTIME = YES;
593 | GENERATE_INFOPLIST_FILE = YES;
594 | INFOPLIST_FILE = ActionExtension/Info.plist;
595 | INFOPLIST_KEY_CFBundleDisplayName = "View Swift Class Diagram";
596 | INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2023-2024 Marco Eidinger. All rights reserved.";
597 | LD_RUNPATH_SEARCH_PATHS = (
598 | "$(inherited)",
599 | "@executable_path/../Frameworks",
600 | "@executable_path/../../../../Frameworks",
601 | );
602 | MACOSX_DEPLOYMENT_TARGET = 10.15;
603 | MARKETING_VERSION = 1.6.0;
604 | PRODUCT_BUNDLE_IDENTIFIER = us.eidinger.SwiftPlantUMLActionExtension;
605 | PRODUCT_NAME = "$(TARGET_NAME)";
606 | SKIP_INSTALL = YES;
607 | SWIFT_EMIT_LOC_STRINGS = YES;
608 | SWIFT_VERSION = 5.0;
609 | };
610 | name = Debug;
611 | };
612 | 192CDFDD2971F5F400CF914F /* Release */ = {
613 | isa = XCBuildConfiguration;
614 | buildSettings = {
615 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++20";
616 | CODE_SIGN_ENTITLEMENTS = ActionExtension/ActionExtension.entitlements;
617 | CODE_SIGN_IDENTITY = "Apple Development";
618 | CODE_SIGN_STYLE = Automatic;
619 | COMBINE_HIDPI_IMAGES = YES;
620 | CURRENT_PROJECT_VERSION = 3;
621 | DEAD_CODE_STRIPPING = YES;
622 | DEVELOPMENT_TEAM = 6V66CC3AN6;
623 | ENABLE_HARDENED_RUNTIME = YES;
624 | GENERATE_INFOPLIST_FILE = YES;
625 | INFOPLIST_FILE = ActionExtension/Info.plist;
626 | INFOPLIST_KEY_CFBundleDisplayName = "View Swift Class Diagram";
627 | INFOPLIST_KEY_NSHumanReadableCopyright = "Copyright © 2023-2024 Marco Eidinger. All rights reserved.";
628 | LD_RUNPATH_SEARCH_PATHS = (
629 | "$(inherited)",
630 | "@executable_path/../Frameworks",
631 | "@executable_path/../../../../Frameworks",
632 | );
633 | MACOSX_DEPLOYMENT_TARGET = 10.15;
634 | MARKETING_VERSION = 1.6.0;
635 | PRODUCT_BUNDLE_IDENTIFIER = us.eidinger.SwiftPlantUMLActionExtension;
636 | PRODUCT_NAME = "$(TARGET_NAME)";
637 | SKIP_INSTALL = YES;
638 | SWIFT_EMIT_LOC_STRINGS = YES;
639 | SWIFT_VERSION = 5.0;
640 | };
641 | name = Release;
642 | };
643 | 8A73D8D625CAE978008DDEA3 /* Debug */ = {
644 | isa = XCBuildConfiguration;
645 | buildSettings = {
646 | ALWAYS_SEARCH_USER_PATHS = NO;
647 | CLANG_ANALYZER_NONNULL = YES;
648 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE;
649 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
650 | CLANG_CXX_LIBRARY = "libc++";
651 | CLANG_ENABLE_MODULES = YES;
652 | CLANG_ENABLE_OBJC_ARC = YES;
653 | CLANG_ENABLE_OBJC_WEAK = YES;
654 | CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
655 | CLANG_WARN_BOOL_CONVERSION = YES;
656 | CLANG_WARN_COMMA = YES;
657 | CLANG_WARN_CONSTANT_CONVERSION = YES;
658 | CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
659 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
660 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES;
661 | CLANG_WARN_EMPTY_BODY = YES;
662 | CLANG_WARN_ENUM_CONVERSION = YES;
663 | CLANG_WARN_INFINITE_RECURSION = YES;
664 | CLANG_WARN_INT_CONVERSION = YES;
665 | CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
666 | CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
667 | CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
668 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
669 | CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES;
670 | CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
671 | CLANG_WARN_STRICT_PROTOTYPES = YES;
672 | CLANG_WARN_SUSPICIOUS_MOVE = YES;
673 | CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
674 | CLANG_WARN_UNREACHABLE_CODE = YES;
675 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
676 | COPY_PHASE_STRIP = NO;
677 | DEAD_CODE_STRIPPING = YES;
678 | DEBUG_INFORMATION_FORMAT = dwarf;
679 | ENABLE_STRICT_OBJC_MSGSEND = YES;
680 | ENABLE_TESTABILITY = YES;
681 | ENABLE_USER_SCRIPT_SANDBOXING = YES;
682 | GCC_C_LANGUAGE_STANDARD = gnu11;
683 | GCC_DYNAMIC_NO_PIC = NO;
684 | GCC_NO_COMMON_BLOCKS = YES;
685 | GCC_OPTIMIZATION_LEVEL = 0;
686 | GCC_PREPROCESSOR_DEFINITIONS = (
687 | "DEBUG=1",
688 | "$(inherited)",
689 | );
690 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
691 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
692 | GCC_WARN_UNDECLARED_SELECTOR = YES;
693 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
694 | GCC_WARN_UNUSED_FUNCTION = YES;
695 | GCC_WARN_UNUSED_VARIABLE = YES;
696 | MACOSX_DEPLOYMENT_TARGET = 10.15;
697 | MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE;
698 | MTL_FAST_MATH = YES;
699 | ONLY_ACTIVE_ARCH = YES;
700 | SDKROOT = macosx;
701 | SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG;
702 | SWIFT_OPTIMIZATION_LEVEL = "-Onone";
703 | };
704 | name = Debug;
705 | };
706 | 8A73D8D725CAE978008DDEA3 /* Release */ = {
707 | isa = XCBuildConfiguration;
708 | buildSettings = {
709 | ALWAYS_SEARCH_USER_PATHS = NO;
710 | CLANG_ANALYZER_NONNULL = YES;
711 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE;
712 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
713 | CLANG_CXX_LIBRARY = "libc++";
714 | CLANG_ENABLE_MODULES = YES;
715 | CLANG_ENABLE_OBJC_ARC = YES;
716 | CLANG_ENABLE_OBJC_WEAK = YES;
717 | CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
718 | CLANG_WARN_BOOL_CONVERSION = YES;
719 | CLANG_WARN_COMMA = YES;
720 | CLANG_WARN_CONSTANT_CONVERSION = YES;
721 | CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
722 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
723 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES;
724 | CLANG_WARN_EMPTY_BODY = YES;
725 | CLANG_WARN_ENUM_CONVERSION = YES;
726 | CLANG_WARN_INFINITE_RECURSION = YES;
727 | CLANG_WARN_INT_CONVERSION = YES;
728 | CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
729 | CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
730 | CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
731 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
732 | CLANG_WARN_QUOTED_INCLUDE_IN_FRAMEWORK_HEADER = YES;
733 | CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
734 | CLANG_WARN_STRICT_PROTOTYPES = YES;
735 | CLANG_WARN_SUSPICIOUS_MOVE = YES;
736 | CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
737 | CLANG_WARN_UNREACHABLE_CODE = YES;
738 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
739 | COPY_PHASE_STRIP = NO;
740 | DEAD_CODE_STRIPPING = YES;
741 | DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
742 | ENABLE_NS_ASSERTIONS = NO;
743 | ENABLE_STRICT_OBJC_MSGSEND = YES;
744 | ENABLE_USER_SCRIPT_SANDBOXING = YES;
745 | GCC_C_LANGUAGE_STANDARD = gnu11;
746 | GCC_NO_COMMON_BLOCKS = YES;
747 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
748 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
749 | GCC_WARN_UNDECLARED_SELECTOR = YES;
750 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
751 | GCC_WARN_UNUSED_FUNCTION = YES;
752 | GCC_WARN_UNUSED_VARIABLE = YES;
753 | MACOSX_DEPLOYMENT_TARGET = 10.15;
754 | MTL_ENABLE_DEBUG_INFO = NO;
755 | MTL_FAST_MATH = YES;
756 | SDKROOT = macosx;
757 | SWIFT_COMPILATION_MODE = wholemodule;
758 | SWIFT_OPTIMIZATION_LEVEL = "-O";
759 | };
760 | name = Release;
761 | };
762 | 8A73D8D925CAE978008DDEA3 /* Debug */ = {
763 | isa = XCBuildConfiguration;
764 | buildSettings = {
765 | ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = YES;
766 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
767 | ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor;
768 | CODE_SIGN_ENTITLEMENTS = SwiftPlantUMLApp/SwiftPlantUMLApp.entitlements;
769 | CODE_SIGN_IDENTITY = "Apple Development";
770 | CODE_SIGN_STYLE = Automatic;
771 | COMBINE_HIDPI_IMAGES = YES;
772 | CURRENT_PROJECT_VERSION = 3;
773 | DEAD_CODE_STRIPPING = YES;
774 | DEVELOPMENT_ASSET_PATHS = "\"SwiftPlantUMLApp/Preview Content\"";
775 | DEVELOPMENT_TEAM = 6V66CC3AN6;
776 | ENABLE_HARDENED_RUNTIME = YES;
777 | ENABLE_PREVIEWS = YES;
778 | INFOPLIST_FILE = SwiftPlantUMLApp/Info.plist;
779 | LD_RUNPATH_SEARCH_PATHS = (
780 | "$(inherited)",
781 | "@executable_path/../Frameworks",
782 | );
783 | MACOSX_DEPLOYMENT_TARGET = 10.15;
784 | MARKETING_VERSION = 1.6.0;
785 | PRODUCT_BUNDLE_IDENTIFIER = us.eidinger.SwiftPlantUML;
786 | PRODUCT_NAME = "$(TARGET_NAME)";
787 | PROVISIONING_PROFILE_SPECIFIER = "";
788 | SWIFT_VERSION = 5.0;
789 | };
790 | name = Debug;
791 | };
792 | 8A73D8DA25CAE978008DDEA3 /* Release */ = {
793 | isa = XCBuildConfiguration;
794 | buildSettings = {
795 | ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = YES;
796 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
797 | ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor;
798 | CODE_SIGN_ENTITLEMENTS = SwiftPlantUMLApp/SwiftPlantUMLApp.entitlements;
799 | CODE_SIGN_IDENTITY = "Apple Development";
800 | CODE_SIGN_STYLE = Automatic;
801 | COMBINE_HIDPI_IMAGES = YES;
802 | CURRENT_PROJECT_VERSION = 3;
803 | DEAD_CODE_STRIPPING = YES;
804 | DEVELOPMENT_ASSET_PATHS = "\"SwiftPlantUMLApp/Preview Content\"";
805 | DEVELOPMENT_TEAM = 6V66CC3AN6;
806 | ENABLE_HARDENED_RUNTIME = YES;
807 | ENABLE_PREVIEWS = YES;
808 | INFOPLIST_FILE = SwiftPlantUMLApp/Info.plist;
809 | LD_RUNPATH_SEARCH_PATHS = (
810 | "$(inherited)",
811 | "@executable_path/../Frameworks",
812 | );
813 | MACOSX_DEPLOYMENT_TARGET = 10.15;
814 | MARKETING_VERSION = 1.6.0;
815 | PRODUCT_BUNDLE_IDENTIFIER = us.eidinger.SwiftPlantUML;
816 | PRODUCT_NAME = "$(TARGET_NAME)";
817 | PROVISIONING_PROFILE_SPECIFIER = "";
818 | SWIFT_VERSION = 5.0;
819 | };
820 | name = Release;
821 | };
822 | 8A73D8F125CAE9AA008DDEA3 /* Debug */ = {
823 | isa = XCBuildConfiguration;
824 | buildSettings = {
825 | CODE_SIGN_ENTITLEMENTS = SourceEditorExtension/SourceEditorExtension.entitlements;
826 | CODE_SIGN_IDENTITY = "Apple Development";
827 | CODE_SIGN_STYLE = Automatic;
828 | COMBINE_HIDPI_IMAGES = YES;
829 | CURRENT_PROJECT_VERSION = 3;
830 | DEAD_CODE_STRIPPING = YES;
831 | DEVELOPMENT_TEAM = 6V66CC3AN6;
832 | ENABLE_HARDENED_RUNTIME = YES;
833 | INFOPLIST_FILE = SourceEditorExtension/Info.plist;
834 | LD_RUNPATH_SEARCH_PATHS = (
835 | "$(inherited)",
836 | "@executable_path/../Frameworks",
837 | "@executable_path/../../../../Frameworks",
838 | );
839 | MARKETING_VERSION = 1.6.0;
840 | PRODUCT_BUNDLE_IDENTIFIER = us.eidinger.SwiftPlantUMLSourceEditorExtension;
841 | PRODUCT_NAME = "$(TARGET_NAME)";
842 | PROVISIONING_PROFILE_SPECIFIER = "";
843 | SKIP_INSTALL = YES;
844 | SWIFT_VERSION = 5.0;
845 | };
846 | name = Debug;
847 | };
848 | 8A73D8F225CAE9AA008DDEA3 /* Release */ = {
849 | isa = XCBuildConfiguration;
850 | buildSettings = {
851 | CODE_SIGN_ENTITLEMENTS = SourceEditorExtension/SourceEditorExtension.entitlements;
852 | CODE_SIGN_IDENTITY = "Apple Development";
853 | CODE_SIGN_STYLE = Automatic;
854 | COMBINE_HIDPI_IMAGES = YES;
855 | CURRENT_PROJECT_VERSION = 3;
856 | DEAD_CODE_STRIPPING = YES;
857 | DEVELOPMENT_TEAM = 6V66CC3AN6;
858 | ENABLE_HARDENED_RUNTIME = YES;
859 | INFOPLIST_FILE = SourceEditorExtension/Info.plist;
860 | LD_RUNPATH_SEARCH_PATHS = (
861 | "$(inherited)",
862 | "@executable_path/../Frameworks",
863 | "@executable_path/../../../../Frameworks",
864 | );
865 | MARKETING_VERSION = 1.6.0;
866 | PRODUCT_BUNDLE_IDENTIFIER = us.eidinger.SwiftPlantUMLSourceEditorExtension;
867 | PRODUCT_NAME = "$(TARGET_NAME)";
868 | PROVISIONING_PROFILE_SPECIFIER = "";
869 | SKIP_INSTALL = YES;
870 | SWIFT_VERSION = 5.0;
871 | };
872 | name = Release;
873 | };
874 | 8A73D90725CAE9DD008DDEA3 /* Debug */ = {
875 | isa = XCBuildConfiguration;
876 | buildSettings = {
877 | CLANG_ENABLE_MODULES = YES;
878 | CODE_SIGN_ENTITLEMENTS = XPCService/XPCService.entitlements;
879 | CODE_SIGN_IDENTITY = "Apple Development";
880 | CODE_SIGN_STYLE = Automatic;
881 | COMBINE_HIDPI_IMAGES = YES;
882 | CURRENT_PROJECT_VERSION = 3;
883 | DEAD_CODE_STRIPPING = YES;
884 | DEVELOPMENT_TEAM = 6V66CC3AN6;
885 | ENABLE_HARDENED_RUNTIME = YES;
886 | INFOPLIST_FILE = XPCService/Info.plist;
887 | LD_RUNPATH_SEARCH_PATHS = (
888 | "$(inherited)",
889 | "@executable_path/../Frameworks",
890 | "@loader_path/../Frameworks",
891 | );
892 | MARKETING_VERSION = 1.6.0;
893 | PRODUCT_BUNDLE_IDENTIFIER = us.eidinger.SwiftPlantUMLXPCService;
894 | PRODUCT_NAME = "$(TARGET_NAME)";
895 | PROVISIONING_PROFILE_SPECIFIER = "";
896 | SKIP_INSTALL = YES;
897 | SWIFT_OPTIMIZATION_LEVEL = "-Onone";
898 | SWIFT_VERSION = 5.0;
899 | };
900 | name = Debug;
901 | };
902 | 8A73D90825CAE9DD008DDEA3 /* Release */ = {
903 | isa = XCBuildConfiguration;
904 | buildSettings = {
905 | CLANG_ENABLE_MODULES = YES;
906 | CODE_SIGN_ENTITLEMENTS = XPCService/XPCService.entitlements;
907 | CODE_SIGN_IDENTITY = "Apple Development";
908 | CODE_SIGN_STYLE = Automatic;
909 | COMBINE_HIDPI_IMAGES = YES;
910 | CURRENT_PROJECT_VERSION = 3;
911 | DEAD_CODE_STRIPPING = YES;
912 | DEVELOPMENT_TEAM = 6V66CC3AN6;
913 | ENABLE_HARDENED_RUNTIME = YES;
914 | INFOPLIST_FILE = XPCService/Info.plist;
915 | LD_RUNPATH_SEARCH_PATHS = (
916 | "$(inherited)",
917 | "@executable_path/../Frameworks",
918 | "@loader_path/../Frameworks",
919 | );
920 | MARKETING_VERSION = 1.6.0;
921 | PRODUCT_BUNDLE_IDENTIFIER = us.eidinger.SwiftPlantUMLXPCService;
922 | PRODUCT_NAME = "$(TARGET_NAME)";
923 | PROVISIONING_PROFILE_SPECIFIER = "";
924 | SKIP_INSTALL = YES;
925 | SWIFT_VERSION = 5.0;
926 | };
927 | name = Release;
928 | };
929 | /* End XCBuildConfiguration section */
930 |
931 | /* Begin XCConfigurationList section */
932 | 192CDFDE2971F5F400CF914F /* Build configuration list for PBXNativeTarget "ActionExtension" */ = {
933 | isa = XCConfigurationList;
934 | buildConfigurations = (
935 | 192CDFDC2971F5F400CF914F /* Debug */,
936 | 192CDFDD2971F5F400CF914F /* Release */,
937 | );
938 | defaultConfigurationIsVisible = 0;
939 | defaultConfigurationName = Release;
940 | };
941 | 8A73D8C325CAE974008DDEA3 /* Build configuration list for PBXProject "SwiftPlantUMLApp" */ = {
942 | isa = XCConfigurationList;
943 | buildConfigurations = (
944 | 8A73D8D625CAE978008DDEA3 /* Debug */,
945 | 8A73D8D725CAE978008DDEA3 /* Release */,
946 | );
947 | defaultConfigurationIsVisible = 0;
948 | defaultConfigurationName = Release;
949 | };
950 | 8A73D8D825CAE978008DDEA3 /* Build configuration list for PBXNativeTarget "SwiftPlantUMLApp" */ = {
951 | isa = XCConfigurationList;
952 | buildConfigurations = (
953 | 8A73D8D925CAE978008DDEA3 /* Debug */,
954 | 8A73D8DA25CAE978008DDEA3 /* Release */,
955 | );
956 | defaultConfigurationIsVisible = 0;
957 | defaultConfigurationName = Release;
958 | };
959 | 8A73D8F025CAE9AA008DDEA3 /* Build configuration list for PBXNativeTarget "SourceEditorExtension" */ = {
960 | isa = XCConfigurationList;
961 | buildConfigurations = (
962 | 8A73D8F125CAE9AA008DDEA3 /* Debug */,
963 | 8A73D8F225CAE9AA008DDEA3 /* Release */,
964 | );
965 | defaultConfigurationIsVisible = 0;
966 | defaultConfigurationName = Release;
967 | };
968 | 8A73D90625CAE9DD008DDEA3 /* Build configuration list for PBXNativeTarget "XPCService" */ = {
969 | isa = XCConfigurationList;
970 | buildConfigurations = (
971 | 8A73D90725CAE9DD008DDEA3 /* Debug */,
972 | 8A73D90825CAE9DD008DDEA3 /* Release */,
973 | );
974 | defaultConfigurationIsVisible = 0;
975 | defaultConfigurationName = Release;
976 | };
977 | /* End XCConfigurationList section */
978 |
979 | /* Begin XCRemoteSwiftPackageReference section */
980 | 1919C9C6296B48EA00804361 /* XCRemoteSwiftPackageReference "SwiftPlantUML" */ = {
981 | isa = XCRemoteSwiftPackageReference;
982 | repositoryURL = "https://github.com/MarcoEidinger/SwiftPlantUML.git";
983 | requirement = {
984 | kind = upToNextMinorVersion;
985 | minimumVersion = 0.8.0;
986 | };
987 | };
988 | /* End XCRemoteSwiftPackageReference section */
989 |
990 | /* Begin XCSwiftPackageProductDependency section */
991 | 1919C9C7296B48EA00804361 /* SwiftPlantUMLFramework */ = {
992 | isa = XCSwiftPackageProductDependency;
993 | package = 1919C9C6296B48EA00804361 /* XCRemoteSwiftPackageReference "SwiftPlantUML" */;
994 | productName = SwiftPlantUMLFramework;
995 | };
996 | 1919C9C9296B48FC00804361 /* SwiftPlantUMLFramework */ = {
997 | isa = XCSwiftPackageProductDependency;
998 | package = 1919C9C6296B48EA00804361 /* XCRemoteSwiftPackageReference "SwiftPlantUML" */;
999 | productName = SwiftPlantUMLFramework;
1000 | };
1001 | 19E9029F29737244002212BA /* SwiftPlantUMLFramework */ = {
1002 | isa = XCSwiftPackageProductDependency;
1003 | package = 1919C9C6296B48EA00804361 /* XCRemoteSwiftPackageReference "SwiftPlantUML" */;
1004 | productName = SwiftPlantUMLFramework;
1005 | };
1006 | /* End XCSwiftPackageProductDependency section */
1007 | };
1008 | rootObject = 8A73D8C025CAE974008DDEA3 /* Project object */;
1009 | }
1010 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp.xcodeproj/project.xcworkspace/contents.xcworkspacedata:
--------------------------------------------------------------------------------
1 |
2 |
4 |
6 |
7 |
8 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | IDEDidComputeMac32BitWarning
6 |
7 |
8 |
9 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp.xcodeproj/project.xcworkspace/xcshareddata/swiftpm/Package.resolved:
--------------------------------------------------------------------------------
1 | {
2 | "pins" : [
3 | {
4 | "identity" : "sourcekitten",
5 | "kind" : "remoteSourceControl",
6 | "location" : "https://github.com/jpsim/SourceKitten",
7 | "state" : {
8 | "revision" : "558628392eb31d37cb251cfe626c53eafd330df6",
9 | "version" : "0.31.1"
10 | }
11 | },
12 | {
13 | "identity" : "swift-argument-parser",
14 | "kind" : "remoteSourceControl",
15 | "location" : "https://github.com/apple/swift-argument-parser.git",
16 | "state" : {
17 | "revision" : "d2930e8fcf9c33162b9fcc1d522bc975e2d4179b",
18 | "version" : "1.0.1"
19 | }
20 | },
21 | {
22 | "identity" : "swiftplantuml",
23 | "kind" : "remoteSourceControl",
24 | "location" : "https://github.com/MarcoEidinger/SwiftPlantUML.git",
25 | "state" : {
26 | "revision" : "e2e93e026b0d1b4bd8947915e06d6ba5051b2da3",
27 | "version" : "0.8.0"
28 | }
29 | },
30 | {
31 | "identity" : "swiftybeaver",
32 | "kind" : "remoteSourceControl",
33 | "location" : "https://github.com/SwiftyBeaver/SwiftyBeaver.git",
34 | "state" : {
35 | "revision" : "2c039501d6eeb4d4cd4aec4a8d884ad28862e044",
36 | "version" : "1.9.5"
37 | }
38 | },
39 | {
40 | "identity" : "swxmlhash",
41 | "kind" : "remoteSourceControl",
42 | "location" : "https://github.com/drmohundro/SWXMLHash.git",
43 | "state" : {
44 | "revision" : "a4931e5c3bafbedeb1601d3bb76bbe835c6d475a",
45 | "version" : "5.0.1"
46 | }
47 | },
48 | {
49 | "identity" : "yams",
50 | "kind" : "remoteSourceControl",
51 | "location" : "https://github.com/jpsim/Yams.git",
52 | "state" : {
53 | "revision" : "9003d51672e516cc59297b7e96bff1dfdedcb4ea",
54 | "version" : "4.0.4"
55 | }
56 | }
57 | ],
58 | "version" : 2
59 | }
60 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp.xcodeproj/xcshareddata/xcschemes/SourceEditorExtension.xcscheme:
--------------------------------------------------------------------------------
1 |
2 |
6 |
9 |
10 |
16 |
22 |
23 |
24 |
30 |
36 |
37 |
38 |
39 |
40 |
45 |
46 |
47 |
48 |
58 |
61 |
62 |
63 |
69 |
70 |
71 |
72 |
80 |
82 |
88 |
89 |
90 |
91 |
93 |
94 |
97 |
98 |
99 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp.xcodeproj/xcshareddata/xcschemes/SwiftPlantUMLApp.xcscheme:
--------------------------------------------------------------------------------
1 |
2 |
5 |
8 |
9 |
15 |
21 |
22 |
23 |
24 |
25 |
30 |
31 |
32 |
33 |
43 |
45 |
51 |
52 |
53 |
54 |
60 |
62 |
68 |
69 |
70 |
71 |
73 |
74 |
77 |
78 |
79 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/AppDelegate.swift:
--------------------------------------------------------------------------------
1 | import Cocoa
2 | import SwiftUI
3 |
4 | @main
5 | class AppDelegate: NSObject, NSApplicationDelegate {
6 | func applicationDidFinishLaunching(_: Notification) {
7 | // Insert code here to initialize your application
8 | NSAppleEventManager.shared().setEventHandler(self, andSelector: #selector(handleAppleEvent(event:replyEvent:)), forEventClass: AEEventClass(kInternetEventClass), andEventID: AEEventID(kAEGetURL))
9 | }
10 |
11 | func application(_: NSApplication, open _: [URL]) {
12 | showPreferences(self)
13 | }
14 |
15 | @objc func handleAppleEvent(event _: NSAppleEventDescriptor, replyEvent _: NSAppleEventDescriptor) {
16 | showPreferences(self)
17 | }
18 |
19 | @IBAction func showPreferences(_ sender: Any) {
20 | let settingsView = NSHostingView(rootView: SettingsView().environmentObject(ContentViewModel()))
21 | settingsView.translatesAutoresizingMaskIntoConstraints = false
22 |
23 | let controller = NSViewController()
24 | controller.view = settingsView
25 |
26 | let window = NSWindow(contentViewController: controller)
27 | window.title = "Preferences"
28 |
29 | NSWindowController(window: window).showWindow(sender)
30 | }
31 |
32 | @IBAction func showTroubleshootingHelp(_: Any) {
33 | NSWorkspace.shared.open(URL(string: "https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension#troubleshooting")!)
34 | }
35 |
36 | @IBAction func showReleaseNotes(_: Any) {
37 | NSWorkspace.shared.open(URL(string: "https://github.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/releases")!)
38 | }
39 |
40 | @IBAction func showCommandLineToolInfo(_: Any) {
41 | NSWorkspace.shared.open(URL(string: "https://github.com/MarcoEidinger/SwiftPlantUML")!)
42 | }
43 |
44 | func applicationWillTerminate(_: Notification) {
45 | // Insert code here to tear down your application
46 | }
47 | }
48 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/AccentColor.colorset/Contents.json:
--------------------------------------------------------------------------------
1 | {
2 | "colors" : [
3 | {
4 | "idiom" : "universal"
5 | }
6 | ],
7 | "info" : {
8 | "author" : "xcode",
9 | "version" : 1
10 | }
11 | }
12 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/AppIcon.appiconset/1024.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/29539e2bd6a45f2e399bb2bcfa0c6f5899481895/SwiftPlantUMLApp/Assets.xcassets/AppIcon.appiconset/1024.png
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/AppIcon.appiconset/128.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/29539e2bd6a45f2e399bb2bcfa0c6f5899481895/SwiftPlantUMLApp/Assets.xcassets/AppIcon.appiconset/128.png
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/AppIcon.appiconset/16.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/29539e2bd6a45f2e399bb2bcfa0c6f5899481895/SwiftPlantUMLApp/Assets.xcassets/AppIcon.appiconset/16.png
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/AppIcon.appiconset/256.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/29539e2bd6a45f2e399bb2bcfa0c6f5899481895/SwiftPlantUMLApp/Assets.xcassets/AppIcon.appiconset/256.png
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/AppIcon.appiconset/32.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/29539e2bd6a45f2e399bb2bcfa0c6f5899481895/SwiftPlantUMLApp/Assets.xcassets/AppIcon.appiconset/32.png
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/AppIcon.appiconset/512.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/29539e2bd6a45f2e399bb2bcfa0c6f5899481895/SwiftPlantUMLApp/Assets.xcassets/AppIcon.appiconset/512.png
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/AppIcon.appiconset/64.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/29539e2bd6a45f2e399bb2bcfa0c6f5899481895/SwiftPlantUMLApp/Assets.xcassets/AppIcon.appiconset/64.png
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/AppIcon.appiconset/Contents.json:
--------------------------------------------------------------------------------
1 | {"images":[{"size":"128x128","expected-size":"128","filename":"128.png","folder":"Assets.xcassets/AppIcon.appiconset/","idiom":"mac","scale":"1x"},{"size":"256x256","expected-size":"256","filename":"256.png","folder":"Assets.xcassets/AppIcon.appiconset/","idiom":"mac","scale":"1x"},{"size":"128x128","expected-size":"256","filename":"256.png","folder":"Assets.xcassets/AppIcon.appiconset/","idiom":"mac","scale":"2x"},{"size":"256x256","expected-size":"512","filename":"512.png","folder":"Assets.xcassets/AppIcon.appiconset/","idiom":"mac","scale":"2x"},{"size":"32x32","expected-size":"32","filename":"32.png","folder":"Assets.xcassets/AppIcon.appiconset/","idiom":"mac","scale":"1x"},{"size":"512x512","expected-size":"512","filename":"512.png","folder":"Assets.xcassets/AppIcon.appiconset/","idiom":"mac","scale":"1x"},{"size":"16x16","expected-size":"16","filename":"16.png","folder":"Assets.xcassets/AppIcon.appiconset/","idiom":"mac","scale":"1x"},{"size":"16x16","expected-size":"32","filename":"32.png","folder":"Assets.xcassets/AppIcon.appiconset/","idiom":"mac","scale":"2x"},{"size":"32x32","expected-size":"64","filename":"64.png","folder":"Assets.xcassets/AppIcon.appiconset/","idiom":"mac","scale":"2x"},{"size":"512x512","expected-size":"1024","filename":"1024.png","folder":"Assets.xcassets/AppIcon.appiconset/","idiom":"mac","scale":"2x"}]}
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/Color.colorset/Contents.json:
--------------------------------------------------------------------------------
1 | {
2 | "colors" : [
3 | {
4 | "color" : {
5 | "color-space" : "srgb",
6 | "components" : {
7 | "alpha" : "1.000",
8 | "blue" : "1.000",
9 | "green" : "1.000",
10 | "red" : "1.000"
11 | }
12 | },
13 | "idiom" : "universal"
14 | },
15 | {
16 | "appearances" : [
17 | {
18 | "appearance" : "luminosity",
19 | "value" : "dark"
20 | }
21 | ],
22 | "color" : {
23 | "color-space" : "srgb",
24 | "components" : {
25 | "alpha" : "1.000",
26 | "blue" : "1.000",
27 | "green" : "1.000",
28 | "red" : "1.000"
29 | }
30 | },
31 | "idiom" : "universal"
32 | }
33 | ],
34 | "info" : {
35 | "author" : "xcode",
36 | "version" : 1
37 | }
38 | }
39 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/Contents.json:
--------------------------------------------------------------------------------
1 | {
2 | "info" : {
3 | "author" : "xcode",
4 | "version" : 1
5 | }
6 | }
7 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/Logo.imageset/128.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/29539e2bd6a45f2e399bb2bcfa0c6f5899481895/SwiftPlantUMLApp/Assets.xcassets/Logo.imageset/128.png
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/Logo.imageset/256.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/29539e2bd6a45f2e399bb2bcfa0c6f5899481895/SwiftPlantUMLApp/Assets.xcassets/Logo.imageset/256.png
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/Logo.imageset/64.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/29539e2bd6a45f2e399bb2bcfa0c6f5899481895/SwiftPlantUMLApp/Assets.xcassets/Logo.imageset/64.png
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/Logo.imageset/Contents.json:
--------------------------------------------------------------------------------
1 | {
2 | "images" : [
3 | {
4 | "filename" : "64.png",
5 | "idiom" : "universal",
6 | "scale" : "1x"
7 | },
8 | {
9 | "filename" : "128.png",
10 | "idiom" : "universal",
11 | "scale" : "2x"
12 | },
13 | {
14 | "filename" : "256.png",
15 | "idiom" : "universal",
16 | "scale" : "3x"
17 | }
18 | ],
19 | "info" : {
20 | "author" : "xcode",
21 | "version" : 1
22 | }
23 | }
24 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Assets.xcassets/appstore.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/MarcoEidinger/SwiftPlantUML-Xcode-Extension/29539e2bd6a45f2e399bb2bcfa0c6f5899481895/SwiftPlantUMLApp/Assets.xcassets/appstore.png
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Base.lproj/Main.storyboard:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
67 |
68 |
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 |
79 |
80 |
81 |
82 |
83 |
84 |
85 |
86 |
87 |
88 |
89 |
90 |
91 |
92 |
93 |
94 |
95 |
96 |
97 |
98 |
99 |
100 |
101 |
102 |
103 |
104 |
105 |
106 |
107 |
108 |
109 |
110 |
111 |
112 |
113 |
114 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/ContentView.swift:
--------------------------------------------------------------------------------
1 | import SwiftUI
2 |
3 | class ContentViewModel: ObservableObject {
4 | @Published var settings = SettingsModel()
5 | }
6 |
7 | struct ContentView: View {
8 | @EnvironmentObject private var mainState: ContentViewModel
9 |
10 | @State var selectedConfigurationScope: ConfigurationScope = .elements
11 |
12 | enum ConfigurationScope {
13 | case elements
14 | case members
15 | case others
16 | }
17 |
18 | var body: some View {
19 | HStack {
20 | Image("Logo")
21 | HStack {
22 | VStack(alignment: .leading) {
23 | HStack {
24 | Text("Step 1:")
25 | Button("Open System Preferences") {
26 | DispatchQueue.global().async {
27 | let task = Process()
28 | task.launchPath = "/usr/bin/env"
29 | task.arguments = ["open", "-b", "com.apple.systempreferences", "/System/Library/PreferencePanes/Extensions.prefPane"]
30 | task.launch()
31 | task.waitUntilExit()
32 | }
33 | }
34 | }.padding(5)
35 | HStack {
36 | Text("Step 2:")
37 | Text("Enable: Xcode Source Editor -> SwiftPlantUML").bold()
38 | }.padding(5)
39 | HStack {
40 | Text("Step 2:").hidden()
41 | Text("Enable: Finder -> View Swift Class Diagram").bold()
42 | }.padding(5)
43 | HStack {
44 | Text("Step 3:")
45 | Button("Set Preferences") {
46 | let appDelegate = NSApplication.shared.delegate! as! AppDelegate
47 | appDelegate.showPreferences(self)
48 | }
49 | Text("(Optional)").italic()
50 | }.padding(5)
51 | HStack {
52 | Text("Step 4:")
53 | Button("Close App") {
54 | NSApplication.shared.terminate(nil)
55 | }
56 | }.padding(5)
57 | }
58 | .padding()
59 | }
60 | }
61 | }
62 | }
63 |
64 | struct ContentView_Previews: PreviewProvider {
65 | static var previews: some View {
66 | if #available(macOS 11.0, *) {
67 | ForEach(ColorScheme.allCases, id: \.self, content:
68 | ContentView()
69 | .environmentObject(ContentViewModel())
70 | .preferredColorScheme)
71 | } else {
72 | ContentView().environmentObject(ContentViewModel())
73 | }
74 | }
75 | }
76 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Info.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | CFBundleDevelopmentRegion
6 | $(DEVELOPMENT_LANGUAGE)
7 | CFBundleExecutable
8 | $(EXECUTABLE_NAME)
9 | CFBundleIdentifier
10 | $(PRODUCT_BUNDLE_IDENTIFIER)
11 | CFBundleInfoDictionaryVersion
12 | 6.0
13 | CFBundleName
14 | SwiftPlantUML
15 | CFBundlePackageType
16 | $(PRODUCT_BUNDLE_PACKAGE_TYPE)
17 | CFBundleShortVersionString
18 | $(MARKETING_VERSION)
19 | CFBundleURLTypes
20 |
21 |
22 | CFBundleTypeRole
23 | Viewer
24 | CFBundleURLIconFile
25 |
26 | CFBundleURLName
27 | us.eidinger.SwiftPlantUML
28 | CFBundleURLSchemes
29 |
30 | swiftplantumlapp
31 |
32 |
33 |
34 | CFBundleVersion
35 | $(CURRENT_PROJECT_VERSION)
36 | LSApplicationCategoryType
37 | public.app-category.developer-tools
38 | LSMinimumSystemVersion
39 | $(MACOSX_DEPLOYMENT_TARGET)
40 | NSHumanReadableCopyright
41 | Copyright © 2021-2024 Marco Eidinger. All rights reserved.
42 | NSMainStoryboardFile
43 | Main
44 | NSPrincipalClass
45 | NSApplication
46 |
47 |
48 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Preview Content/Preview Assets.xcassets/Contents.json:
--------------------------------------------------------------------------------
1 | {
2 | "info" : {
3 | "author" : "xcode",
4 | "version" : 1
5 | }
6 | }
7 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/SettingsView.swift:
--------------------------------------------------------------------------------
1 | import Foundation
2 | import SwiftUI
3 | import SwiftPlantUMLFramework
4 |
5 | extension Theme {
6 | public static var chooseable: [String] {
7 | var values: [String] = []
8 | values.append("")
9 | values.append(contentsOf: Theme.preferred.map { $0.rawValue })
10 | return values
11 | }
12 | }
13 |
14 | struct SettingsView: View {
15 | @EnvironmentObject private var mainState: ContentViewModel
16 |
17 | @State var selectedConfigurationScope: ConfigurationScope = .elements
18 |
19 | enum ConfigurationScope {
20 | case elements
21 | case members
22 | case others
23 | }
24 |
25 | var body: some View {
26 | VStack(alignment: .leading) {
27 | HStack {
28 | Text("Choose what should be rendered by SwiftPlantUML")
29 | if #available(macOS 11.0, *) {
30 | Button {
31 | mainState.settings.resetDefaults()
32 | } label: {
33 | Image(systemName: "arrow.uturn.backward")
34 | }
35 | } else {
36 | Button("Reset") {
37 | mainState.settings.resetDefaults()
38 | }
39 | }
40 | }
41 | Text("")
42 | Picker("", selection: $selectedConfigurationScope) {
43 | Text("Elements").tag(ConfigurationScope.elements)
44 | Text("Members").tag(ConfigurationScope.members)
45 | Text("Others").tag(ConfigurationScope.others)
46 | }
47 | .pickerStyle(.segmented)
48 |
49 | VStack(alignment: .leading) {
50 | if selectedConfigurationScope == .elements {
51 | VStack {
52 | Text("having access level")
53 | VStack(alignment: .leading) {
54 | Toggle("Open", isOn: $mainState.settings.showElementsWithAccessLevelOpen)
55 | Toggle("Public", isOn: $mainState.settings.showElementsWithAccessLevelPublic)
56 | Toggle("Package", isOn: $mainState.settings.showElementsWithAccessLevelPackage)
57 | Toggle("Internal", isOn: $mainState.settings.showElementsWithAccessLevelPrivate)
58 | Toggle("Private", isOn: $mainState.settings.showElementsWithAccessLevelInternal)
59 | }
60 | }
61 | Toggle("with no members", isOn: $mainState.settings.showEmptyMembers)
62 | }
63 | if selectedConfigurationScope == .members {
64 | VStack(alignment: .leading) {
65 | Text("having access level")
66 | Toggle("Open", isOn: $mainState.settings.showMembersWithAccessLevelOpen)
67 | Toggle("Public", isOn: $mainState.settings.showMembersWithAccessLevelPublic)
68 | Toggle("Package", isOn: $mainState.settings.showMembersWithAccessLevelPackage)
69 | Toggle("Internal", isOn: $mainState.settings.showMembersWithAccessLevelInternal)
70 | Toggle("Private", isOn: $mainState.settings.showMembersWithAccessLevelPrivate)
71 | }
72 | }
73 | if selectedConfigurationScope == .others {
74 | VStack(alignment: .leading) {
75 | HStack {
76 | Spacer(minLength: 19)
77 | Picker("Theme", selection: $mainState.settings.theme) {
78 | ForEach(Theme.chooseable, id: \.self) {
79 | Text($0)
80 | }
81 | }
82 | Spacer(minLength: 150)
83 | }
84 | HStack {
85 | Spacer(minLength: 19)
86 | Picker("Show extensions", selection: $mainState.settings.showExtensionsValue) {
87 | Text(ExtensionVisualization.all.rawValue).tag(ExtensionVisualization.all.rawValue)
88 | Text(ExtensionVisualization.merged.rawValue).tag(ExtensionVisualization.merged.rawValue)
89 | Text(ExtensionVisualization.none.rawValue).tag(ExtensionVisualization.none.rawValue)
90 | }
91 | Spacer(minLength: 150)
92 | }
93 | Toggle("Show generics", isOn: $mainState.settings.showGenerics)
94 | Toggle("Show nested types", isOn: $mainState.settings.showNestedTypes)
95 | }
96 | }
97 | }
98 | .frame(height: 150)
99 | }
100 | .padding()
101 | .frame(width: 400, height: 250)
102 | }
103 | }
104 |
105 | struct SettingsView_Previews: PreviewProvider {
106 | static var previews: some View {
107 | if #available(macOS 11.0, *) {
108 | ForEach(ColorScheme.allCases, id: \.self, content:
109 | SettingsView()
110 | .environmentObject(ContentViewModel())
111 | .preferredColorScheme)
112 | } else {
113 | SettingsView()
114 | .environmentObject(ContentViewModel())
115 | }
116 | }
117 | }
118 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Shared/SettingsModel.swift:
--------------------------------------------------------------------------------
1 | import Foundation
2 |
3 | struct SettingsModel {
4 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.theme.key, defaultValue: "")
5 | var theme: String
6 |
7 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showGenerics.key, defaultValue: true)
8 | var showGenerics: Bool
9 |
10 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showNestedTypes.key, defaultValue: true)
11 | var showNestedTypes: Bool
12 |
13 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showExtensionsValue.key, defaultValue: "all")
14 | var showExtensionsValue: String
15 |
16 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showEmptyMembers.key, defaultValue: true)
17 | var showEmptyMembers: Bool
18 |
19 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showMembersWithAccessLevelOpen.key, defaultValue: true)
20 | var showMembersWithAccessLevelOpen
21 |
22 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showMembersWithAccessLevelPublic.key, defaultValue: true)
23 | var showMembersWithAccessLevelPublic
24 |
25 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showMembersWithAccessLevelPackage.key, defaultValue: true)
26 | var showMembersWithAccessLevelPackage
27 |
28 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showMembersWithAccessLevelInternal.key, defaultValue: true)
29 | var showMembersWithAccessLevelInternal
30 |
31 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showMembersWithAccessLevelPrivate.key, defaultValue: true)
32 | var showMembersWithAccessLevelPrivate: Bool
33 |
34 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showElementsWithAccessLevelOpen.key, defaultValue: true)
35 | var showElementsWithAccessLevelOpen: Bool
36 |
37 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showElementsWithAccessLevelPublic.key, defaultValue: true)
38 | var showElementsWithAccessLevelPublic: Bool
39 |
40 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showElementsWithAccessLevelPackage.key, defaultValue: true)
41 | var showElementsWithAccessLevelPackage: Bool
42 |
43 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showElementsWithAccessLevelInternal.key, defaultValue: true)
44 | var showElementsWithAccessLevelInternal: Bool
45 |
46 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showElementsWithAccessLevelPrivate.key, defaultValue: true)
47 | var showElementsWithAccessLevelPrivate: Bool
48 |
49 | mutating func resetDefaults() {
50 | theme = ""
51 | showGenerics = true
52 | showNestedTypes = true
53 | showExtensionsValue = "all"
54 | showEmptyMembers = true
55 | showMembersWithAccessLevelOpen = true
56 | showMembersWithAccessLevelPublic = true
57 | showMembersWithAccessLevelPackage = true
58 | showMembersWithAccessLevelInternal = true
59 | showMembersWithAccessLevelPrivate = true
60 | showElementsWithAccessLevelOpen = true
61 | showElementsWithAccessLevelPublic = true
62 | showElementsWithAccessLevelPackage = true
63 | showElementsWithAccessLevelInternal = true
64 | showElementsWithAccessLevelPrivate = true
65 | }
66 | }
67 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/Shared/Utils.swift:
--------------------------------------------------------------------------------
1 | import Foundation
2 |
3 | public extension Bool {
4 | func toString() -> String {
5 | self == true ? "true" : "false"
6 | }
7 | }
8 |
9 | public extension UserDefaults {
10 | static let swiftplantumlapp = UserDefaults(suiteName: "group.6V66CC3AN6.us.eidinger.SwiftPlantUML")!
11 |
12 | static func printKeyValues(group _: UserDefaults) {
13 | for (key, value) in UserDefaults.swiftplantumlapp.dictionaryRepresentation() {
14 | print("\(key) = \(value) \n")
15 | }
16 | }
17 | }
18 |
19 | @propertyWrapper struct UserDefaultsWrapper {
20 | let key: String
21 | let defaultValue: T
22 |
23 | init(_ key: String, defaultValue: T) {
24 | self.key = key
25 | self.defaultValue = defaultValue
26 | }
27 |
28 | var wrappedValue: T {
29 | get {
30 | UserDefaults.swiftplantumlapp.object(forKey: key) as? T ?? defaultValue
31 | }
32 | set {
33 | UserDefaults.swiftplantumlapp.set(newValue, forKey: key)
34 | }
35 | }
36 | }
37 |
38 | // MARK: Settings
39 |
40 | public enum UserDefaultsKeys {
41 | public enum SettingsKeys: String, CaseIterable {
42 | case theme
43 | case showGenerics
44 | case showNestedTypes
45 | case showExtensionsValue
46 | case showEmptyMembers
47 | case showMembersWithAccessLevelOpen
48 | case showMembersWithAccessLevelPublic
49 | case showMembersWithAccessLevelPackage
50 | case showMembersWithAccessLevelInternal
51 | case showMembersWithAccessLevelPrivate
52 | case showElementsWithAccessLevelOpen
53 | case showElementsWithAccessLevelPublic
54 | case showElementsWithAccessLevelPackage
55 | case showElementsWithAccessLevelInternal
56 | case showElementsWithAccessLevelPrivate
57 |
58 | var key: String {
59 | "us.eidinger.SwiftPlantUML." + rawValue
60 | }
61 | }
62 | }
63 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/SwiftPlantUMLApp.entitlements:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | com.apple.security.app-sandbox
6 |
7 | com.apple.security.application-groups
8 |
9 | group.$(TeamIdentifierPrefix)us.eidinger.SwiftPlantUML
10 |
11 | com.apple.security.files.user-selected.read-only
12 |
13 |
14 |
15 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/SwiftPlantUMLAppApp.swift:
--------------------------------------------------------------------------------
1 | import SwiftUI
2 |
3 | // @main
4 | // struct SwiftPlantUMLAppApp: App {
5 | // @StateObject private var mainState = ContentViewModel()
6 | //
7 | // var body: some Scene {
8 | // WindowGroup {
9 | // ContentView()
10 | // .environmentObject(mainState)
11 | // .frame(width: 800, height: 650)
12 | // }
13 | // }
14 | // }
15 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/ThemeView.swift:
--------------------------------------------------------------------------------
1 | //
2 | // ThemeView.swift
3 | // SwiftPlantUMLApp
4 | //
5 | // Created by Marco Eidinger on 1/20/23.
6 | //
7 |
8 | import SwiftUI
9 |
10 | struct ThemeView: View {
11 | var body: some View {
12 | Text(/*@START_MENU_TOKEN@*/"Hello, World!"/*@END_MENU_TOKEN@*/)
13 | }
14 | }
15 |
16 | struct ThemeView_Previews: PreviewProvider {
17 | static var previews: some View {
18 | ThemeView()
19 | }
20 | }
21 |
--------------------------------------------------------------------------------
/SwiftPlantUMLApp/ViewController.swift:
--------------------------------------------------------------------------------
1 | import Cocoa
2 | import SwiftUI
3 |
4 | class ViewController: NSViewController {
5 | override func viewDidLoad() {
6 | super.viewDidLoad()
7 |
8 | let swiftUIView = NSHostingView(rootView: ContentView().environmentObject(ContentViewModel()))
9 | swiftUIView.translatesAutoresizingMaskIntoConstraints = false
10 |
11 | view.addSubview(swiftUIView)
12 | swiftUIView.centerYAnchor.constraint(equalTo: view.centerYAnchor).isActive = true
13 | swiftUIView.centerXAnchor.constraint(equalTo: view.centerXAnchor).isActive = true
14 | }
15 |
16 | override var representedObject: Any? {
17 | didSet {
18 | // Update the view, if already loaded.
19 | }
20 | }
21 | }
22 |
--------------------------------------------------------------------------------
/XPCService/Info.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | CFBundleDevelopmentRegion
6 | $(DEVELOPMENT_LANGUAGE)
7 | CFBundleDisplayName
8 | XPCService
9 | CFBundleExecutable
10 | $(EXECUTABLE_NAME)
11 | CFBundleIdentifier
12 | $(PRODUCT_BUNDLE_IDENTIFIER)
13 | CFBundleInfoDictionaryVersion
14 | 6.0
15 | CFBundleName
16 | $(PRODUCT_NAME)
17 | CFBundlePackageType
18 | $(PRODUCT_BUNDLE_PACKAGE_TYPE)
19 | CFBundleShortVersionString
20 | $(MARKETING_VERSION)
21 | CFBundleVersion
22 | $(CURRENT_PROJECT_VERSION)
23 | NSHumanReadableCopyright
24 | Copyright © 2021-2024 Marco Eidinger. All rights reserved.
25 | XPCService
26 |
27 | ServiceType
28 | Application
29 |
30 |
31 |
32 |
--------------------------------------------------------------------------------
/XPCService/XPCService.entitlements:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | com.apple.security.application-groups
6 |
7 | group.$(TeamIdentifierPrefix)us.eidinger.SwiftPlantUML
8 |
9 |
10 |
11 |
--------------------------------------------------------------------------------
/XPCService/XPCService.swift:
--------------------------------------------------------------------------------
1 | import Foundation
2 | import SwiftPlantUMLFramework
3 |
4 | @objc class XPCService: NSObject, XPCServiceProtocol {
5 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.theme.key, defaultValue: "")
6 | var theme: String
7 |
8 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showGenerics.key, defaultValue: true)
9 | var showGenerics: Bool
10 |
11 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showNestedTypes.key, defaultValue: true)
12 | var showNestedTypes: Bool
13 |
14 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showExtensionsValue.key, defaultValue: ExtensionVisualization.default.rawValue)
15 | var showExtensionsValue: String
16 |
17 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showEmptyMembers.key, defaultValue: true)
18 | var showEmptyMembers: Bool
19 |
20 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showMembersWithAccessLevelOpen.key, defaultValue: true)
21 | var showMembersWithAccessLevelOpen: Bool
22 |
23 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showMembersWithAccessLevelPublic.key, defaultValue: true)
24 | var showMembersWithAccessLevelPublic: Bool
25 |
26 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showMembersWithAccessLevelPackage.key, defaultValue: true)
27 | var showMembersWithAccessLevelPackage: Bool
28 |
29 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showMembersWithAccessLevelInternal.key, defaultValue: true)
30 | var showMembersWithAccessLevelInternal: Bool
31 |
32 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showMembersWithAccessLevelPrivate.key, defaultValue: true)
33 | var showMembersWithAccessLevelPrivate: Bool
34 |
35 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showElementsWithAccessLevelOpen.key, defaultValue: true)
36 | var showElementsWithAccessLevelOpen: Bool
37 |
38 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showElementsWithAccessLevelPublic.key, defaultValue: true)
39 | var showElementsWithAccessLevelPublic: Bool
40 |
41 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showElementsWithAccessLevelPackage.key, defaultValue: true)
42 | var showElementsWithAccessLevelPackage: Bool
43 |
44 |
45 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showElementsWithAccessLevelInternal.key, defaultValue: true)
46 | var showElementsWithAccessLevelInternal: Bool
47 |
48 | @UserDefaultsWrapper(UserDefaultsKeys.SettingsKeys.showElementsWithAccessLevelPrivate.key, defaultValue: true)
49 | var showElementsWithAccessLevelPrivate: Bool
50 |
51 | var extensionVisualization: ExtensionVisualization {
52 | ExtensionVisualization(rawValue: showExtensionsValue) ?? .all
53 | }
54 |
55 | var showElementsWithAccessLevel: [AccessLevel] {
56 | var showElementsWithAccessLevel: [AccessLevel] = []
57 | if showElementsWithAccessLevelOpen {
58 | showElementsWithAccessLevel.append(.open)
59 | }
60 | if showElementsWithAccessLevelPublic {
61 | showElementsWithAccessLevel.append(.public)
62 | }
63 | if showElementsWithAccessLevelPackage {
64 | showElementsWithAccessLevel.append(.package)
65 | }
66 | if showElementsWithAccessLevelInternal {
67 | showElementsWithAccessLevel.append(.internal)
68 | }
69 | if showElementsWithAccessLevelPrivate {
70 | showElementsWithAccessLevel.append(.private)
71 | }
72 | return showElementsWithAccessLevel
73 | }
74 |
75 | var showMembersWithAccessLevel: [AccessLevel] {
76 | var showMembersWithAccessLevel: [AccessLevel] = []
77 | if showMembersWithAccessLevelOpen {
78 | showMembersWithAccessLevel.append(.open)
79 | }
80 | if showMembersWithAccessLevelPublic {
81 | showMembersWithAccessLevel.append(.public)
82 | }
83 | if showMembersWithAccessLevelPackage {
84 | showMembersWithAccessLevel.append(.package)
85 | }
86 | if showMembersWithAccessLevelInternal {
87 | showMembersWithAccessLevel.append(.internal)
88 | }
89 | if showMembersWithAccessLevelPrivate {
90 | showMembersWithAccessLevel.append(.private)
91 | }
92 | return showMembersWithAccessLevel
93 | }
94 |
95 | var hideShowCommands: [String] {
96 | var hideShowCommands = [String]()
97 | if !showEmptyMembers {
98 | hideShowCommands.append("hide empty members")
99 | }
100 | return hideShowCommands
101 | }
102 |
103 | var selectedTheme: Theme? {
104 | var selTheme: Theme? = nil
105 | if !theme.isEmpty {
106 | selTheme = Theme.__directive__(theme)
107 | }
108 | return selTheme
109 | }
110 |
111 | func generateDiagram(from content: String, completionHandler: @escaping (() -> Void)) {
112 | let config = assembleConfig()
113 | ClassDiagramGenerator().generate(from: content, with: config)
114 | completionHandler()
115 | }
116 |
117 | func generateDiagram(for paths: [String], completionHandler: @escaping (() -> Void)) {
118 | let config = assembleConfig()
119 | ClassDiagramGenerator().generate(for: paths, with: config, presentedBy: PlantUMLBrowserPresenter(format: .svg))
120 | completionHandler()
121 | }
122 |
123 | func assembleConfig() -> Configuration {
124 | let showNestedTypes = showNestedTypes
125 | let extensionVisualization = extensionVisualization
126 | let selectedTheme = selectedTheme
127 |
128 | return Configuration(elements: ElementOptions(havingAccessLevel: showElementsWithAccessLevel, showMembersWithAccessLevel: showMembersWithAccessLevel, showNestedTypes: showNestedTypes, showGenerics: showGenerics, showExtensions: extensionVisualization, showMemberAccessLevelAttribute: true, exclude: nil), hideShowCommands: hideShowCommands, theme: selectedTheme)
129 | }
130 | }
131 |
--------------------------------------------------------------------------------
/XPCService/XPCServiceProtocol.swift:
--------------------------------------------------------------------------------
1 | import Foundation
2 |
3 | @objc protocol XPCServiceProtocol {
4 | func generateDiagram(from content: String, completionHandler: @escaping (() -> Void))
5 | func generateDiagram(for paths: [String], completionHandler: @escaping (() -> Void))
6 | }
7 |
--------------------------------------------------------------------------------
/XPCService/main.swift:
--------------------------------------------------------------------------------
1 | import Foundation
2 |
3 | class ServiceDelegate: NSObject, NSXPCListenerDelegate {
4 | func listener(_: NSXPCListener, shouldAcceptNewConnection newConnection: NSXPCConnection) -> Bool {
5 | newConnection.exportedInterface = NSXPCInterface(with: XPCServiceProtocol.self)
6 | let exportedObject = XPCService()
7 | newConnection.exportedObject = exportedObject
8 | newConnection.resume()
9 | return true
10 | }
11 | }
12 |
13 | // Create the listener and resume it:
14 | let delegate = ServiceDelegate()
15 | let listener = NSXPCListener.service()
16 | listener.delegate = delegate
17 | listener.resume()
18 |
--------------------------------------------------------------------------------