From 6f30d9287c3616cb311979415b331eda0e2e787c Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Tue, 7 May 2024 19:15:23 +0100 Subject: [PATCH 01/66] Package.resolved changed --- .../xcshareddata/swiftpm/Package.resolved | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/CodeEdit.xcodeproj/project.xcworkspace/xcshareddata/swiftpm/Package.resolved b/CodeEdit.xcodeproj/project.xcworkspace/xcshareddata/swiftpm/Package.resolved index cb92aa4d41..7790485dfd 100644 --- a/CodeEdit.xcodeproj/project.xcworkspace/xcshareddata/swiftpm/Package.resolved +++ b/CodeEdit.xcodeproj/project.xcworkspace/xcshareddata/swiftpm/Package.resolved @@ -1,5 +1,5 @@ { - "originHash" : "029e3feb7277e502c419e04acfc23af6dd70755f3984e9902ec582890724706b", + "originHash" : "41fcbec1ecbb7853d9ead798bba9d46f35f28767f4d41a009c8eeee022e99a84", "pins" : [ { "identity" : "anycodable", @@ -87,7 +87,7 @@ "kind" : "remoteSourceControl", "location" : "https://github.com/Wouter01/LogStream", "state" : { - "revision" : "5378bafdbf5de66b69da8cca9df9d16e19bfcf89", + "revision" : "6f83694b2675dcf3b1cea0a52546ff4469c18282", "version" : "1.3.0" } }, @@ -200,5 +200,5 @@ } } ], - "version" : 2 + "version" : 3 } From 71133895551a85f4c1a4b3c116fd316fa89ed807 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Tue, 7 May 2024 19:15:45 +0100 Subject: [PATCH 02/66] progress --- CodeEdit.xcodeproj/project.pbxproj | 4 + .../Views/WorkspaceCodeFileView.swift | 99 +++++++++++++-- .../Views/WorkspaceNonTextFileView.swift | 120 ++++++++++++++++++ 3 files changed, 209 insertions(+), 14 deletions(-) create mode 100644 CodeEdit/Features/Documents/Views/WorkspaceNonTextFileView.swift diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index a00ba87409..48665a81c3 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -285,6 +285,7 @@ 6195E3112B640485007261CA /* WorkspaceDocument+SearchState+IndexTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6195E3102B640485007261CA /* WorkspaceDocument+SearchState+IndexTests.swift */; }; 61A53A7E2B4449870093BF8A /* WorkspaceDocument+Find.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */; }; 61A53A812B4449F00093BF8A /* WorkspaceDocument+Index.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */; }; + 66F2C8C22BEAA700004674F7 /* WorkspaceNonTextFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C12BEAA700004674F7 /* WorkspaceNonTextFileView.swift */; }; 6C049A372A49E2DB00D42923 /* DirectoryEventStream.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */; }; 6C05A8AF284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */; }; 6C0617D62BDB4432008C9C42 /* LogStream in Frameworks */ = {isa = PBXBuildFile; productRef = 6C0617D52BDB4432008C9C42 /* LogStream */; }; @@ -848,6 +849,7 @@ 6195E3102B640485007261CA /* WorkspaceDocument+SearchState+IndexTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+SearchState+IndexTests.swift"; sourceTree = ""; }; 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Find.swift"; sourceTree = ""; }; 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Index.swift"; sourceTree = ""; }; + 66F2C8C12BEAA700004674F7 /* WorkspaceNonTextFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceNonTextFileView.swift; sourceTree = ""; }; 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DirectoryEventStream.swift; sourceTree = ""; }; 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Listeners.swift"; sourceTree = ""; }; 6C092ED92A53A58600489202 /* EditorLayout+StateRestoration.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "EditorLayout+StateRestoration.swift"; sourceTree = ""; }; @@ -1500,6 +1502,7 @@ isa = PBXGroup; children = ( 0485EB1E27E7458B00138301 /* WorkspaceCodeFileView.swift */, + 66F2C8C12BEAA700004674F7 /* WorkspaceNonTextFileView.swift */, ); path = Views; sourceTree = ""; @@ -3436,6 +3439,7 @@ B6D7EA5C297107DD00301FAC /* InspectorField.swift in Sources */, 043C321427E31FF6006AE443 /* CodeEditDocumentController.swift in Sources */, 85E4122A2A46C8CA00183F2B /* LocationsSettings.swift in Sources */, + 66F2C8C22BEAA700004674F7 /* WorkspaceNonTextFileView.swift in Sources */, 613899B12B6E6FDC00A5CAF6 /* Collection+FuzzySearch.swift in Sources */, 581550D129FBD30400684881 /* TextTableViewCell.swift in Sources */, 587B9E6629301D8F00AC7927 /* GitLabProjectHook.swift in Sources */, diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index b18c4a65fc..5418d206bb 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -8,29 +8,76 @@ import SwiftUI import UniformTypeIdentifiers import CodeEditSourceEditor +import AVKit +import PDFKit struct WorkspaceCodeFileView: View { - + @EnvironmentObject private var editorManager: EditorManager - + @EnvironmentObject private var editor: Editor - + + @Environment(\.edgeInsets) + private var edgeInsets + var file: CEWorkspaceFile var textViewCoordinators: [TextViewCoordinator] = [] - + + var workspaceStatusBarHeight = CGFloat(13) + @State private var update: Bool = false - + @ViewBuilder var codeView: some View { if let document = file.fileDocument { Group { - switch document.typeOfFile { - case .some(.text), .some(.data): - CodeFileView(codeFile: document, textViewCoordinators: textViewCoordinators) - default: - otherFileView(document, for: file) - } + + PdfFileView(document) + .padding(.top, edgeInsets.top - 1) + .padding(.bottom, StatusBarView.height - 11) } - .frame(maxWidth: .infinity, maxHeight: .infinity) + + // Group { + // switch document.typeOfFile { + // case .some(.text): + // CodeFileView(codeFile: document, textViewCoordinators: textViewCoordinators) + // .frame(maxWidth: .infinity, maxHeight: .infinity) + + // case .some(.image): + // OtherFileView(document) + .padding(.bottom, workspaceStatusBarHeight) + // GeometryReader { proxy in + // let nsImg = NSImage(contentsOf: document.fileURL!)! + // let pixelWidth = CGFloat(nsImg.representations.first!.pixelsWide) + // let pixelHeight = CGFloat(nsImg.representations.first!.pixelsHigh) + // + // var _ = print("proxy.size:", proxy.size.width, proxy.size.height) + // var _ = print("pixels:", pixelWidth, pixelHeight) + // + // if pixelWidth >= proxy.size.width || pixelHeight >= proxy.size.height { + // Image(nsImage: nsImg) + // .resizable() + // .scaledToFit() + // OtherFileView(document) + // .padding(.bottom, 25) + // //.containerRelativeFrame(<#T##Axis.Set#>, count: <#T##Int#>, span: <#T##Int#>, spacing: <#T##CGFloat#>, alignment: <#T##Alignment#>) + // } else { + // Image(nsImage: nsImg) + // .resizable() + // .frame(width: pixelWidth, height: pixelHeight) + // } + // } + + // case .some(.audiovisualContent): + // VideoPlayer(player: AVPlayer(playerItem: AVPlayerItem(url: document.fileURL!))) + // .padding(.top, 80) + // .padding(.bottom, 30) + // + // default: + // OtherFileView(document) + // .padding(.bottom, 25) + // } + // } + } else { if update { Spacer() @@ -58,7 +105,7 @@ struct WorkspaceCodeFileView: View { } } } - + @ViewBuilder private func otherFileView( _ otherFile: CodeFileDocument, @@ -85,7 +132,7 @@ struct WorkspaceCodeFileView: View { } } } - + var body: some View { codeView .frame(maxWidth: .infinity, maxHeight: .infinity) @@ -100,3 +147,27 @@ struct WorkspaceCodeFileView: View { } } } + +struct PdfFileView: NSViewRepresentable { + + private var fileDoc: CodeFileDocument + + init(_ fileDoc: CodeFileDocument) { + self.fileDoc = fileDoc + } + + func makeNSView(context: Context) -> PDFView { + let pdfView = PDFView() + if let fileDocURL = fileDoc.fileURL { + pdfView.document = PDFDocument(url: fileDocURL) + } + pdfView.backgroundColor = NSColor.windowBackgroundColor + return pdfView + } + + func updateNSView(_ pdfView: PDFView, context: Context) { + if let fileDocURL = fileDoc.fileURL { + pdfView.document = PDFDocument(url: fileDocURL) + } + } +} diff --git a/CodeEdit/Features/Documents/Views/WorkspaceNonTextFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceNonTextFileView.swift new file mode 100644 index 0000000000..ca68205b8d --- /dev/null +++ b/CodeEdit/Features/Documents/Views/WorkspaceNonTextFileView.swift @@ -0,0 +1,120 @@ +// +// WorkspaceNonTextFileView.swift +// CodeEdit +// +// Created by Paul Ebose on 2024/5/7. +// + +//import SwiftUI +//import Quartz +// +//struct WorkspaceNonTextFileView: NSViewRepresentable { +// // Properties: the file name (without extension), and whether we'll let +// // the user scale the preview content. +// private let file: CodeFileDocument +// +// func makeCoordinator() -> WorkspaceNonTextFileView.QLCoordinator { +// // The coordinator object implements the mechanics of dealing with +// // the live UIKit view controller. +// QLCoordinator(self) +// } +// +// func makeNSView(context: Context) -> QLPreviewView { +// // Create the preview view, and assign our Coordinator class +// // as its preview item. +// let preview = QLPreviewView() +// if let previewItem = file.previewItemURL { +// preview.previewItem = previewItem as QLPreviewItem +// } +// //preview.previewItem = context.coordinator +// return preview +// } +// +// func updateNSView(_ nsView: QLPreviewView, context: Context) { +// // do nothing +// } +// +// class QLCoordinator: NSObject, QLPreviewPanelDataSource { +// let parent: WorkspaceNonTextFileView +// private lazy var fileURL: URL = Bundle.main.url(forResource: parent.name, withExtension: "reality")! +// +// init(_ parent: WorkspaceNonTextFileView) { +// self.parent = parent +// super.init() +// } +// +// func numberOfPreviewItems(in panel: QLPreviewPanel!) -> Int { +// return 1 +// } +// +// func previewPanel(_ panel: QLPreviewPanel!, previewItemAt index: Int) -> (any QLPreviewItem)! { +// self.file +// } +// +// // let parent: ARQuickLookView +// // private lazy var fileURL: URL = Bundle.main.url(forResource: parent.name, +// // withExtension: "reality")! +// // +// // init(_ parent: ARQuickLookView) { +// // self.parent = parent +// // super.init() +// // } +// // +// // // The QLPreviewController asks its delegate how many items it has: +// // func numberOfPreviewItems(in controller: QLPreviewController) -> Int { +// // return 1 +// // } +// // +// // // For each item (see method above), the QLPreviewController asks for +// // // a QLPreviewItem instance describing that item: +// // func previewController( +// // _ controller: QLPreviewController, +// // previewItemAt index: Int +// // ) -> QLPreviewItem { +// // guard let fileURL = Bundle.main.url(forResource: parent.name, withExtension: "usdz") else { +// // fatalError("Unable to load \(parent.name).reality from main bundle") +// // } +// // +// // let item = ARQuickLookPreviewItem(fileAt: fileURL) +// // item.allowsContentScaling = parent.allowScaling +// // return item +// // } +// +// } +//} +// +////struct ContentView: View { +//// let qlCoordinator = QLCoordinator() +//// +//// var body: some View { +//// +//// // example.pdf is expected in app bundle resources +//// VStack { +//// MyPreview(fileName: "example.pdf") +//// Divider() +//// Button("Show panel") { +//// let panel = QLPreviewPanel.shared() +//// panel?.center() +//// panel?.dataSource = self.qlCoordinator +//// panel?.makeKeyAndOrderFront(nil) +//// } +//// } +//// } +//// +//// class QLCoordinator: NSObject, QLPreviewPanelDataSource { +//// func previewPanel(_ panel: QLPreviewPanel!, previewItemAt index: Int) -> QLPreviewItem! { +//// return loadPreviewItem(with: "example.pdf") as QLPreviewItem +//// } +//// +//// func numberOfPreviewItems(in controller: QLPreviewPanel) -> Int { +//// return 1 +//// } +//// } +////} +// +////struct WorkspaceNonTextFileView_Previews: PreviewProvider { +//// static var previews: some View { +//// WorkspaceNonTextFileView(file:) +//// } +////} + From 9a8500577d4512aec855ac5129f71692d35a6746 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Tue, 7 May 2024 19:22:01 +0100 Subject: [PATCH 03/66] minor doc change in CodeEditUI EffectView --- CodeEdit/Features/CodeEditUI/Views/EffectView.swift | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CodeEdit/Features/CodeEditUI/Views/EffectView.swift b/CodeEdit/Features/CodeEditUI/Views/EffectView.swift index 0c60b1384f..16389ee2c7 100644 --- a/CodeEdit/Features/CodeEditUI/Views/EffectView.swift +++ b/CodeEdit/Features/CodeEditUI/Views/EffectView.swift @@ -26,7 +26,7 @@ struct EffectView: NSViewRepresentable { /// /// By setting the /// [`emphasized`](https://developer.apple.com/documentation/appkit/nsvisualeffectview/1644721-isemphasized) - /// flag the emphasized state of the material will be used if available. + /// flag, the emphasized state of the material will be used if available. /// /// - Parameters: /// - material: The material to use. Defaults to `.headerView`. From 67499153ba07aed2153f9b1086a060d4fedbe7d6 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Tue, 7 May 2024 20:36:20 +0100 Subject: [PATCH 04/66] add WorkspacePdfFileView --- CodeEdit.xcodeproj/project.pbxproj | 4 ++ .../Views/WorkspaceCodeFileView.swift | 61 ++++++------------- .../Views/WorkspacePdfFileView.swift | 43 +++++++++++++ 3 files changed, 64 insertions(+), 44 deletions(-) create mode 100644 CodeEdit/Features/Documents/Views/WorkspacePdfFileView.swift diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index 48665a81c3..c7c82565a9 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -286,6 +286,7 @@ 61A53A7E2B4449870093BF8A /* WorkspaceDocument+Find.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */; }; 61A53A812B4449F00093BF8A /* WorkspaceDocument+Index.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */; }; 66F2C8C22BEAA700004674F7 /* WorkspaceNonTextFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C12BEAA700004674F7 /* WorkspaceNonTextFileView.swift */; }; + 66F2C8C42BEAA939004674F7 /* WorkspacePdfFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C32BEAA939004674F7 /* WorkspacePdfFileView.swift */; }; 6C049A372A49E2DB00D42923 /* DirectoryEventStream.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */; }; 6C05A8AF284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */; }; 6C0617D62BDB4432008C9C42 /* LogStream in Frameworks */ = {isa = PBXBuildFile; productRef = 6C0617D52BDB4432008C9C42 /* LogStream */; }; @@ -850,6 +851,7 @@ 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Find.swift"; sourceTree = ""; }; 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Index.swift"; sourceTree = ""; }; 66F2C8C12BEAA700004674F7 /* WorkspaceNonTextFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceNonTextFileView.swift; sourceTree = ""; }; + 66F2C8C32BEAA939004674F7 /* WorkspacePdfFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspacePdfFileView.swift; sourceTree = ""; }; 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DirectoryEventStream.swift; sourceTree = ""; }; 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Listeners.swift"; sourceTree = ""; }; 6C092ED92A53A58600489202 /* EditorLayout+StateRestoration.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "EditorLayout+StateRestoration.swift"; sourceTree = ""; }; @@ -1502,6 +1504,7 @@ isa = PBXGroup; children = ( 0485EB1E27E7458B00138301 /* WorkspaceCodeFileView.swift */, + 66F2C8C32BEAA939004674F7 /* WorkspacePdfFileView.swift */, 66F2C8C12BEAA700004674F7 /* WorkspaceNonTextFileView.swift */, ); path = Views; @@ -3365,6 +3368,7 @@ B6C4F2A62B3CABD200B2B140 /* HistoryInspectorItemView.swift in Sources */, B65B10FE2B08B07D002852CF /* SourceControlNavigatorChangesList.swift in Sources */, 58F2EB03292FB2B0004A9BDE /* Documentation.docc in Sources */, + 66F2C8C42BEAA939004674F7 /* WorkspacePdfFileView.swift in Sources */, 611192042B08CCED00D4459B /* SearchIndexer+ProgressiveSearch.swift in Sources */, 611192022B08CCDC00D4459B /* SearchIndexer+Search.swift in Sources */, 04BA7C272AE2E9F100584E1C /* GitClient+Push.swift in Sources */, diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 5418d206bb..07f7dd6bf5 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -12,39 +12,36 @@ import AVKit import PDFKit struct WorkspaceCodeFileView: View { - + @EnvironmentObject private var editorManager: EditorManager - + @EnvironmentObject private var editor: Editor - + @Environment(\.edgeInsets) private var edgeInsets - + var file: CEWorkspaceFile var textViewCoordinators: [TextViewCoordinator] = [] - - var workspaceStatusBarHeight = CGFloat(13) - + @State private var update: Bool = false - + @ViewBuilder var codeView: some View { - if let document = file.fileDocument { + if let documentURL = file.fileDocument?.fileURL { Group { - - PdfFileView(document) - .padding(.top, edgeInsets.top - 1) - .padding(.bottom, StatusBarView.height - 11) + WorkspacePdfFileView(documentURL) + .padding(.top, edgeInsets.top - 1.5) + .padding(.bottom, StatusBarView.height + 2) } - + // Group { // switch document.typeOfFile { // case .some(.text): // CodeFileView(codeFile: document, textViewCoordinators: textViewCoordinators) // .frame(maxWidth: .infinity, maxHeight: .infinity) - + // case .some(.image): // OtherFileView(document) - .padding(.bottom, workspaceStatusBarHeight) + // .padding(.bottom, workspaceStatusBarHeight) // GeometryReader { proxy in // let nsImg = NSImage(contentsOf: document.fileURL!)! // let pixelWidth = CGFloat(nsImg.representations.first!.pixelsWide) @@ -66,7 +63,7 @@ struct WorkspaceCodeFileView: View { // .frame(width: pixelWidth, height: pixelHeight) // } // } - + // case .some(.audiovisualContent): // VideoPlayer(player: AVPlayer(playerItem: AVPlayerItem(url: document.fileURL!))) // .padding(.top, 80) @@ -77,7 +74,7 @@ struct WorkspaceCodeFileView: View { // .padding(.bottom, 25) // } // } - + } else { if update { Spacer() @@ -105,7 +102,7 @@ struct WorkspaceCodeFileView: View { } } } - + @ViewBuilder private func otherFileView( _ otherFile: CodeFileDocument, @@ -132,7 +129,7 @@ struct WorkspaceCodeFileView: View { } } } - + var body: some View { codeView .frame(maxWidth: .infinity, maxHeight: .infinity) @@ -147,27 +144,3 @@ struct WorkspaceCodeFileView: View { } } } - -struct PdfFileView: NSViewRepresentable { - - private var fileDoc: CodeFileDocument - - init(_ fileDoc: CodeFileDocument) { - self.fileDoc = fileDoc - } - - func makeNSView(context: Context) -> PDFView { - let pdfView = PDFView() - if let fileDocURL = fileDoc.fileURL { - pdfView.document = PDFDocument(url: fileDocURL) - } - pdfView.backgroundColor = NSColor.windowBackgroundColor - return pdfView - } - - func updateNSView(_ pdfView: PDFView, context: Context) { - if let fileDocURL = fileDoc.fileURL { - pdfView.document = PDFDocument(url: fileDocURL) - } - } -} diff --git a/CodeEdit/Features/Documents/Views/WorkspacePdfFileView.swift b/CodeEdit/Features/Documents/Views/WorkspacePdfFileView.swift new file mode 100644 index 0000000000..bed0029026 --- /dev/null +++ b/CodeEdit/Features/Documents/Views/WorkspacePdfFileView.swift @@ -0,0 +1,43 @@ +// +// WorkspacePdfFileView.swift +// CodeEdit +// +// Created by Paul Ebose on 2024/5/7. +// + +import SwiftUI +import PDFKit.PDFView + +/// A SwiftUI view for previewing a PDF file. +/// +/// It takes in a file URL and attempts to preview a PDF. +/// +/// **Example Usage**: +/// ```swift +/// WorkspacePdfFileView(fileURL) +/// .padding(.top, tabBarHeight) +/// .padding(.bottom, statusBarHeight) +/// ``` +/// +/// This view has the same context menu available in the native MacOS Preview application. +struct WorkspacePdfFileView: NSViewRepresentable { + + private let fileURL: URL + + /// - Parameter fileURL: URL to the PDF file you want to preview. + init(_ fileURL: URL) { + self.fileURL = fileURL + } + + func makeNSView(context: Context) -> PDFView { + let pdfView = PDFView() + pdfView.document = PDFDocument(url: fileURL) + pdfView.backgroundColor = NSColor.windowBackgroundColor + return pdfView + } + + func updateNSView(_ pdfView: PDFView, context: Context) { + pdfView.document = PDFDocument(url: fileURL) + } + +} From 3d3893e513bb457322688b07077d8056d2f3b0c8 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Tue, 7 May 2024 21:18:38 +0100 Subject: [PATCH 05/66] allow WorkspacePdfFileView to be able to send data to SwiftUI --- .../Views/WorkspaceCodeFileView.swift | 4 ++- .../Views/WorkspacePdfFileView.swift | 36 ++++++++++++------- 2 files changed, 27 insertions(+), 13 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 07f7dd6bf5..d23fd65acc 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -25,10 +25,12 @@ struct WorkspaceCodeFileView: View { @State private var update: Bool = false + @State private var canPreviewFile: Bool = false + @ViewBuilder var codeView: some View { if let documentURL = file.fileDocument?.fileURL { Group { - WorkspacePdfFileView(documentURL) + WorkspacePdfFileView(fileURL: documentURL, canPreviewFile: $canPreviewFile) .padding(.top, edgeInsets.top - 1.5) .padding(.bottom, StatusBarView.height + 2) } diff --git a/CodeEdit/Features/Documents/Views/WorkspacePdfFileView.swift b/CodeEdit/Features/Documents/Views/WorkspacePdfFileView.swift index bed0029026..f23957ff1f 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePdfFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspacePdfFileView.swift @@ -21,23 +21,35 @@ import PDFKit.PDFView /// /// This view has the same context menu available in the native MacOS Preview application. struct WorkspacePdfFileView: NSViewRepresentable { - - private let fileURL: URL - - /// - Parameter fileURL: URL to the PDF file you want to preview. - init(_ fileURL: URL) { - self.fileURL = fileURL - } - + + let fileURL: URL + @Binding var canPreviewFile: Bool + func makeNSView(context: Context) -> PDFView { let pdfView = PDFView() pdfView.document = PDFDocument(url: fileURL) + if pdfView.document != nil { + // use the coordinator to update the binding + context.coordinator.pdfView.canPreviewFile = true + } pdfView.backgroundColor = NSColor.windowBackgroundColor return pdfView } - - func updateNSView(_ pdfView: PDFView, context: Context) { - pdfView.document = PDFDocument(url: fileURL) + + func updateNSView(_ nsView: PDFView, context: Context) { + nsView.document = PDFDocument(url: fileURL) + } + + func makeCoordinator() -> WorkspacePdfFileView.Coordinator { + // The coordinator object implements the mechanics of passing + // data between the NS view representable and Swift UI. + Coordinator(self) + } + + final class Coordinator: NSObject { + let pdfView: WorkspacePdfFileView + init(_ pdfView: WorkspacePdfFileView) { + self.pdfView = pdfView + } } - } From bd3fe372aab51d25074383e4b931514371970599 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Wed, 8 May 2024 07:51:41 +0100 Subject: [PATCH 06/66] properly name `WorkspacePdfFileView` to `WorkspacePDFView` --- CodeEdit.xcodeproj/project.pbxproj | 8 ++++---- .../Documents/Views/WorkspaceCodeFileView.swift | 2 +- ...spacePdfFileView.swift => WorkspacePDFView.swift} | 12 ++++++------ 3 files changed, 11 insertions(+), 11 deletions(-) rename CodeEdit/Features/Documents/Views/{WorkspacePdfFileView.swift => WorkspacePDFView.swift} (82%) diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index c7c82565a9..692011dc1e 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -286,7 +286,7 @@ 61A53A7E2B4449870093BF8A /* WorkspaceDocument+Find.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */; }; 61A53A812B4449F00093BF8A /* WorkspaceDocument+Index.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */; }; 66F2C8C22BEAA700004674F7 /* WorkspaceNonTextFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C12BEAA700004674F7 /* WorkspaceNonTextFileView.swift */; }; - 66F2C8C42BEAA939004674F7 /* WorkspacePdfFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C32BEAA939004674F7 /* WorkspacePdfFileView.swift */; }; + 66F2C8C42BEAA939004674F7 /* WorkspacePDFView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */; }; 6C049A372A49E2DB00D42923 /* DirectoryEventStream.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */; }; 6C05A8AF284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */; }; 6C0617D62BDB4432008C9C42 /* LogStream in Frameworks */ = {isa = PBXBuildFile; productRef = 6C0617D52BDB4432008C9C42 /* LogStream */; }; @@ -851,7 +851,7 @@ 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Find.swift"; sourceTree = ""; }; 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Index.swift"; sourceTree = ""; }; 66F2C8C12BEAA700004674F7 /* WorkspaceNonTextFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceNonTextFileView.swift; sourceTree = ""; }; - 66F2C8C32BEAA939004674F7 /* WorkspacePdfFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspacePdfFileView.swift; sourceTree = ""; }; + 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspacePDFView.swift; sourceTree = ""; }; 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DirectoryEventStream.swift; sourceTree = ""; }; 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Listeners.swift"; sourceTree = ""; }; 6C092ED92A53A58600489202 /* EditorLayout+StateRestoration.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "EditorLayout+StateRestoration.swift"; sourceTree = ""; }; @@ -1504,7 +1504,7 @@ isa = PBXGroup; children = ( 0485EB1E27E7458B00138301 /* WorkspaceCodeFileView.swift */, - 66F2C8C32BEAA939004674F7 /* WorkspacePdfFileView.swift */, + 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */, 66F2C8C12BEAA700004674F7 /* WorkspaceNonTextFileView.swift */, ); path = Views; @@ -3368,7 +3368,7 @@ B6C4F2A62B3CABD200B2B140 /* HistoryInspectorItemView.swift in Sources */, B65B10FE2B08B07D002852CF /* SourceControlNavigatorChangesList.swift in Sources */, 58F2EB03292FB2B0004A9BDE /* Documentation.docc in Sources */, - 66F2C8C42BEAA939004674F7 /* WorkspacePdfFileView.swift in Sources */, + 66F2C8C42BEAA939004674F7 /* WorkspacePDFView.swift in Sources */, 611192042B08CCED00D4459B /* SearchIndexer+ProgressiveSearch.swift in Sources */, 611192022B08CCDC00D4459B /* SearchIndexer+Search.swift in Sources */, 04BA7C272AE2E9F100584E1C /* GitClient+Push.swift in Sources */, diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index d23fd65acc..3ef1b8d9a5 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -30,7 +30,7 @@ struct WorkspaceCodeFileView: View { @ViewBuilder var codeView: some View { if let documentURL = file.fileDocument?.fileURL { Group { - WorkspacePdfFileView(fileURL: documentURL, canPreviewFile: $canPreviewFile) + WorkspacePDFView(fileURL: documentURL, canPreviewFile: $canPreviewFile) .padding(.top, edgeInsets.top - 1.5) .padding(.bottom, StatusBarView.height + 2) } diff --git a/CodeEdit/Features/Documents/Views/WorkspacePdfFileView.swift b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift similarity index 82% rename from CodeEdit/Features/Documents/Views/WorkspacePdfFileView.swift rename to CodeEdit/Features/Documents/Views/WorkspacePDFView.swift index f23957ff1f..97abd9ccf7 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePdfFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift @@ -1,5 +1,5 @@ // -// WorkspacePdfFileView.swift +// WorkspacePDFView.swift // CodeEdit // // Created by Paul Ebose on 2024/5/7. @@ -14,13 +14,13 @@ import PDFKit.PDFView /// /// **Example Usage**: /// ```swift -/// WorkspacePdfFileView(fileURL) +/// WorkspacePDFView(fileURL) /// .padding(.top, tabBarHeight) /// .padding(.bottom, statusBarHeight) /// ``` /// /// This view has the same context menu available in the native MacOS Preview application. -struct WorkspacePdfFileView: NSViewRepresentable { +struct WorkspacePDFView: NSViewRepresentable { let fileURL: URL @Binding var canPreviewFile: Bool @@ -40,15 +40,15 @@ struct WorkspacePdfFileView: NSViewRepresentable { nsView.document = PDFDocument(url: fileURL) } - func makeCoordinator() -> WorkspacePdfFileView.Coordinator { + func makeCoordinator() -> WorkspacePDFView.Coordinator { // The coordinator object implements the mechanics of passing // data between the NS view representable and Swift UI. Coordinator(self) } final class Coordinator: NSObject { - let pdfView: WorkspacePdfFileView - init(_ pdfView: WorkspacePdfFileView) { + let pdfView: WorkspacePDFView + init(_ pdfView: WorkspacePDFView) { self.pdfView = pdfView } } From a12e51ccf504150b877220fb56ef07acffb55034 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Wed, 8 May 2024 08:10:15 +0100 Subject: [PATCH 07/66] improve WorkspacePDFView docs --- CodeEdit/Features/Documents/Views/WorkspacePDFView.swift | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift index 97abd9ccf7..5b0e01652d 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift @@ -12,14 +12,19 @@ import PDFKit.PDFView /// /// It takes in a file URL and attempts to preview a PDF. /// +/// When a valid PDF view is created, the `canPreviewFile` boolean updates to `true`. +/// /// **Example Usage**: /// ```swift -/// WorkspacePDFView(fileURL) +/// WorkspacePDFView( +/// fileUrl: documentURL, +/// canPreviewFile: $canPreviewFile +/// ) /// .padding(.top, tabBarHeight) /// .padding(.bottom, statusBarHeight) /// ``` /// -/// This view has the same context menu available in the native MacOS Preview application. +/// This view provides a context menu that is the same as the one in the native MacOS Preview application, for PDF files. struct WorkspacePDFView: NSViewRepresentable { let fileURL: URL From 2b59534c058f28f72eb6828da40b8ea407863299 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Wed, 8 May 2024 08:17:56 +0100 Subject: [PATCH 08/66] add guards to WorkspacePDFView (makeNSView, updateNSView) --- .../Documents/Views/WorkspacePDFView.swift | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift index 5b0e01652d..6cd0f72fc0 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift @@ -32,17 +32,20 @@ struct WorkspacePDFView: NSViewRepresentable { func makeNSView(context: Context) -> PDFView { let pdfView = PDFView() - pdfView.document = PDFDocument(url: fileURL) - if pdfView.document != nil { - // use the coordinator to update the binding - context.coordinator.pdfView.canPreviewFile = true + // use the coordinator to update the state binding + guard let pdfDocument = PDFDocument(url: fileURL) else { + context.coordinator.pdfView.canPreviewFile = false + return pdfView } + context.coordinator.pdfView.canPreviewFile = true + pdfView.document = pdfDocument pdfView.backgroundColor = NSColor.windowBackgroundColor return pdfView } - func updateNSView(_ nsView: PDFView, context: Context) { - nsView.document = PDFDocument(url: fileURL) + func updateNSView(_ pdfView: PDFView, context: Context) { + guard let pdfDocument = PDFDocument(url: fileURL) else { return } + pdfView.document = pdfDocument } func makeCoordinator() -> WorkspacePDFView.Coordinator { From 6797552760a2f29d9a8b8421a2b1a2d5e3b723fa Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Wed, 8 May 2024 10:22:59 +0100 Subject: [PATCH 09/66] wip --- .../Views/WorkspaceCodeFileView.swift | 31 +++++++++++++++++-- 1 file changed, 28 insertions(+), 3 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 3ef1b8d9a5..e4614b9c66 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -29,10 +29,35 @@ struct WorkspaceCodeFileView: View { @ViewBuilder var codeView: some View { if let documentURL = file.fileDocument?.fileURL { + + // WorkspacePDFView(fileUrl: documentURL, canPreviewFile: $canPreviewFile) + // .padding(.top, edgeInsets.top - 1.5) + // .padding(.bottom, StatusBarView.height + 2) + Group { - WorkspacePDFView(fileURL: documentURL, canPreviewFile: $canPreviewFile) - .padding(.top, edgeInsets.top - 1.5) - .padding(.bottom, StatusBarView.height + 2) + GeometryReader { proxy in + let nsImage = NSImage(contentsOf: documentURL)! + let pixelWidth = CGFloat(nsImage.representations.first!.pixelsWide) + let pixelHeight = CGFloat(nsImage.representations.first!.pixelsHigh) + + // var _ = print("proxy.size:", proxy.size.width, proxy.size.height) + // var _ = print("pixels:", pixelWidth, pixelHeight) + // var _ = print("proxy.frame(in: .local).minX:", proxy.frame(in: .local).minX) + // var _ = print("proxy.frame(in: .local).midX:", proxy.frame(in: .local).midX) + // var _ = print("proxy.frame(in: .local).maxX:", proxy.frame(in: .local).maxX) + var _ = print("proxy.size.width:", proxy.size.width) + var _ = print("pixelWidth:", pixelWidth) + var _ = print("(proxy.size.width / 2) - (pixelWidth / 2):", ((proxy.size.width/2) - pixelWidth) / 2) + + Image(nsImage: nsImage) + .resizable() + .scaledToFit() + .padding(.top, edgeInsets.top) + .padding(.bottom, StatusBarView.height) + .frame(maxWidth: min(proxy.size.width, pixelWidth), maxHeight: min(proxy.size.height, pixelHeight)) + .position(x: 457, y: 0) // 649 + .background(.bar) + } } // Group { From 15291c086e33e7100583909933446be878ebb480 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Wed, 8 May 2024 11:09:05 +0100 Subject: [PATCH 10/66] wip 2 --- .../Views/WorkspaceCodeFileView.swift | 45 +++++++++---------- 1 file changed, 21 insertions(+), 24 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index e4614b9c66..5d7998d06f 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -34,30 +34,27 @@ struct WorkspaceCodeFileView: View { // .padding(.top, edgeInsets.top - 1.5) // .padding(.bottom, StatusBarView.height + 2) - Group { - GeometryReader { proxy in - let nsImage = NSImage(contentsOf: documentURL)! - let pixelWidth = CGFloat(nsImage.representations.first!.pixelsWide) - let pixelHeight = CGFloat(nsImage.representations.first!.pixelsHigh) - - // var _ = print("proxy.size:", proxy.size.width, proxy.size.height) - // var _ = print("pixels:", pixelWidth, pixelHeight) - // var _ = print("proxy.frame(in: .local).minX:", proxy.frame(in: .local).minX) - // var _ = print("proxy.frame(in: .local).midX:", proxy.frame(in: .local).midX) - // var _ = print("proxy.frame(in: .local).maxX:", proxy.frame(in: .local).maxX) - var _ = print("proxy.size.width:", proxy.size.width) - var _ = print("pixelWidth:", pixelWidth) - var _ = print("(proxy.size.width / 2) - (pixelWidth / 2):", ((proxy.size.width/2) - pixelWidth) / 2) - - Image(nsImage: nsImage) - .resizable() - .scaledToFit() - .padding(.top, edgeInsets.top) - .padding(.bottom, StatusBarView.height) - .frame(maxWidth: min(proxy.size.width, pixelWidth), maxHeight: min(proxy.size.height, pixelHeight)) - .position(x: 457, y: 0) // 649 - .background(.bar) - } + GeometryReader { proxy in + let nsImage = NSImage(contentsOf: documentURL)! + let pixelWidth = CGFloat(nsImage.representations.first!.pixelsWide) + let pixelHeight = CGFloat(nsImage.representations.first!.pixelsHigh) + + // var _ = print("proxy.size:", proxy.size.width, proxy.size.height) + // var _ = print("pixels:", pixelWidth, pixelHeight) + // var _ = print("proxy.frame(in: .local).minX:", proxy.frame(in: .local).minX) + // var _ = print("proxy.frame(in: .local).midX:", proxy.frame(in: .local).midX) + // var _ = print("proxy.frame(in: .local).maxX:", proxy.frame(in: .local).maxX) + var _ = print("proxy.size.width:", proxy.size.width) + var _ = print("pixelWidth:", pixelWidth) + + Image(nsImage: nsImage) + .resizable() + .scaledToFit() + .padding(.top, edgeInsets.top) + .padding(.bottom, StatusBarView.height) + .frame(width: min(proxy.size.width, pixelWidth), height: min(proxy.size.height, pixelHeight)) + .position(x: (pixelWidth / 2) + ((proxy.size.width - pixelWidth) / 2) - (proxy.size.width / 2), y: (pixelHeight / 2) + ((proxy.size.height - pixelHeight) / 2)) + } // Group { From 2fd13b42fa7cc2c63e39c7335db6448d00484704 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Wed, 8 May 2024 11:46:29 +0100 Subject: [PATCH 11/66] correct padding --- .../Views/WorkspaceCodeFileView.swift | 21 ++++++++++++------- 1 file changed, 13 insertions(+), 8 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 5d7998d06f..e75ce83039 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -31,8 +31,8 @@ struct WorkspaceCodeFileView: View { if let documentURL = file.fileDocument?.fileURL { // WorkspacePDFView(fileUrl: documentURL, canPreviewFile: $canPreviewFile) - // .padding(.top, edgeInsets.top - 1.5) - // .padding(.bottom, StatusBarView.height + 2) + // .padding(.top, edgeInsets.top - 1.74) + // .padding(.bottom, StatusBarView.height + 1.26) GeometryReader { proxy in let nsImage = NSImage(contentsOf: documentURL)! @@ -44,18 +44,23 @@ struct WorkspaceCodeFileView: View { // var _ = print("proxy.frame(in: .local).minX:", proxy.frame(in: .local).minX) // var _ = print("proxy.frame(in: .local).midX:", proxy.frame(in: .local).midX) // var _ = print("proxy.frame(in: .local).maxX:", proxy.frame(in: .local).maxX) - var _ = print("proxy.size.width:", proxy.size.width) - var _ = print("pixelWidth:", pixelWidth) + // var _ = print("proxy.size.width:", proxy.size.width) + // var _ = print("pixelWidth:", pixelWidth) Image(nsImage: nsImage) .resizable() + .background(.red) .scaledToFit() - .padding(.top, edgeInsets.top) - .padding(.bottom, StatusBarView.height) - .frame(width: min(proxy.size.width, pixelWidth), height: min(proxy.size.height, pixelHeight)) - .position(x: (pixelWidth / 2) + ((proxy.size.width - pixelWidth) / 2) - (proxy.size.width / 2), y: (pixelHeight / 2) + ((proxy.size.height - pixelHeight) / 2)) + .background(.blue) + .frame(maxWidth: min(pixelWidth, .infinity), maxHeight: min(pixelHeight, .infinity)) + .border(.purple) + // .padding() + // .position(x: (pixelWidth / 2) + ((proxy.size.width - pixelWidth) / 2) - (proxy.size.width / 2), y: (pixelHeight / 2) + ((proxy.size.height - pixelHeight) / 2)) } + .padding(.top, edgeInsets.top - 1.74) + .padding(.bottom, StatusBarView.height + 1.26) + .background(.teal) // Group { // switch document.typeOfFile { From 7ae71a07a35a1698735109e065aa037b06b5dc5b Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Wed, 8 May 2024 22:58:10 +0100 Subject: [PATCH 12/66] progress? not --- .../Views/WorkspaceCodeFileView.swift | 43 +++++++++++-------- 1 file changed, 24 insertions(+), 19 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index e75ce83039..6ab3c72c94 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -10,6 +10,8 @@ import UniformTypeIdentifiers import CodeEditSourceEditor import AVKit import PDFKit +import QuickLookUI +import QuickLook struct WorkspaceCodeFileView: View { @@ -39,27 +41,30 @@ struct WorkspaceCodeFileView: View { let pixelWidth = CGFloat(nsImage.representations.first!.pixelsWide) let pixelHeight = CGFloat(nsImage.representations.first!.pixelsHigh) - // var _ = print("proxy.size:", proxy.size.width, proxy.size.height) - // var _ = print("pixels:", pixelWidth, pixelHeight) - // var _ = print("proxy.frame(in: .local).minX:", proxy.frame(in: .local).minX) - // var _ = print("proxy.frame(in: .local).midX:", proxy.frame(in: .local).midX) - // var _ = print("proxy.frame(in: .local).maxX:", proxy.frame(in: .local).maxX) - // var _ = print("proxy.size.width:", proxy.size.width) - // var _ = print("pixelWidth:", pixelWidth) - - Image(nsImage: nsImage) - .resizable() - .background(.red) - .scaledToFit() - .background(.blue) - .frame(maxWidth: min(pixelWidth, .infinity), maxHeight: min(pixelHeight, .infinity)) - .border(.purple) - // .padding() - // .position(x: (pixelWidth / 2) + ((proxy.size.width - pixelWidth) / 2) - (proxy.size.width / 2), y: (pixelHeight / 2) + ((proxy.size.height - pixelHeight) / 2)) + var _ = print("proxy.size:", proxy.size.width, proxy.size.height) + var _ = print("pixels:", pixelWidth, pixelHeight) + var _ = print("nsImage.size:", nsImage.size.width, nsImage.size.height) + var _ = print("::::::::") + + ZStack { + Image(nsImage: nsImage) + .resizable() + .background(.red) + .scaledToFit() + .padding(.top, edgeInsets.top - 1.74) + .padding(.bottom, StatusBarView.height + 1.26) + .background(.blue) + .frame(maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), maxHeight: min(pixelHeight, proxy.size.width, nsImage.size.height)) + .clipped() + // .position(x: proxy.frame(in: .local).midX / 2, y: proxy.frame(in: .local).midY) + .background(.gray) + .border(.purple) + } + // .padding(.leading, (proxy.size.width - pixelWidth) / 2) + .frame(maxWidth: proxy.size.width / 2, maxHeight: proxy.size.height - 50) + .background(.black) } - .padding(.top, edgeInsets.top - 1.74) - .padding(.bottom, StatusBarView.height + 1.26) .background(.teal) // Group { From ff47ae846dcd247c6812ac2eff6a4f5d8aae3051 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 05:05:49 +0100 Subject: [PATCH 13/66] add attachPDFDocumentToView helper in WorkspacePDFView --- .../Documents/Views/WorkspacePDFView.swift | 27 ++++++++++--------- 1 file changed, 15 insertions(+), 12 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift index 6cd0f72fc0..51d83ddd3c 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift @@ -31,21 +31,12 @@ struct WorkspacePDFView: NSViewRepresentable { @Binding var canPreviewFile: Bool func makeNSView(context: Context) -> PDFView { - let pdfView = PDFView() - // use the coordinator to update the state binding - guard let pdfDocument = PDFDocument(url: fileURL) else { - context.coordinator.pdfView.canPreviewFile = false - return pdfView - } - context.coordinator.pdfView.canPreviewFile = true - pdfView.document = pdfDocument - pdfView.backgroundColor = NSColor.windowBackgroundColor + let pdfView = attachPDFDocumentToView(PDFView(), context: context) return pdfView } func updateNSView(_ pdfView: PDFView, context: Context) { - guard let pdfDocument = PDFDocument(url: fileURL) else { return } - pdfView.document = pdfDocument + attachPDFDocumentToView(pdfView, context: context) } func makeCoordinator() -> WorkspacePDFView.Coordinator { @@ -54,10 +45,22 @@ struct WorkspacePDFView: NSViewRepresentable { Coordinator(self) } - final class Coordinator: NSObject { + final class Coordinator { let pdfView: WorkspacePDFView init(_ pdfView: WorkspacePDFView) { self.pdfView = pdfView } } + + @discardableResult private func attachPDFDocumentToView (_ pdfView: PDFView, context: Context) -> PDFView { + // use the coordinator to update the state binding + guard let pdfDocument = PDFDocument(url: fileURL) else { + context.coordinator.pdfView.canPreviewFile = false + return pdfView + } + context.coordinator.pdfView.canPreviewFile = true + pdfView.document = pdfDocument + pdfView.backgroundColor = NSColor.windowBackgroundColor + return pdfView + } } From d820eb933a465a6853bd0ff0b9d263b7e81e675c Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 07:39:39 +0100 Subject: [PATCH 14/66] update WorkspacePDFView docs --- .../Documents/Views/WorkspacePDFView.swift | 18 +++++++++++++++--- 1 file changed, 15 insertions(+), 3 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift index 51d83ddd3c..af3ff87c75 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift @@ -12,22 +12,27 @@ import PDFKit.PDFView /// /// It takes in a file URL and attempts to preview a PDF. /// -/// When a valid PDF view is created, the `canPreviewFile` boolean updates to `true`. +/// When a valid PDF is created, the `canPreviewFile` boolean updates to `true`. /// /// **Example Usage**: /// ```swift /// WorkspacePDFView( -/// fileUrl: documentURL, +/// fileURL: documentURL, /// canPreviewFile: $canPreviewFile /// ) /// .padding(.top, tabBarHeight) /// .padding(.bottom, statusBarHeight) /// ``` /// -/// This view provides a context menu that is the same as the one in the native MacOS Preview application, for PDF files. +/// This view provides a context menu that is the same as the one in the +/// native MacOS Preview application, for PDF files. struct WorkspacePDFView: NSViewRepresentable { + /// URL of the PDF file you want to preview. let fileURL: URL + /// This value updates after attempting to create a valid PDF. + /// + /// `true` when created successfully, and `false` when failed to create. @Binding var canPreviewFile: Bool func makeNSView(context: Context) -> PDFView { @@ -52,6 +57,12 @@ struct WorkspacePDFView: NSViewRepresentable { } } + /// Creates a PDF document using ``WorkspacePDFView/fileURL``, and attaches it to the passed in `pdfView`. + /// - Parameters: + /// - pdfView: The [`PDFView`](https://developer.apple.com/documentation/pdfkit/pdfview) you wish to modify. + /// - context: The NS view representable context for ``WorkspacePDFView``. This is used to access the coordinator. + /// - Returns: A modified `pdfView` if a valid document was created, or an unmodified `pdfView` if a valid + /// document could not be created. @discardableResult private func attachPDFDocumentToView (_ pdfView: PDFView, context: Context) -> PDFView { // use the coordinator to update the state binding guard let pdfDocument = PDFDocument(url: fileURL) else { @@ -63,4 +74,5 @@ struct WorkspacePDFView: NSViewRepresentable { pdfView.backgroundColor = NSColor.windowBackgroundColor return pdfView } + } From b5f161413b46f99c586384f61d80d445ef7c8a22 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 07:42:06 +0100 Subject: [PATCH 15/66] remove WorkspaceNonTextFileView --- CodeEdit.xcodeproj/project.pbxproj | 4 - .../Views/WorkspaceNonTextFileView.swift | 120 ------------------ 2 files changed, 124 deletions(-) delete mode 100644 CodeEdit/Features/Documents/Views/WorkspaceNonTextFileView.swift diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index 692011dc1e..d866ab65a4 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -285,7 +285,6 @@ 6195E3112B640485007261CA /* WorkspaceDocument+SearchState+IndexTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6195E3102B640485007261CA /* WorkspaceDocument+SearchState+IndexTests.swift */; }; 61A53A7E2B4449870093BF8A /* WorkspaceDocument+Find.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */; }; 61A53A812B4449F00093BF8A /* WorkspaceDocument+Index.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */; }; - 66F2C8C22BEAA700004674F7 /* WorkspaceNonTextFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C12BEAA700004674F7 /* WorkspaceNonTextFileView.swift */; }; 66F2C8C42BEAA939004674F7 /* WorkspacePDFView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */; }; 6C049A372A49E2DB00D42923 /* DirectoryEventStream.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */; }; 6C05A8AF284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */; }; @@ -850,7 +849,6 @@ 6195E3102B640485007261CA /* WorkspaceDocument+SearchState+IndexTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+SearchState+IndexTests.swift"; sourceTree = ""; }; 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Find.swift"; sourceTree = ""; }; 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Index.swift"; sourceTree = ""; }; - 66F2C8C12BEAA700004674F7 /* WorkspaceNonTextFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceNonTextFileView.swift; sourceTree = ""; }; 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspacePDFView.swift; sourceTree = ""; }; 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DirectoryEventStream.swift; sourceTree = ""; }; 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Listeners.swift"; sourceTree = ""; }; @@ -1505,7 +1503,6 @@ children = ( 0485EB1E27E7458B00138301 /* WorkspaceCodeFileView.swift */, 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */, - 66F2C8C12BEAA700004674F7 /* WorkspaceNonTextFileView.swift */, ); path = Views; sourceTree = ""; @@ -3443,7 +3440,6 @@ B6D7EA5C297107DD00301FAC /* InspectorField.swift in Sources */, 043C321427E31FF6006AE443 /* CodeEditDocumentController.swift in Sources */, 85E4122A2A46C8CA00183F2B /* LocationsSettings.swift in Sources */, - 66F2C8C22BEAA700004674F7 /* WorkspaceNonTextFileView.swift in Sources */, 613899B12B6E6FDC00A5CAF6 /* Collection+FuzzySearch.swift in Sources */, 581550D129FBD30400684881 /* TextTableViewCell.swift in Sources */, 587B9E6629301D8F00AC7927 /* GitLabProjectHook.swift in Sources */, diff --git a/CodeEdit/Features/Documents/Views/WorkspaceNonTextFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceNonTextFileView.swift deleted file mode 100644 index ca68205b8d..0000000000 --- a/CodeEdit/Features/Documents/Views/WorkspaceNonTextFileView.swift +++ /dev/null @@ -1,120 +0,0 @@ -// -// WorkspaceNonTextFileView.swift -// CodeEdit -// -// Created by Paul Ebose on 2024/5/7. -// - -//import SwiftUI -//import Quartz -// -//struct WorkspaceNonTextFileView: NSViewRepresentable { -// // Properties: the file name (without extension), and whether we'll let -// // the user scale the preview content. -// private let file: CodeFileDocument -// -// func makeCoordinator() -> WorkspaceNonTextFileView.QLCoordinator { -// // The coordinator object implements the mechanics of dealing with -// // the live UIKit view controller. -// QLCoordinator(self) -// } -// -// func makeNSView(context: Context) -> QLPreviewView { -// // Create the preview view, and assign our Coordinator class -// // as its preview item. -// let preview = QLPreviewView() -// if let previewItem = file.previewItemURL { -// preview.previewItem = previewItem as QLPreviewItem -// } -// //preview.previewItem = context.coordinator -// return preview -// } -// -// func updateNSView(_ nsView: QLPreviewView, context: Context) { -// // do nothing -// } -// -// class QLCoordinator: NSObject, QLPreviewPanelDataSource { -// let parent: WorkspaceNonTextFileView -// private lazy var fileURL: URL = Bundle.main.url(forResource: parent.name, withExtension: "reality")! -// -// init(_ parent: WorkspaceNonTextFileView) { -// self.parent = parent -// super.init() -// } -// -// func numberOfPreviewItems(in panel: QLPreviewPanel!) -> Int { -// return 1 -// } -// -// func previewPanel(_ panel: QLPreviewPanel!, previewItemAt index: Int) -> (any QLPreviewItem)! { -// self.file -// } -// -// // let parent: ARQuickLookView -// // private lazy var fileURL: URL = Bundle.main.url(forResource: parent.name, -// // withExtension: "reality")! -// // -// // init(_ parent: ARQuickLookView) { -// // self.parent = parent -// // super.init() -// // } -// // -// // // The QLPreviewController asks its delegate how many items it has: -// // func numberOfPreviewItems(in controller: QLPreviewController) -> Int { -// // return 1 -// // } -// // -// // // For each item (see method above), the QLPreviewController asks for -// // // a QLPreviewItem instance describing that item: -// // func previewController( -// // _ controller: QLPreviewController, -// // previewItemAt index: Int -// // ) -> QLPreviewItem { -// // guard let fileURL = Bundle.main.url(forResource: parent.name, withExtension: "usdz") else { -// // fatalError("Unable to load \(parent.name).reality from main bundle") -// // } -// // -// // let item = ARQuickLookPreviewItem(fileAt: fileURL) -// // item.allowsContentScaling = parent.allowScaling -// // return item -// // } -// -// } -//} -// -////struct ContentView: View { -//// let qlCoordinator = QLCoordinator() -//// -//// var body: some View { -//// -//// // example.pdf is expected in app bundle resources -//// VStack { -//// MyPreview(fileName: "example.pdf") -//// Divider() -//// Button("Show panel") { -//// let panel = QLPreviewPanel.shared() -//// panel?.center() -//// panel?.dataSource = self.qlCoordinator -//// panel?.makeKeyAndOrderFront(nil) -//// } -//// } -//// } -//// -//// class QLCoordinator: NSObject, QLPreviewPanelDataSource { -//// func previewPanel(_ panel: QLPreviewPanel!, previewItemAt index: Int) -> QLPreviewItem! { -//// return loadPreviewItem(with: "example.pdf") as QLPreviewItem -//// } -//// -//// func numberOfPreviewItems(in controller: QLPreviewPanel) -> Int { -//// return 1 -//// } -//// } -////} -// -////struct WorkspaceNonTextFileView_Previews: PreviewProvider { -//// static var previews: some View { -//// WorkspaceNonTextFileView(file:) -//// } -////} - From 7ef31167e30b297c938d1760098b5207fe36b6bc Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 07:44:21 +0100 Subject: [PATCH 16/66] fix SwiftLint violations in WorkspacePDFView, WorkspaceCodeFileView --- .../Features/Documents/Views/WorkspaceCodeFileView.swift | 9 ++++++--- CodeEdit/Features/Documents/Views/WorkspacePDFView.swift | 3 ++- 2 files changed, 8 insertions(+), 4 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 6ab3c72c94..50153ef743 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -54,9 +54,12 @@ struct WorkspaceCodeFileView: View { .padding(.top, edgeInsets.top - 1.74) .padding(.bottom, StatusBarView.height + 1.26) .background(.blue) - .frame(maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), maxHeight: min(pixelHeight, proxy.size.width, nsImage.size.height)) + .frame( + maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), + maxHeight: min(pixelHeight, proxy.size.width, nsImage.size.height) + ) .clipped() - // .position(x: proxy.frame(in: .local).midX / 2, y: proxy.frame(in: .local).midY) + // .position(x: proxy.frame(in: .local).midX / 2, y: proxy.frame(in: .local).midY) .background(.gray) .border(.purple) } @@ -90,7 +93,7 @@ struct WorkspaceCodeFileView: View { // .scaledToFit() // OtherFileView(document) // .padding(.bottom, 25) - // //.containerRelativeFrame(<#T##Axis.Set#>, count: <#T##Int#>, span: <#T##Int#>, spacing: <#T##CGFloat#>, alignment: <#T##Alignment#>) + // //.containerRelativeFrame() // } else { // Image(nsImage: nsImg) // .resizable() diff --git a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift index af3ff87c75..7241d5f8fa 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift @@ -63,7 +63,8 @@ struct WorkspacePDFView: NSViewRepresentable { /// - context: The NS view representable context for ``WorkspacePDFView``. This is used to access the coordinator. /// - Returns: A modified `pdfView` if a valid document was created, or an unmodified `pdfView` if a valid /// document could not be created. - @discardableResult private func attachPDFDocumentToView (_ pdfView: PDFView, context: Context) -> PDFView { + @discardableResult + private func attachPDFDocumentToView (_ pdfView: PDFView, context: Context) -> PDFView { // use the coordinator to update the state binding guard let pdfDocument = PDFDocument(url: fileURL) else { context.coordinator.pdfView.canPreviewFile = false From 6d7f7d819d7f9404774daaf3a332205b34ab071b Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 07:46:04 +0100 Subject: [PATCH 17/66] add magic numbers comment to WorkspaceCodeFileView --- CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift | 2 ++ 1 file changed, 2 insertions(+) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 50153ef743..09311297b4 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -33,6 +33,7 @@ struct WorkspaceCodeFileView: View { if let documentURL = file.fileDocument?.fileURL { // WorkspacePDFView(fileUrl: documentURL, canPreviewFile: $canPreviewFile) + // use the magic numbers to fine-tune its appearance // .padding(.top, edgeInsets.top - 1.74) // .padding(.bottom, StatusBarView.height + 1.26) @@ -51,6 +52,7 @@ struct WorkspaceCodeFileView: View { .resizable() .background(.red) .scaledToFit() + // use the magic numbers to fine-tune its appearance .padding(.top, edgeInsets.top - 1.74) .padding(.bottom, StatusBarView.height + 1.26) .background(.blue) From 2192c703cc3bcc0f30f48bf119ec5f3c898c4473 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 07:50:30 +0100 Subject: [PATCH 18/66] update WorkspacePDFView docs --- CodeEdit/Features/Documents/Views/WorkspacePDFView.swift | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift index 7241d5f8fa..6f3492338a 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift @@ -61,8 +61,8 @@ struct WorkspacePDFView: NSViewRepresentable { /// - Parameters: /// - pdfView: The [`PDFView`](https://developer.apple.com/documentation/pdfkit/pdfview) you wish to modify. /// - context: The NS view representable context for ``WorkspacePDFView``. This is used to access the coordinator. - /// - Returns: A modified `pdfView` if a valid document was created, or an unmodified `pdfView` if a valid - /// document could not be created. + /// - Returns: A modified `pdfView` if a valid PDF was created, or an unmodified `pdfView` if it could not create a + /// valid PDF. @discardableResult private func attachPDFDocumentToView (_ pdfView: PDFView, context: Context) -> PDFView { // use the coordinator to update the state binding From 74cd22bba50b8dc81ccc1746a56fe56bfb36e9e3 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 08:27:24 +0100 Subject: [PATCH 19/66] before i forget --- .../Features/Documents/Views/WorkspaceCodeFileView.swift | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 09311297b4..541f6dfa43 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -53,14 +53,13 @@ struct WorkspaceCodeFileView: View { .background(.red) .scaledToFit() // use the magic numbers to fine-tune its appearance - .padding(.top, edgeInsets.top - 1.74) - .padding(.bottom, StatusBarView.height + 1.26) - .background(.blue) + // .padding(.top, edgeInsets.top - 1.74) + // .padding(.bottom, StatusBarView.height + 1.26) + // .background(.blue) .frame( maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), - maxHeight: min(pixelHeight, proxy.size.width, nsImage.size.height) + maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) ) - .clipped() // .position(x: proxy.frame(in: .local).midX / 2, y: proxy.frame(in: .local).midY) .background(.gray) .border(.purple) From 8ef8461eed202569e7127fc3086d06c28f46d5bc Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 08:42:45 +0100 Subject: [PATCH 20/66] progressss --- .../Documents/Views/WorkspaceCodeFileView.swift | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 541f6dfa43..4d2a7b7b68 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -52,10 +52,7 @@ struct WorkspaceCodeFileView: View { .resizable() .background(.red) .scaledToFit() - // use the magic numbers to fine-tune its appearance - // .padding(.top, edgeInsets.top - 1.74) - // .padding(.bottom, StatusBarView.height + 1.26) - // .background(.blue) + .background(.blue) .frame( maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) @@ -64,11 +61,13 @@ struct WorkspaceCodeFileView: View { .background(.gray) .border(.purple) } - // .padding(.leading, (proxy.size.width - pixelWidth) / 2) - .frame(maxWidth: proxy.size.width / 2, maxHeight: proxy.size.height - 50) + // .padding(.leading, (proxy.size.width - pixelWidth) / 2) + // .frame(maxWidth: proxy.size.width / 2, maxHeight: proxy.size.height - 50) .background(.black) } + .padding(.top, edgeInsets.top - 1.74) + .padding(.bottom, StatusBarView.height + 1.26) .background(.teal) // Group { From a643b43f7298a4f5c2ef32fd9754d8249a3976ad Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 09:58:41 +0100 Subject: [PATCH 21/66] too slow --- .../Views/WorkspaceCodeFileView.swift | 72 ++++++++++++++----- 1 file changed, 55 insertions(+), 17 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 4d2a7b7b68..a485c9485a 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -29,6 +29,29 @@ struct WorkspaceCodeFileView: View { @State private var canPreviewFile: Bool = false + private func computeFrame ( + pixelWidth: CGFloat, + proxyWidth: CGFloat, + nsImageWidth: CGFloat, + pixelHeight: CGFloat, + proxyHeight: CGFloat, + nsImageHeight: CGFloat + ) -> (CGFloat, CGFloat) { + let aspectRatio = pixelWidth / pixelHeight + var frameWidth = min(pixelWidth, nsImageWidth) + var frameHeight = min(pixelHeight, nsImageHeight) + + if frameWidth > proxyWidth { + frameHeight = min(pixelHeight, proxyHeight, nsImageHeight) + frameWidth = frameHeight * aspectRatio + } else if frameHeight > proxyHeight { + frameWidth = min(pixelWidth, proxyWidth, nsImageWidth) + frameHeight = frameWidth / aspectRatio + } + + return (frameWidth, frameHeight) + } + @ViewBuilder var codeView: some View { if let documentURL = file.fileDocument?.fileURL { @@ -45,25 +68,40 @@ struct WorkspaceCodeFileView: View { var _ = print("proxy.size:", proxy.size.width, proxy.size.height) var _ = print("pixels:", pixelWidth, pixelHeight) var _ = print("nsImage.size:", nsImage.size.width, nsImage.size.height) - var _ = print("::::::::") - - ZStack { - Image(nsImage: nsImage) - .resizable() - .background(.red) - .scaledToFit() - .background(.blue) - .frame( - maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), - maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) - ) - // .position(x: proxy.frame(in: .local).midX / 2, y: proxy.frame(in: .local).midY) - .background(.gray) - .border(.purple) - } + + let (frameWidth, frameHeight) = computeFrame( + pixelWidth: pixelWidth, + proxyWidth: proxy.size.width, + nsImageWidth: nsImage.size.width, + pixelHeight: pixelHeight, + proxyHeight: proxy.size.height, + nsImageHeight: nsImage.size.height + ) + + var _ = print("frame:", frameWidth, frameHeight) + var _ = print("----------") + + // ZStack(alignment: .bottomTrailing) { + Image(nsImage: nsImage) + .resizable() + .background(.red) + .scaledToFit() + .background(.blue) + .frame( // 3328 235 - 1352.97 901.98... w/h = aspect ratio; minH * aspectRatio = maxWidth + // its width that is changing + // w/h = aspect ratio; if minW > proxyW, newW = proxyW, newH = newW/aspectRatio + maxWidth: frameWidth, + maxHeight: frameHeight + // maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), + // maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) + ) + // .position(x: proxy.frame(in: .local).midX / 2, y: proxy.frame(in: .local).midY) + .background(.gray) + .border(.purple) + // } // .padding(.leading, (proxy.size.width - pixelWidth) / 2) // .frame(maxWidth: proxy.size.width / 2, maxHeight: proxy.size.height - 50) - .background(.black) + // .background(.black) } .padding(.top, edgeInsets.top - 1.74) From f583df0444bad96dce9f4e65e0b80b57fc0f4727 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 10:30:38 +0100 Subject: [PATCH 22/66] wip: the best work yet --- .../Views/WorkspaceCodeFileView.swift | 85 ++++++++++--------- 1 file changed, 45 insertions(+), 40 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index a485c9485a..cbdadc7202 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -12,6 +12,7 @@ import AVKit import PDFKit import QuickLookUI import QuickLook +import AppKit struct WorkspaceCodeFileView: View { @@ -32,23 +33,23 @@ struct WorkspaceCodeFileView: View { private func computeFrame ( pixelWidth: CGFloat, proxyWidth: CGFloat, - nsImageWidth: CGFloat, pixelHeight: CGFloat, - proxyHeight: CGFloat, - nsImageHeight: CGFloat + proxyHeight: CGFloat ) -> (CGFloat, CGFloat) { let aspectRatio = pixelWidth / pixelHeight - var frameWidth = min(pixelWidth, nsImageWidth) - var frameHeight = min(pixelHeight, nsImageHeight) - - if frameWidth > proxyWidth { - frameHeight = min(pixelHeight, proxyHeight, nsImageHeight) - frameWidth = frameHeight * aspectRatio - } else if frameHeight > proxyHeight { - frameWidth = min(pixelWidth, proxyWidth, nsImageWidth) + var frameWidth = pixelWidth + var frameHeight = pixelHeight + + if pixelWidth > proxyWidth { + frameWidth = proxyWidth frameHeight = frameWidth / aspectRatio } + if pixelHeight >= proxyHeight { + frameHeight = proxyHeight + frameWidth = aspectRatio * frameHeight + } + return (frameWidth, frameHeight) } @@ -68,40 +69,44 @@ struct WorkspaceCodeFileView: View { var _ = print("proxy.size:", proxy.size.width, proxy.size.height) var _ = print("pixels:", pixelWidth, pixelHeight) var _ = print("nsImage.size:", nsImage.size.width, nsImage.size.height) + var _ = print("proxWidth rm:", proxy.size.width - 1680) + var _ = print("proxWidth:", proxy.size.width) - let (frameWidth, frameHeight) = computeFrame( - pixelWidth: pixelWidth, - proxyWidth: proxy.size.width, - nsImageWidth: nsImage.size.width, - pixelHeight: pixelHeight, - proxyHeight: proxy.size.height, - nsImageHeight: nsImage.size.height - ) + // let (frameWidth, frameHeight) = computeFrame( + // pixelWidth: pixelWidth, + // proxyWidth: proxy.size.width, + // pixelHeight: pixelHeight, + // proxyHeight: proxy.size.height + // ) - var _ = print("frame:", frameWidth, frameHeight) + // var _ = print("frame:", frameWidth, frameHeight) var _ = print("----------") - // ZStack(alignment: .bottomTrailing) { - Image(nsImage: nsImage) - .resizable() - .background(.red) - .scaledToFit() - .background(.blue) - .frame( // 3328 235 - 1352.97 901.98... w/h = aspect ratio; minH * aspectRatio = maxWidth - // its width that is changing - // w/h = aspect ratio; if minW > proxyW, newW = proxyW, newH = newW/aspectRatio - maxWidth: frameWidth, - maxHeight: frameHeight - // maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), - // maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) - ) - // .position(x: proxy.frame(in: .local).midX / 2, y: proxy.frame(in: .local).midY) - .background(.gray) - .border(.purple) - // } + ZStack { + Image(nsImage: nsImage) + .resizable() + .background(.red) + .scaledToFit() + .background(.blue) + // .frame( + // 3328 235 - 1352.97 901.98... w/h = aspect ratio; minH * aspectRatio = maxWidth + // its width that is changing + // w/h = aspect ratio; if minW > proxyW, newW = proxyW, newH = newW/aspectRatio + // maxWidth: proxy.size.width, + // maxHeight: proxy.size.height + // maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), + // maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) + // ) + // .position(x: proxy.frame(in: .local).midX / 2, y: proxy.frame(in: .local).midY) + .background(.gray) + // .scaleEffect(0.7891589506, anchor: .leading) + .border(.purple) + .border(.orange) + } // .padding(.leading, (proxy.size.width - pixelWidth) / 2) - // .frame(maxWidth: proxy.size.width / 2, maxHeight: proxy.size.height - 50) - // .background(.black) + .frame(width: proxy.size.width, height: proxy.size.height) + .border(.yellow) + .background(.black) } .padding(.top, edgeInsets.top - 1.74) From 410f62d086a307b50ec5e01387138fc43e0285cf Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 10:37:15 +0100 Subject: [PATCH 23/66] it really works!! --- .../Views/WorkspaceCodeFileView.swift | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index cbdadc7202..063f287ef7 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -88,15 +88,15 @@ struct WorkspaceCodeFileView: View { .background(.red) .scaledToFit() .background(.blue) - // .frame( - // 3328 235 - 1352.97 901.98... w/h = aspect ratio; minH * aspectRatio = maxWidth - // its width that is changing - // w/h = aspect ratio; if minW > proxyW, newW = proxyW, newH = newW/aspectRatio - // maxWidth: proxy.size.width, - // maxHeight: proxy.size.height - // maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), - // maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) - // ) + .frame( + // 3328 235 - 1352.97 901.98... w/h = aspect ratio; minH * aspectRatio = maxWidth + // its width that is changing + // w/h = aspect ratio; if minW > proxyW, newW = proxyW, newH = newW/aspectRatio + // maxWidth: proxy.size.width, + // maxHeight: proxy.size.height + maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), + maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) + ) // .position(x: proxy.frame(in: .local).midX / 2, y: proxy.frame(in: .local).midY) .background(.gray) // .scaleEffect(0.7891589506, anchor: .leading) From b80dc31915974df895949f140a15eb4b7cc1f0e5 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 10:49:43 +0100 Subject: [PATCH 24/66] add WorkspaceImageView --- CodeEdit.xcodeproj/project.pbxproj | 4 ++ .../Documents/Views/WorkspaceImageView.swift | 37 +++++++++++++++++++ 2 files changed, 41 insertions(+) create mode 100644 CodeEdit/Features/Documents/Views/WorkspaceImageView.swift diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index d866ab65a4..e4c5852ae8 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -285,6 +285,7 @@ 6195E3112B640485007261CA /* WorkspaceDocument+SearchState+IndexTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6195E3102B640485007261CA /* WorkspaceDocument+SearchState+IndexTests.swift */; }; 61A53A7E2B4449870093BF8A /* WorkspaceDocument+Find.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */; }; 61A53A812B4449F00093BF8A /* WorkspaceDocument+Index.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */; }; + 661EF7B82BEE215300C3E577 /* WorkspaceImageView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */; }; 66F2C8C42BEAA939004674F7 /* WorkspacePDFView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */; }; 6C049A372A49E2DB00D42923 /* DirectoryEventStream.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */; }; 6C05A8AF284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */; }; @@ -849,6 +850,7 @@ 6195E3102B640485007261CA /* WorkspaceDocument+SearchState+IndexTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+SearchState+IndexTests.swift"; sourceTree = ""; }; 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Find.swift"; sourceTree = ""; }; 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Index.swift"; sourceTree = ""; }; + 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceImageView.swift; sourceTree = ""; }; 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspacePDFView.swift; sourceTree = ""; }; 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DirectoryEventStream.swift; sourceTree = ""; }; 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Listeners.swift"; sourceTree = ""; }; @@ -1502,6 +1504,7 @@ isa = PBXGroup; children = ( 0485EB1E27E7458B00138301 /* WorkspaceCodeFileView.swift */, + 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */, 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */, ); path = Views; @@ -3413,6 +3416,7 @@ B6C4F2AC2B3CC4D000B2B140 /* CommitChangedFileListItemView.swift in Sources */, 6C82D6B329BFD88700495C54 /* NavigateCommands.swift in Sources */, B66A4E4C29C9179B004573B4 /* CodeEditApp.swift in Sources */, + 661EF7B82BEE215300C3E577 /* WorkspaceImageView.swift in Sources */, 4E7F066629602E7B00BB3C12 /* CodeEditSplitViewController.swift in Sources */, 587B9E8D29301D8F00AC7927 /* GitHubAccount.swift in Sources */, 201169E72837B5CA00F92B46 /* SourceControlManager.swift in Sources */, diff --git a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift new file mode 100644 index 0000000000..af683db54f --- /dev/null +++ b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift @@ -0,0 +1,37 @@ +// +// WorkspaceImageView.swift +// CodeEdit +// +// Created by Paul Ebose on 2024/5/9. +// + +import SwiftUI + +struct WorkspaceImageView: View { + + /// URL of the image you want to preview. + let imageUrl: URL + + var body: some View { + if let nsImage = NSImage(contentsOf: imageUrl), + let imageReps = nsImage.representations.first { + // --- + let pixelWidth = CGFloat(imageReps.pixelsWide) + let pixelHeight = CGFloat(imageReps.pixelsHigh) + + GeometryReader { proxy in + ZStack { + Image(nsImage: nsImage) + .resizable() + .scaledToFit() + .frame( + maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), + maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) + ) + } + .frame(width: proxy.size.width, height: proxy.size.height) + } + } + } + +} From a9ed5ad505e7a3369b3b7e3290707a0b0d0daa5b Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 10:51:32 +0100 Subject: [PATCH 25/66] add WorkspaceCannotPreviewFileView --- CodeEdit.xcodeproj/project.pbxproj | 4 ++++ .../Views/WorkspaceCannotPreviewFileView.swift | 18 ++++++++++++++++++ .../Documents/Views/WorkspaceImageView.swift | 2 ++ 3 files changed, 24 insertions(+) create mode 100644 CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index e4c5852ae8..33cf578a8f 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -286,6 +286,7 @@ 61A53A7E2B4449870093BF8A /* WorkspaceDocument+Find.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */; }; 61A53A812B4449F00093BF8A /* WorkspaceDocument+Index.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */; }; 661EF7B82BEE215300C3E577 /* WorkspaceImageView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */; }; + 661EF7BA2BEE215300C3E577 /* WorkspaceCannotPreviewFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7B92BEE215300C3E577 /* WorkspaceCannotPreviewFileView.swift */; }; 66F2C8C42BEAA939004674F7 /* WorkspacePDFView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */; }; 6C049A372A49E2DB00D42923 /* DirectoryEventStream.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */; }; 6C05A8AF284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */; }; @@ -851,6 +852,7 @@ 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Find.swift"; sourceTree = ""; }; 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Index.swift"; sourceTree = ""; }; 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceImageView.swift; sourceTree = ""; }; + 661EF7B92BEE215300C3E577 /* WorkspaceCannotPreviewFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceCannotPreviewFileView.swift; sourceTree = ""; }; 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspacePDFView.swift; sourceTree = ""; }; 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DirectoryEventStream.swift; sourceTree = ""; }; 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Listeners.swift"; sourceTree = ""; }; @@ -1506,6 +1508,7 @@ 0485EB1E27E7458B00138301 /* WorkspaceCodeFileView.swift */, 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */, 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */, + 661EF7B92BEE215300C3E577 /* WorkspaceCannotPreviewFileView.swift */, ); path = Views; sourceTree = ""; @@ -3637,6 +3640,7 @@ B68C7C212A01DEFE004EA6D6 /* GitHubComment.swift in Sources */, 613899B72B6E702F00A5CAF6 /* String+LengthOfMatchingPrefix.swift in Sources */, 6C48D8F42972DB1A00D6D205 /* Env+Window.swift in Sources */, + 661EF7BA2BEE215300C3E577 /* WorkspaceCannotPreviewFileView.swift in Sources */, 6C5FDF7A29E6160000BC08C0 /* AppSettings.swift in Sources */, 58F2EB07292FB2B0004A9BDE /* GeneralSettings.swift in Sources */, B6041F4D29D7A4E9000F3454 /* SettingsPageView.swift in Sources */, diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift new file mode 100644 index 0000000000..595ed3cb25 --- /dev/null +++ b/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift @@ -0,0 +1,18 @@ +// +// WorkspaceCannotPreviewFileView.swift +// CodeEdit +// +// Created by Paul Ebose on 2024/5/9. +// + +import SwiftUI + +struct WorkspaceCannotPreviewFileView: View { + var body: some View { + Text(/*@START_MENU_TOKEN@*/"Hello, World!"/*@END_MENU_TOKEN@*/) + } +} + +#Preview { + WorkspaceCannotPreviewFileView() +} diff --git a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift index af683db54f..133270635c 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift @@ -31,6 +31,8 @@ struct WorkspaceImageView: View { } .frame(width: proxy.size.width, height: proxy.size.height) } + } else { + WorkspaceCannotPreviewFileView() } } From ff57cc81490816d3a4c0d88089d925d8ad2e3bca Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 10:58:07 +0100 Subject: [PATCH 26/66] its working very predictably but showing/hiding navigator pane isn't smooth --- .../Views/WorkspaceCodeFileView.swift | 55 ++----------------- 1 file changed, 4 insertions(+), 51 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 063f287ef7..5ab2347acd 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -61,57 +61,10 @@ struct WorkspaceCodeFileView: View { // .padding(.top, edgeInsets.top - 1.74) // .padding(.bottom, StatusBarView.height + 1.26) - GeometryReader { proxy in - let nsImage = NSImage(contentsOf: documentURL)! - let pixelWidth = CGFloat(nsImage.representations.first!.pixelsWide) - let pixelHeight = CGFloat(nsImage.representations.first!.pixelsHigh) - - var _ = print("proxy.size:", proxy.size.width, proxy.size.height) - var _ = print("pixels:", pixelWidth, pixelHeight) - var _ = print("nsImage.size:", nsImage.size.width, nsImage.size.height) - var _ = print("proxWidth rm:", proxy.size.width - 1680) - var _ = print("proxWidth:", proxy.size.width) - - // let (frameWidth, frameHeight) = computeFrame( - // pixelWidth: pixelWidth, - // proxyWidth: proxy.size.width, - // pixelHeight: pixelHeight, - // proxyHeight: proxy.size.height - // ) - - // var _ = print("frame:", frameWidth, frameHeight) - var _ = print("----------") - - ZStack { - Image(nsImage: nsImage) - .resizable() - .background(.red) - .scaledToFit() - .background(.blue) - .frame( - // 3328 235 - 1352.97 901.98... w/h = aspect ratio; minH * aspectRatio = maxWidth - // its width that is changing - // w/h = aspect ratio; if minW > proxyW, newW = proxyW, newH = newW/aspectRatio - // maxWidth: proxy.size.width, - // maxHeight: proxy.size.height - maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), - maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) - ) - // .position(x: proxy.frame(in: .local).midX / 2, y: proxy.frame(in: .local).midY) - .background(.gray) - // .scaleEffect(0.7891589506, anchor: .leading) - .border(.purple) - .border(.orange) - } - // .padding(.leading, (proxy.size.width - pixelWidth) / 2) - .frame(width: proxy.size.width, height: proxy.size.height) - .border(.yellow) - .background(.black) - - } - .padding(.top, edgeInsets.top - 1.74) - .padding(.bottom, StatusBarView.height + 1.26) - .background(.teal) + WorkspaceImageView(imageUrl: documentURL) + // use the magic numbers to fine-tune its appearance + .padding(.top, edgeInsets.top - 1.74) + .padding(.bottom, StatusBarView.height + 1.26) // Group { // switch document.typeOfFile { From 18134163f12dadb76d55fa205fc0ce6534378c10 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 11:04:14 +0100 Subject: [PATCH 27/66] remove the use of canPreview as it can cause unexpected behaviour --- .../Views/WorkspaceCodeFileView.swift | 14 +++---- .../Documents/Views/WorkspacePDFView.swift | 40 +++++-------------- 2 files changed, 15 insertions(+), 39 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 5ab2347acd..0a27d95022 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -28,8 +28,6 @@ struct WorkspaceCodeFileView: View { @State private var update: Bool = false - @State private var canPreviewFile: Bool = false - private func computeFrame ( pixelWidth: CGFloat, proxyWidth: CGFloat, @@ -56,16 +54,16 @@ struct WorkspaceCodeFileView: View { @ViewBuilder var codeView: some View { if let documentURL = file.fileDocument?.fileURL { - // WorkspacePDFView(fileUrl: documentURL, canPreviewFile: $canPreviewFile) - // use the magic numbers to fine-tune its appearance - // .padding(.top, edgeInsets.top - 1.74) - // .padding(.bottom, StatusBarView.height + 1.26) - - WorkspaceImageView(imageUrl: documentURL) + WorkspacePDFView(documentURL) // use the magic numbers to fine-tune its appearance .padding(.top, edgeInsets.top - 1.74) .padding(.bottom, StatusBarView.height + 1.26) + // WorkspaceImageView(imageUrl: documentURL) + // use the magic numbers to fine-tune its appearance + // .padding(.top, edgeInsets.top - 1.74) + // .padding(.bottom, StatusBarView.height + 1.26) + // Group { // switch document.typeOfFile { // case .some(.text): diff --git a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift index 6f3492338a..eb85cfef4c 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift @@ -12,14 +12,9 @@ import PDFKit.PDFView /// /// It takes in a file URL and attempts to preview a PDF. /// -/// When a valid PDF is created, the `canPreviewFile` boolean updates to `true`. -/// /// **Example Usage**: /// ```swift -/// WorkspacePDFView( -/// fileURL: documentURL, -/// canPreviewFile: $canPreviewFile -/// ) +/// WorkspacePDFView(documentURL) /// .padding(.top, tabBarHeight) /// .padding(.bottom, statusBarHeight) /// ``` @@ -30,49 +25,32 @@ struct WorkspacePDFView: NSViewRepresentable { /// URL of the PDF file you want to preview. let fileURL: URL - /// This value updates after attempting to create a valid PDF. - /// - /// `true` when created successfully, and `false` when failed to create. - @Binding var canPreviewFile: Bool + + init(_ fileURL: URL) { + self.fileURL = fileURL + } func makeNSView(context: Context) -> PDFView { - let pdfView = attachPDFDocumentToView(PDFView(), context: context) + let pdfView = attachPDFDocumentToView(PDFView()) return pdfView } func updateNSView(_ pdfView: PDFView, context: Context) { - attachPDFDocumentToView(pdfView, context: context) - } - - func makeCoordinator() -> WorkspacePDFView.Coordinator { - // The coordinator object implements the mechanics of passing - // data between the NS view representable and Swift UI. - Coordinator(self) - } - - final class Coordinator { - let pdfView: WorkspacePDFView - init(_ pdfView: WorkspacePDFView) { - self.pdfView = pdfView - } + attachPDFDocumentToView(pdfView) } /// Creates a PDF document using ``WorkspacePDFView/fileURL``, and attaches it to the passed in `pdfView`. /// - Parameters: /// - pdfView: The [`PDFView`](https://developer.apple.com/documentation/pdfkit/pdfview) you wish to modify. - /// - context: The NS view representable context for ``WorkspacePDFView``. This is used to access the coordinator. /// - Returns: A modified `pdfView` if a valid PDF was created, or an unmodified `pdfView` if it could not create a /// valid PDF. @discardableResult - private func attachPDFDocumentToView (_ pdfView: PDFView, context: Context) -> PDFView { - // use the coordinator to update the state binding + private func attachPDFDocumentToView (_ pdfView: PDFView) -> PDFView { guard let pdfDocument = PDFDocument(url: fileURL) else { - context.coordinator.pdfView.canPreviewFile = false return pdfView } - context.coordinator.pdfView.canPreviewFile = true pdfView.document = pdfDocument - pdfView.backgroundColor = NSColor.windowBackgroundColor + // pdfView.backgroundColor = NSColor.windowBackgroundColor return pdfView } From 6106b64852c0fa10e02abd9bfc43cb23186fed97 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 11:05:20 +0100 Subject: [PATCH 28/66] remove computeFrame helper in WorkspaceCodeFileView --- .../Views/WorkspaceCodeFileView.swift | 23 ------------------- 1 file changed, 23 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 0a27d95022..144821f6bd 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -28,29 +28,6 @@ struct WorkspaceCodeFileView: View { @State private var update: Bool = false - private func computeFrame ( - pixelWidth: CGFloat, - proxyWidth: CGFloat, - pixelHeight: CGFloat, - proxyHeight: CGFloat - ) -> (CGFloat, CGFloat) { - let aspectRatio = pixelWidth / pixelHeight - var frameWidth = pixelWidth - var frameHeight = pixelHeight - - if pixelWidth > proxyWidth { - frameWidth = proxyWidth - frameHeight = frameWidth / aspectRatio - } - - if pixelHeight >= proxyHeight { - frameHeight = proxyHeight - frameWidth = aspectRatio * frameHeight - } - - return (frameWidth, frameHeight) - } - @ViewBuilder var codeView: some View { if let documentURL = file.fileDocument?.fileURL { From dc7bcadfecdfc10ba5c1164b74469083d60393ba Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 11:07:04 +0100 Subject: [PATCH 29/66] update PDF preview's background color --- CodeEdit/Features/Documents/Views/WorkspacePDFView.swift | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift index eb85cfef4c..2c8365ed91 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift @@ -50,7 +50,7 @@ struct WorkspacePDFView: NSViewRepresentable { return pdfView } pdfView.document = pdfDocument - // pdfView.backgroundColor = NSColor.windowBackgroundColor + pdfView.backgroundColor = NSColor.controlBackgroundColor return pdfView } From 2e4dd0202cdf51cfefef55d835b3d8c1ca0985c7 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 11:08:22 +0100 Subject: [PATCH 30/66] add note for when PDF preview cannot create PDF document --- CodeEdit/Features/Documents/Views/WorkspacePDFView.swift | 1 + 1 file changed, 1 insertion(+) diff --git a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift index 2c8365ed91..0ea8ed9eea 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift @@ -47,6 +47,7 @@ struct WorkspacePDFView: NSViewRepresentable { @discardableResult private func attachPDFDocumentToView (_ pdfView: PDFView) -> PDFView { guard let pdfDocument = PDFDocument(url: fileURL) else { + // what can happen is the view doesn't redraw, so whatever was in the tab content view remains as is. return pdfView } pdfView.document = pdfDocument From c2fcacc52be0a711fcf390ad2c4d476ba758cc0d Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 11:10:39 +0100 Subject: [PATCH 31/66] improve docs for WorkspaceImageView & WorkspacePDFView --- .../Features/Documents/Views/WorkspaceImageView.swift | 8 ++++++++ CodeEdit/Features/Documents/Views/WorkspacePDFView.swift | 4 ++-- 2 files changed, 10 insertions(+), 2 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift index 133270635c..50c014418d 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift @@ -7,6 +7,14 @@ import SwiftUI +/// A SwiftUI view for previewing an image. +/// +/// It receives a url to an image file and attempts to preview it. +/// +/// ```swift +/// WorkspaceImageView(imageUrl: imageURL) +/// ``` +/// If the preview image cannot be created, it shows a ``WorkspaceCannotPreviewFileView`` view. struct WorkspaceImageView: View { /// URL of the image you want to preview. diff --git a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift index 0ea8ed9eea..bd094a1f6e 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift @@ -15,12 +15,12 @@ import PDFKit.PDFView /// **Example Usage**: /// ```swift /// WorkspacePDFView(documentURL) -/// .padding(.top, tabBarHeight) -/// .padding(.bottom, statusBarHeight) /// ``` /// /// This view provides a context menu that is the same as the one in the /// native MacOS Preview application, for PDF files. +/// +/// - Note: If a PDF cannot be previewed, nothing happens, no redraw or anything. struct WorkspacePDFView: NSViewRepresentable { /// URL of the PDF file you want to preview. From 2d448f6e42b70c6298c2116d022d728f22aa3c46 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 11:12:28 +0100 Subject: [PATCH 32/66] use unnamed parameter for imageUrl in WorkspaceImageView --- .../Documents/Views/WorkspaceCodeFileView.swift | 2 +- .../Features/Documents/Views/WorkspaceImageView.swift | 10 +++++++--- 2 files changed, 8 insertions(+), 4 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 144821f6bd..7e74de1815 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -36,7 +36,7 @@ struct WorkspaceCodeFileView: View { .padding(.top, edgeInsets.top - 1.74) .padding(.bottom, StatusBarView.height + 1.26) - // WorkspaceImageView(imageUrl: documentURL) + // WorkspaceImageView(documentURL) // use the magic numbers to fine-tune its appearance // .padding(.top, edgeInsets.top - 1.74) // .padding(.bottom, StatusBarView.height + 1.26) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift index 50c014418d..5a8b304638 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift @@ -12,16 +12,20 @@ import SwiftUI /// It receives a url to an image file and attempts to preview it. /// /// ```swift -/// WorkspaceImageView(imageUrl: imageURL) +/// WorkspaceImageView(imageURL) /// ``` /// If the preview image cannot be created, it shows a ``WorkspaceCannotPreviewFileView`` view. struct WorkspaceImageView: View { /// URL of the image you want to preview. - let imageUrl: URL + let imageURL: URL + + init(_ imageURL: URL) { + self.imageURL = imageURL + } var body: some View { - if let nsImage = NSImage(contentsOf: imageUrl), + if let nsImage = NSImage(contentsOf: imageURL), let imageReps = nsImage.representations.first { // --- let pixelWidth = CGFloat(imageReps.pixelsWide) From f2ca16428ad1130476837503ef851cfd1794fdfa Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 12:10:52 +0100 Subject: [PATCH 33/66] implement `WorkspaceCannotPreviewFileView` --- .../WorkspaceCannotPreviewFileView.swift | 58 +++++++++++++++++-- .../Views/WorkspaceCodeFileView.swift | 15 +++-- .../Documents/Views/WorkspaceImageView.swift | 2 +- 3 files changed, 64 insertions(+), 11 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift index 595ed3cb25..e37f5d5e73 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift @@ -6,13 +6,61 @@ // import SwiftUI +import QuickLookThumbnailing +/// This displays a thumbnail for the inputted `fileURL`. +/// +/// The thumbnail displayed is a file icon. +///```swift +/// WorkspaceCannotPreviewFileView(fileURL) +/// ``` struct WorkspaceCannotPreviewFileView: View { - var body: some View { - Text(/*@START_MENU_TOKEN@*/"Hello, World!"/*@END_MENU_TOKEN@*/) + + /// URL of the file that cannot be previewed. + let fileURL: URL + + /// The icon that will be shown instead of the file contents, since the file cannot be previewed. + @State private var thumbnail: NSImage? + + init(_ fileURL: URL) { + self.fileURL = fileURL } -} -#Preview { - WorkspaceCannotPreviewFileView() + /// Generate the file icon that will be used as a thumbnail, and update the `thumbnail` state value. + private func generateThumbnailRepresentation() { + // Set up the parameters of the request. + let size: CGSize = CGSize(width: 256, height: 256) + let scale = NSScreen.main?.backingScaleFactor ?? 1.0 + + // Create the thumbnail request. + let request = QLThumbnailGenerator.Request( + fileAt: fileURL, + size: size, + scale: scale, + representationTypes: .icon + ) + + // Retrieve the singleton instance of the thumbnail generator and generate the thumbnails. + let generator = QLThumbnailGenerator.shared + generator.generateRepresentations(for: request) { (qlThumbnail, _, _) in + guard let qlThumbnail else { return } + thumbnail = qlThumbnail.nsImage + } + } + + var body: some View { + ZStack { + if let thumbnail { + Image(nsImage: thumbnail) + } else { + VStack(spacing: 10) { + ProgressView() + Text("Opening...") + } + } + } + .onAppear(perform: { + if thumbnail == nil { generateThumbnailRepresentation() } + }) + } } diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 7e74de1815..3a6b497bff 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -30,17 +30,22 @@ struct WorkspaceCodeFileView: View { @ViewBuilder var codeView: some View { if let documentURL = file.fileDocument?.fileURL { - - WorkspacePDFView(documentURL) + + // WorkspacePDFView(documentURL) + // use the magic numbers to fine-tune its appearance + // .padding(.top, edgeInsets.top - 1.74) + // .padding(.bottom, StatusBarView.height + 1.26) + + WorkspaceImageView(documentURL) // use the magic numbers to fine-tune its appearance .padding(.top, edgeInsets.top - 1.74) .padding(.bottom, StatusBarView.height + 1.26) - - // WorkspaceImageView(documentURL) + + // VideoPlayer(player: AVPlayer(playerItem: AVPlayerItem(url: documentURL))) // use the magic numbers to fine-tune its appearance // .padding(.top, edgeInsets.top - 1.74) // .padding(.bottom, StatusBarView.height + 1.26) - + // Group { // switch document.typeOfFile { // case .some(.text): diff --git a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift index 5a8b304638..69947d72af 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift @@ -44,7 +44,7 @@ struct WorkspaceImageView: View { .frame(width: proxy.size.width, height: proxy.size.height) } } else { - WorkspaceCannotPreviewFileView() + WorkspaceCannotPreviewFileView(imageURL) } } From c248a9d68b10b29b2147a8d3d31b217da4a71669 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 12:18:26 +0100 Subject: [PATCH 34/66] change url variables in `WorkspaceImageView`, `WorkspacePDFView` & `WorkspaceCannotPreviewFileView` to private --- .../Documents/Views/WorkspaceCannotPreviewFileView.swift | 2 +- CodeEdit/Features/Documents/Views/WorkspaceImageView.swift | 2 +- CodeEdit/Features/Documents/Views/WorkspacePDFView.swift | 4 ++-- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift index e37f5d5e73..a1c1c7a8c4 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift @@ -17,7 +17,7 @@ import QuickLookThumbnailing struct WorkspaceCannotPreviewFileView: View { /// URL of the file that cannot be previewed. - let fileURL: URL + private let fileURL: URL /// The icon that will be shown instead of the file contents, since the file cannot be previewed. @State private var thumbnail: NSImage? diff --git a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift index 69947d72af..b6c7633534 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift @@ -18,7 +18,7 @@ import SwiftUI struct WorkspaceImageView: View { /// URL of the image you want to preview. - let imageURL: URL + private let imageURL: URL init(_ imageURL: URL) { self.imageURL = imageURL diff --git a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift index bd094a1f6e..377af50ed3 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift @@ -24,7 +24,7 @@ import PDFKit.PDFView struct WorkspacePDFView: NSViewRepresentable { /// URL of the PDF file you want to preview. - let fileURL: URL + private let fileURL: URL init(_ fileURL: URL) { self.fileURL = fileURL @@ -39,7 +39,7 @@ struct WorkspacePDFView: NSViewRepresentable { attachPDFDocumentToView(pdfView) } - /// Creates a PDF document using ``WorkspacePDFView/fileURL``, and attaches it to the passed in `pdfView`. + /// Creates a PDF document using `fileURL`, and attaches it to the passed in `pdfView`. /// - Parameters: /// - pdfView: The [`PDFView`](https://developer.apple.com/documentation/pdfkit/pdfview) you wish to modify. /// - Returns: A modified `pdfView` if a valid PDF was created, or an unmodified `pdfView` if it could not create a From 82ef086c265921266cf97842973092c16695d0ec Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 17:03:02 +0100 Subject: [PATCH 35/66] add `WorkspaceLoadingView` --- CodeEdit.xcodeproj/project.pbxproj | 4 +++ .../WorkspaceCannotPreviewFileView.swift | 5 +-- .../Views/WorkspaceCodeFileView.swift | 13 +++----- .../Views/WorkspaceLoadingView.swift | 32 +++++++++++++++++++ 4 files changed, 42 insertions(+), 12 deletions(-) create mode 100644 CodeEdit/Features/Documents/Views/WorkspaceLoadingView.swift diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index 33cf578a8f..b4c95b71d3 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -287,6 +287,7 @@ 61A53A812B4449F00093BF8A /* WorkspaceDocument+Index.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */; }; 661EF7B82BEE215300C3E577 /* WorkspaceImageView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */; }; 661EF7BA2BEE215300C3E577 /* WorkspaceCannotPreviewFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7B92BEE215300C3E577 /* WorkspaceCannotPreviewFileView.swift */; }; + 661EF7BD2BEE215300C3E577 /* WorkspaceLoadingView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */; }; 66F2C8C42BEAA939004674F7 /* WorkspacePDFView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */; }; 6C049A372A49E2DB00D42923 /* DirectoryEventStream.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */; }; 6C05A8AF284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */; }; @@ -853,6 +854,7 @@ 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Index.swift"; sourceTree = ""; }; 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceImageView.swift; sourceTree = ""; }; 661EF7B92BEE215300C3E577 /* WorkspaceCannotPreviewFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceCannotPreviewFileView.swift; sourceTree = ""; }; + 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceLoadingView.swift; sourceTree = ""; }; 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspacePDFView.swift; sourceTree = ""; }; 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DirectoryEventStream.swift; sourceTree = ""; }; 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Listeners.swift"; sourceTree = ""; }; @@ -1507,6 +1509,7 @@ children = ( 0485EB1E27E7458B00138301 /* WorkspaceCodeFileView.swift */, 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */, + 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */, 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */, 661EF7B92BEE215300C3E577 /* WorkspaceCannotPreviewFileView.swift */, ); @@ -3499,6 +3502,7 @@ B6E55C3B2A95368E003ECC7D /* EditorTabsOverflowShadow.swift in Sources */, 58A5DFA229339F6400D1BD5D /* KeybindingManager.swift in Sources */, B62AEDB32A1FD95B009A9F52 /* UtilityAreaTerminalView.swift in Sources */, + 661EF7BD2BEE215300C3E577 /* WorkspaceLoadingView.swift in Sources */, 58AFAA2E2933C69E00482B53 /* EditorTabRepresentable.swift in Sources */, 6C4104E6297C884F00F472BA /* AboutDetailView.swift in Sources */, 6C6BD6F129CD13FA00235D17 /* ExtensionDiscovery.swift in Sources */, diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift index a1c1c7a8c4..3dcadf4e18 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift @@ -53,10 +53,7 @@ struct WorkspaceCannotPreviewFileView: View { if let thumbnail { Image(nsImage: thumbnail) } else { - VStack(spacing: 10) { - ProgressView() - Text("Opening...") - } + WorkspaceLoadingView() } } .onAppear(perform: { diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 3a6b497bff..fa9982946a 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -30,22 +30,22 @@ struct WorkspaceCodeFileView: View { @ViewBuilder var codeView: some View { if let documentURL = file.fileDocument?.fileURL { - + // WorkspacePDFView(documentURL) // use the magic numbers to fine-tune its appearance // .padding(.top, edgeInsets.top - 1.74) // .padding(.bottom, StatusBarView.height + 1.26) - + WorkspaceImageView(documentURL) // use the magic numbers to fine-tune its appearance .padding(.top, edgeInsets.top - 1.74) .padding(.bottom, StatusBarView.height + 1.26) - + // VideoPlayer(player: AVPlayer(playerItem: AVPlayerItem(url: documentURL))) // use the magic numbers to fine-tune its appearance // .padding(.top, edgeInsets.top - 1.74) // .padding(.bottom, StatusBarView.height + 1.26) - + // Group { // switch document.typeOfFile { // case .some(.text): @@ -93,10 +93,7 @@ struct WorkspaceCodeFileView: View { Spacer() } Spacer() - VStack(spacing: 10) { - ProgressView() - Text("Opening \(file.name)...") - } + WorkspaceLoadingView(file.name) Spacer() .onAppear { Task.detached { diff --git a/CodeEdit/Features/Documents/Views/WorkspaceLoadingView.swift b/CodeEdit/Features/Documents/Views/WorkspaceLoadingView.swift new file mode 100644 index 0000000000..089a270e7f --- /dev/null +++ b/CodeEdit/Features/Documents/Views/WorkspaceLoadingView.swift @@ -0,0 +1,32 @@ +// +// WorkspaceLoadingView.swift +// CodeEdit +// +// Created by Paul Ebose on 2024/5/9. +// + +import SwiftUI + +/// A placeholder view that shows a spinner and label. +/// +/// Examples: +/// ```swift +/// WorkspaceLoadingView("ContentView.swift") +/// WorkspaceLoadingView(filename) +/// ``` +struct WorkspaceLoadingView: View { + + /// Name of file that is about to open. + private var filename = "" + + init(_ filename: String = "") { + self.filename = filename + } + + var body: some View { + VStack(spacing: 10) { + ProgressView() + Text("Opening \(filename)...") + } + } +} From eb15141f95995865ff840b2243434f5feabf31f9 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 17:03:56 +0100 Subject: [PATCH 36/66] spacing violation --- .../Documents/Views/WorkspaceCannotPreviewFileView.swift | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift index 3dcadf4e18..7f46a355e1 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift @@ -11,7 +11,7 @@ import QuickLookThumbnailing /// This displays a thumbnail for the inputted `fileURL`. /// /// The thumbnail displayed is a file icon. -///```swift +/// ```swift /// WorkspaceCannotPreviewFileView(fileURL) /// ``` struct WorkspaceCannotPreviewFileView: View { From d32436ad1d919ac86304d828d23d389c402bd974 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 17:05:53 +0100 Subject: [PATCH 37/66] change onAppear modifier in WorkspaceCannotPreviewFileView --- .../Documents/Views/WorkspaceCannotPreviewFileView.swift | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift index 7f46a355e1..769138d225 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift @@ -56,8 +56,8 @@ struct WorkspaceCannotPreviewFileView: View { WorkspaceLoadingView() } } - .onAppear(perform: { - if thumbnail == nil { generateThumbnailRepresentation() } - }) + .onAppear { + generateThumbnailRepresentation() + } } } From 4238f2c2f8700536c42f12dc03d239453b9f91a8 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 17:20:20 +0100 Subject: [PATCH 38/66] remove `WorkspaceCannotPreviewFileView` as it creates a bug that makes thumbnailing slightly unpredictable Will use QLPreview instead --- CodeEdit.xcodeproj/project.pbxproj | 4 -- .../WorkspaceCannotPreviewFileView.swift | 63 ------------------- .../Documents/Views/WorkspaceImageView.swift | 2 +- 3 files changed, 1 insertion(+), 68 deletions(-) delete mode 100644 CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index b4c95b71d3..1dddc79409 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -286,7 +286,6 @@ 61A53A7E2B4449870093BF8A /* WorkspaceDocument+Find.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */; }; 61A53A812B4449F00093BF8A /* WorkspaceDocument+Index.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */; }; 661EF7B82BEE215300C3E577 /* WorkspaceImageView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */; }; - 661EF7BA2BEE215300C3E577 /* WorkspaceCannotPreviewFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7B92BEE215300C3E577 /* WorkspaceCannotPreviewFileView.swift */; }; 661EF7BD2BEE215300C3E577 /* WorkspaceLoadingView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */; }; 66F2C8C42BEAA939004674F7 /* WorkspacePDFView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */; }; 6C049A372A49E2DB00D42923 /* DirectoryEventStream.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */; }; @@ -853,7 +852,6 @@ 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Find.swift"; sourceTree = ""; }; 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Index.swift"; sourceTree = ""; }; 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceImageView.swift; sourceTree = ""; }; - 661EF7B92BEE215300C3E577 /* WorkspaceCannotPreviewFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceCannotPreviewFileView.swift; sourceTree = ""; }; 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceLoadingView.swift; sourceTree = ""; }; 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspacePDFView.swift; sourceTree = ""; }; 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DirectoryEventStream.swift; sourceTree = ""; }; @@ -1511,7 +1509,6 @@ 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */, 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */, 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */, - 661EF7B92BEE215300C3E577 /* WorkspaceCannotPreviewFileView.swift */, ); path = Views; sourceTree = ""; @@ -3644,7 +3641,6 @@ B68C7C212A01DEFE004EA6D6 /* GitHubComment.swift in Sources */, 613899B72B6E702F00A5CAF6 /* String+LengthOfMatchingPrefix.swift in Sources */, 6C48D8F42972DB1A00D6D205 /* Env+Window.swift in Sources */, - 661EF7BA2BEE215300C3E577 /* WorkspaceCannotPreviewFileView.swift in Sources */, 6C5FDF7A29E6160000BC08C0 /* AppSettings.swift in Sources */, 58F2EB07292FB2B0004A9BDE /* GeneralSettings.swift in Sources */, B6041F4D29D7A4E9000F3454 /* SettingsPageView.swift in Sources */, diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift deleted file mode 100644 index 769138d225..0000000000 --- a/CodeEdit/Features/Documents/Views/WorkspaceCannotPreviewFileView.swift +++ /dev/null @@ -1,63 +0,0 @@ -// -// WorkspaceCannotPreviewFileView.swift -// CodeEdit -// -// Created by Paul Ebose on 2024/5/9. -// - -import SwiftUI -import QuickLookThumbnailing - -/// This displays a thumbnail for the inputted `fileURL`. -/// -/// The thumbnail displayed is a file icon. -/// ```swift -/// WorkspaceCannotPreviewFileView(fileURL) -/// ``` -struct WorkspaceCannotPreviewFileView: View { - - /// URL of the file that cannot be previewed. - private let fileURL: URL - - /// The icon that will be shown instead of the file contents, since the file cannot be previewed. - @State private var thumbnail: NSImage? - - init(_ fileURL: URL) { - self.fileURL = fileURL - } - - /// Generate the file icon that will be used as a thumbnail, and update the `thumbnail` state value. - private func generateThumbnailRepresentation() { - // Set up the parameters of the request. - let size: CGSize = CGSize(width: 256, height: 256) - let scale = NSScreen.main?.backingScaleFactor ?? 1.0 - - // Create the thumbnail request. - let request = QLThumbnailGenerator.Request( - fileAt: fileURL, - size: size, - scale: scale, - representationTypes: .icon - ) - - // Retrieve the singleton instance of the thumbnail generator and generate the thumbnails. - let generator = QLThumbnailGenerator.shared - generator.generateRepresentations(for: request) { (qlThumbnail, _, _) in - guard let qlThumbnail else { return } - thumbnail = qlThumbnail.nsImage - } - } - - var body: some View { - ZStack { - if let thumbnail { - Image(nsImage: thumbnail) - } else { - WorkspaceLoadingView() - } - } - .onAppear { - generateThumbnailRepresentation() - } - } -} diff --git a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift index b6c7633534..a3cd767f78 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift @@ -44,7 +44,7 @@ struct WorkspaceImageView: View { .frame(width: proxy.size.width, height: proxy.size.height) } } else { - WorkspaceCannotPreviewFileView(imageURL) + Text("Cannot preview image") } } From 5c5c81bfaa231f1b6ced3485e531d86337f07912 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 17:24:05 +0100 Subject: [PATCH 39/66] improve docs in `WorkspacePDFView` & `WorkspaceImageView` --- .../Features/Documents/Views/WorkspaceImageView.swift | 3 +++ .../Features/Documents/Views/WorkspacePDFView.swift | 10 +++++----- 2 files changed, 8 insertions(+), 5 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift index a3cd767f78..aace1159d5 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift @@ -15,6 +15,9 @@ import SwiftUI /// WorkspaceImageView(imageURL) /// ``` /// If the preview image cannot be created, it shows a ``WorkspaceCannotPreviewFileView`` view. +/// +/// This implementation allows for proper image scaling, especially when the image dimensions are smaller than +/// the size of the editor area. struct WorkspaceImageView: View { /// URL of the image you want to preview. diff --git a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift index 377af50ed3..bd3d327077 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift @@ -14,13 +14,13 @@ import PDFKit.PDFView /// /// **Example Usage**: /// ```swift -/// WorkspacePDFView(documentURL) +/// WorkspacePDFView(fileURL) /// ``` /// -/// This view provides a context menu that is the same as the one in the -/// native MacOS Preview application, for PDF files. +/// This view provides a context menu that is the same as the one in the native MacOS Preview application, for PDF +/// files. This view also allows for proper scaling of the PDF. /// -/// - Note: If a PDF cannot be previewed, nothing happens, no redraw or anything. +/// - Note: If the file located at the `fileUrl` cannot be previewed as a PDF, nothing happens, no redraw or anything. struct WorkspacePDFView: NSViewRepresentable { /// URL of the PDF file you want to preview. @@ -47,7 +47,7 @@ struct WorkspacePDFView: NSViewRepresentable { @discardableResult private func attachPDFDocumentToView (_ pdfView: PDFView) -> PDFView { guard let pdfDocument = PDFDocument(url: fileURL) else { - // what can happen is the view doesn't redraw, so whatever was in the tab content view remains as is. + // What can happen is the view doesn't redraw, so whatever was in the tab content view remains as is. return pdfView } pdfView.document = pdfDocument From b24b6ff47f61e532016cf5de2f4ca61633d98a61 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 22:20:41 +0100 Subject: [PATCH 40/66] add `WorkspaceAnyFileView` to properly preview files of different file types --- CodeEdit.xcodeproj/project.pbxproj | 4 + .../Features/CodeFile/CodeFileDocument.swift | 6 ++ .../Views/WorkspaceAnyFileView.swift | 36 ++++++++ .../Views/WorkspaceCodeFileView.swift | 86 +++++-------------- 4 files changed, 66 insertions(+), 66 deletions(-) create mode 100644 CodeEdit/Features/Documents/Views/WorkspaceAnyFileView.swift diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index 1dddc79409..385ba52cdd 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -287,6 +287,7 @@ 61A53A812B4449F00093BF8A /* WorkspaceDocument+Index.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */; }; 661EF7B82BEE215300C3E577 /* WorkspaceImageView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */; }; 661EF7BD2BEE215300C3E577 /* WorkspaceLoadingView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */; }; + 669BC4082BED306400D1197C /* WorkspaceAnyFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 669BC4072BED306400D1197C /* WorkspaceAnyFileView.swift */; }; 66F2C8C42BEAA939004674F7 /* WorkspacePDFView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */; }; 6C049A372A49E2DB00D42923 /* DirectoryEventStream.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */; }; 6C05A8AF284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */; }; @@ -853,6 +854,7 @@ 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Index.swift"; sourceTree = ""; }; 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceImageView.swift; sourceTree = ""; }; 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceLoadingView.swift; sourceTree = ""; }; + 669BC4072BED306400D1197C /* WorkspaceAnyFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceAnyFileView.swift; sourceTree = ""; }; 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspacePDFView.swift; sourceTree = ""; }; 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DirectoryEventStream.swift; sourceTree = ""; }; 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Listeners.swift"; sourceTree = ""; }; @@ -1508,6 +1510,7 @@ 0485EB1E27E7458B00138301 /* WorkspaceCodeFileView.swift */, 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */, 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */, + 669BC4072BED306400D1197C /* WorkspaceAnyFileView.swift */, 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */, ); path = Views; @@ -3511,6 +3514,7 @@ 6CABB1A129C5593800340467 /* SearchPanelView.swift in Sources */, D7211D4327E066CE008F2ED7 /* Localized+Ex.swift in Sources */, 581BFB692926431000D251EC /* WelcomeActionView.swift in Sources */, + 669BC4082BED306400D1197C /* WorkspaceAnyFileView.swift in Sources */, 20D839AE280E0CA700B27357 /* HistoryPopoverView.swift in Sources */, B6E41C7029DD157F0088F9F4 /* AccountsSettingsView.swift in Sources */, 6CFF967A29BEBD2400182D6F /* ViewCommands.swift in Sources */, diff --git a/CodeEdit/Features/CodeFile/CodeFileDocument.swift b/CodeEdit/Features/CodeFile/CodeFileDocument.swift index 9cdde5b239..f734b4e5a1 100644 --- a/CodeEdit/Features/CodeFile/CodeFileDocument.swift +++ b/CodeEdit/Features/CodeFile/CodeFileDocument.swift @@ -61,6 +61,12 @@ final class CodeFileDocument: NSDocument, ObservableObject, QLPreviewItem { if type.conforms(to: UTType.text) { return UTType.text } + if type.conforms(to: .pdf) { + return .pdf + } + if type.conforms(to: .movie) { + return .movie + } if type.conforms(to: .data) { return .data } diff --git a/CodeEdit/Features/Documents/Views/WorkspaceAnyFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceAnyFileView.swift new file mode 100644 index 0000000000..96a38ec878 --- /dev/null +++ b/CodeEdit/Features/Documents/Views/WorkspaceAnyFileView.swift @@ -0,0 +1,36 @@ +// +// WorkspaceAnyFileView.swift +// CodeEdit +// +// Created by Paul Ebose on 2024/5/9. +// + +import SwiftUI +import QuickLookUI + +/// Previews the file located at passed in `fileURL`. +/// +/// ```swift +/// WorkspaceAnyFileView(fileURL) +/// ``` +/// If the file cannot be previewed, a file icon thumbnail is shown instead. +struct WorkspaceAnyFileView: NSViewRepresentable { + + /// URL of the file to preview. You can pass in any file type. + private let fileURL: URL + + init(_ fileURL: URL) { + self.fileURL = fileURL + } + + func makeNSView(context: Context) -> QLPreviewView { + let qlPreviewView = QLPreviewView() + qlPreviewView.previewItem = fileURL as any QLPreviewItem + return qlPreviewView + } + + func updateNSView(_ qlPreviewView: QLPreviewView, context: Context) { + qlPreviewView.previewItem = fileURL as any QLPreviewItem + } + +} diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index fa9982946a..8326f89b9b 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -5,14 +5,10 @@ // Created by Pavel Kasila on 20.03.22. // -import SwiftUI -import UniformTypeIdentifiers -import CodeEditSourceEditor -import AVKit -import PDFKit -import QuickLookUI -import QuickLook import AppKit +import AVKit +import CodeEditSourceEditor +import SwiftUI struct WorkspaceCodeFileView: View { @@ -29,65 +25,21 @@ struct WorkspaceCodeFileView: View { @State private var update: Bool = false @ViewBuilder var codeView: some View { - if let documentURL = file.fileDocument?.fileURL { - - // WorkspacePDFView(documentURL) - // use the magic numbers to fine-tune its appearance - // .padding(.top, edgeInsets.top - 1.74) - // .padding(.bottom, StatusBarView.height + 1.26) - - WorkspaceImageView(documentURL) - // use the magic numbers to fine-tune its appearance - .padding(.top, edgeInsets.top - 1.74) - .padding(.bottom, StatusBarView.height + 1.26) - - // VideoPlayer(player: AVPlayer(playerItem: AVPlayerItem(url: documentURL))) - // use the magic numbers to fine-tune its appearance - // .padding(.top, edgeInsets.top - 1.74) - // .padding(.bottom, StatusBarView.height + 1.26) - - // Group { - // switch document.typeOfFile { - // case .some(.text): - // CodeFileView(codeFile: document, textViewCoordinators: textViewCoordinators) - // .frame(maxWidth: .infinity, maxHeight: .infinity) - - // case .some(.image): - // OtherFileView(document) - // .padding(.bottom, workspaceStatusBarHeight) - // GeometryReader { proxy in - // let nsImg = NSImage(contentsOf: document.fileURL!)! - // let pixelWidth = CGFloat(nsImg.representations.first!.pixelsWide) - // let pixelHeight = CGFloat(nsImg.representations.first!.pixelsHigh) - // - // var _ = print("proxy.size:", proxy.size.width, proxy.size.height) - // var _ = print("pixels:", pixelWidth, pixelHeight) - // - // if pixelWidth >= proxy.size.width || pixelHeight >= proxy.size.height { - // Image(nsImage: nsImg) - // .resizable() - // .scaledToFit() - // OtherFileView(document) - // .padding(.bottom, 25) - // //.containerRelativeFrame() - // } else { - // Image(nsImage: nsImg) - // .resizable() - // .frame(width: pixelWidth, height: pixelHeight) - // } - // } - - // case .some(.audiovisualContent): - // VideoPlayer(player: AVPlayer(playerItem: AVPlayerItem(url: document.fileURL!))) - // .padding(.top, 80) - // .padding(.bottom, 30) - // - // default: - // OtherFileView(document) - // .padding(.bottom, 25) - // } - // } - + if let document = file.fileDocument, + let documentURL = document.fileURL { + switch document.typeOfFile { + case .some(.text): + CodeFileView(codeFile: document, textViewCoordinators: textViewCoordinators) + case .some(.image): + WorkspaceImageView(documentURL) + case .some(.pdf): + WorkspacePDFView(documentURL) + case .some(.movie): + // Has more interaction options than WorkspaceOtherFileView + VideoPlayer(player: AVPlayer(playerItem: AVPlayerItem(url: documentURL))) + default: + WorkspaceAnyFileView(documentURL) + } } else { if update { Spacer() @@ -142,6 +94,8 @@ struct WorkspaceCodeFileView: View { var body: some View { codeView + .padding(.top, edgeInsets.top - 1.74) // Use the magic number to fine-tune its appearance + .padding(.bottom, StatusBarView.height + 1.26) // Use the magic number to fine-tune its appearance .frame(maxWidth: .infinity, maxHeight: .infinity) .onHover { hover in DispatchQueue.main.async { From d2664bdda254000aa3730d039b8a8134461917ec Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 22:24:08 +0100 Subject: [PATCH 41/66] rearrange files in `CodeEdit/Features/Documents/Views` --- CodeEdit.xcodeproj/project.pbxproj | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index 385ba52cdd..4a19198412 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -1507,10 +1507,10 @@ 5831E3CF2933F4E000D5A6D2 /* Views */ = { isa = PBXGroup; children = ( + 669BC4072BED306400D1197C /* WorkspaceAnyFileView.swift */, 0485EB1E27E7458B00138301 /* WorkspaceCodeFileView.swift */, - 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */, 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */, - 669BC4072BED306400D1197C /* WorkspaceAnyFileView.swift */, + 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */, 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */, ); path = Views; From 2fbc351645b2e7499ecbbd2d3271f1cac5259419 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 22:27:16 +0100 Subject: [PATCH 42/66] add `WorkspaceAnyFileView`, `WorkspaceLoadingView`, `WorkspaceImageView`, & `WorkspacePDFView` to DocC Documentation --- Documentation.docc/Documentation.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/Documentation.docc/Documentation.md b/Documentation.docc/Documentation.md index 95dd8eba5d..a970a22951 100644 --- a/Documentation.docc/Documentation.md +++ b/Documentation.docc/Documentation.md @@ -42,6 +42,10 @@ - ``CodeFileDocument`` - ``CodeEditDocumentController`` - ``WorkspaceCodeFileView`` +- ``WorkspaceAnyFileView`` +- ``WorkspaceLoadingView`` +- ``WorkspaceImageView`` +- ``WorkspacePDFView`` - ``WorkspaceNotificationModel`` ### Feedback From afc0a822bbc9b6d06dba55eb1c5a2b2a9c3c2920 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 22:44:59 +0100 Subject: [PATCH 43/66] update docs in `WorkspaceAnyFileView`, `WorkspaceLoadingView`, `WorkspaceImageView`, & `WorkspacePDFView` --- .../Documents/Views/WorkspaceAnyFileView.swift | 2 +- .../Documents/Views/WorkspaceImageView.swift | 10 +++++----- .../Documents/Views/WorkspaceLoadingView.swift | 6 +++--- .../Documents/Views/WorkspacePDFView.swift | 15 ++++++++------- 4 files changed, 17 insertions(+), 16 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceAnyFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceAnyFileView.swift index 96a38ec878..c7ea1d3cad 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceAnyFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceAnyFileView.swift @@ -8,7 +8,7 @@ import SwiftUI import QuickLookUI -/// Previews the file located at passed in `fileURL`. +/// A view for previewing any kind of file. /// /// ```swift /// WorkspaceAnyFileView(fileURL) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift index aace1159d5..9428ea7335 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift @@ -7,17 +7,17 @@ import SwiftUI -/// A SwiftUI view for previewing an image. +/// A view for previewing an image in a constrained space, while respecting the image dimensions. /// -/// It receives a url to an image file and attempts to preview it. +/// It receives a URL to an image file and attempts to preview it. /// /// ```swift /// WorkspaceImageView(imageURL) /// ``` -/// If the preview image cannot be created, it shows a ``WorkspaceCannotPreviewFileView`` view. +/// This implementation allows for proper image scaling, especially when the image dimensions is smaller than +/// the size of the image view area. /// -/// This implementation allows for proper image scaling, especially when the image dimensions are smaller than -/// the size of the editor area. +/// If the preview image cannot be created, it shows a *"Cannot preview image"* text. struct WorkspaceImageView: View { /// URL of the image you want to preview. diff --git a/CodeEdit/Features/Documents/Views/WorkspaceLoadingView.swift b/CodeEdit/Features/Documents/Views/WorkspaceLoadingView.swift index 089a270e7f..3d05c90ff7 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceLoadingView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceLoadingView.swift @@ -7,12 +7,12 @@ import SwiftUI -/// A placeholder view that shows a spinner and label. +/// A placeholder view that shows a spinner and text. /// -/// Examples: +/// It optionally receives a file name. /// ```swift -/// WorkspaceLoadingView("ContentView.swift") /// WorkspaceLoadingView(filename) +/// WorkspaceLoadingView() /// ``` struct WorkspaceLoadingView: View { diff --git a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift index bd3d327077..40be1a5369 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift @@ -8,19 +8,20 @@ import SwiftUI import PDFKit.PDFView -/// A SwiftUI view for previewing a PDF file. +/// A view for previewing a PDF file. /// /// It takes in a file URL and attempts to preview a PDF. /// -/// **Example Usage**: /// ```swift /// WorkspacePDFView(fileURL) /// ``` /// -/// This view provides a context menu that is the same as the one in the native MacOS Preview application, for PDF -/// files. This view also allows for proper scaling of the PDF. +/// This view provides a context menu that is the same as the one in the native MacOS Preview +/// application, for PDF files. /// -/// - Note: If the file located at the `fileUrl` cannot be previewed as a PDF, nothing happens, no redraw or anything. +/// This view also allows for proper scaling of the PDF. +/// +/// - Note: If the file located at the `fileURL` cannot be previewed as a PDF, nothing happens, no redraw or anything. struct WorkspacePDFView: NSViewRepresentable { /// URL of the PDF file you want to preview. @@ -39,7 +40,7 @@ struct WorkspacePDFView: NSViewRepresentable { attachPDFDocumentToView(pdfView) } - /// Creates a PDF document using `fileURL`, and attaches it to the passed in `pdfView`. + /// Creates a PDF document using ``WorkspacePDFView`` `.fileUrl`, and attaches it to the passed in `pdfView`. /// - Parameters: /// - pdfView: The [`PDFView`](https://developer.apple.com/documentation/pdfkit/pdfview) you wish to modify. /// - Returns: A modified `pdfView` if a valid PDF was created, or an unmodified `pdfView` if it could not create a @@ -47,7 +48,7 @@ struct WorkspacePDFView: NSViewRepresentable { @discardableResult private func attachPDFDocumentToView (_ pdfView: PDFView) -> PDFView { guard let pdfDocument = PDFDocument(url: fileURL) else { - // What can happen is the view doesn't redraw, so whatever was in the tab content view remains as is. + // What can happen is the view doesn't redraw, so whatever was in the editor area view remains as is. return pdfView } pdfView.document = pdfDocument From ccc79b3c27e9928d81e1ea3f288ce22d51301d36 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 22:45:44 +0100 Subject: [PATCH 44/66] rename `CodeFileDocument.typeOfFile` to `CodeFileDocument.utType` --- CodeEdit/Features/CodeFile/CodeFileDocument.swift | 2 +- .../Features/Documents/Views/WorkspaceCodeFileView.swift | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/CodeEdit/Features/CodeFile/CodeFileDocument.swift b/CodeEdit/Features/CodeFile/CodeFileDocument.swift index f734b4e5a1..02f87d059e 100644 --- a/CodeEdit/Features/CodeFile/CodeFileDocument.swift +++ b/CodeEdit/Features/CodeFile/CodeFileDocument.swift @@ -48,7 +48,7 @@ final class CodeFileDocument: NSDocument, ObservableObject, QLPreviewItem { If text content is not empty, return text If its neither image or text, this could be nil. */ - var typeOfFile: UTType? { + var utType: UTType? { if !self.content.isEmpty { return UTType.text } diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 8326f89b9b..5ae3493aeb 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -27,7 +27,7 @@ struct WorkspaceCodeFileView: View { @ViewBuilder var codeView: some View { if let document = file.fileDocument, let documentURL = document.fileURL { - switch document.typeOfFile { + switch document.utType { case .some(.text): CodeFileView(codeFile: document, textViewCoordinators: textViewCoordinators) case .some(.image): @@ -35,7 +35,7 @@ struct WorkspaceCodeFileView: View { case .some(.pdf): WorkspacePDFView(documentURL) case .some(.movie): - // Has more interaction options than WorkspaceOtherFileView + // Has more interaction options than WorkspaceAnyFileView VideoPlayer(player: AVPlayer(playerItem: AVPlayerItem(url: documentURL))) default: WorkspaceAnyFileView(documentURL) @@ -73,7 +73,7 @@ struct WorkspaceCodeFileView: View { VStack(spacing: 0) { if let url = otherFile.previewItemURL, let image = NSImage(contentsOf: url), - otherFile.typeOfFile == .image { + otherFile.utType == .image { GeometryReader { proxy in if image.size.width > proxy.size.width || image.size.height > proxy.size.height { OtherFileView(otherFile) From 12aa788aa419a348429848add02f422cbb9c6e88 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 22:49:39 +0100 Subject: [PATCH 45/66] do not return data UTType from CodeFileDocument.utType --- CodeEdit/Features/CodeFile/CodeFileDocument.swift | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/CodeEdit/Features/CodeFile/CodeFileDocument.swift b/CodeEdit/Features/CodeFile/CodeFileDocument.swift index 02f87d059e..cae94445e5 100644 --- a/CodeEdit/Features/CodeFile/CodeFileDocument.swift +++ b/CodeEdit/Features/CodeFile/CodeFileDocument.swift @@ -55,21 +55,18 @@ final class CodeFileDocument: NSDocument, ObservableObject, QLPreviewItem { guard let fileType, let type = UTType(fileType) else { return nil } - if type.conforms(to: UTType.image) { - return UTType.image - } if type.conforms(to: UTType.text) { return UTType.text } + if type.conforms(to: UTType.image) { + return UTType.image + } if type.conforms(to: .pdf) { return .pdf } if type.conforms(to: .movie) { return .movie } - if type.conforms(to: .data) { - return .data - } return nil } From f039914dd4ad8b6b2cd16faff962db89fe8fb49e Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 22:52:34 +0100 Subject: [PATCH 46/66] update docs for CodeFileDocument.utType --- .../Features/CodeFile/CodeFileDocument.swift | 16 +++++++++------- 1 file changed, 9 insertions(+), 7 deletions(-) diff --git a/CodeEdit/Features/CodeFile/CodeFileDocument.swift b/CodeEdit/Features/CodeFile/CodeFileDocument.swift index cae94445e5..d7720097fe 100644 --- a/CodeEdit/Features/CodeFile/CodeFileDocument.swift +++ b/CodeEdit/Features/CodeFile/CodeFileDocument.swift @@ -41,13 +41,15 @@ final class CodeFileDocument: NSDocument, ObservableObject, QLPreviewItem { /// Document-specific overridden line wrap preference. @Published var wrapLines: Bool? - /* - This is the main type of the document. - For example, if the file is end with '.png', it will be an image, - if the file is end with '.py', it will be a text file. - If text content is not empty, return text - If its neither image or text, this could be nil. - */ + /// The type of data this document contains. + /// + /// If for example, the file ends with `.py`, its type is a text file. + /// Or if it ends with `.png`, then it is an image. + /// Same goes for PDF and video formats. + /// + /// Also, if the text content is not empty, it is a text file. + /// + /// If it is neither a text, image, PDF nor video format, it will be nil. var utType: UTType? { if !self.content.isEmpty { return UTType.text From b660ac7e3c611fa49b3d118eb2d0c4024b6f0db9 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 22:04:04 +0100 Subject: [PATCH 47/66] change conformance from movie to audiovisualContent in CodeFileDocument.utType --- CodeEdit/Features/CodeFile/CodeFileDocument.swift | 14 +++++++------- .../Documents/Views/WorkspaceCodeFileView.swift | 2 +- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/CodeEdit/Features/CodeFile/CodeFileDocument.swift b/CodeEdit/Features/CodeFile/CodeFileDocument.swift index d7720097fe..7cb251f8ff 100644 --- a/CodeEdit/Features/CodeFile/CodeFileDocument.swift +++ b/CodeEdit/Features/CodeFile/CodeFileDocument.swift @@ -52,22 +52,22 @@ final class CodeFileDocument: NSDocument, ObservableObject, QLPreviewItem { /// If it is neither a text, image, PDF nor video format, it will be nil. var utType: UTType? { if !self.content.isEmpty { - return UTType.text + return .text } guard let fileType, let type = UTType(fileType) else { return nil } - if type.conforms(to: UTType.text) { - return UTType.text + if type.conforms(to: .text) { + return .text } - if type.conforms(to: UTType.image) { - return UTType.image + if type.conforms(to: .image) { + return .image } if type.conforms(to: .pdf) { return .pdf } - if type.conforms(to: .movie) { - return .movie + if type.conforms(to: .audiovisualContent) { + return .audiovisualContent } return nil } diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 5ae3493aeb..70b39d9fb4 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -34,7 +34,7 @@ struct WorkspaceCodeFileView: View { WorkspaceImageView(documentURL) case .some(.pdf): WorkspacePDFView(documentURL) - case .some(.movie): + case .some(.audiovisualContent): // Has more interaction options than WorkspaceAnyFileView VideoPlayer(player: AVPlayer(playerItem: AVPlayerItem(url: documentURL))) default: From 752fe3b2c42b426f951179690d800acabcdfdff6 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 22:09:13 +0100 Subject: [PATCH 48/66] use `WorkspaceAnyFileView` to preview GIF images --- CodeEdit/Features/CodeFile/CodeFileDocument.swift | 4 ++++ CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift | 4 ++++ 2 files changed, 8 insertions(+) diff --git a/CodeEdit/Features/CodeFile/CodeFileDocument.swift b/CodeEdit/Features/CodeFile/CodeFileDocument.swift index 7cb251f8ff..ba313c71d9 100644 --- a/CodeEdit/Features/CodeFile/CodeFileDocument.swift +++ b/CodeEdit/Features/CodeFile/CodeFileDocument.swift @@ -60,6 +60,10 @@ final class CodeFileDocument: NSDocument, ObservableObject, QLPreviewItem { if type.conforms(to: .text) { return .text } + // GIF conforms to image, so to differentiate, the GIF check has to be before the image check. + if type.conforms(to: .gif) { + return .gif + } if type.conforms(to: .image) { return .image } diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 70b39d9fb4..f64734a68b 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -30,6 +30,10 @@ struct WorkspaceCodeFileView: View { switch document.utType { case .some(.text): CodeFileView(codeFile: document, textViewCoordinators: textViewCoordinators) + case .some(.gif): + // GIF conforms to image, so to differentiate, the GIF check has to be before the image check. + // Using WorkspaceAnyFileView allows the GIF to play. + WorkspaceAnyFileView(documentURL) case .some(.image): WorkspaceImageView(documentURL) case .some(.pdf): From 40d52c61847be8ae60df69e0fccf53194b7300ee Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 22:13:40 +0100 Subject: [PATCH 49/66] add a note to the documentation for `CodeFileDocument.utType` --- CodeEdit/Features/CodeFile/CodeFileDocument.swift | 2 ++ 1 file changed, 2 insertions(+) diff --git a/CodeEdit/Features/CodeFile/CodeFileDocument.swift b/CodeEdit/Features/CodeFile/CodeFileDocument.swift index ba313c71d9..8f77becc0c 100644 --- a/CodeEdit/Features/CodeFile/CodeFileDocument.swift +++ b/CodeEdit/Features/CodeFile/CodeFileDocument.swift @@ -50,6 +50,8 @@ final class CodeFileDocument: NSDocument, ObservableObject, QLPreviewItem { /// Also, if the text content is not empty, it is a text file. /// /// If it is neither a text, image, PDF nor video format, it will be nil. + /// - Note: The UTType doesn't necessarily mean the file extension, it can be the MIME + /// type or any other form of data representation. var utType: UTType? { if !self.content.isEmpty { return .text From 6561d2575ef573b3dc91483190332c5f169d8f89 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Thu, 9 May 2024 22:47:46 +0100 Subject: [PATCH 50/66] fix: allow GIF previews to play, and with their proper dimensions --- .../Features/CodeFile/CodeFileDocument.swift | 2 +- .../Views/WorkspaceCodeFileView.swift | 5 ++- .../Documents/Views/WorkspaceImageView.swift | 33 ++++++++++++++----- 3 files changed, 27 insertions(+), 13 deletions(-) diff --git a/CodeEdit/Features/CodeFile/CodeFileDocument.swift b/CodeEdit/Features/CodeFile/CodeFileDocument.swift index 8f77becc0c..b7934e192b 100644 --- a/CodeEdit/Features/CodeFile/CodeFileDocument.swift +++ b/CodeEdit/Features/CodeFile/CodeFileDocument.swift @@ -62,7 +62,7 @@ final class CodeFileDocument: NSDocument, ObservableObject, QLPreviewItem { if type.conforms(to: .text) { return .text } - // GIF conforms to image, so to differentiate, the GIF check has to be before the image check. + // GIF conforms to image, so to differentiate, the GIF check has to come before the image check. if type.conforms(to: .gif) { return .gif } diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index f64734a68b..b41ce79122 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -31,9 +31,8 @@ struct WorkspaceCodeFileView: View { case .some(.text): CodeFileView(codeFile: document, textViewCoordinators: textViewCoordinators) case .some(.gif): - // GIF conforms to image, so to differentiate, the GIF check has to be before the image check. - // Using WorkspaceAnyFileView allows the GIF to play. - WorkspaceAnyFileView(documentURL) + // GIF conforms to image, so to differentiate, the GIF check has to come before the image check. + WorkspaceImageView(documentURL, isGif: true) case .some(.image): WorkspaceImageView(documentURL) case .some(.pdf): diff --git a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift index 9428ea7335..6d24a76a19 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift @@ -18,31 +18,46 @@ import SwiftUI /// the size of the image view area. /// /// If the preview image cannot be created, it shows a *"Cannot preview image"* text. +/// +/// - Note: Since SwiftUI Image view does not play GIFs, you should indicate when passing in a GIF +/// file, so this view can handle the GIF file correctly. struct WorkspaceImageView: View { /// URL of the image you want to preview. private let imageURL: URL - init(_ imageURL: URL) { + /// Indicates whether the image is a GIF. + private let isGif: Bool + + init(_ imageURL: URL, isGif: Bool = false) { self.imageURL = imageURL + self.isGif = isGif } var body: some View { if let nsImage = NSImage(contentsOf: imageURL), let imageReps = nsImage.representations.first { - // --- + let pixelWidth = CGFloat(imageReps.pixelsWide) let pixelHeight = CGFloat(imageReps.pixelsHigh) GeometryReader { proxy in ZStack { - Image(nsImage: nsImage) - .resizable() - .scaledToFit() - .frame( - maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), - maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) - ) + if isGif { + WorkspaceAnyFileView(imageURL) + .frame( + maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), + maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) + ) + } else { + Image(nsImage: nsImage) + .resizable() + .scaledToFit() + .frame( + maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), + maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) + ) + } } .frame(width: proxy.size.width, height: proxy.size.height) } From d0c2671fee638a82b563f46983f1320ade30e9f9 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 08:11:16 +0100 Subject: [PATCH 51/66] properly display CodeFileView contents by undo-ing the padding in its parent view --- CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift | 2 ++ 1 file changed, 2 insertions(+) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index b41ce79122..cb9998ba9b 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -30,6 +30,8 @@ struct WorkspaceCodeFileView: View { switch document.utType { case .some(.text): CodeFileView(codeFile: document, textViewCoordinators: textViewCoordinators) + .padding(.top, -edgeInsets.top + 1.74) // Undo the padding in the parent view + .padding(.bottom, -StatusBarView.height - 1.26) // Undo the padding in the parent view case .some(.gif): // GIF conforms to image, so to differentiate, the GIF check has to come before the image check. WorkspaceImageView(documentURL, isGif: true) From 1b8c8b3a0f52827d23eb4dcbde7189972ed4f5e1 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 08:15:11 +0100 Subject: [PATCH 52/66] remove text, image, PDF, video restrictions on `CodeFileDocument.utType` --- CodeEdit/Features/CodeFile/CodeFileDocument.swift | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/CodeEdit/Features/CodeFile/CodeFileDocument.swift b/CodeEdit/Features/CodeFile/CodeFileDocument.swift index b7934e192b..a33fedd286 100644 --- a/CodeEdit/Features/CodeFile/CodeFileDocument.swift +++ b/CodeEdit/Features/CodeFile/CodeFileDocument.swift @@ -49,7 +49,6 @@ final class CodeFileDocument: NSDocument, ObservableObject, QLPreviewItem { /// /// Also, if the text content is not empty, it is a text file. /// - /// If it is neither a text, image, PDF nor video format, it will be nil. /// - Note: The UTType doesn't necessarily mean the file extension, it can be the MIME /// type or any other form of data representation. var utType: UTType? { @@ -75,7 +74,7 @@ final class CodeFileDocument: NSDocument, ObservableObject, QLPreviewItem { if type.conforms(to: .audiovisualContent) { return .audiovisualContent } - return nil + return type } /* From 2ac22a76ab9299498ea1c490ec584c655e79392a Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 08:18:13 +0100 Subject: [PATCH 53/66] update docs in WorkspaceImageView --- CodeEdit/Features/Documents/Views/WorkspaceImageView.swift | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift index 6d24a76a19..41e163ced2 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift @@ -7,7 +7,7 @@ import SwiftUI -/// A view for previewing an image in a constrained space, while respecting the image dimensions. +/// A view for previewing an image, while respecting its image dimensions. /// /// It receives a URL to an image file and attempts to preview it. /// @@ -19,8 +19,8 @@ import SwiftUI /// /// If the preview image cannot be created, it shows a *"Cannot preview image"* text. /// -/// - Note: Since SwiftUI Image view does not play GIFs, you should indicate when passing in a GIF -/// file, so this view can handle the GIF file correctly. +/// - Note: This view wraps around SwiftUI Image. Since SwiftUI Image view do not play GIFs, you should indicate +/// when passing in a GIF file, so this view can handle the GIF file correctly. struct WorkspaceImageView: View { /// URL of the image you want to preview. From c3d31a6cdf4b3881297e94529208b6fc03b10ef1 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 08:24:52 +0100 Subject: [PATCH 54/66] WorkspaceCodeFileView: group non-text files, so they inherit modifiers from the parent Group view --- .../Views/WorkspaceCodeFileView.swift | 41 +++++++++++-------- 1 file changed, 25 insertions(+), 16 deletions(-) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index cb9998ba9b..a6be5eb31c 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -30,21 +30,32 @@ struct WorkspaceCodeFileView: View { switch document.utType { case .some(.text): CodeFileView(codeFile: document, textViewCoordinators: textViewCoordinators) - .padding(.top, -edgeInsets.top + 1.74) // Undo the padding in the parent view - .padding(.bottom, -StatusBarView.height - 1.26) // Undo the padding in the parent view - case .some(.gif): - // GIF conforms to image, so to differentiate, the GIF check has to come before the image check. - WorkspaceImageView(documentURL, isGif: true) - case .some(.image): - WorkspaceImageView(documentURL) - case .some(.pdf): - WorkspacePDFView(documentURL) - case .some(.audiovisualContent): - // Has more interaction options than WorkspaceAnyFileView - VideoPlayer(player: AVPlayer(playerItem: AVPlayerItem(url: documentURL))) + + // Group non-text files, so they inherit modifiers from the parent Group view. default: - WorkspaceAnyFileView(documentURL) - } + Group { + switch document.utType { + case .some(.gif): + // GIF conforms to image, so to differentiate, the GIF check has to come before the image check + WorkspaceImageView(documentURL, isGif: true) + + case .some(.image): + WorkspaceImageView(documentURL) + + case .some(.pdf): + WorkspacePDFView(documentURL) + + case .some(.audiovisualContent): + // Has more interaction options than WorkspaceAnyFileView. + VideoPlayer(player: AVPlayer(playerItem: AVPlayerItem(url: documentURL))) + + default: + WorkspaceAnyFileView(documentURL) + } + } + .padding(.top, edgeInsets.top - 1.74) // Use the magic number to fine-tune its appearance. + .padding(.bottom, StatusBarView.height + 1.26) // Use the magic number to fine-tune its appearance. + } } else { if update { Spacer() @@ -99,8 +110,6 @@ struct WorkspaceCodeFileView: View { var body: some View { codeView - .padding(.top, edgeInsets.top - 1.74) // Use the magic number to fine-tune its appearance - .padding(.bottom, StatusBarView.height + 1.26) // Use the magic number to fine-tune its appearance .frame(maxWidth: .infinity, maxHeight: .infinity) .onHover { hover in DispatchQueue.main.async { From 12e0ba15bac38fee6f6259f7460d55099de13b95 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 08:27:05 +0100 Subject: [PATCH 55/66] WorkspaceCodeFileView: add important note on document.utType --- CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index a6be5eb31c..26280e2875 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -27,6 +27,10 @@ struct WorkspaceCodeFileView: View { @ViewBuilder var codeView: some View { if let document = file.fileDocument, let documentURL = document.fileURL { + + // `document.utType` should remain an Optional, or else, it skips this 'if' block. + // We should still display WorkspaceAnyFileView when there is a 'nil' utType. + switch document.utType { case .some(.text): CodeFileView(codeFile: document, textViewCoordinators: textViewCoordinators) From 8f04013486cef3190bcac73528cec673a1789610 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 08:46:04 +0100 Subject: [PATCH 56/66] remove SwiftUI VideoPlayer view for now, it creates a bug that I can't work around - the first play click doesn't start the video, but the audio starts playing in the background, even after closing the editor tab - and everything in-between --- CodeEdit/Features/CodeFile/CodeFileDocument.swift | 3 --- CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift | 4 ---- 2 files changed, 7 deletions(-) diff --git a/CodeEdit/Features/CodeFile/CodeFileDocument.swift b/CodeEdit/Features/CodeFile/CodeFileDocument.swift index a33fedd286..84ecfd34af 100644 --- a/CodeEdit/Features/CodeFile/CodeFileDocument.swift +++ b/CodeEdit/Features/CodeFile/CodeFileDocument.swift @@ -71,9 +71,6 @@ final class CodeFileDocument: NSDocument, ObservableObject, QLPreviewItem { if type.conforms(to: .pdf) { return .pdf } - if type.conforms(to: .audiovisualContent) { - return .audiovisualContent - } return type } diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 26280e2875..40eb3e3953 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -49,10 +49,6 @@ struct WorkspaceCodeFileView: View { case .some(.pdf): WorkspacePDFView(documentURL) - case .some(.audiovisualContent): - // Has more interaction options than WorkspaceAnyFileView. - VideoPlayer(player: AVPlayer(playerItem: AVPlayerItem(url: documentURL))) - default: WorkspaceAnyFileView(documentURL) } From acb8a63bb20a922f15c74013a400027a8f2425c4 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 14:52:26 +0100 Subject: [PATCH 57/66] add `NonTextFileView` to clean up code - NonTextFileView, OtherFileView, URL+isImage, are not needed anymore --- CodeEdit.xcodeproj/project.pbxproj | 48 ++++---------- .../CodeFile/Image/ImageFileView.swift | 34 ---------- .../CodeFile/Other/OtherFileView.swift | 46 -------------- .../NonTextFile/NonTextFileView.swift | 46 ++++++++++++++ .../Views/WorkspaceCodeFileView.swift | 62 +++---------------- .../Views/QuickOpenPreviewView.swift | 34 ++-------- .../Utils/Extensions/URL/URL+isImage.swift | 38 ------------ Documentation.docc/App Window/App Window.md | 3 +- 8 files changed, 71 insertions(+), 240 deletions(-) delete mode 100644 CodeEdit/Features/CodeFile/Image/ImageFileView.swift delete mode 100644 CodeEdit/Features/CodeFile/Other/OtherFileView.swift create mode 100644 CodeEdit/Features/Documents/NonTextFile/NonTextFileView.swift delete mode 100644 CodeEdit/Utils/Extensions/URL/URL+isImage.swift diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index 4a19198412..a11620a057 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -115,8 +115,6 @@ 58798238292E30B90085B254 /* FeedbackWindowController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 58798232292E30B90085B254 /* FeedbackWindowController.swift */; }; 5879824F292E78D80085B254 /* CodeFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 58798248292E78D80085B254 /* CodeFileView.swift */; }; 58798250292E78D80085B254 /* CodeFileDocument.swift in Sources */ = {isa = PBXBuildFile; fileRef = 58798249292E78D80085B254 /* CodeFileDocument.swift */; }; - 58798251292E78D80085B254 /* OtherFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5879824B292E78D80085B254 /* OtherFileView.swift */; }; - 58798252292E78D80085B254 /* ImageFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5879824D292E78D80085B254 /* ImageFileView.swift */; }; 58798284292ED0FB0085B254 /* TerminalEmulatorView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 58798280292ED0FB0085B254 /* TerminalEmulatorView.swift */; }; 58798285292ED0FB0085B254 /* TerminalEmulatorView+Coordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = 58798281292ED0FB0085B254 /* TerminalEmulatorView+Coordinator.swift */; }; 58798286292ED0FB0085B254 /* SwiftTerm+Color+Init.swift in Sources */ = {isa = PBXBuildFile; fileRef = 58798283292ED0FB0085B254 /* SwiftTerm+Color+Init.swift */; }; @@ -289,6 +287,7 @@ 661EF7BD2BEE215300C3E577 /* WorkspaceLoadingView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */; }; 669BC4082BED306400D1197C /* WorkspaceAnyFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 669BC4072BED306400D1197C /* WorkspaceAnyFileView.swift */; }; 66F2C8C42BEAA939004674F7 /* WorkspacePDFView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */; }; + 66F370342BEE537B00D3B823 /* NonTextFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F370332BEE537B00D3B823 /* NonTextFileView.swift */; }; 6C049A372A49E2DB00D42923 /* DirectoryEventStream.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */; }; 6C05A8AF284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */; }; 6C0617D62BDB4432008C9C42 /* LogStream in Frameworks */ = {isa = PBXBuildFile; productRef = 6C0617D52BDB4432008C9C42 /* LogStream */; }; @@ -399,7 +398,6 @@ 852E62012A5C17E500447138 /* PageAndSettings.swift in Sources */ = {isa = PBXBuildFile; fileRef = 852E62002A5C17E500447138 /* PageAndSettings.swift */; }; 85745D632A38F8D900089AAB /* String+HighlightOccurrences.swift in Sources */ = {isa = PBXBuildFile; fileRef = 85745D622A38F8D900089AAB /* String+HighlightOccurrences.swift */; }; 85773E1E2A3E0A1F00C5D926 /* SettingsSearchResult.swift in Sources */ = {isa = PBXBuildFile; fileRef = 85773E1D2A3E0A1F00C5D926 /* SettingsSearchResult.swift */; }; - 85CD0C5F2A10CC3200E531FD /* URL+isImage.swift in Sources */ = {isa = PBXBuildFile; fileRef = 85CD0C5E2A10CC3200E531FD /* URL+isImage.swift */; }; 85E4122A2A46C8CA00183F2B /* LocationsSettings.swift in Sources */ = {isa = PBXBuildFile; fileRef = 85E412292A46C8CA00183F2B /* LocationsSettings.swift */; }; 9D36E1BF2B5E7D7500443C41 /* GitBranchesGroup.swift in Sources */ = {isa = PBXBuildFile; fileRef = 9D36E1BE2B5E7D7500443C41 /* GitBranchesGroup.swift */; }; B6041F4D29D7A4E9000F3454 /* SettingsPageView.swift in Sources */ = {isa = PBXBuildFile; fileRef = B6041F4C29D7A4E9000F3454 /* SettingsPageView.swift */; }; @@ -682,8 +680,6 @@ 58798232292E30B90085B254 /* FeedbackWindowController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = FeedbackWindowController.swift; sourceTree = ""; }; 58798248292E78D80085B254 /* CodeFileView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = CodeFileView.swift; sourceTree = ""; }; 58798249292E78D80085B254 /* CodeFileDocument.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = CodeFileDocument.swift; sourceTree = ""; }; - 5879824B292E78D80085B254 /* OtherFileView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = OtherFileView.swift; sourceTree = ""; }; - 5879824D292E78D80085B254 /* ImageFileView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ImageFileView.swift; sourceTree = ""; }; 58798280292ED0FB0085B254 /* TerminalEmulatorView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = TerminalEmulatorView.swift; sourceTree = ""; }; 58798281292ED0FB0085B254 /* TerminalEmulatorView+Coordinator.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = "TerminalEmulatorView+Coordinator.swift"; sourceTree = ""; }; 58798283292ED0FB0085B254 /* SwiftTerm+Color+Init.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = "SwiftTerm+Color+Init.swift"; sourceTree = ""; }; @@ -856,6 +852,7 @@ 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceLoadingView.swift; sourceTree = ""; }; 669BC4072BED306400D1197C /* WorkspaceAnyFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceAnyFileView.swift; sourceTree = ""; }; 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspacePDFView.swift; sourceTree = ""; }; + 66F370332BEE537B00D3B823 /* NonTextFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NonTextFileView.swift; sourceTree = ""; }; 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DirectoryEventStream.swift; sourceTree = ""; }; 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Listeners.swift"; sourceTree = ""; }; 6C092ED92A53A58600489202 /* EditorLayout+StateRestoration.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "EditorLayout+StateRestoration.swift"; sourceTree = ""; }; @@ -949,7 +946,6 @@ 852E62002A5C17E500447138 /* PageAndSettings.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = PageAndSettings.swift; sourceTree = ""; }; 85745D622A38F8D900089AAB /* String+HighlightOccurrences.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "String+HighlightOccurrences.swift"; sourceTree = ""; }; 85773E1D2A3E0A1F00C5D926 /* SettingsSearchResult.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SettingsSearchResult.swift; sourceTree = ""; }; - 85CD0C5E2A10CC3200E531FD /* URL+isImage.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "URL+isImage.swift"; sourceTree = ""; }; 85E412292A46C8CA00183F2B /* LocationsSettings.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LocationsSettings.swift; sourceTree = ""; }; 8B9A0E162B9FE84B007E2DBF /* Pre.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; path = Pre.xcconfig; sourceTree = ""; }; 9D36E1BE2B5E7D7500443C41 /* GitBranchesGroup.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = GitBranchesGroup.swift; sourceTree = ""; }; @@ -1116,6 +1112,7 @@ 043C321227E31FE8006AE443 /* Documents */ = { isa = PBXGroup; children = ( + 66F370302BEE533A00D3B823 /* NonTextFile */, 5831E3CE2933F3DE00D5A6D2 /* Controllers */, 5831E3CF2933F4E000D5A6D2 /* Views */, 043C321527E3201F006AE443 /* WorkspaceDocument.swift */, @@ -1712,8 +1709,6 @@ 58798244292E78D80085B254 /* CodeFile */ = { isa = PBXGroup; children = ( - 5879824C292E78D80085B254 /* Image */, - 5879824A292E78D80085B254 /* Other */, 58798249292E78D80085B254 /* CodeFileDocument.swift */, 58798248292E78D80085B254 /* CodeFileView.swift */, 6C5B63DD29C76213005454BA /* WindowCodeFileView.swift */, @@ -1721,22 +1716,6 @@ path = CodeFile; sourceTree = ""; }; - 5879824A292E78D80085B254 /* Other */ = { - isa = PBXGroup; - children = ( - 5879824B292E78D80085B254 /* OtherFileView.swift */, - ); - path = Other; - sourceTree = ""; - }; - 5879824C292E78D80085B254 /* Image */ = { - isa = PBXGroup; - children = ( - 5879824D292E78D80085B254 /* ImageFileView.swift */, - ); - path = Image; - sourceTree = ""; - }; 5879827E292ED0FB0085B254 /* TerminalEmulator */ = { isa = PBXGroup; children = ( @@ -2207,7 +2186,6 @@ 58D01C87293167DC00C5B6B4 /* Extensions */ = { isa = PBXGroup; children = ( - 85CD0C5D2A10CC2500E531FD /* URL */, 6C82D6C429C0129E00495C54 /* NSApplication */, 77A01E922BCA9C0400F0EA38 /* NSWindow */, 588847672992AAB800996D95 /* Array */, @@ -2377,6 +2355,14 @@ path = FuzzySearch; sourceTree = ""; }; + 66F370302BEE533A00D3B823 /* NonTextFile */ = { + isa = PBXGroup; + children = ( + 66F370332BEE537B00D3B823 /* NonTextFileView.swift */, + ); + path = NonTextFile; + sourceTree = ""; + }; 6C092EDC2A53A63E00489202 /* Views */ = { isa = PBXGroup; children = ( @@ -2538,14 +2524,6 @@ path = NSWindow; sourceTree = ""; }; - 85CD0C5D2A10CC2500E531FD /* URL */ = { - isa = PBXGroup; - children = ( - 85CD0C5E2A10CC3200E531FD /* URL+isImage.swift */, - ); - path = URL; - sourceTree = ""; - }; 85E412282A46C8B900183F2B /* Models */ = { isa = PBXGroup; children = ( @@ -3362,7 +3340,6 @@ B67DB0F92AFDF638002DC647 /* IconButtonStyle.swift in Sources */, 587B9E5E29301D8F00AC7927 /* GitLabCommitRouter.swift in Sources */, 58F2EB0D292FB2B0004A9BDE /* ThemeSettings.swift in Sources */, - 85CD0C5F2A10CC3200E531FD /* URL+isImage.swift in Sources */, 587B9D9F29300ABD00AC7927 /* SegmentedControl.swift in Sources */, 6C7256D729A3D7D000C2D3E0 /* SplitViewControllerView.swift in Sources */, B6EA1FE529DA33DB001BF195 /* ThemeModel.swift in Sources */, @@ -3473,7 +3450,6 @@ 77A01E322BB4274B00F0EA38 /* TasksCEWorkspaceSettingsView.swift in Sources */, B6E41C8F29DE9CD80088F9F4 /* AccountsSettingsDetailsView.swift in Sources */, 5882252B292C280D00E83CDE /* StatusBarCursorLocationLabel.swift in Sources */, - 58798252292E78D80085B254 /* ImageFileView.swift in Sources */, 5882252D292C280D00E83CDE /* StatusBarSplitTerminalButton.swift in Sources */, 58798238292E30B90085B254 /* FeedbackWindowController.swift in Sources */, 587B9E6C29301D8F00AC7927 /* GitLabNamespace.swift in Sources */, @@ -3569,7 +3545,6 @@ 58D01C94293167DC00C5B6B4 /* Color+HEX.swift in Sources */, 6C578D8729CD345900DC73B2 /* ExtensionSceneView.swift in Sources */, B640A9A129E2188F00715F20 /* View+NavigationBarBackButtonVisible.swift in Sources */, - 58798251292E78D80085B254 /* OtherFileView.swift in Sources */, 587B9E7929301D8F00AC7927 /* GitHubIssueRouter.swift in Sources */, 587B9E8029301D8F00AC7927 /* GitHubConfiguration.swift in Sources */, 58822524292C280D00E83CDE /* StatusBarView.swift in Sources */, @@ -3642,6 +3617,7 @@ B65B10F22B07D34F002852CF /* GitRemote.swift in Sources */, B6A43C5D29FC4AF00027E0E0 /* CreateSSHKeyView.swift in Sources */, B6EA200229DB7F81001BF195 /* View+ConstrainHeightToWindow.swift in Sources */, + 66F370342BEE537B00D3B823 /* NonTextFileView.swift in Sources */, B68C7C212A01DEFE004EA6D6 /* GitHubComment.swift in Sources */, 613899B72B6E702F00A5CAF6 /* String+LengthOfMatchingPrefix.swift in Sources */, 6C48D8F42972DB1A00D6D205 /* Env+Window.swift in Sources */, diff --git a/CodeEdit/Features/CodeFile/Image/ImageFileView.swift b/CodeEdit/Features/CodeFile/Image/ImageFileView.swift deleted file mode 100644 index 8e599ecf50..0000000000 --- a/CodeEdit/Features/CodeFile/Image/ImageFileView.swift +++ /dev/null @@ -1,34 +0,0 @@ -// -// ImageFileView.swift -// CodeEditModules/CodeFile -// -// Created by Nanashi Li on 2022/04/16. -// - -import SwiftUI - -struct ImageFileView: View { - - private let image: NSImage? - - init(image: NSImage?) { - self.image = image - } - - var body: some View { - GeometryReader { proxy in - if let image { - if image.size.width > proxy.size.width || image.size.height > proxy.size.height { - Image(nsImage: image) - .resizable() - .scaledToFit() - } else { - Image(nsImage: image) - .frame(width: proxy.size.width, height: proxy.size.height) - } - } else { - EmptyView() - } - } - } -} diff --git a/CodeEdit/Features/CodeFile/Other/OtherFileView.swift b/CodeEdit/Features/CodeFile/Other/OtherFileView.swift deleted file mode 100644 index f501dae720..0000000000 --- a/CodeEdit/Features/CodeFile/Other/OtherFileView.swift +++ /dev/null @@ -1,46 +0,0 @@ -// -// OtherFileView.swift -// -// -// Created by Shibo Tong on 10/7/2022. -// - -import SwiftUI -import QuickLookUI - -/// A SwiftUI Wrapper for `QLPreviewView` -/// Mainly used for other unsupported files -/// ## Usage -/// ```swift -/// OtherFileView(otherFile) -/// ``` -struct OtherFileView: NSViewRepresentable { - - private var otherFile: CodeFileDocument - - /// Initialize the OtherFileView - /// - Parameter otherFile: a file which contains URL to show preview - init( - _ otherFile: CodeFileDocument - ) { - self.otherFile = otherFile - } - - func makeNSView(context: Context) -> QLPreviewView { - let qlPreviewView = QLPreviewView() - if let previewItemURL = otherFile.previewItemURL { - qlPreviewView.previewItem = previewItemURL as QLPreviewItem - } - return qlPreviewView - } - - /// Update preview file when file changed - func updateNSView(_ nsView: QLPreviewView, context: Context) { - guard let currentPreviewItem = nsView.previewItem else { - return - } - if let previewItemURL = otherFile.previewItemURL, previewItemURL != currentPreviewItem.previewItemURL { - nsView.previewItem = previewItemURL as QLPreviewItem - } - } -} diff --git a/CodeEdit/Features/Documents/NonTextFile/NonTextFileView.swift b/CodeEdit/Features/Documents/NonTextFile/NonTextFileView.swift new file mode 100644 index 0000000000..c6b872514d --- /dev/null +++ b/CodeEdit/Features/Documents/NonTextFile/NonTextFileView.swift @@ -0,0 +1,46 @@ +// +// NonTextFileView.swift +// CodeEdit +// +// Created by Paul Ebose on 2024/5/10. +// + +import SwiftUI + +/// Determines what type of file is passed in, and previews it accordingly. +/// +/// ```swift +/// NonTextFileView(fileDocument) +/// ``` +struct NonTextFileView: View { + + /// The file document you wish to open. + let fileDocument: CodeFileDocument + + var body: some View { + + if let fileURL = fileDocument.fileURL { + + switch fileDocument.utType { + case .some(.gif): + // GIF conforms to image, so to differentiate, the GIF check has to come before the image check. + WorkspaceImageView(fileURL, isGif: true) + + case .some(.image): + WorkspaceImageView(fileURL) + + case .some(.pdf): + WorkspacePDFView(fileURL) + + default: + WorkspaceAnyFileView(fileURL) + } + + } else { + ZStack { + Text("Cannot retrieve URL to the file you opened.") + } + } + + } +} diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift index 40eb3e3953..0880e2308a 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift @@ -25,37 +25,16 @@ struct WorkspaceCodeFileView: View { @State private var update: Bool = false @ViewBuilder var codeView: some View { - if let document = file.fileDocument, - let documentURL = document.fileURL { + if let document = file.fileDocument { - // `document.utType` should remain an Optional, or else, it skips this 'if' block. - // We should still display WorkspaceAnyFileView when there is a 'nil' utType. - - switch document.utType { - case .some(.text): + if let utType = document.utType, utType.conforms(to: .text) { CodeFileView(codeFile: document, textViewCoordinators: textViewCoordinators) + } else { + NonTextFileView(fileDocument: document) + .padding(.top, edgeInsets.top - 1.74) // Use the magic number to fine-tune its appearance. + .padding(.bottom, StatusBarView.height + 1.26) // Use the magic number to fine-tune its appearance. + } - // Group non-text files, so they inherit modifiers from the parent Group view. - default: - Group { - switch document.utType { - case .some(.gif): - // GIF conforms to image, so to differentiate, the GIF check has to come before the image check - WorkspaceImageView(documentURL, isGif: true) - - case .some(.image): - WorkspaceImageView(documentURL) - - case .some(.pdf): - WorkspacePDFView(documentURL) - - default: - WorkspaceAnyFileView(documentURL) - } - } - .padding(.top, edgeInsets.top - 1.74) // Use the magic number to fine-tune its appearance. - .padding(.bottom, StatusBarView.height + 1.26) // Use the magic number to fine-tune its appearance. - } } else { if update { Spacer() @@ -81,33 +60,6 @@ struct WorkspaceCodeFileView: View { } } - @ViewBuilder - private func otherFileView( - _ otherFile: CodeFileDocument, - for item: CEWorkspaceFile - ) -> some View { - VStack(spacing: 0) { - if let url = otherFile.previewItemURL, - let image = NSImage(contentsOf: url), - otherFile.utType == .image { - GeometryReader { proxy in - if image.size.width > proxy.size.width || image.size.height > proxy.size.height { - OtherFileView(otherFile) - } else { - OtherFileView(otherFile) - .frame( - width: proxy.size.width * (proxy.size.width / image.size.width), - height: proxy.size.height - ) - .position(x: proxy.frame(in: .local).midX, y: proxy.frame(in: .local).midY) - } - } - } else { - OtherFileView(otherFile) - } - } - } - var body: some View { codeView .frame(maxWidth: .infinity, maxHeight: .infinity) diff --git a/CodeEdit/Features/QuickOpen/Views/QuickOpenPreviewView.swift b/CodeEdit/Features/QuickOpen/Views/QuickOpenPreviewView.swift index 38ba4953d9..caaf72806a 100644 --- a/CodeEdit/Features/QuickOpen/Views/QuickOpenPreviewView.swift +++ b/CodeEdit/Features/QuickOpen/Views/QuickOpenPreviewView.swift @@ -14,9 +14,7 @@ struct QuickOpenPreviewView: View { @ObservedObject var document: CodeFileDocument - init( - item: CEWorkspaceFile - ) { + init(item: CEWorkspaceFile) { self.item = item let doc = try? CodeFileDocument( for: item.url, @@ -27,32 +25,10 @@ struct QuickOpenPreviewView: View { } var body: some View { - if let url = document.fileURL { - if url.isImage() { - if let image = NSImage(contentsOf: url) { - GeometryReader { proxy in - if image.size.width > proxy.size.width || image.size.height > proxy.size.height { - OtherFileView(document) - } else { - // FIXME: The following code causes a bug where the image size doesn't change when zooming. - // The proper version found in WorkspaceCodeFile.swift line 59 to 60. - // Cannot use that code as the image obscures the open quickly overlay. - // There might be a solution for this in QuickOpenView.swift or OverlayView.swift - - OtherFileView(document) - .frame( - width: image.size.width, - height: image.size.height - ) - .position(x: proxy.frame(in: .local).midX, y: proxy.frame(in: .local).midY) - } - } - } else { - OtherFileView(document) - } - } else { - CodeFileView(codeFile: document, isEditable: false) - } + if let utType = document.utType, utType.conforms(to: .text) { + CodeFileView(codeFile: document, isEditable: false) + } else { + NonTextFileView(fileDocument: document) } } } diff --git a/CodeEdit/Utils/Extensions/URL/URL+isImage.swift b/CodeEdit/Utils/Extensions/URL/URL+isImage.swift deleted file mode 100644 index 6e3dea3372..0000000000 --- a/CodeEdit/Utils/Extensions/URL/URL+isImage.swift +++ /dev/null @@ -1,38 +0,0 @@ -// -// URL+isImage.swift -// CodeEdit -// -// Created by Raymond Vleeshouwer on 14/05/23. -// - -import Foundation - -extension URL { - func isImage() -> Bool { - let ext: String = self.pathExtension.lowercased() - - // A list of supported file types by QLPreviewItem - // Some of the image file types (in UTType) are not supported by QLPreviewItem - let quickLookImageFileTypes: [String] = [ - "png", - "jpg", - "jpeg", - "bmp", - "pdf", - "heic", - "webp", - "tiff", - "gif", - "tga", - "avif", - "psd", - "svg" - ] - - if quickLookImageFileTypes.contains(ext) { - return true - } else { - return false - } - } -} diff --git a/Documentation.docc/App Window/App Window.md b/Documentation.docc/App Window/App Window.md index 9996089981..d0b7138a77 100644 --- a/Documentation.docc/App Window/App Window.md +++ b/Documentation.docc/App Window/App Window.md @@ -12,8 +12,7 @@ A collection of all the views that make up the main app window. ### Main Content - ``CodeFileView`` -- ``ImageFileView`` -- ``OtherFileView`` +- ``NonTextFileView`` ### PathBar From 9688746f48a738377368c655693666d0e6f317fd Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 14:56:48 +0100 Subject: [PATCH 58/66] remove QLPreviewItem subclass from CodeFileDocument --- CodeEdit/Features/CodeFile/CodeFileDocument.swift | 10 +--------- 1 file changed, 1 insertion(+), 9 deletions(-) diff --git a/CodeEdit/Features/CodeFile/CodeFileDocument.swift b/CodeEdit/Features/CodeFile/CodeFileDocument.swift index 84ecfd34af..61883bc21d 100644 --- a/CodeEdit/Features/CodeFile/CodeFileDocument.swift +++ b/CodeEdit/Features/CodeFile/CodeFileDocument.swift @@ -9,7 +9,6 @@ import AppKit import Foundation import SwiftUI import UniformTypeIdentifiers -import QuickLookUI import CodeEditSourceEditor import CodeEditTextView import CodeEditLanguages @@ -22,7 +21,7 @@ enum CodeFileError: Error { } @objc(CodeFileDocument) -final class CodeFileDocument: NSDocument, ObservableObject, QLPreviewItem { +final class CodeFileDocument: NSDocument, ObservableObject { struct OpenOptions { let cursorPositions: [CursorPosition] } @@ -74,13 +73,6 @@ final class CodeFileDocument: NSDocument, ObservableObject, QLPreviewItem { return type } - /* - This is the QLPreviewItemURL - */ - var previewItemURL: URL? { - fileURL - } - /// Specify options for opening the file such as the initial cursor positions. /// Nulled by ``CodeFileView`` on first load. var openOptions: OpenOptions? From 425f806f507293714fcb772f957b5406361032fe Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 15:29:55 +0100 Subject: [PATCH 59/66] rename `WorkspaceCodeFileView` to `EditorAreaFileView` --- CodeEdit.xcodeproj/project.pbxproj | 8 ++++---- ...rkspaceCodeFileView.swift => EditorAreaFileView.swift} | 8 ++++---- CodeEdit/Features/Editor/Views/EditorView.swift | 2 +- Documentation.docc/Documentation.md | 2 +- 4 files changed, 10 insertions(+), 10 deletions(-) rename CodeEdit/Features/Documents/Views/{WorkspaceCodeFileView.swift => EditorAreaFileView.swift} (94%) diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index a11620a057..597047ef5b 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -13,7 +13,7 @@ 043C321627E3201F006AE443 /* WorkspaceDocument.swift in Sources */ = {isa = PBXBuildFile; fileRef = 043C321527E3201F006AE443 /* WorkspaceDocument.swift */; }; 04540D5E27DD08C300E91B77 /* WorkspaceView.swift in Sources */ = {isa = PBXBuildFile; fileRef = B658FB3127DA9E0F00EA4DBD /* WorkspaceView.swift */; }; 04660F6A27E51E5C00477777 /* CodeEditWindowController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 04660F6927E51E5C00477777 /* CodeEditWindowController.swift */; }; - 0485EB1F27E7458B00138301 /* WorkspaceCodeFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0485EB1E27E7458B00138301 /* WorkspaceCodeFileView.swift */; }; + 0485EB1F27E7458B00138301 /* EditorAreaFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0485EB1E27E7458B00138301 /* EditorAreaFileView.swift */; }; 04BA7C0B2AE2A2D100584E1C /* GitBranch.swift in Sources */ = {isa = PBXBuildFile; fileRef = 04BA7C0A2AE2A2D100584E1C /* GitBranch.swift */; }; 04BA7C0E2AE2A76E00584E1C /* SourceControlNavigatorChangesCommitView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 04BA7C0D2AE2A76E00584E1C /* SourceControlNavigatorChangesCommitView.swift */; }; 04BA7C132AE2AA7300584E1C /* GitCheckoutBranchViewModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 04BA7C112AE2AA7300584E1C /* GitCheckoutBranchViewModel.swift */; }; @@ -575,7 +575,7 @@ 04660F6027E3A68A00477777 /* Info.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 04660F6927E51E5C00477777 /* CodeEditWindowController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CodeEditWindowController.swift; sourceTree = ""; }; 0468438427DC76E200F8E88E /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = ""; }; - 0485EB1E27E7458B00138301 /* WorkspaceCodeFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceCodeFileView.swift; sourceTree = ""; }; + 0485EB1E27E7458B00138301 /* EditorAreaFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = EditorAreaFileView.swift; sourceTree = ""; }; 04BA7C0A2AE2A2D100584E1C /* GitBranch.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = GitBranch.swift; sourceTree = ""; }; 04BA7C0D2AE2A76E00584E1C /* SourceControlNavigatorChangesCommitView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SourceControlNavigatorChangesCommitView.swift; sourceTree = ""; }; 04BA7C112AE2AA7300584E1C /* GitCheckoutBranchViewModel.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = GitCheckoutBranchViewModel.swift; sourceTree = ""; }; @@ -1505,7 +1505,7 @@ isa = PBXGroup; children = ( 669BC4072BED306400D1197C /* WorkspaceAnyFileView.swift */, - 0485EB1E27E7458B00138301 /* WorkspaceCodeFileView.swift */, + 0485EB1E27E7458B00138301 /* EditorAreaFileView.swift */, 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */, 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */, 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */, @@ -3538,7 +3538,7 @@ 5879821A292D92370085B254 /* SearchResultModel.swift in Sources */, B6F0517729D9E3AD00D72287 /* SourceControlGeneralView.swift in Sources */, 587B9E8929301D8F00AC7927 /* GitHubGist.swift in Sources */, - 0485EB1F27E7458B00138301 /* WorkspaceCodeFileView.swift in Sources */, + 0485EB1F27E7458B00138301 /* EditorAreaFileView.swift in Sources */, 6C092EDA2A53A58600489202 /* EditorLayout+StateRestoration.swift in Sources */, 6C092EE02A53BFCF00489202 /* WorkspaceStateKey.swift in Sources */, 613899B52B6E700300A5CAF6 /* FuzzySearchModels.swift in Sources */, diff --git a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift b/CodeEdit/Features/Documents/Views/EditorAreaFileView.swift similarity index 94% rename from CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift rename to CodeEdit/Features/Documents/Views/EditorAreaFileView.swift index 0880e2308a..35446401d8 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceCodeFileView.swift +++ b/CodeEdit/Features/Documents/Views/EditorAreaFileView.swift @@ -1,5 +1,5 @@ // -// WorkspaceCodeFileView.swift +// EditorAreaFileView.swift // CodeEdit // // Created by Pavel Kasila on 20.03.22. @@ -10,7 +10,7 @@ import AVKit import CodeEditSourceEditor import SwiftUI -struct WorkspaceCodeFileView: View { +struct EditorAreaFileView: View { @EnvironmentObject private var editorManager: EditorManager @@ -24,7 +24,7 @@ struct WorkspaceCodeFileView: View { @State private var update: Bool = false - @ViewBuilder var codeView: some View { + @ViewBuilder var editorAreaFileView: some View { if let document = file.fileDocument { if let utType = document.utType, utType.conforms(to: .text) { @@ -61,7 +61,7 @@ struct WorkspaceCodeFileView: View { } var body: some View { - codeView + editorAreaFileView .frame(maxWidth: .infinity, maxHeight: .infinity) .onHover { hover in DispatchQueue.main.async { diff --git a/CodeEdit/Features/Editor/Views/EditorView.swift b/CodeEdit/Features/Editor/Views/EditorView.swift index 6ca74ae35c..8de286e576 100644 --- a/CodeEdit/Features/Editor/Views/EditorView.swift +++ b/CodeEdit/Features/Editor/Views/EditorView.swift @@ -40,7 +40,7 @@ struct EditorView: View { VStack { if let selected = editor.selectedTab { - WorkspaceCodeFileView( + EditorAreaFileView( file: selected.file, textViewCoordinators: [selected.rangeTranslator].compactMap({ $0 }) ) diff --git a/Documentation.docc/Documentation.md b/Documentation.docc/Documentation.md index a970a22951..28f2a1a7be 100644 --- a/Documentation.docc/Documentation.md +++ b/Documentation.docc/Documentation.md @@ -41,7 +41,7 @@ - ``CEWorkspaceFileManager`` - ``CodeFileDocument`` - ``CodeEditDocumentController`` -- ``WorkspaceCodeFileView`` +- ``EditorAreaFileView`` - ``WorkspaceAnyFileView`` - ``WorkspaceLoadingView`` - ``WorkspaceImageView`` From 151e34532fdcedf331cbd7971a6609f43c062bb4 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 15:45:19 +0100 Subject: [PATCH 60/66] rename `EditorView` to `EditorAreaView` - also added the view to the App Window docs --- CodeEdit.xcodeproj/project.pbxproj | 8 ++++---- .../Views/{EditorView.swift => EditorAreaView.swift} | 4 ++-- CodeEdit/Features/Editor/Views/EditorLayoutView.swift | 2 +- Documentation.docc/App Window/App Window.md | 1 + 4 files changed, 8 insertions(+), 7 deletions(-) rename CodeEdit/Features/Editor/Views/{EditorView.swift => EditorAreaView.swift} (98%) diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index 597047ef5b..443eca4b8a 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -301,7 +301,7 @@ 6C147C4529A329350089B630 /* OrderedCollections in Frameworks */ = {isa = PBXBuildFile; productRef = 6C147C4429A329350089B630 /* OrderedCollections */; }; 6C147C4929A32A080089B630 /* EditorLayoutView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C147C4829A32A080089B630 /* EditorLayoutView.swift */; }; 6C147C4B29A32A7B0089B630 /* Environment+SplitEditor.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C147C4A29A32A7B0089B630 /* Environment+SplitEditor.swift */; }; - 6C147C4D29A32AA30089B630 /* EditorView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C147C4C29A32AA30089B630 /* EditorView.swift */; }; + 6C147C4D29A32AA30089B630 /* EditorAreaView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C147C4C29A32AA30089B630 /* EditorAreaView.swift */; }; 6C14CEB028777D3C001468FE /* FindNavigatorListViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C14CEAF28777D3C001468FE /* FindNavigatorListViewController.swift */; }; 6C14CEB32877A68F001468FE /* FindNavigatorMatchListCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C14CEB22877A68F001468FE /* FindNavigatorMatchListCell.swift */; }; 6C18620A298BF5A800C663EA /* RecentProjectsListView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C186209298BF5A800C663EA /* RecentProjectsListView.swift */; }; @@ -863,7 +863,7 @@ 6C147C3F29A328560089B630 /* SplitViewData.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SplitViewData.swift; sourceTree = ""; }; 6C147C4829A32A080089B630 /* EditorLayoutView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = EditorLayoutView.swift; sourceTree = ""; }; 6C147C4A29A32A7B0089B630 /* Environment+SplitEditor.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "Environment+SplitEditor.swift"; sourceTree = ""; }; - 6C147C4C29A32AA30089B630 /* EditorView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = EditorView.swift; sourceTree = ""; }; + 6C147C4C29A32AA30089B630 /* EditorAreaView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = EditorAreaView.swift; sourceTree = ""; }; 6C14CEAF28777D3C001468FE /* FindNavigatorListViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FindNavigatorListViewController.swift; sourceTree = ""; }; 6C14CEB22877A68F001468FE /* FindNavigatorMatchListCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FindNavigatorMatchListCell.swift; sourceTree = ""; }; 6C186209298BF5A800C663EA /* RecentProjectsListView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = RecentProjectsListView.swift; sourceTree = ""; }; @@ -2729,7 +2729,7 @@ B67660632AA970E300CD56B0 /* Views */ = { isa = PBXGroup; children = ( - 6C147C4C29A32AA30089B630 /* EditorView.swift */, + 6C147C4C29A32AA30089B630 /* EditorAreaView.swift */, 6C147C4829A32A080089B630 /* EditorLayoutView.swift */, ); path = Views; @@ -3458,7 +3458,7 @@ 6CE6226B2A2A1C730013085C /* UtilityAreaTab.swift in Sources */, 587B9DA329300ABD00AC7927 /* SettingsTextEditor.swift in Sources */, B6F0517B29D9E46400D72287 /* SourceControlSettingsView.swift in Sources */, - 6C147C4D29A32AA30089B630 /* EditorView.swift in Sources */, + 6C147C4D29A32AA30089B630 /* EditorAreaView.swift in Sources */, B6152B802ADAE421004C6012 /* CodeEditWindowControllerExtensions.swift in Sources */, 587B9E7B29301D8F00AC7927 /* GitHubRouter.swift in Sources */, 201169E22837B3D800F92B46 /* SourceControlNavigatorChangesView.swift in Sources */, diff --git a/CodeEdit/Features/Editor/Views/EditorView.swift b/CodeEdit/Features/Editor/Views/EditorAreaView.swift similarity index 98% rename from CodeEdit/Features/Editor/Views/EditorView.swift rename to CodeEdit/Features/Editor/Views/EditorAreaView.swift index 8de286e576..11a63f8d0d 100644 --- a/CodeEdit/Features/Editor/Views/EditorView.swift +++ b/CodeEdit/Features/Editor/Views/EditorAreaView.swift @@ -1,5 +1,5 @@ // -// EditorView.swift +// EditorAreaView.swift // CodeEdit // // Created by Wouter Hennen on 16/02/2023. @@ -7,7 +7,7 @@ import SwiftUI -struct EditorView: View { +struct EditorAreaView: View { @AppSettings(\.general.showEditorPathBar) var showEditorPathBar diff --git a/CodeEdit/Features/Editor/Views/EditorLayoutView.swift b/CodeEdit/Features/Editor/Views/EditorLayoutView.swift index 408bf476a7..0402aae008 100644 --- a/CodeEdit/Features/Editor/Views/EditorLayoutView.swift +++ b/CodeEdit/Features/Editor/Views/EditorLayoutView.swift @@ -26,7 +26,7 @@ struct EditorLayoutView: View { VStack { switch layout { case .one(let detailEditor): - EditorView(editor: detailEditor, focus: $focus) + EditorAreaView(editor: detailEditor, focus: $focus) .transformEnvironment(\.edgeInsets) { insets in switch isAtEdge { case .all: diff --git a/Documentation.docc/App Window/App Window.md b/Documentation.docc/App Window/App Window.md index d0b7138a77..d7b090fb28 100644 --- a/Documentation.docc/App Window/App Window.md +++ b/Documentation.docc/App Window/App Window.md @@ -11,6 +11,7 @@ A collection of all the views that make up the main app window. ### Main Content +- ``EditorAreaView`` - ``CodeFileView`` - ``NonTextFileView`` From fe1f7bb944d674f52fd65232aa046ca23b37c7ba Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 15:57:22 +0100 Subject: [PATCH 61/66] rename 4 Workspace view files - `WorkspaceAnyFileView` -> `AnyFileView` - `WorkspaceLoadingView` -> `LoadingFileView` - `WorkspaceImageView` -> `ImageFileView` - `WorkspacePDFView` -> `PDFFileView` --- CodeEdit.xcodeproj/project.pbxproj | 32 +++++++++---------- .../NonTextFile/NonTextFileView.swift | 8 ++--- ...aceAnyFileView.swift => AnyFileView.swift} | 6 ++-- .../Documents/Views/EditorAreaFileView.swift | 2 +- ...aceImageView.swift => ImageFileView.swift} | 8 ++--- ...oadingView.swift => LoadingFileView.swift} | 8 ++--- ...rkspacePDFView.swift => PDFFileView.swift} | 8 ++--- Documentation.docc/App Window/App Window.md | 5 +++ Documentation.docc/Documentation.md | 6 ---- 9 files changed, 41 insertions(+), 42 deletions(-) rename CodeEdit/Features/Documents/Views/{WorkspaceAnyFileView.swift => AnyFileView.swift} (86%) rename CodeEdit/Features/Documents/Views/{WorkspaceImageView.swift => ImageFileView.swift} (93%) rename CodeEdit/Features/Documents/Views/{WorkspaceLoadingView.swift => LoadingFileView.swift} (79%) rename CodeEdit/Features/Documents/Views/{WorkspacePDFView.swift => PDFFileView.swift} (88%) diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index 443eca4b8a..30dbc0e8fc 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -283,10 +283,10 @@ 6195E3112B640485007261CA /* WorkspaceDocument+SearchState+IndexTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6195E3102B640485007261CA /* WorkspaceDocument+SearchState+IndexTests.swift */; }; 61A53A7E2B4449870093BF8A /* WorkspaceDocument+Find.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */; }; 61A53A812B4449F00093BF8A /* WorkspaceDocument+Index.swift in Sources */ = {isa = PBXBuildFile; fileRef = 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */; }; - 661EF7B82BEE215300C3E577 /* WorkspaceImageView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */; }; - 661EF7BD2BEE215300C3E577 /* WorkspaceLoadingView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */; }; - 669BC4082BED306400D1197C /* WorkspaceAnyFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 669BC4072BED306400D1197C /* WorkspaceAnyFileView.swift */; }; - 66F2C8C42BEAA939004674F7 /* WorkspacePDFView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */; }; + 661EF7B82BEE215300C3E577 /* ImageFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7B72BEE215300C3E577 /* ImageFileView.swift */; }; + 661EF7BD2BEE215300C3E577 /* LoadingFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 661EF7BC2BEE215300C3E577 /* LoadingFileView.swift */; }; + 669BC4082BED306400D1197C /* AnyFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 669BC4072BED306400D1197C /* AnyFileView.swift */; }; + 66F2C8C42BEAA939004674F7 /* PDFFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F2C8C32BEAA939004674F7 /* PDFFileView.swift */; }; 66F370342BEE537B00D3B823 /* NonTextFileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 66F370332BEE537B00D3B823 /* NonTextFileView.swift */; }; 6C049A372A49E2DB00D42923 /* DirectoryEventStream.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */; }; 6C05A8AF284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */; }; @@ -848,10 +848,10 @@ 6195E3102B640485007261CA /* WorkspaceDocument+SearchState+IndexTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+SearchState+IndexTests.swift"; sourceTree = ""; }; 61A53A7D2B4449870093BF8A /* WorkspaceDocument+Find.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Find.swift"; sourceTree = ""; }; 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Index.swift"; sourceTree = ""; }; - 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceImageView.swift; sourceTree = ""; }; - 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceLoadingView.swift; sourceTree = ""; }; - 669BC4072BED306400D1197C /* WorkspaceAnyFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspaceAnyFileView.swift; sourceTree = ""; }; - 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WorkspacePDFView.swift; sourceTree = ""; }; + 661EF7B72BEE215300C3E577 /* ImageFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ImageFileView.swift; sourceTree = ""; }; + 661EF7BC2BEE215300C3E577 /* LoadingFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LoadingFileView.swift; sourceTree = ""; }; + 669BC4072BED306400D1197C /* AnyFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AnyFileView.swift; sourceTree = ""; }; + 66F2C8C32BEAA939004674F7 /* PDFFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = PDFFileView.swift; sourceTree = ""; }; 66F370332BEE537B00D3B823 /* NonTextFileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NonTextFileView.swift; sourceTree = ""; }; 6C049A362A49E2DB00D42923 /* DirectoryEventStream.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DirectoryEventStream.swift; sourceTree = ""; }; 6C05A8AE284D0CA3007F4EAA /* WorkspaceDocument+Listeners.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "WorkspaceDocument+Listeners.swift"; sourceTree = ""; }; @@ -1504,11 +1504,11 @@ 5831E3CF2933F4E000D5A6D2 /* Views */ = { isa = PBXGroup; children = ( - 669BC4072BED306400D1197C /* WorkspaceAnyFileView.swift */, 0485EB1E27E7458B00138301 /* EditorAreaFileView.swift */, - 661EF7BC2BEE215300C3E577 /* WorkspaceLoadingView.swift */, - 661EF7B72BEE215300C3E577 /* WorkspaceImageView.swift */, - 66F2C8C32BEAA939004674F7 /* WorkspacePDFView.swift */, + 669BC4072BED306400D1197C /* AnyFileView.swift */, + 661EF7BC2BEE215300C3E577 /* LoadingFileView.swift */, + 661EF7B72BEE215300C3E577 /* ImageFileView.swift */, + 66F2C8C32BEAA939004674F7 /* PDFFileView.swift */, ); path = Views; sourceTree = ""; @@ -3351,7 +3351,7 @@ B6C4F2A62B3CABD200B2B140 /* HistoryInspectorItemView.swift in Sources */, B65B10FE2B08B07D002852CF /* SourceControlNavigatorChangesList.swift in Sources */, 58F2EB03292FB2B0004A9BDE /* Documentation.docc in Sources */, - 66F2C8C42BEAA939004674F7 /* WorkspacePDFView.swift in Sources */, + 66F2C8C42BEAA939004674F7 /* PDFFileView.swift in Sources */, 611192042B08CCED00D4459B /* SearchIndexer+ProgressiveSearch.swift in Sources */, 611192022B08CCDC00D4459B /* SearchIndexer+Search.swift in Sources */, 04BA7C272AE2E9F100584E1C /* GitClient+Push.swift in Sources */, @@ -3399,7 +3399,7 @@ B6C4F2AC2B3CC4D000B2B140 /* CommitChangedFileListItemView.swift in Sources */, 6C82D6B329BFD88700495C54 /* NavigateCommands.swift in Sources */, B66A4E4C29C9179B004573B4 /* CodeEditApp.swift in Sources */, - 661EF7B82BEE215300C3E577 /* WorkspaceImageView.swift in Sources */, + 661EF7B82BEE215300C3E577 /* ImageFileView.swift in Sources */, 4E7F066629602E7B00BB3C12 /* CodeEditSplitViewController.swift in Sources */, 587B9E8D29301D8F00AC7927 /* GitHubAccount.swift in Sources */, 201169E72837B5CA00F92B46 /* SourceControlManager.swift in Sources */, @@ -3478,7 +3478,7 @@ B6E55C3B2A95368E003ECC7D /* EditorTabsOverflowShadow.swift in Sources */, 58A5DFA229339F6400D1BD5D /* KeybindingManager.swift in Sources */, B62AEDB32A1FD95B009A9F52 /* UtilityAreaTerminalView.swift in Sources */, - 661EF7BD2BEE215300C3E577 /* WorkspaceLoadingView.swift in Sources */, + 661EF7BD2BEE215300C3E577 /* LoadingFileView.swift in Sources */, 58AFAA2E2933C69E00482B53 /* EditorTabRepresentable.swift in Sources */, 6C4104E6297C884F00F472BA /* AboutDetailView.swift in Sources */, 6C6BD6F129CD13FA00235D17 /* ExtensionDiscovery.swift in Sources */, @@ -3490,7 +3490,7 @@ 6CABB1A129C5593800340467 /* SearchPanelView.swift in Sources */, D7211D4327E066CE008F2ED7 /* Localized+Ex.swift in Sources */, 581BFB692926431000D251EC /* WelcomeActionView.swift in Sources */, - 669BC4082BED306400D1197C /* WorkspaceAnyFileView.swift in Sources */, + 669BC4082BED306400D1197C /* AnyFileView.swift in Sources */, 20D839AE280E0CA700B27357 /* HistoryPopoverView.swift in Sources */, B6E41C7029DD157F0088F9F4 /* AccountsSettingsView.swift in Sources */, 6CFF967A29BEBD2400182D6F /* ViewCommands.swift in Sources */, diff --git a/CodeEdit/Features/Documents/NonTextFile/NonTextFileView.swift b/CodeEdit/Features/Documents/NonTextFile/NonTextFileView.swift index c6b872514d..126646d02e 100644 --- a/CodeEdit/Features/Documents/NonTextFile/NonTextFileView.swift +++ b/CodeEdit/Features/Documents/NonTextFile/NonTextFileView.swift @@ -24,16 +24,16 @@ struct NonTextFileView: View { switch fileDocument.utType { case .some(.gif): // GIF conforms to image, so to differentiate, the GIF check has to come before the image check. - WorkspaceImageView(fileURL, isGif: true) + ImageFileView(fileURL, isGif: true) case .some(.image): - WorkspaceImageView(fileURL) + ImageFileView(fileURL) case .some(.pdf): - WorkspacePDFView(fileURL) + PDFFileView(fileURL) default: - WorkspaceAnyFileView(fileURL) + AnyFileView(fileURL) } } else { diff --git a/CodeEdit/Features/Documents/Views/WorkspaceAnyFileView.swift b/CodeEdit/Features/Documents/Views/AnyFileView.swift similarity index 86% rename from CodeEdit/Features/Documents/Views/WorkspaceAnyFileView.swift rename to CodeEdit/Features/Documents/Views/AnyFileView.swift index c7ea1d3cad..9851fa6af3 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceAnyFileView.swift +++ b/CodeEdit/Features/Documents/Views/AnyFileView.swift @@ -1,5 +1,5 @@ // -// WorkspaceAnyFileView.swift +// AnyFileView.swift // CodeEdit // // Created by Paul Ebose on 2024/5/9. @@ -11,10 +11,10 @@ import QuickLookUI /// A view for previewing any kind of file. /// /// ```swift -/// WorkspaceAnyFileView(fileURL) +/// AnyFileView(fileURL) /// ``` /// If the file cannot be previewed, a file icon thumbnail is shown instead. -struct WorkspaceAnyFileView: NSViewRepresentable { +struct AnyFileView: NSViewRepresentable { /// URL of the file to preview. You can pass in any file type. private let fileURL: URL diff --git a/CodeEdit/Features/Documents/Views/EditorAreaFileView.swift b/CodeEdit/Features/Documents/Views/EditorAreaFileView.swift index 35446401d8..4746c6b825 100644 --- a/CodeEdit/Features/Documents/Views/EditorAreaFileView.swift +++ b/CodeEdit/Features/Documents/Views/EditorAreaFileView.swift @@ -40,7 +40,7 @@ struct EditorAreaFileView: View { Spacer() } Spacer() - WorkspaceLoadingView(file.name) + LoadingFileView(file.name) Spacer() .onAppear { Task.detached { diff --git a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift b/CodeEdit/Features/Documents/Views/ImageFileView.swift similarity index 93% rename from CodeEdit/Features/Documents/Views/WorkspaceImageView.swift rename to CodeEdit/Features/Documents/Views/ImageFileView.swift index 41e163ced2..a20f693f19 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceImageView.swift +++ b/CodeEdit/Features/Documents/Views/ImageFileView.swift @@ -1,5 +1,5 @@ // -// WorkspaceImageView.swift +// ImageFileView.swift // CodeEdit // // Created by Paul Ebose on 2024/5/9. @@ -12,7 +12,7 @@ import SwiftUI /// It receives a URL to an image file and attempts to preview it. /// /// ```swift -/// WorkspaceImageView(imageURL) +/// ImageFileView(imageURL) /// ``` /// This implementation allows for proper image scaling, especially when the image dimensions is smaller than /// the size of the image view area. @@ -21,7 +21,7 @@ import SwiftUI /// /// - Note: This view wraps around SwiftUI Image. Since SwiftUI Image view do not play GIFs, you should indicate /// when passing in a GIF file, so this view can handle the GIF file correctly. -struct WorkspaceImageView: View { +struct ImageFileView: View { /// URL of the image you want to preview. private let imageURL: URL @@ -44,7 +44,7 @@ struct WorkspaceImageView: View { GeometryReader { proxy in ZStack { if isGif { - WorkspaceAnyFileView(imageURL) + AnyFileView(imageURL) .frame( maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) diff --git a/CodeEdit/Features/Documents/Views/WorkspaceLoadingView.swift b/CodeEdit/Features/Documents/Views/LoadingFileView.swift similarity index 79% rename from CodeEdit/Features/Documents/Views/WorkspaceLoadingView.swift rename to CodeEdit/Features/Documents/Views/LoadingFileView.swift index 3d05c90ff7..71eb34699a 100644 --- a/CodeEdit/Features/Documents/Views/WorkspaceLoadingView.swift +++ b/CodeEdit/Features/Documents/Views/LoadingFileView.swift @@ -1,5 +1,5 @@ // -// WorkspaceLoadingView.swift +// LoadingFileView.swift // CodeEdit // // Created by Paul Ebose on 2024/5/9. @@ -11,10 +11,10 @@ import SwiftUI /// /// It optionally receives a file name. /// ```swift -/// WorkspaceLoadingView(filename) -/// WorkspaceLoadingView() +/// LoadingFileView(filename) +/// LoadingFileView() /// ``` -struct WorkspaceLoadingView: View { +struct LoadingFileView: View { /// Name of file that is about to open. private var filename = "" diff --git a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift b/CodeEdit/Features/Documents/Views/PDFFileView.swift similarity index 88% rename from CodeEdit/Features/Documents/Views/WorkspacePDFView.swift rename to CodeEdit/Features/Documents/Views/PDFFileView.swift index 40be1a5369..60058807a6 100644 --- a/CodeEdit/Features/Documents/Views/WorkspacePDFView.swift +++ b/CodeEdit/Features/Documents/Views/PDFFileView.swift @@ -1,5 +1,5 @@ // -// WorkspacePDFView.swift +// PDFFileView.swift // CodeEdit // // Created by Paul Ebose on 2024/5/7. @@ -13,7 +13,7 @@ import PDFKit.PDFView /// It takes in a file URL and attempts to preview a PDF. /// /// ```swift -/// WorkspacePDFView(fileURL) +/// PDFFileView(fileURL) /// ``` /// /// This view provides a context menu that is the same as the one in the native MacOS Preview @@ -22,7 +22,7 @@ import PDFKit.PDFView /// This view also allows for proper scaling of the PDF. /// /// - Note: If the file located at the `fileURL` cannot be previewed as a PDF, nothing happens, no redraw or anything. -struct WorkspacePDFView: NSViewRepresentable { +struct PDFFileView: NSViewRepresentable { /// URL of the PDF file you want to preview. private let fileURL: URL @@ -40,7 +40,7 @@ struct WorkspacePDFView: NSViewRepresentable { attachPDFDocumentToView(pdfView) } - /// Creates a PDF document using ``WorkspacePDFView`` `.fileUrl`, and attaches it to the passed in `pdfView`. + /// Creates a PDF document using ``PDFFileView`` `.fileUrl`, and attaches it to the passed in `pdfView`. /// - Parameters: /// - pdfView: The [`PDFView`](https://developer.apple.com/documentation/pdfkit/pdfview) you wish to modify. /// - Returns: A modified `pdfView` if a valid PDF was created, or an unmodified `pdfView` if it could not create a diff --git a/Documentation.docc/App Window/App Window.md b/Documentation.docc/App Window/App Window.md index d7b090fb28..a1bd2b9c86 100644 --- a/Documentation.docc/App Window/App Window.md +++ b/Documentation.docc/App Window/App Window.md @@ -12,8 +12,13 @@ A collection of all the views that make up the main app window. ### Main Content - ``EditorAreaView`` +- ``EditorAreaFileView`` - ``CodeFileView`` - ``NonTextFileView`` +- ``AnyFileView`` +- ``LoadingFileView`` +- ``ImageFileView`` +- ``PDFFileView`` ### PathBar diff --git a/Documentation.docc/Documentation.md b/Documentation.docc/Documentation.md index 28f2a1a7be..5825064d5c 100644 --- a/Documentation.docc/Documentation.md +++ b/Documentation.docc/Documentation.md @@ -41,12 +41,6 @@ - ``CEWorkspaceFileManager`` - ``CodeFileDocument`` - ``CodeEditDocumentController`` -- ``EditorAreaFileView`` -- ``WorkspaceAnyFileView`` -- ``WorkspaceLoadingView`` -- ``WorkspaceImageView`` -- ``WorkspacePDFView`` -- ``WorkspaceNotificationModel`` ### Feedback From cb88ec2496fe09828e1d6a691d2daacd358ba77e Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 16:03:00 +0100 Subject: [PATCH 62/66] move views for opening files to `CodeEdit/Features/Editor` --- CodeEdit.xcodeproj/project.pbxproj | 30 +++++-------------- .../Views/AnyFileView.swift | 0 .../Views}/CodeFileView.swift | 0 .../Views/EditorAreaFileView.swift | 0 .../Views/ImageFileView.swift | 0 .../Views/LoadingFileView.swift | 0 .../Views}/NonTextFileView.swift | 0 .../Views/PDFFileView.swift | 0 8 files changed, 7 insertions(+), 23 deletions(-) rename CodeEdit/Features/{Documents => Editor}/Views/AnyFileView.swift (100%) rename CodeEdit/Features/{CodeFile => Editor/Views}/CodeFileView.swift (100%) rename CodeEdit/Features/{Documents => Editor}/Views/EditorAreaFileView.swift (100%) rename CodeEdit/Features/{Documents => Editor}/Views/ImageFileView.swift (100%) rename CodeEdit/Features/{Documents => Editor}/Views/LoadingFileView.swift (100%) rename CodeEdit/Features/{Documents/NonTextFile => Editor/Views}/NonTextFileView.swift (100%) rename CodeEdit/Features/{Documents => Editor}/Views/PDFFileView.swift (100%) diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index 30dbc0e8fc..b77280ae6b 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -1112,9 +1112,7 @@ 043C321227E31FE8006AE443 /* Documents */ = { isa = PBXGroup; children = ( - 66F370302BEE533A00D3B823 /* NonTextFile */, 5831E3CE2933F3DE00D5A6D2 /* Controllers */, - 5831E3CF2933F4E000D5A6D2 /* Views */, 043C321527E3201F006AE443 /* WorkspaceDocument.swift */, 043BCF02281DA18A000AC47C /* WorkspaceDocument+SearchState.swift */, 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */, @@ -1501,18 +1499,6 @@ path = Controllers; sourceTree = ""; }; - 5831E3CF2933F4E000D5A6D2 /* Views */ = { - isa = PBXGroup; - children = ( - 0485EB1E27E7458B00138301 /* EditorAreaFileView.swift */, - 669BC4072BED306400D1197C /* AnyFileView.swift */, - 661EF7BC2BEE215300C3E577 /* LoadingFileView.swift */, - 661EF7B72BEE215300C3E577 /* ImageFileView.swift */, - 66F2C8C32BEAA939004674F7 /* PDFFileView.swift */, - ); - path = Views; - sourceTree = ""; - }; 5831E3D02934036D00D5A6D2 /* NSTableView */ = { isa = PBXGroup; children = ( @@ -1710,7 +1696,6 @@ isa = PBXGroup; children = ( 58798249292E78D80085B254 /* CodeFileDocument.swift */, - 58798248292E78D80085B254 /* CodeFileView.swift */, 6C5B63DD29C76213005454BA /* WindowCodeFileView.swift */, ); path = CodeFile; @@ -2355,14 +2340,6 @@ path = FuzzySearch; sourceTree = ""; }; - 66F370302BEE533A00D3B823 /* NonTextFile */ = { - isa = PBXGroup; - children = ( - 66F370332BEE537B00D3B823 /* NonTextFileView.swift */, - ); - path = NonTextFile; - sourceTree = ""; - }; 6C092EDC2A53A63E00489202 /* Views */ = { isa = PBXGroup; children = ( @@ -2729,8 +2706,15 @@ B67660632AA970E300CD56B0 /* Views */ = { isa = PBXGroup; children = ( + 669BC4072BED306400D1197C /* AnyFileView.swift */, + 58798248292E78D80085B254 /* CodeFileView.swift */, 6C147C4C29A32AA30089B630 /* EditorAreaView.swift */, + 0485EB1E27E7458B00138301 /* EditorAreaFileView.swift */, 6C147C4829A32A080089B630 /* EditorLayoutView.swift */, + 661EF7BC2BEE215300C3E577 /* LoadingFileView.swift */, + 661EF7B72BEE215300C3E577 /* ImageFileView.swift */, + 66F370332BEE537B00D3B823 /* NonTextFileView.swift */, + 66F2C8C32BEAA939004674F7 /* PDFFileView.swift */, ); path = Views; sourceTree = ""; diff --git a/CodeEdit/Features/Documents/Views/AnyFileView.swift b/CodeEdit/Features/Editor/Views/AnyFileView.swift similarity index 100% rename from CodeEdit/Features/Documents/Views/AnyFileView.swift rename to CodeEdit/Features/Editor/Views/AnyFileView.swift diff --git a/CodeEdit/Features/CodeFile/CodeFileView.swift b/CodeEdit/Features/Editor/Views/CodeFileView.swift similarity index 100% rename from CodeEdit/Features/CodeFile/CodeFileView.swift rename to CodeEdit/Features/Editor/Views/CodeFileView.swift diff --git a/CodeEdit/Features/Documents/Views/EditorAreaFileView.swift b/CodeEdit/Features/Editor/Views/EditorAreaFileView.swift similarity index 100% rename from CodeEdit/Features/Documents/Views/EditorAreaFileView.swift rename to CodeEdit/Features/Editor/Views/EditorAreaFileView.swift diff --git a/CodeEdit/Features/Documents/Views/ImageFileView.swift b/CodeEdit/Features/Editor/Views/ImageFileView.swift similarity index 100% rename from CodeEdit/Features/Documents/Views/ImageFileView.swift rename to CodeEdit/Features/Editor/Views/ImageFileView.swift diff --git a/CodeEdit/Features/Documents/Views/LoadingFileView.swift b/CodeEdit/Features/Editor/Views/LoadingFileView.swift similarity index 100% rename from CodeEdit/Features/Documents/Views/LoadingFileView.swift rename to CodeEdit/Features/Editor/Views/LoadingFileView.swift diff --git a/CodeEdit/Features/Documents/NonTextFile/NonTextFileView.swift b/CodeEdit/Features/Editor/Views/NonTextFileView.swift similarity index 100% rename from CodeEdit/Features/Documents/NonTextFile/NonTextFileView.swift rename to CodeEdit/Features/Editor/Views/NonTextFileView.swift diff --git a/CodeEdit/Features/Documents/Views/PDFFileView.swift b/CodeEdit/Features/Editor/Views/PDFFileView.swift similarity index 100% rename from CodeEdit/Features/Documents/Views/PDFFileView.swift rename to CodeEdit/Features/Editor/Views/PDFFileView.swift From 096bb687b14313324a1dd3f8ba03c2ce44014462 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 16:09:02 +0100 Subject: [PATCH 63/66] move `CodeFileDocument` to `CodeEdit/Features/Documents` --- CodeEdit.xcodeproj/project.pbxproj | 4 ++-- .../Features/{CodeFile => Documents}/CodeFileDocument.swift | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) rename CodeEdit/Features/{CodeFile => Documents}/CodeFileDocument.swift (99%) diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index b77280ae6b..92e4b71757 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -1113,6 +1113,8 @@ isa = PBXGroup; children = ( 5831E3CE2933F3DE00D5A6D2 /* Controllers */, + 611191F82B08CC8000D4459B /* Indexer */, + 58798249292E78D80085B254 /* CodeFileDocument.swift */, 043C321527E3201F006AE443 /* WorkspaceDocument.swift */, 043BCF02281DA18A000AC47C /* WorkspaceDocument+SearchState.swift */, 61A53A802B4449F00093BF8A /* WorkspaceDocument+Index.swift */, @@ -1123,7 +1125,6 @@ 6C092EDF2A53BFCF00489202 /* WorkspaceStateKey.swift */, 61538B8F2B111FE800A88846 /* String+AppearancesOfSubstring.swift */, 61538B922B11201900A88846 /* String+Character.swift */, - 611191F82B08CC8000D4459B /* Indexer */, ); path = Documents; sourceTree = ""; @@ -1695,7 +1696,6 @@ 58798244292E78D80085B254 /* CodeFile */ = { isa = PBXGroup; children = ( - 58798249292E78D80085B254 /* CodeFileDocument.swift */, 6C5B63DD29C76213005454BA /* WindowCodeFileView.swift */, ); path = CodeFile; diff --git a/CodeEdit/Features/CodeFile/CodeFileDocument.swift b/CodeEdit/Features/Documents/CodeFileDocument.swift similarity index 99% rename from CodeEdit/Features/CodeFile/CodeFileDocument.swift rename to CodeEdit/Features/Documents/CodeFileDocument.swift index 61883bc21d..e8fa2bb2ca 100644 --- a/CodeEdit/Features/CodeFile/CodeFileDocument.swift +++ b/CodeEdit/Features/Documents/CodeFileDocument.swift @@ -1,5 +1,5 @@ // -// CodeFile.swift +// CodeFileDocument.swift // CodeEditModules/CodeFile // // Created by Rehatbir Singh on 12/03/2022. From cf17bc7da9e2d6ef83010c555cdc4eba28cea139 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 16:12:46 +0100 Subject: [PATCH 64/66] NSTableViewWrapper: minor change in comment --- CodeEdit/Features/QuickOpen/Views/NSTableViewWrapper.swift | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CodeEdit/Features/QuickOpen/Views/NSTableViewWrapper.swift b/CodeEdit/Features/QuickOpen/Views/NSTableViewWrapper.swift index c538f8e0fd..c2b3383e1f 100644 --- a/CodeEdit/Features/QuickOpen/Views/NSTableViewWrapper.swift +++ b/CodeEdit/Features/QuickOpen/Views/NSTableViewWrapper.swift @@ -1,5 +1,5 @@ // -// NotList.swift +// NSTableViewWrapper.swift // CodeEdit // // Created by Wouter Hennen on 18/03/2023. From 950d7ed7f3524184ad0c43bc226e4a4b31194e3f Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 17:48:52 +0100 Subject: [PATCH 65/66] move `WindowCodeFileView` to `CodeEdit/Features/Editor/Views` --- CodeEdit.xcodeproj/project.pbxproj | 12 ++---------- .../Views}/WindowCodeFileView.swift | 0 2 files changed, 2 insertions(+), 10 deletions(-) rename CodeEdit/Features/{CodeFile => Editor/Views}/WindowCodeFileView.swift (100%) diff --git a/CodeEdit.xcodeproj/project.pbxproj b/CodeEdit.xcodeproj/project.pbxproj index 92e4b71757..45913944ae 100644 --- a/CodeEdit.xcodeproj/project.pbxproj +++ b/CodeEdit.xcodeproj/project.pbxproj @@ -1407,7 +1407,6 @@ 5878DA7D291862BC00DD95A3 /* Acknowledgements */, 588847642992A30900996D95 /* CEWorkspace */, 587B9D7529300ABD00AC7927 /* CodeEditUI */, - 58798244292E78D80085B254 /* CodeFile */, 58FD7603291EA1CB0051D6E4 /* Commands */, 284DC84B2978B5EB00BF2770 /* Contributors */, 043C321227E31FE8006AE443 /* Documents */, @@ -1693,14 +1692,6 @@ path = Controllers; sourceTree = ""; }; - 58798244292E78D80085B254 /* CodeFile */ = { - isa = PBXGroup; - children = ( - 6C5B63DD29C76213005454BA /* WindowCodeFileView.swift */, - ); - path = CodeFile; - sourceTree = ""; - }; 5879827E292ED0FB0085B254 /* TerminalEmulator */ = { isa = PBXGroup; children = ( @@ -2439,6 +2430,7 @@ 6CAAF68F29BCC6F900A1F48A /* WindowCommands */ = { isa = PBXGroup; children = ( + 6C82D6BF29C00EE300495C54 /* Utils */, B66A4E5229C91831004573B4 /* CodeEditCommands.swift */, 6CFF967729BEBCF600182D6F /* MainCommands.swift */, 6CFF967529BEBCD900182D6F /* FileCommands.swift */, @@ -2448,7 +2440,6 @@ 6CFF967B29BEBD5200182D6F /* WindowCommands.swift */, 6C82D6B829BFE34900495C54 /* HelpCommands.swift */, 6C578D8B29CD372700DC73B2 /* ExtensionCommands.swift */, - 6C82D6BF29C00EE300495C54 /* Utils */, ); path = WindowCommands; sourceTree = ""; @@ -2715,6 +2706,7 @@ 661EF7B72BEE215300C3E577 /* ImageFileView.swift */, 66F370332BEE537B00D3B823 /* NonTextFileView.swift */, 66F2C8C32BEAA939004674F7 /* PDFFileView.swift */, + 6C5B63DD29C76213005454BA /* WindowCodeFileView.swift */, ); path = Views; sourceTree = ""; diff --git a/CodeEdit/Features/CodeFile/WindowCodeFileView.swift b/CodeEdit/Features/Editor/Views/WindowCodeFileView.swift similarity index 100% rename from CodeEdit/Features/CodeFile/WindowCodeFileView.swift rename to CodeEdit/Features/Editor/Views/WindowCodeFileView.swift From b373bb6c6118b4c3fb8d0a8c147e4fa247d45463 Mon Sep 17 00:00:00 2001 From: Paul Ebose Date: Fri, 10 May 2024 19:32:08 +0100 Subject: [PATCH 66/66] use `AnyFileView` to view all images - this removes the need to check for GIF images - this also has a nice add-on of using gestures for zoom --- .../Features/Documents/CodeFileDocument.swift | 4 --- .../Features/Editor/Views/ImageFileView.swift | 33 +++++-------------- .../Editor/Views/NonTextFileView.swift | 4 --- 3 files changed, 8 insertions(+), 33 deletions(-) diff --git a/CodeEdit/Features/Documents/CodeFileDocument.swift b/CodeEdit/Features/Documents/CodeFileDocument.swift index e8fa2bb2ca..b92d529c65 100644 --- a/CodeEdit/Features/Documents/CodeFileDocument.swift +++ b/CodeEdit/Features/Documents/CodeFileDocument.swift @@ -60,10 +60,6 @@ final class CodeFileDocument: NSDocument, ObservableObject { if type.conforms(to: .text) { return .text } - // GIF conforms to image, so to differentiate, the GIF check has to come before the image check. - if type.conforms(to: .gif) { - return .gif - } if type.conforms(to: .image) { return .image } diff --git a/CodeEdit/Features/Editor/Views/ImageFileView.swift b/CodeEdit/Features/Editor/Views/ImageFileView.swift index a20f693f19..044f4ed8da 100644 --- a/CodeEdit/Features/Editor/Views/ImageFileView.swift +++ b/CodeEdit/Features/Editor/Views/ImageFileView.swift @@ -7,31 +7,24 @@ import SwiftUI -/// A view for previewing an image, while respecting its image dimensions. +/// A view for previewing an image, while respecting its dimensions. /// /// It receives a URL to an image file and attempts to preview it. /// /// ```swift /// ImageFileView(imageURL) /// ``` -/// This implementation allows for proper image scaling, especially when the image dimensions is smaller than +/// This implementation allows for proper image scaling, especially when the image dimensions are smaller than /// the size of the image view area. /// /// If the preview image cannot be created, it shows a *"Cannot preview image"* text. -/// -/// - Note: This view wraps around SwiftUI Image. Since SwiftUI Image view do not play GIFs, you should indicate -/// when passing in a GIF file, so this view can handle the GIF file correctly. struct ImageFileView: View { /// URL of the image you want to preview. private let imageURL: URL - /// Indicates whether the image is a GIF. - private let isGif: Bool - - init(_ imageURL: URL, isGif: Bool = false) { + init(_ imageURL: URL) { self.imageURL = imageURL - self.isGif = isGif } var body: some View { @@ -43,21 +36,11 @@ struct ImageFileView: View { GeometryReader { proxy in ZStack { - if isGif { - AnyFileView(imageURL) - .frame( - maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), - maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) - ) - } else { - Image(nsImage: nsImage) - .resizable() - .scaledToFit() - .frame( - maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), - maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) - ) - } + AnyFileView(imageURL) + .frame( + maxWidth: min(pixelWidth, proxy.size.width, nsImage.size.width), + maxHeight: min(pixelHeight, proxy.size.height, nsImage.size.height) + ) } .frame(width: proxy.size.width, height: proxy.size.height) } diff --git a/CodeEdit/Features/Editor/Views/NonTextFileView.swift b/CodeEdit/Features/Editor/Views/NonTextFileView.swift index 126646d02e..cb5c776bcb 100644 --- a/CodeEdit/Features/Editor/Views/NonTextFileView.swift +++ b/CodeEdit/Features/Editor/Views/NonTextFileView.swift @@ -22,10 +22,6 @@ struct NonTextFileView: View { if let fileURL = fileDocument.fileURL { switch fileDocument.utType { - case .some(.gif): - // GIF conforms to image, so to differentiate, the GIF check has to come before the image check. - ImageFileView(fileURL, isGif: true) - case .some(.image): ImageFileView(fileURL)