Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -39,8 +39,8 @@ into four A4 pages at one inch per square (see [Sample map](#sample-map)).*
from [Pluck](https://github.com/scooper4711/pluck), can be dropped too.
- **Open from Scrollkeeper** (⇧⌘O): type part of a map's name to search the Flip-Mats, Flip-Tiles and other
maps you own on paizo.com, as listed by [Scrollkeeper](https://github.com/scooper4711/scrollkeeper)
(1.2 or later). A cloud marks the maps not downloaded yet: click it to download one in the background, or
press Return to download and open it in one go. For a map pack Scrollkeeper sends the PDF, which has twice
(1.4 or later), which stays in the background. A cloud marks the maps not downloaded yet: click it to
download one, or press Return to download and open it in one go, and watch the download's progress. For a map pack Scrollkeeper sends the PDF, which has twice
the resolution of the pack's JPGs. Mapsmith never signs in to Paizo itself; Scrollkeeper does the downloading.
- **Select** a map: its grid is detected and it is split into pages that fit the printable area of the
current printer and paper (**File › Page Setup…**). Edge strips thinner than 1 in are trimmed rather
Expand Down
43 changes: 43 additions & 0 deletions Resources/Info.plist
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,49 @@
<string>public.image</string>
</array>
</dict>
<dict>
<key>CFBundleTypeName</key>
<string>Scrollkeeper Library List</string>
<key>CFBundleTypeRole</key>
<string>Viewer</string>
<key>LSHandlerRank</key>
<string>Alternate</string>
<key>LSItemContentTypes</key>
<array>
<string>io.github.scooper4711.scrollkeeper.index</string>
</array>
</dict>
</array>
<key>UTImportedTypeDeclarations</key>
<array>
<dict>
<key>UTTypeIdentifier</key>
<string>io.github.scooper4711.scrollkeeper.index</string>
<key>UTTypeDescription</key>
<string>Scrollkeeper Library List</string>
<key>UTTypeConformsTo</key>
<array>
<string>public.json</string>
</array>
<key>UTTypeTagSpecification</key>
<dict>
<key>public.filename-extension</key>
<array>
<string>scrollkeeperindex</string>
</array>
</dict>
</dict>
</array>
<key>CFBundleURLTypes</key>
<array>
<dict>
<key>CFBundleURLName</key>
<string>com.github.scooper4711.Mapsmith.handoff</string>
<key>CFBundleURLSchemes</key>
<array>
<string>mapsmith</string>
</array>
</dict>
</array>
</dict>
</plist>
2 changes: 0 additions & 2 deletions Sources/Mapsmith/AppModel.swift
Original file line number Diff line number Diff line change
Expand Up @@ -29,8 +29,6 @@ final class AppModel {
private(set) var scaleSource: ScaleSource?
private(set) var isBusy = false
var errorMessage: String?
/// Shows File ▸ Open from Scrollkeeper… on this window.
var showsScrollkeeperSearch = false

/// User-entered pixels per inch; overrides detection when set.
var manualPixelsPerInch: Double?
Expand Down
6 changes: 2 additions & 4 deletions Sources/Mapsmith/ContentView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -23,9 +23,6 @@ struct ContentView: View {
.onDrop(of: MapDrop.acceptedTypes, isTargeted: nil) { providers in
MapDrop.open(providers, with: router)
}
.sheet(isPresented: $model.showsScrollkeeperSearch) {
ScrollkeeperSearchSheet(library: ScrollkeeperLibrary(launcher: WorkspaceLauncher()))
}
.alert("Something went wrong", isPresented: Binding(
get: { model.errorMessage != nil }, set: { if !$0 { model.errorMessage = nil } }
)) {
Expand All @@ -51,6 +48,7 @@ struct ContentView: View {
/// Sidebar: a thumbnail for every map in the open file.
struct MapListView: View {
@Environment(AppModel.self) private var model
@Environment(\.openWindow) private var openWindow

var body: some View {
@Bindable var model = model
Expand All @@ -60,7 +58,7 @@ struct MapListView: View {
} description: {
Text("Open or drop a PDF or image of a battle map.")
} actions: {
Button("Open from Scrollkeeper…") { model.showsScrollkeeperSearch = true }
Button("Open from Scrollkeeper…") { openWindow(id: ScrollkeeperWindow.id) }
}
} else {
List(model.items, selection: $model.selectedItemID) { item in
Expand Down
27 changes: 23 additions & 4 deletions Sources/Mapsmith/MapsmithApp.swift
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,13 @@ struct MapsmithApp: App {
}
.defaultSize(width: 1300, height: 850)
.commands { AppCommands(router: appDelegate.router, recents: appDelegate.recents) }

// A window of its own, not a sheet: the links and the list Scrollkeeper sends arrive while it is
// open, and SwiftUI gives them a new document window when the frontmost one has a sheet up.
Window("Open from Scrollkeeper", id: ScrollkeeperWindow.id) {
ScrollkeeperWindow(bridge: appDelegate.scrollkeeper)
}
.windowResizability(.contentSize)
}
}

Expand All @@ -23,14 +30,14 @@ struct AppCommands: Commands {
let router: DocumentRouter
@ObservedObject var recents: RecentDocuments
@FocusedValue(\.documentModel) private var model
@Environment(\.openWindow) private var openWindow

var body: some Commands {
CommandGroup(replacing: .newItem) {
Button("Open…") { router.open(OpenPanel.chooseFiles()) }
.keyboardShortcut("o")
Button("Open from Scrollkeeper…") { model?.showsScrollkeeperSearch = true }
Button("Open from Scrollkeeper…") { openWindow(id: ScrollkeeperWindow.id) }
.keyboardShortcut("o", modifiers: [.command, .shift])
.disabled(model == nil)
Menu("Open Recent") {
ForEach(recents.urls, id: \.self) { url in
Button(url.lastPathComponent) { router.open([url]) }
Expand Down Expand Up @@ -72,14 +79,26 @@ enum OpenPanel {
}
}

/// Handles files opened from Finder (double-click, drag onto the Dock icon, Open With).
/// Handles files opened from Finder (double-click, drag onto the Dock icon, Open With), and what
/// Scrollkeeper hands over: the list of maps, status links and the maps themselves.
@MainActor
final class AppDelegate: NSObject, NSApplicationDelegate {
let router = DocumentRouter()
let recents = RecentDocuments(store: SystemRecentDocuments())
let scrollkeeper = ScrollkeeperBridge(launcher: WorkspaceLauncher())

func application(_ application: NSApplication, open urls: [URL]) {
router.open(urls)
var documents: [URL] = []
for url in urls {
if ScrollkeeperBridge.isStatusLink(url) {
scrollkeeper.receiveStatus(url)
} else if ScrollkeeperIndex.isIndexFile(url) {
scrollkeeper.receive(url)
} else {
documents.append(url)
}
}
router.open(documents)
}

func applicationShouldTerminateAfterLastWindowClosed(_ sender: NSApplication) -> Bool { true }
Expand Down
166 changes: 0 additions & 166 deletions Sources/Mapsmith/ScrollkeeperSearch.swift

This file was deleted.

Loading
Loading