Browse Source

【书签】书签显示,删除功能完善

lizhe 1 year ago
parent
commit
48f3c13f5e

+ 5 - 3
PDF Office/PDF Master/Class/PDFTools/KMBookmark/Controller/KMBookmarkController.swift

@@ -187,6 +187,7 @@ class KMBookmarkController: NSWindowController {
             guard let parent = item.parent, let itemIndex = parent.children.firstIndex(of: item) else { continue }
             parent.removeObjectFromChildren(index: itemIndex)
         }
+        outlineView.reloadData()
     }
     
     
@@ -244,9 +245,10 @@ class KMBookmarkController: NSWindowController {
             }
         }
     }
-
+    
     @IBAction func deleteBookmark(_ sender: Any) {
-        self.deleteBookmarks(bookmarks: [])
+        print("deleteBookmark")
+        self.deleteBookmarks(bookmarks: [outlineView.selectedItem() as! KMBookmark])
     }
 //
 //    @IBAction func toggleStatusBar(_ sender: Any) {
@@ -501,7 +503,7 @@ extension KMBookmarkController: NSOutlineViewDelegate, NSOutlineViewDataSource {
         var minimalCover = [KMBookmark]()
 
         for bm in items {
-            if lastBm != nil && !(bm.isDescendant(of: lastBm!)) {
+            if !(bm.isDescendant(of: lastBm)) {
                 minimalCover.append(bm)
                 lastBm = bm
             }

+ 1 - 5
PDF Office/PDF Master/Class/PDFTools/KMBookmark/Controller/KMBookmarkController.xib

@@ -26,10 +26,6 @@
                     <view translatesAutoresizingMaskIntoConstraints="NO" id="8va-Ju-ebM">
                         <rect key="frame" x="0.0" y="0.0" width="512" height="233"/>
                         <subviews>
-                            <customView fixedFrame="YES" translatesAutoresizingMaskIntoConstraints="NO" id="2O4-Fv-tBM" customClass="SKStatusBar">
-                                <rect key="frame" x="0.0" y="0.0" width="512" height="22"/>
-                                <autoresizingMask key="autoresizingMask" widthSizable="YES" flexibleMaxY="YES"/>
-                            </customView>
                             <scrollView fixedFrame="YES" borderType="none" autohidesScrollers="YES" horizontalLineScroll="18" horizontalPageScroll="10" verticalLineScroll="18" verticalPageScroll="10" usesPredominantAxisScrolling="NO" translatesAutoresizingMaskIntoConstraints="NO" id="3xo-BF-qal">
                                 <rect key="frame" x="0.0" y="22" width="512" height="212"/>
                                 <autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
@@ -49,7 +45,7 @@
                                                         <color key="textColor" name="headerTextColor" catalog="System" colorSpace="catalog"/>
                                                         <color key="backgroundColor" white="0.33333298560000002" alpha="1" colorSpace="calibratedWhite"/>
                                                     </tableHeaderCell>
-                                                    <textFieldCell key="dataCell" lineBreakMode="truncatingTail" selectable="YES" editable="YES" alignment="left" id="FJd-fo-cum" customClass="SKTextWithIconCell">
+                                                    <textFieldCell key="dataCell" lineBreakMode="truncatingTail" selectable="YES" editable="YES" alignment="left" id="FJd-fo-cum" customClass="KMTextWithIconCell" customModule="PDF_Reader_Pro" customModuleProvider="target">
                                                         <font key="font" metaFont="cellTitle"/>
                                                         <color key="textColor" name="controlTextColor" catalog="System" colorSpace="catalog"/>
                                                         <color key="backgroundColor" name="textBackgroundColor" catalog="System" colorSpace="catalog"/>

+ 12 - 7
PDF Office/PDF Master/Class/PDFTools/KMBookmark/Model/KMBookmark.swift

@@ -85,11 +85,15 @@ class KMBookmark: NSObject {
         child.parent = self
     }
     
-    func isDescendant(of bookmark: KMBookmark) -> Bool {
+    func isDescendant(of bookmark: KMBookmark?) -> Bool {
+        if bookmark == nil {
+            return false
+        }
+        
         if self == bookmark {
             return true
         }
-        for child in bookmark.children {
+        for child in bookmark!.children {
             if self.isDescendant(of: child) {
                 return true
             }
@@ -174,16 +178,17 @@ class KMFolderBookmark: KMBookmark {
 
 class KMRootBookmark: KMFolderBookmark {
     static func bookmarkRoot(childrenProperties: NSArray) -> KMRootBookmark {
-        let bookmark = KMRootBookmark()
+        let rootBookmark = KMRootBookmark()
         var childs: [KMBookmark] = []
         for setup in childrenProperties {
             let bookmark = KMBookmark()
-            bookmark.documentSetup = setup as! [String : Any]
+            bookmark.documentSetup = setup as? [String : Any]
+            bookmark.parent = rootBookmark
             childs.append(bookmark)
         }
-        bookmark.children = childs
-        bookmark.label = NSLocalizedString("Bookmarks Menu", comment: "")
-        return bookmark
+        rootBookmark.children = childs
+        rootBookmark.label = NSLocalizedString("Bookmarks Menu", comment: "")
+        return rootBookmark
     }
     
     override var icon: NSImage {

+ 123 - 0
PDF Office/PDF Master/Class/PDFTools/KMBookmark/View/KMTextWithIconCell.swift

@@ -0,0 +1,123 @@
+//
+//  KMTextWithIconCell.swift
+//  PDF Reader Pro
+//
+//  Created by lizhe on 2024/2/21.
+//
+
+import Cocoa
+
+let SKTextWithIconStringKey = "string"
+let SKTextWithIconImageKey = "image"
+let BORDER_BETWEEN_EDGE_AND_IMAGE: CGFloat = 2.0
+let BORDER_BETWEEN_IMAGE_AND_TEXT: CGFloat = 2.0
+let IMAGE_OFFSET: CGFloat = 1.0
+
+class KMTextWithIconCell: NSTextFieldCell {
+    private var imageCell: NSImageCell = NSImageCell()
+    
+    override init(textCell string: String) {
+        super.init(textCell: string)
+        commonInit()
+    }
+    
+    required init(coder: NSCoder) {
+        super.init(coder: coder)
+        commonInit()
+    }
+    
+    private func commonInit() {
+        imageCell.imageScaling = .scaleProportionallyUpOrDown
+//        if formatter == nil {
+//            formatter = DictionaryFormatter(key: SKTextWithIconStringKey)
+//        }
+    }
+    
+    override func copy(with zone: NSZone? = nil) -> Any {
+        let copy = super.copy(with: zone) as! KMTextWithIconCell
+        copy.imageCell = imageCell.copy() as! NSImageCell
+        return copy
+    }
+    
+    override func cellSize(forBounds rect: NSRect) -> NSSize {
+        var cellSize = super.cellSize(forBounds: rect)
+        cellSize.width += cellSize.height - 1 + BORDER_BETWEEN_EDGE_AND_IMAGE + BORDER_BETWEEN_IMAGE_AND_TEXT
+        cellSize.width = min(cellSize.width, rect.width)
+        return cellSize
+    }
+    
+    private func textRect(forBounds rect: NSRect) -> NSRect {
+        return KMShrinkRect(rect, NSHeight(rect) - 1 + BORDER_BETWEEN_EDGE_AND_IMAGE + BORDER_BETWEEN_IMAGE_AND_TEXT, .minX)
+    }
+    
+    private func iconRect(forBounds rect: NSRect) -> NSRect {
+        return KMSliceRect(KMShrinkRect(rect, BORDER_BETWEEN_EDGE_AND_IMAGE, .minX), NSHeight(rect) - 1, .minX)
+    }
+    
+    override func drawInterior(withFrame cellFrame: NSRect, in controlView: NSView) {
+        // let super draw the text
+        let textRect = textRect(forBounds: cellFrame)
+        super.drawInterior(withFrame: textRect, in: controlView)
+        
+        // Draw the image
+        var imageRect = iconRect(forBounds: cellFrame)
+        imageRect = KMCenterRectVertically(rect: imageRect, height: NSWidth(imageRect), offset: IMAGE_OFFSET, flipped: controlView.isFlipped)
+        imageCell.drawInterior(withFrame: imageRect, in: controlView)
+    }
+    
+    override func edit(withFrame cellFrame: NSRect, in controlView: NSView, editor textObj: NSText, delegate anObject: Any?, event: NSEvent?) {
+        super.edit(withFrame: textRect(forBounds: cellFrame), in: controlView, editor: textObj, delegate: anObject, event: event)
+    }
+    
+    override func select(withFrame cellFrame: NSRect, in controlView: NSView, editor textObj: NSText, delegate anObject: Any?, start selStart: Int, length selLength: Int) {
+        super.select(withFrame: textRect(forBounds: cellFrame), in: controlView, editor: textObj, delegate: anObject, start: selStart, length: selLength)
+    }
+    
+    override func hitTest(for event: NSEvent, in rect: NSRect, of controlView: NSView) -> NSCell.HitResult {
+        let textRect = textRect(forBounds: rect)
+        let mouseLoc = event.location(inPDFListView: controlView)
+        var hit: NSCell.HitResult = []
+        if NSMouseInRect(mouseLoc, textRect, controlView.isFlipped) {
+            hit = super.hitTest(for: event, in: textRect, of: controlView)
+        } else if NSMouseInRect(mouseLoc, iconRect(forBounds: rect), controlView.isFlipped) {
+            hit = .contentArea
+        }
+        return hit
+    }
+    
+    override var objectValue: Any? {
+        didSet {
+            if let obj = objectValue as? NSDictionary {
+                imageCell.image = obj[SKTextWithIconImageKey] as? NSImage
+            }
+        }
+    }
+    
+    var icon: NSImage? {
+        return imageCell.image
+    }
+}
+
+extension KMTextWithIconCell {
+    func KMSliceRect(_ rect: NSRect, _ amount: CGFloat, _ edge: NSRectEdge) -> NSRect {
+        var rect = rect
+        var ignored = NSRect.zero
+        NSDivideRect(rect, &rect, &ignored, amount, edge);
+        return rect
+    }
+
+    func KMShrinkRect(_ rect: NSRect, _ amount: CGFloat, _ edge: NSRectEdge) -> NSRect {
+        var rect = rect
+        var ignored = NSRect.zero
+        NSDivideRect(rect, &ignored, &rect, amount, edge);
+        return rect
+    }
+    
+    func KMCenterRectVertically(rect: NSRect, height: CGFloat , offset: CGFloat, flipped: Bool) -> NSRect {
+        var rect = rect
+        rect.origin.y += 0.5 * (NSHeight(rect) - height);
+        rect.origin.y = flipped ? ceil(rect.origin.y) - offset  : floor(rect.origin.y) + offset;
+        rect.size.height = height;
+        return rect;
+    }
+}

+ 4 - 4
PDF Office/PDF Master/Class/PDFWindowController/Side/LeftSide/Outline/OutlineView/View/KMCustomOutlineView.swift

@@ -187,10 +187,10 @@ class KMCustomOutlineView: NSOutlineView {
         return false
     }
     
-    @objc func delete(_ sender: AnyObject?) {
-        if self.canDelete() {
-            self.botaDelegate?.outlineView?(self, deleteItems: self.selectedItems())
-        }
+    @objc func delete(_ sender: Any) {
+//        if self.canDelete() {
+//            self.botaDelegate?.outlineView?(self, deleteItems: self.selectedItems())
+//        }
     }
     
     func selectedItems() -> [Any] {

+ 8 - 0
PDF Office/PDF Reader Pro.xcodeproj/project.pbxproj

@@ -1246,6 +1246,9 @@
 		AD055E5C2B85C9A70035F824 /* KMSeparatorCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = AD055E5B2B85C9A70035F824 /* KMSeparatorCell.swift */; };
 		AD055E5D2B85C9A70035F824 /* KMSeparatorCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = AD055E5B2B85C9A70035F824 /* KMSeparatorCell.swift */; };
 		AD055E5E2B85C9A70035F824 /* KMSeparatorCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = AD055E5B2B85C9A70035F824 /* KMSeparatorCell.swift */; };
+		AD055E602B85E04C0035F824 /* KMTextWithIconCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = AD055E5F2B85E04C0035F824 /* KMTextWithIconCell.swift */; };
+		AD055E612B85E04C0035F824 /* KMTextWithIconCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = AD055E5F2B85E04C0035F824 /* KMTextWithIconCell.swift */; };
+		AD055E622B85E04C0035F824 /* KMTextWithIconCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = AD055E5F2B85E04C0035F824 /* KMTextWithIconCell.swift */; };
 		AD0E8AB02A31B76300DBFD3C /* KMInAppPurchaseManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = AD0E8AAF2A31B76300DBFD3C /* KMInAppPurchaseManager.swift */; };
 		AD0E8AB12A31B76300DBFD3C /* KMInAppPurchaseManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = AD0E8AAF2A31B76300DBFD3C /* KMInAppPurchaseManager.swift */; };
 		AD0E8AB42A31B78900DBFD3C /* KMDMGPurchaseManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = AD0E8AB32A31B78900DBFD3C /* KMDMGPurchaseManager.swift */; };
@@ -5561,6 +5564,7 @@
 		AD055E4D2B7234810035F824 /* KMBookmarkSheetView.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; path = KMBookmarkSheetView.xib; sourceTree = "<group>"; };
 		AD055E522B73220A0035F824 /* KMBookmarkManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KMBookmarkManager.swift; sourceTree = "<group>"; };
 		AD055E5B2B85C9A70035F824 /* KMSeparatorCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KMSeparatorCell.swift; sourceTree = "<group>"; };
+		AD055E5F2B85E04C0035F824 /* KMTextWithIconCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KMTextWithIconCell.swift; sourceTree = "<group>"; };
 		AD0E8AAF2A31B76300DBFD3C /* KMInAppPurchaseManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KMInAppPurchaseManager.swift; sourceTree = "<group>"; };
 		AD0E8AB32A31B78900DBFD3C /* KMDMGPurchaseManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KMDMGPurchaseManager.swift; sourceTree = "<group>"; };
 		AD0E8AB82A31BDDD00DBFD3C /* KMProduct.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KMProduct.swift; sourceTree = "<group>"; };
@@ -8287,6 +8291,7 @@
 				AD055E492B72346E0035F824 /* KMBookmarkSheetView.swift */,
 				AD055E4D2B7234810035F824 /* KMBookmarkSheetView.xib */,
 				AD055E5B2B85C9A70035F824 /* KMSeparatorCell.swift */,
+				AD055E5F2B85E04C0035F824 /* KMTextWithIconCell.swift */,
 			);
 			path = View;
 			sourceTree = "<group>";
@@ -15212,6 +15217,7 @@
 				BB67EE262B54FFEF00573BF0 /* ASINetworkQueue.m in Sources */,
 				BB4DD043299B291A00E80DF6 /* KMCloudNoNetworkView.swift in Sources */,
 				BB49ECF6293F44DC00C82CA2 /* KMConvertExcelWindowController.swift in Sources */,
+				AD055E602B85E04C0035F824 /* KMTextWithIconCell.swift in Sources */,
 				BB8810D62B4F984000AFA63E /* JSONKit.m in Sources */,
 				BBC4F9F62AEB69940098A1A8 /* NSArray+Extension.swift in Sources */,
 				BBC348432956A638008D2CD1 /* KMEditBackgroundController.swift in Sources */,
@@ -16846,6 +16852,7 @@
 				ADDF83A22B391A5D00A81A4E /* DSignatureFileListViewController.swift in Sources */,
 				BB96A0B92AFCE45800559E24 /* WaitingView.swift in Sources */,
 				ADD1B70B29471FA500C3FFF7 /* KMPrintChoosePresenter.swift in Sources */,
+				AD055E612B85E04C0035F824 /* KMTextWithIconCell.swift in Sources */,
 				AD8810AA29A8463600178CA1 /* KMAccountInfoWindowController.swift in Sources */,
 				89752DF329389F82003FF08E /* KMToolbarItem.m in Sources */,
 				9F0CB526298656BA00007028 /* KMDesignToken+BorderWidth.swift in Sources */,
@@ -17410,6 +17417,7 @@
 				BBD1F79E296FF7A600343885 /* KMPageEditSplitSettingModel.swift in Sources */,
 				9F8810872B564E9700F69815 /* KMAnnotationButtonWidgetOptionsViewController.swift in Sources */,
 				9F0CB527298656BA00007028 /* KMDesignToken+BorderWidth.swift in Sources */,
+				AD055E622B85E04C0035F824 /* KMTextWithIconCell.swift in Sources */,
 				ADDF835B2B391A5C00A81A4E /* CDSignatureCertificateStateViewController.swift in Sources */,
 				ADE86AB82B0343E600414DFA /* KMWatermarkView.swift in Sources */,
 				BB897277294DC04F0045787C /* KMWatermartAdjectivePageRangeView.swift in Sources */,

+ 7 - 0
PDF Office/PDF Reader Pro.xcodeproj/xcshareddata/xcschemes/PDF Reader Pro Edition.xcscheme

@@ -73,6 +73,13 @@
             ReferencedContainer = "container:PDF Reader Pro.xcodeproj">
          </BuildableReference>
       </BuildableProductRunnable>
+      <AdditionalOptions>
+         <AdditionalOption
+            key = "NSZombieEnabled"
+            value = "YES"
+            isEnabled = "YES">
+         </AdditionalOption>
+      </AdditionalOptions>
    </LaunchAction>
    <ProfileAction
       buildConfiguration = "Release"