Browse Source

Merge branch 'develop_PDFReaderProNew' of git.kdan.cc:Mac_PDF/PDF_Office into develop_PDFReaderProNew

niehaoyu 11 months ago
parent
commit
fa1dd92705

+ 1 - 1
PDF Office/PDF Master/Class/PDFTools/OCRNew/Controller/KMOCRPDFWindowController.swift

@@ -745,7 +745,7 @@ class KMOCRPDFWindowController: NSWindowController, NSWindowDelegate, KMGOCRMana
                 PDFView.go(to: pdfDocument?.page(at: UInt(index-1))!)
                 reloadPDFData()
             } else {
-                currentPageLabel.stringValue = "(currentPageIndex+1)"
+                currentPageLabel.stringValue = "\((currentPageIndex ?? 0)+1)"
             }
         }
     }

+ 4 - 4
PDF Office/PDF Master/Class/PDFTools/Secure/Window/KMPasswordInputWindow.swift

@@ -87,7 +87,7 @@ private var passwordInputWindow_private: KMPasswordInputWindow?
                 ps.lineSpacing = 5
 
                     despLabel!.stringValue = "\"\(fileName)\"\(NSLocalizedString("This PDF is password protected. Please enter the password below to access this PDF.", comment: ""))"
-                    despLabel!.attributedStringValue = NSAttributedString(string: despLabel!.stringValue, attributes: [.foregroundColor : NSColor.titleColor(), .font : NSFont.SFProTextRegularFont(14), .paragraphStyle : ps])
+                    despLabel!.attributedStringValue = NSAttributedString(string: despLabel!.stringValue, attributes: [.foregroundColor : KMAppearance.Layout.h0Color(), .font : NSFont.SFProTextRegularFont(14), .paragraphStyle : ps])
             }
             
         }
@@ -111,14 +111,14 @@ private var passwordInputWindow_private: KMPasswordInputWindow?
             passwordInputWindow_private = self
             
             titleLabel.stringValue = NSLocalizedString("Permission Password", comment: "")
-            self.titleLabel.textColor = NSColor.titleColor()
+            self.titleLabel.textColor = KMAppearance.Layout.h0Color()
             titleLabel.font = NSFont.SFProTextRegularFont(16)
 //            self.titleLabel.window?.appearance = NSAppearance(named: .aqua)
         }
         
         if despLabel != nil {
             despLabel.stringValue = NSLocalizedString("This PDF is password protected. Please enter the password below to access this PDF.", comment: "")
-            self.despLabel.textColor = NSColor.titleColor()
+            self.despLabel.textColor = KMAppearance.Layout.h0Color()
             despLabel.font = NSFont.SFProTextRegularFont(14)
             despLabel.isSelectable = false
             let ps = NSMutableParagraphStyle()
@@ -126,7 +126,7 @@ private var passwordInputWindow_private: KMPasswordInputWindow?
             despLabel.maximumNumberOfLines = 2
             despLabel.lineBreakMode = .byTruncatingTail
             ps.lineBreakMode = .byTruncatingTail
-            despLabel.attributedStringValue = NSAttributedString(string: despLabel.stringValue, attributes: [.foregroundColor : NSColor.titleColor(), .font : NSFont.SFProTextRegularFont(14), .paragraphStyle : ps])
+            despLabel.attributedStringValue = NSAttributedString(string: despLabel.stringValue, attributes: [.foregroundColor : KMAppearance.Layout.h0Color(), .font : NSFont.SFProTextRegularFont(14), .paragraphStyle : ps])
         }
         
         if (iconImageView != nil) {

+ 20 - 158
PDF Office/PDF Master/Class/PDFWindowController/Side/LeftSide/KMLeftSideViewController+Action.swift

@@ -11,8 +11,11 @@ import Foundation
 
 extension KMLeftSideViewController {
     @IBAction func leftSideViewMoreButtonAction(_ sender: AnyObject?) {
-        let button = sender as? NSButton
-        let tag = button?.tag ?? 0
+        guard let button = sender as? NSButton else {
+            NSSound.beep()
+            return
+        }
+        let tag = button.tag
         if (tag == 300) {
             var selectedRow = 0
             if (self.snapshotTableView.selectedRow >= 0) {
@@ -46,8 +49,9 @@ extension KMLeftSideViewController {
 
             let itemDeleteAllSnapshot = menu.addItem(title: KMLocalizedString("Delete All Snapshots", "Menu item title"), action: #selector(deleteAllSnapshot), target: self)
             itemDeleteAllSnapshot?.representedObject = controller
-//
-            NSMenu.popUpContextMenu(menu, with: NSApp.currentEvent!, for: sender as! NSButton)
+            if let data = NSApp.currentEvent {
+                NSMenu.popUpContextMenu(menu, with: data, for: button)
+            }
         } else if (tag == 302) {
             let menu = NSMenu()
             let expandAllCommentsItem = menu.addItem(title: KMLocalizedString("Expand All", nil), action: #selector(toc_expandAllComments), target: self)
@@ -85,7 +89,9 @@ extension KMLeftSideViewController {
             }
             let removeEntryItem = menu.addItem(title: KMLocalizedString("Remove All Outlines", nil), action: #selector(leftSideEmptyAnnotationClick_DeleteOutline), target: self)
             removeEntryItem?.representedObject = self.tocOutlineView
-            NSMenu.popUpContextMenu(menu, with: NSApp.currentEvent!, for: sender as! NSButton)
+            if let data = NSApp.currentEvent {
+                NSMenu.popUpContextMenu(menu, with: data, for: button)
+            }
         } else if (tag == 304) {
             let menu = NSMenu()
             let object = KMPopupMenuObject()
@@ -173,7 +179,9 @@ extension KMLeftSideViewController {
 
             let removeAllAnnotationsItem = menu.addItem(title: NSLocalizedString("Remove All Annotations", comment: ""), action: #selector(leftSideEmptyAnnotationClick_DeleteAnnotation), target: self)
             removeAllAnnotationsItem?.representedObject = self.noteOutlineView
-            NSMenu.popUpContextMenu(menu, with: NSApp.currentEvent!, for: button!, with: nil)
+            if let data = NSApp.currentEvent {
+                NSMenu.popUpContextMenu(menu, with: data, for: button, with: nil)
+            }
         }
     }
     
@@ -469,7 +477,8 @@ extension KMLeftSideViewController: NSMenuDelegate {
                     let annotation = self.noteItems(items!).lastObject as? CPDFAnnotation
                     if let data = annotation?.isEditable(), data {
                         if annotation?.type == nil {
-                            if annotation!.isNote() {
+                            let isNote = annotation?.isNote() ?? false
+                            if isNote {
                                 // [NSLocalizedString(@"Edit", @"Menu item title") stringByAppendingEllipsis]
                                 item = menu.addItem(title: KMLocalizedString("Edit", "Menu item title"), action: #selector(editNoteTextFromTable), target: self)
                                 item?.representedObject = annotation
@@ -510,7 +519,7 @@ extension KMLeftSideViewController: NSMenuDelegate {
                     item?.tag = 6
                     
                     menu.addItem(.separator())
-                    if self.outlineView(self.noteOutlineView, canDeleteItems: items as! [Any]) {
+                    if self.outlineView(self.noteOutlineView, canDeleteItems: items as? [Any] ?? []) {
                         item = menu.addItem(title: KMLocalizedString("Delete", "Menu item title"), action: #selector(deleteNotes), target: self)
                         item?.representedObject = items
                     }
@@ -556,162 +565,14 @@ extension KMLeftSideViewController: NSMenuItemValidation {
         //            BOOL isMarkup = [menuItem tag] == SKHighlightNote || [menuItem tag] == SKUnderlineNote || [menuItem tag] == SKStrikeOutNote;
         //            isMarkup = NO;
         //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] allowsNotes] && ([pdfView toolMode] == SKTextToolMode || [pdfView toolMode] == SKNoteToolMode) && [pdfView hideNotes] == NO && (isMarkup == NO || [[pdfView currentSelection] hasCharacters]);
-        //        } else if (action == @selector(editNote:)) {
-        //            PDFAnnotation *annotation = [pdfView activeAnnotation];
-        //            return [self interactionMode] != SKPresentationMode && [annotation isSkimNote] && ([annotation isEditable]);
-        //        } else if (action == @selector(alignLeft:) || action == @selector(alignRight:) || action == @selector(alignCenter:)) {
-        //            PDFAnnotation *annotation = [pdfView activeAnnotation];
-        //            return [self interactionMode] != SKPresentationMode && [annotation isSkimNote] && ([annotation isEditable]) && [annotation respondsToSelector:@selector(setAlignment:)];
         //        } else if (action == @selector(toggleHideNotes:)) {
         //            if ([pdfView hideNotes])
         //                [menuItem setTitle:NSLocalizedString(@"Show Notes", @"Menu item title")];
         //            else
         //                [menuItem setTitle:NSLocalizedString(@"Hide Notes", @"Menu item title")];
         //            return YES;
-        //        } else if (action == @selector(changeDisplaySinglePages:)) {
-        //            [menuItem setState:([pdfView displayMode] & kPDFDisplayTwoUp) == (PDFDisplayMode)[menuItem tag] ? NSOnState : NSOffState];
-        //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] isLocked] == NO;
-        //        } else if (action == @selector(changeDisplayContinuous:)) {
-        //            [menuItem setState:([pdfView displayMode] & kPDFDisplaySinglePageContinuous) == (PDFDisplayMode)[menuItem tag] ? NSOnState : NSOffState];
-        //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] isLocked] == NO;
-        //        } else if (action == @selector(changeDisplayMode:)) {
-        //            [menuItem setState:[pdfView displayMode] == (PDFDisplayMode)[menuItem tag] ? NSOnState : NSOffState];
-        //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] isLocked] == NO;
-        //        } else if (action == @selector(toggleDisplayAsBook:)) {
-        //            [menuItem setState:[pdfView displaysAsBook] ? NSOnState : NSOffState];
-        //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] isLocked] == NO && ([pdfView displayMode] == kPDFDisplayTwoUp || [pdfView displayMode] == kPDFDisplayTwoUpContinuous);
-        //        } else if (action == @selector(toggleDisplayPageBreaks:)) {
-        //            [menuItem setState:[pdfView displaysPageBreaks] ? NSOnState : NSOffState];
-        //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] isLocked] == NO;
-        //        } else if (action == @selector(changeDisplayBox:)) {
-        //            [menuItem setState:[pdfView displayBox] == (PDFDisplayBox)[menuItem tag] ? NSOnState : NSOffState];
-        //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] isLocked] == NO;
-        //        } else if (action == @selector(delete:) || action == @selector(copy:) || action == @selector(cut:) || action == @selector(paste:) || action == @selector(alternatePaste:) || action == @selector(pasteAsPlainText:) || action == @selector(deselectAll:) || action == @selector(changeAnnotationMode:) || action == @selector(changeToolMode:) || action == @selector(changeToolMode:)) {
-        //            return [pdfView validateMenuItem:menuItem];
-        //        } else
-        //        if (action == @selector(doGoToNextPage:)) {
-        //            return [pdfView canGoToNextPage];
-        //        } else if (action == @selector(doGoToPreviousPage:) ) {
-        //            return [pdfView canGoToPreviousPage];
-        //        } else if (action == @selector(doGoToFirstPage:)) {
-        //            return [pdfView canGoToFirstPage];
-        //        } else if (action == @selector(doGoToLastPage:)) {
-        //            return [pdfView canGoToLastPage];
-        //        } else if (action == @selector(doGoToPage:)) {
-        //            return [[self pdfDocument] isLocked] == NO;
-        //        } else if (action == @selector(allGoToNextPage:)) {
-        //            return [[allMainDocumentPDFViews() valueForKeyPath:@"@min.canGoToNextPage"] boolValue];
-        //        } else if (action == @selector(allGoToPreviousPage:)) {
-        //            return [[allMainDocumentPDFViews() valueForKeyPath:@"@min.canGoToPreviousPage"] boolValue];
-        //        } else if (action == @selector(allGoToFirstPage:)) {
-        //            return [[allMainDocumentPDFViews() valueForKeyPath:@"@min.canGoToFirstPage"] boolValue];
-        //        } else if (action == @selector(allGoToLastPage:)) {
-        //            return [[allMainDocumentPDFViews() valueForKeyPath:@"@min.canGoToLastPage"] boolValue];
-        //        } else if (action == @selector(doGoBack:)) {
-        //            return [pdfView canGoBack];
-        //        } else if (action == @selector(doGoForward:)) {
-        //            return [pdfView canGoForward];
-        //        } else if (action == @selector(goToMarkedPage:)) {
-        //            if (beforeMarkedPageIndex != NSNotFound) {
-        //                [menuItem setTitle:NSLocalizedString(@"Jump Back From Marked Page", @"Menu item title")];
-        //                return YES;
-        //            } else {
-        //                [menuItem setTitle:NSLocalizedString(@"Go To Marked Page", @"Menu item title")];
-        //                return markedPageIndex != NSNotFound && markedPageIndex != [[pdfView currentPage] pageIndex];
-        //            }
-        //        } else if (action == @selector(markPage:)) {
-        //            return [[self pdfDocument] isLocked] == NO;
-        //        } else if (action == @selector(doZoomIn:)) {
-        //            return [self interactionMode] != SKPresentationMode && [pdfView canZoomIn];
-        //        } else if (action == @selector(doZoomOut:)) {
-        //            return [self interactionMode] != SKPresentationMode && [pdfView canZoomOut];
-        //        } else if (action == @selector(doZoomToActualSize:)) {
-        //            return [[self pdfDocument] isLocked] == NO && ([pdfView autoScales] || fabs([pdfView scaleFactor] - 1.0 ) > 0.01);
-        //        } else if (action == @selector(doZoomToPhysicalSize:)) {
-        //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] isLocked] == NO && ([pdfView autoScales] || fabs([pdfView physicalScaleFactor] - 1.0 ) > 0.01);
-        //        } else if (action == @selector(doMarqueeZoomTool:)) {
-        //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] isLocked] == NO;
-        //        } else if (action == @selector(doZoomToFit:)) {
-        //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] isLocked] == NO && [pdfView autoScales] == NO;
-        //        } else if (action == @selector(alternateZoomToFit:)) {
-        //            PDFDisplayMode displayMode = [pdfView displayMode];
-        //            if (displayMode == kPDFDisplaySinglePage || displayMode == kPDFDisplayTwoUp) {
-        //                [menuItem setTitle:NSLocalizedString(@"Zoom To Width", @"Menu item title")];
-        //            } else {
-        //                [menuItem setTitle:NSLocalizedString(@"Zoom To Height", @"Menu item title")];
-        //            }
-        //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] isLocked] == NO;
-        //        } else
-        //        if (action == @selector(doAutoScale:)) {
-        //            return [[self pdfDocument] isLocked] == NO && [pdfView autoScales] == NO;
-        //        } else if (action == @selector(toggleAutoScale:)) {
-        //            [menuItem setState:[pdfView autoScales] ? NSOnState : NSOffState];
-        //            return [[self pdfDocument] isLocked] == NO;
-        //        } else if (action == @selector(rotateRight:) || action == @selector(rotateLeft:) || action == @selector(rotateAllRight:) || action == @selector(rotateAllLeft:)) {
-        //            return [[self pdfDocument] isLocked] == NO;
-        //        } else if (action == @selector(cropAll:) || action == @selector(crop:) || action == @selector(autoCropAll:) || action == @selector(smartAutoCropAll:)) {
-        //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] isLocked] == NO;
-        //        } else if (action == @selector(autoSelectContent:)) {
-        //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] isLocked] == NO && [pdfView toolMode] == SKSelectToolMode;
-        //        } else if (action == @selector(takeSnapshot:)) {
-        //            return [[self pdfDocument] isLocked] == NO;
-        //        } else if (action == @selector(changeLeftSidePaneState:)) {
-        //            [menuItem setState:mwcFlags.leftSidePaneState == (SKLeftSidePaneState)[menuItem tag] ? (([leftSideController.findTableView window] || [leftSideController.groupedFindTableView window]) ? NSMixedState : NSOnState) : NSOffState];
-        //            return (SKLeftSidePaneState)[menuItem tag] == SKSidePaneStateThumbnail || [[pdfView document] outlineRoot];
-        //        } else if (action == @selector(changeRightSidePaneState:)) {
-        //            [menuItem setState:mwcFlags.rightSidePaneState == (SKRightSidePaneState)[menuItem tag] ? NSOnState : NSOffState];
-        //            return [self interactionMode] != SKPresentationMode;
         //        }
-        //    //    else if (action == @selector(toggleSplitPDF:)) {
-        //    //        if ([(NSView *)secondaryPdfView window])
-        //    //            [menuItem setTitle:NSLocalizedString(@"Hide Split PDF", @"Menu item title")];
-        //    //        else
-        //    //            [menuItem setTitle:NSLocalizedString(@"Show Split PDF", @"Menu item title")];
-        //    //        return [self interactionMode] != SKPresentationMode;
-        //    //    }
-        //        else
-        //        if (action == @selector(toggleStatusBar:)) {
-        //            if ([statusBar isVisible])
-        //                [menuItem setTitle:NSLocalizedString(@"Hide Status Bar", @"Menu item title")];
-        //            else
-        //                [menuItem setTitle:NSLocalizedString(@"Show Status Bar", @"Menu item title")];
-        //            return [self interactionMode] == SKNormalMode || [self interactionMode] == SKFullScreenMode;
-        //        } else if (action == @selector(searchPDF:)) {
-        //            return [self interactionMode] != SKPresentationMode;
-        //        } else if (action == @selector(toggleFullscreen:)) {
-        //            if ([self interactionMode] == SKFullScreenMode || [self interactionMode] == SKLegacyFullScreenMode)
-        //                [menuItem setTitle:NSLocalizedString(@"Exit Full Screen", @"Menu item title")];
-        //            else
-        //                [menuItem setTitle:NSLocalizedString(@"Full Screen", @"Menu item title")];
-        //            return [self canEnterFullscreen] || [self canExitFullscreen];
-        //        } else if (action == @selector(togglePresentation:)) {
-        //            if ([self interactionMode] == SKPresentationMode)
-        //                [menuItem setTitle:NSLocalizedString(@"Exit Presentation", @"Menu item title")];
-        //            else
-        //                [menuItem setTitle:NSLocalizedString(@"Presentation", @"Menu item title")];
-        //            return [self canEnterPresentation] || [self canExitPresentation];
-        //        } else if (action == @selector(getInfo:)) {
-        //            return [self interactionMode] != SKPresentationMode;
-        //        } else if (action == @selector(performFit:)) {
-        //            return [self interactionMode] == SKNormalMode && [[self pdfDocument] isLocked] == NO;
-        //        } else if (action == @selector(password:)) {
-        //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] permissionsStatus] != kPDFDocumentPermissionsOwner;
-        //        } else if (action == @selector(toggleReadingBar:)) {
-        //            if ([[self pdfView] hasReadingBar])
-        //                [menuItem setTitle:NSLocalizedString(@"Hide Reading Bar", @"Menu item title")];
-        //            else
-        //                [menuItem setTitle:NSLocalizedString(@"Show Reading Bar", @"Menu item title")];
-        //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] isLocked] == NO;
-        //        } else
-        //        if (action == @selector(savePDFSettingToDefaults:)) {
-        //            if ([self interactionMode] == SKFullScreenMode || [self interactionMode] == SKLegacyFullScreenMode)
-        //                [menuItem setTitle:NSLocalizedString(@"Use Current View Settings as Default for Full Screen", @"Menu item title")];
-        //            else
-        //                [menuItem setTitle:NSLocalizedString(@"Use Current View Settings as Default", @"Menu item title")];
-        //            return [self interactionMode] != SKPresentationMode && [[self pdfDocument] isLocked] == NO;
-        //        } else if (action == @selector(chooseTransition:)) {
-        //            return [[self pdfDocument] pageCount] > 1;
-        //        } else
+        //
         if (action == #selector(toggleCaseInsensitiveSearch)) {
             let state = KMDataManager.ud_integer(forKey: SKCaseInsensitiveSearchKey)
             menuItem.state = state == 1 ? .on : .off
@@ -1044,8 +905,9 @@ extension KMLeftSideViewController: NSSearchFieldDelegate {
                 self.leftSideEmptyVC.outlineSearchView.removeFromSuperview()
             } else {
                 let view = self.snapshotTableView.enclosingScrollView
+                let viewFrmae = view?.frame ?? .zero
                 let emptyVcSize =  self.leftSideEmptyVC.outlineSearchView.frame.size
-                self.leftSideEmptyVC.outlineSearchView.frame = NSMakeRect((view!.frame.size.width-emptyVcSize.width)/2.0,(view!.frame.size.height-emptyVcSize.height)/2.0, emptyVcSize.width, emptyVcSize.height)
+                self.leftSideEmptyVC.outlineSearchView.frame = NSMakeRect((viewFrmae.size.width-emptyVcSize.width)/2.0,(viewFrmae.size.height-emptyVcSize.height)/2.0, emptyVcSize.width, emptyVcSize.height)
                 self.leftSideEmptyVC.outlineSearchView.autoresizingMask = [.minXMargin, .maxXMargin, .minYMargin, .maxYMargin]
                 self.snapshotTableView.enclosingScrollView?.documentView?.addSubview(self.leftSideEmptyVC.outlineSearchView)
             }

+ 26 - 16
PDF Office/PDF Master/Class/PDFWindowController/Side/LeftSide/KMLeftSideViewController+Note.swift

@@ -143,7 +143,7 @@ extension KMLeftSideViewController {
         self.noteHeaderView.layer?.cornerRadius = 1.0
         let sortType = KMDataManager.ud_integer(forKey: Self.Key.noteSortTypeKey)
         if (sortType == 1) {
-            self.noteSortType = KMNoteSortType(rawValue: sortType)!
+            self.noteSortType = KMNoteSortType(rawValue: sortType) ?? .none
             if (self.noteSortType == .time) {
                 self.sortTypeLabel.stringValue = KMLocalizedString("Time", nil)
                 self.sortTypeBox.toolTip = KMLocalizedString("Time", nil)
@@ -295,7 +295,7 @@ extension KMLeftSideViewController {
     }
     
     @objc func deleteNotes(_ sender: NSMenuItem) {
-        self.outlineView(self.noteOutlineView, deleteItems: sender.representedObject as! [Any])
+        self.outlineView(self.noteOutlineView, deleteItems: sender.representedObject as? [Any] ?? [])
     }
     
     @objc func removeAllAnnotations(_ sender: AnyObject?) {
@@ -565,9 +565,9 @@ extension KMLeftSideViewController {
                 var annotationItemArray: [KMBOTAAnnotationItem] = []
                 let page = self.listView.document.page(at: i)
                 let types = ["Highlight","Underline","Strikeout","Freehand","FreeText","Note","Square","Circle","Line","Stamp","Arrow","Image","Redact","Sign"]
-                var pageAnnotations: [CPDFAnnotation] = KMOCToolClass.filterAnnotation(annotations: page!.annotations,types: types) as! [CPDFAnnotation]
+                var pageAnnotations: [CPDFAnnotation] = KMOCToolClass.filterAnnotation(annotations: page?.annotations ?? [],types: types) as? [CPDFAnnotation] ?? []
                 //添加签名注释
-                for annotation in page!.annotations {
+                for annotation in page?.annotations ?? [] {
                    if annotation.isKind(of: CPDFSignatureAnnotation.self) {
                        pageAnnotations.append(annotation)
                    }
@@ -605,9 +605,17 @@ extension KMLeftSideViewController {
             if self.noteSortType == .page {
                 /// 根据id进行排序(升序)
                 if self.isAscendSort {
-                    dataArray.sort { $0.page!.pageIndex() > $1.page!.pageIndex()}
+                    dataArray.sort {
+                        let idx0 = $0.page?.pageIndex() ?? 0
+                        let idx1 = $1.page?.pageIndex() ?? 0
+                        return idx0 > idx1
+                    }
                 } else {
-                    dataArray.sort { $0.page!.pageIndex() <= $1.page!.pageIndex()}
+                    dataArray.sort {
+                        let idx0 = $0.page?.pageIndex() ?? 0
+                        let idx1 = $1.page?.pageIndex() ?? 0
+                        return idx0 <= idx1
+                    }
                 }
                 self.annotations = dataArray
             } else if self.noteSortType == .time {
@@ -671,17 +679,17 @@ extension KMLeftSideViewController {
             let sud = UserDefaults.standard
             let typeData = KMDataManager.ud_object(forKey: NoteFilterVC.filterSelectTypeKey + self.listView.document.documentURL.path) as? Data
             if typeData != nil {
-                typeArr = NSKeyedUnarchiver.unarchiveObject(with: typeData!) as! [Any]
+                typeArr = NSKeyedUnarchiver.unarchiveObject(with: typeData!) as? [Any] ?? []
             }
             
             let colorData = sud.object(forKey: NoteFilterVC.filterSelectColorKey + self.listView.document.documentURL.path) as? Data
             if colorData != nil {
-                colorArr = NSKeyedUnarchiver.unarchiveObject(with: colorData!) as! [Any]
+                colorArr = NSKeyedUnarchiver.unarchiveObject(with: colorData!) as? [Any] ?? []
             }
             
             let authorData = sud.object(forKey: NoteFilterVC.filterSelectAuthorKey + self.listView.document.documentURL.path) as? Data
             if authorData != nil {
-                authorArr = NSKeyedUnarchiver.unarchiveObject(with: authorData!) as! [Any]
+                authorArr = NSKeyedUnarchiver.unarchiveObject(with: authorData!) as? [Any] ?? []
             }
             
             var colorMutableArray = NSMutableArray()
@@ -838,17 +846,19 @@ extension KMLeftSideViewController {
                 var allAnnotation: [CPDFAnnotation] = []
                 for i in 0 ..< self.listView.document.pageCount {
                     var annotationItemArray: [KMBOTAAnnotationItem] = []
-                    let page = self.listView.document.page(at: i)
-                    if page!.annotations.count > 0 {
-                        var filterAnnotations: [CPDFAnnotation] = page!.annotations
+                    guard let page = self.listView.document.page(at: i) else {
+                        continue
+                    }
+                    if page.annotations.count > 0 {
+                        var filterAnnotations: [CPDFAnnotation] = page.annotations
                         if typeArr.count > 0 {
-                            filterAnnotations = (KMOCToolClass.filterAnnotation(annotations: filterAnnotations, types: typeArr) as! [CPDFAnnotation])
+                            filterAnnotations = (KMOCToolClass.filterAnnotation(annotations: filterAnnotations, types: typeArr) as? [CPDFAnnotation]) ?? []
                         }
                         if (colorArr.count > 0) {
-                            filterAnnotations = (KMOCToolClass.filterAnnotation(annotations: filterAnnotations,colors: colorArr) as! [CPDFAnnotation])
+                            filterAnnotations = (KMOCToolClass.filterAnnotation(annotations: filterAnnotations,colors: colorArr) as? [CPDFAnnotation]) ?? []
                         }
                         if (authorArr.count > 0) {
-                            filterAnnotations = (KMOCToolClass.filterAnnotation(annotations: filterAnnotations,authors: authorArr) as! [CPDFAnnotation])
+                            filterAnnotations = (KMOCToolClass.filterAnnotation(annotations: filterAnnotations,authors: authorArr) as? [CPDFAnnotation]) ?? []
                         }
                         
                         let section = KMBOTAAnnotationSection()
@@ -856,7 +866,7 @@ extension KMLeftSideViewController {
                             let item = KMBOTAAnnotationItem()
                             item.section = section
                             item.annotation = annotation
-                            item.index = Int(page!.pageIndex())
+                            item.index = Int(page.pageIndex())
                             annotationItemArray.append(item)
                             allAnnotation.append(annotation)
                         }

+ 13 - 9
PDF Office/PDF Master/Class/PDFWindowController/Side/LeftSide/KMLeftSideViewController+Outline.swift

@@ -250,7 +250,7 @@ extension KMLeftSideViewController {
 
             var rootPDFOutline: CPDFOutline?
             if (lastPDFLine != nil) {
-                while (lastPDFLine!.parent != nil) {
+                while (lastPDFLine?.parent != nil) {
                     lastPDFLine = lastPDFLine?.parent
                 }
                 rootPDFOutline = lastPDFLine
@@ -329,7 +329,8 @@ extension KMLeftSideViewController {
     
     func showSearchOutlineBlankState(_ toShowState: Bool) {
         if (toShowState) {
-            self.leftSideEmptyVC.outlineSearchView.frame = CGRectMake((self.tocOutlineView.enclosingScrollView!.documentView!.frame.size.width - self.leftSideEmptyVC.outlineSearchView.bounds.size.width)/2.0, (self.tocOutlineView.enclosingScrollView!.documentView!.frame.size.height - self.leftSideEmptyVC.outlineSearchView.bounds.size.height)/2.0, self.leftSideEmptyVC.outlineSearchView.bounds.size.width, self.leftSideEmptyVC.outlineSearchView.bounds.size.height);
+            let documentViewFrame = self.tocOutlineView.enclosingScrollView?.documentView?.frame ?? .zero
+            self.leftSideEmptyVC.outlineSearchView.frame = CGRectMake((documentViewFrame.size.width - self.leftSideEmptyVC.outlineSearchView.bounds.size.width)/2.0, (documentViewFrame.size.height - self.leftSideEmptyVC.outlineSearchView.bounds.size.height)/2.0, self.leftSideEmptyVC.outlineSearchView.bounds.size.width, self.leftSideEmptyVC.outlineSearchView.bounds.size.height);
             self.tocOutlineView.enclosingScrollView?.documentView?.addSubview(self.leftSideEmptyVC.outlineSearchView)
             self.leftSideEmptyVC.outlineSearchView.autoresizingMask = [.minXMargin, .maxXMargin, .minYMargin, .maxYMargin]
         } else {
@@ -357,7 +358,7 @@ extension KMLeftSideViewController {
         }
         var attributedString = NSMutableAttributedString()
         var dictAttr1 = [NSAttributedString.Key.foregroundColor : KMAppearance.Layout.h0Color()]
-        var attr1 = NSAttributedString(string: outline!.label, attributes: dictAttr1)
+        var attr1 = NSAttributedString(string: outline?.label ?? "", attributes: dictAttr1)
         attributedString.append(attr1)
 
         let row = self.tocOutlineView.selectedRow
@@ -615,11 +616,12 @@ extension KMLeftSideViewController {
         popover.delegate = self
         let targetOutline: CPDFOutline? = self.tocOutlineView.km.clickedItem()
         let outlineEditViewController = KMOutlineEditViewController(outline: targetOutline, document: self.listView)
-        let cell = self.tocOutlineView.rowView(atRow: self.tocOutlineView.clickedRow, makeIfNecessary: true)
-        popover.contentViewController = outlineEditViewController
-        popover.animates = true
-        popover.behavior = .transient
-        popover.show(relativeTo: cell?.bounds ?? .zero, of: cell!, preferredEdge: .minX)
+        if let cell = self.tocOutlineView.rowView(atRow: self.tocOutlineView.clickedRow, makeIfNecessary: true) {
+            popover.contentViewController = outlineEditViewController
+            popover.animates = true
+            popover.behavior = .transient
+            popover.show(relativeTo: cell.bounds, of: cell, preferredEdge: .minX)
+        }
     }
     
     //重命名
@@ -659,7 +661,9 @@ extension KMLeftSideViewController {
         let currentIndex = currentOutline.index
         currentOutline.removeFromParent()
 
-        self.demoteOutlineWithGrandParent(newParentOutLine!, demoteOutline: currentOutline, index: Int(currentIndex))
+        if let data = newParentOutLine {
+            self.demoteOutlineWithGrandParent(data, demoteOutline: currentOutline, index: Int(currentIndex))
+        }
     }
     
     //升级节点

+ 3 - 2
PDF Office/PDF Master/Class/PDFWindowController/Side/LeftSide/KMLeftSideViewController+Snapshot.swift

@@ -205,9 +205,10 @@ extension KMLeftSideViewController {
             self.leftSideEmptyVC.exportSnapBtn.isEnabled = false
             self.leftSideEmptyVC.printSnapBtn.isEnabled = false
             self.snapshotTableView.usesAlternatingRowBackgroundColors = false
-            let view = self.snapshotTableView.enclosingScrollView!
+            let view = self.snapshotTableView.enclosingScrollView
+            let viewSize = view?.frame.size ?? .zero
             let emptyVcSize =  self.leftSideEmptyVC.emptySnapView.frame.size
-            self.leftSideEmptyVC.emptySnapView.frame = NSMakeRect((view.frame.size.width-emptyVcSize.width)/2.0,(view.frame.size.height-emptyVcSize.height)/2.0, emptyVcSize.width, emptyVcSize.height);
+            self.leftSideEmptyVC.emptySnapView.frame = NSMakeRect((viewSize.width-emptyVcSize.width)/2.0,(viewSize.height-emptyVcSize.height)/2.0, emptyVcSize.width, emptyVcSize.height);
             self.leftSideEmptyVC.emptySnapView.autoresizingMask = [.minXMargin, .maxXMargin, .minYMargin, .maxYMargin]
             self.snapshotTableView.enclosingScrollView?.documentView?.addSubview(self.leftSideEmptyVC.emptySnapView)
         } else {

+ 9 - 10
PDF Office/PDF Master/Class/PDFWindowController/Side/LeftSide/KMLeftSideViewController+Thumbnail.swift

@@ -590,12 +590,11 @@ extension KMLeftSideViewController {
         let url = URL(fileURLWithPath: cachesDir)
         array.add(url)
         let vc = KMProgressWindowController()
-//    //    [NSApp beginSheet:[vc window]
-//    //       modalForWindow:self.window
-//    //        modalDelegate:nil
-//    //       didEndSelector:nil
-//    //          contextInfo:NULL];
-        self.view.window?.beginSheet(vc.window!, completionHandler: { [unowned self] returnCode in
+        guard let win = vc.window else {
+            NSSound.beep()
+            return
+        }
+        self.view.window?.beginSheet(win, completionHandler: { [unowned self] returnCode in
             NSApp.endSheet(self.view.window!, returnCode: returnCode.rawValue)
         })
 
@@ -604,14 +603,14 @@ extension KMLeftSideViewController {
             if (sucess) {
                 DispatchQueue.main.async {
 //                    [[sender representedObject] performWithItems:array];
-                    let represent : NSSharingService = (sender as! NSMenuItem).representedObject as! NSSharingService
-                    represent.perform(withItems: [url])
+                    let represent = (sender as? NSMenuItem)?.representedObject as? NSSharingService
+                    represent?.perform(withItems: [url])
                     
-                    NSApp.endSheet(vc.window!)
+                    NSApp.endSheet(win)
                     vc.close()
                 }
             } else {
-                NSApp.endSheet(vc.window!)
+                NSApp.endSheet(win)
                 vc.close()
             }
         }

+ 293 - 403
PDF Office/PDF Master/Class/PDFWindowController/Side/LeftSide/KMLeftSideViewController.swift

@@ -430,7 +430,9 @@ class KMLeftSideViewController: KMSideViewController {
     }
     
     func displayThumbnailViewAnimating(_ animate: Bool) {
-        self.replaceSideView(self.thumbnailTableView.enclosingScrollView!, animate: animate)
+        if let enclosingScrollView = self.thumbnailTableView.enclosingScrollView {
+            self.replaceSideView(enclosingScrollView, animate: animate)
+        }
         
         var frame = self.thumbnailTableView.enclosingScrollView?.frame ?? .zero
         frame.origin.y = 0
@@ -537,7 +539,9 @@ class KMLeftSideViewController: KMSideViewController {
         self.annotationSort(sortArray: [])
         
         self.searchViewController.contentView = nil
-        self.replaceSideView(self.noteOutlineView.enclosingScrollView!, animate: animate)
+        if let data = self.noteOutlineView.enclosingScrollView {
+            self.replaceSideView(data, animate: animate)
+        }
         if (self.findState != .note) {
             self.findState = .note
         } else {
@@ -559,9 +563,10 @@ class KMLeftSideViewController: KMSideViewController {
         frame.size.height = self.snapshotTableView.enclosingScrollView?.superview?.frame.size.height ?? 0
         self.snapshotTableView.enclosingScrollView?.frame = frame
             
-        let view = self.noteOutlineView.enclosingScrollView!
+        let view = self.noteOutlineView.enclosingScrollView
+        let viewFrame = view?.frame ?? .zero
         let emptyVcSize =  self.leftSideEmptyVC.emptyAnnotationView.frame.size
-        self.leftSideEmptyVC.emptyAnnotationView.frame = NSMakeRect((view.frame.size.width-emptyVcSize.width)/2.0,(view.frame.size.height-emptyVcSize.height)/2.0, emptyVcSize.width, emptyVcSize.height)
+        self.leftSideEmptyVC.emptyAnnotationView.frame = NSMakeRect((viewFrame.size.width-emptyVcSize.width)/2.0,(viewFrame.size.height-emptyVcSize.height)/2.0, emptyVcSize.width, emptyVcSize.height)
         
         DispatchQueue.main.async {
             self.noteOutlineView.reloadData()
@@ -570,7 +575,9 @@ class KMLeftSideViewController: KMSideViewController {
     
     func displaySnapshotViewAnimating(_ animate: Bool) {
         self.searchViewController.contentView = nil
-        self.replaceSideView(self.snapshotTableView.enclosingScrollView!, animate: animate)
+        if let data = self.snapshotTableView.enclosingScrollView {
+            self.replaceSideView(data, animate: animate)
+        }
         if (self.findState != .snapshot) {
             self.findState = .snapshot
         } else {
@@ -627,7 +634,9 @@ class KMLeftSideViewController: KMSideViewController {
     }
     
     func displayTocViewAnimating(_ animate: Bool) {
-        self.replaceSideView(self.tocOutlineView.enclosingScrollView!, animate: animate)
+        if let data = self.tocOutlineView.enclosingScrollView {
+            self.replaceSideView(data, animate: animate)
+        }
         
         var frame = self.tocOutlineView.enclosingScrollView?.frame ?? .zero
         frame.origin.y = 0
@@ -644,10 +653,11 @@ class KMLeftSideViewController: KMSideViewController {
         frame.size.height = self.snapshotTableView.enclosingScrollView?.superview?.frame.size.height ?? 0
         self.snapshotTableView.enclosingScrollView?.frame = frame
         
-        let view = self.tocOutlineView.enclosingScrollView!
+        let view = self.tocOutlineView.enclosingScrollView
+        let viewFrame = view?.frame ?? .zero
         let emptyVcSize =  self.leftSideEmptyVC.emptyOutlineView.frame.size
         
-        self.leftSideEmptyVC.emptyOutlineView.frame = NSMakeRect((view.frame.size.width-emptyVcSize.width)/2.0,(view.frame.size.height-emptyVcSize.height)/2.0, emptyVcSize.width, emptyVcSize.height);
+        self.leftSideEmptyVC.emptyOutlineView.frame = NSMakeRect((viewFrame.size.width-emptyVcSize.width)/2.0,(viewFrame.size.height-emptyVcSize.height)/2.0, emptyVcSize.width, emptyVcSize.height);
         
         DispatchQueue.main.async {
             self.tocOutlineView.reloadData()
@@ -697,7 +707,7 @@ class KMLeftSideViewController: KMSideViewController {
             emptyPage.setBounds(firstFrame2, for: .mediaBox)
             emptyPage.rotation = firstPage?.rotation ?? 0
             
-            let pageImage = firstPage!.thumbnail(of: NSMakeSize(self.thumbnailCacheSize, self.thumbnailCacheSize))
+            let pageImage = firstPage?.thumbnail(of: NSMakeSize(self.thumbnailCacheSize, self.thumbnailCacheSize))
 //            NSImage * = [emptyPage thumbnailWithSize:thumbnailCacheSize forBox:[pdfView displayBox]];
             var rect: NSRect = .zero
             rect.size = pageImage?.size ?? .zero
@@ -1376,10 +1386,14 @@ extension KMLeftSideViewController: NSTableViewDelegate, NSTableViewDataSource {
         let pasteboard = info.draggingPasteboard
         if (pasteboard.availableType(from: [.localDraggedTypes]) != nil) {
             result = true
-            let rowData = pasteboard.data(forType: .localDraggedTypes)
-            let rowIndexes = NSKeyedUnarchiver.unarchiveObject(with: rowData!) as? IndexSet ?? IndexSet()
-            let urlData = pasteboard.data(forType: KPDFThumbnailDoucumentURLForDraggedTypes)
-            let url = NSKeyedUnarchiver.unarchiveObject(with: urlData!) as? String
+            guard let rowData = pasteboard.data(forType: .localDraggedTypes) else {
+                return false
+            }
+            let rowIndexes = NSKeyedUnarchiver.unarchiveObject(with: rowData) as? IndexSet ?? IndexSet()
+            guard let urlData = pasteboard.data(forType: KPDFThumbnailDoucumentURLForDraggedTypes) else {
+                return false
+            }
+            let url = NSKeyedUnarchiver.unarchiveObject(with: urlData) as? String
             if url != nil && url != self.listView.document.documentURL.absoluteString {
                 if (pasteboard.availableType(from: [.fileURL]) != nil) {
                     //                if ([pasteboard availableTypeFromArray:[NSArray arrayWithObject:NSFilenamesPboardType]]){
@@ -1396,10 +1410,11 @@ extension KMLeftSideViewController: NSTableViewDelegate, NSTableViewDataSource {
                                 KMBaseWindowController.checkPassword(url: URL(fileURLWithPath: path), type: .owner) { success, resultPassword in
                                     if success && resultPassword.isEmpty == false {
                                         for i in 0 ..< (pdf?.pageCount ?? 0) {
-                                            let page = pdf?.page(at: i).copy() as? CPDFPage
-                                            self.listView.document.insertPageObject(page!, at: UInt(index))
-                                            insertIndexSet.insert(index)
-                                            index += 1
+                                            if let page = pdf?.page(at: i).copy() as? CPDFPage {
+                                                self.listView.document.insertPageObject(page, at: UInt(index))
+                                                insertIndexSet.insert(index)
+                                                index += 1
+                                            }
                                         }
                                         self.insertPages(insertIndexSet, pageAt: index-1)
                                     }
@@ -1422,8 +1437,9 @@ extension KMLeftSideViewController: NSTableViewDelegate, NSTableViewDataSource {
             var pageIndex = 0
             var pages: [CPDFPage] = []
             for idx in rowIndexes {
-                let page = self.listView.document.page(at: UInt(idx))?.copy() as? CPDFPage
-                pages.append(page!)
+                if let page = self.listView.document.page(at: UInt(idx))?.copy() as? CPDFPage {
+                    pages.append(page)
+                }
             }
             var toPage: CPDFPage?
             if row < self.listView.document.pageCount {
@@ -1446,14 +1462,16 @@ extension KMLeftSideViewController: NSTableViewDelegate, NSTableViewDataSource {
             for idx in rowIndexes {
                 if idx < toPageIndex {
                     if((idx+pageIndex) < self.listView.document.pageCount) {
-                        var page = self.listView.document.page(at: UInt(idx))
-                        deletepages.append(page!)
+                        if let page = self.listView.document.page(at: UInt(idx)) {
+                            deletepages.append(page)
+                        }
                         self.listView.document.removePage(at: IndexSet(integer: idx))
                     }
                 } else {
                     if((idx+pageIndex) < self.listView.document.pageCount) {
-                        let page = self.listView.document.page(at: UInt(idx+pageIndex))
-                        deletepages.append(page!)
+                        if let page = self.listView.document.page(at: UInt(idx+pageIndex)) {
+                            deletepages.append(page)
+                        }
                         self.listView.document.removePage(at: IndexSet(integer: idx+pageIndex))
                     }
                 }
@@ -1481,16 +1499,16 @@ extension KMLeftSideViewController: NSTableViewDelegate, NSTableViewDataSource {
                 if pathExtension == "pdf" {
                     let pdf = CPDFDocument(url: url!)
                     if let data = pdf?.isEncrypted, data {
-//                        KMDecryptWindowController *vc = [[KMDecryptWindowController alloc] init];
                         KMBaseWindowController.checkPassword(url: url!, type: .owner) { success, resultPassword in
                             if success && resultPassword.isEmpty == false {
                                 pdf?.unlock(withPassword: resultPassword)
                                 for i in 0 ..< (pdf?.pageCount ?? 0) {
-//                                    let page = pdf?.page(at: i).copy() as? CPDFPage
-                                    let page = pdf?.page(at: i)
-                                    self.listView.document.insertPageObject(page!, at: UInt(index))
-                                    insertIndexSet.insert(index)
-                                    index += 1
+                                    //                                    let page = pdf?.page(at: i).copy() as? CPDFPage
+                                    if let page = pdf?.page(at: i) {
+                                        self.listView.document.insertPageObject(page, at: UInt(index))
+                                        insertIndexSet.insert(index)
+                                        index += 1
+                                    }
                                 }
                                 self.insertPages(insertIndexSet, pageAt: index-1)
                             }
@@ -1498,20 +1516,22 @@ extension KMLeftSideViewController: NSTableViewDelegate, NSTableViewDataSource {
                     } else {
                         for i in 0 ..< (pdf?.pageCount ?? 0) {
 //                            let page = pdf?.page(at: i).copy() as? CPDFPage
-                            let page = pdf?.page(at: i)
-                            self.listView.document.insertPageObject(page!, at: UInt(index))
-                            insertIndexSet.insert(index)
-                            index += 1
+                            if let page = pdf?.page(at: i) {
+                                self.listView.document.insertPageObject(page, at: UInt(index))
+                                insertIndexSet.insert(index)
+                                index += 1
+                            }
                         }
                         self.insertPages(insertIndexSet, pageAt: index-1)
                     }
                 } else if KMImageToPDFMethod.supportedImageTypes().contains(pathExtension) {
-                    let image = NSImage(contentsOfFile: url?.path ?? "")
-//                    PDFPage * page = [[[PDFPage alloc] initWithImage:image] autorelease];
-//                    [pdfView.document insertPage:page atIndex:index];
-                    _ = self.listView.document.km_insert(image: image!, at: UInt(index))
-                    insertIndexSet.insert(index)
-                    self.insertPages(insertIndexSet, pageAt: index-1)
+                    if let image = NSImage(contentsOfFile: url?.path ?? "") {
+                        //                    PDFPage * page = [[[PDFPage alloc] initWithImage:image] autorelease];
+                        //                    [pdfView.document insertPage:page atIndex:index];
+                        _ = self.listView.document.km_insert(image: image, at: UInt(index))
+                        insertIndexSet.insert(index)
+                        self.insertPages(insertIndexSet, pageAt: index-1)
+                    }
                 }
                 result = true
             } else {
@@ -1808,8 +1828,8 @@ extension KMLeftSideViewController: NSTableViewDelegate, NSTableViewDataSource {
                     }
                     
                     fileURL = fileURL.appendingPathExtension(pathExt).uniqueFileURL()
-                    let success = try?fileData?.write(to: fileURL)
-                    if success != nil {
+                    let success = (try?fileData?.write(to: fileURL)) != nil
+                    if success {
                         fileURLArray.append(fileURL.lastPathComponent)
                     }
                 }
@@ -1951,7 +1971,7 @@ extension KMLeftSideViewController: NSFilePromiseProviderDelegate {
 extension KMLeftSideViewController {
     var dragTempFloderPath: String? {
         get {
-            return NSSearchPathForDirectoriesInDomains(FileManager.SearchPathDirectory.applicationSupportDirectory, FileManager.SearchPathDomainMask.userDomainMask, true).last?.stringByAppendingPathComponent(Bundle.main.bundleIdentifier!).stringByAppendingPathComponent("KMPDFThumbnailView_Drag_Temp")
+            return NSSearchPathForDirectoriesInDomains(FileManager.SearchPathDirectory.applicationSupportDirectory, FileManager.SearchPathDomainMask.userDomainMask, true).last?.stringByAppendingPathComponent(Bundle.main.bundleIdentifier ?? "").stringByAppendingPathComponent("KMPDFThumbnailView_Drag_Temp")
         }
     }
     var dragTempFilePath: String? {
@@ -1963,144 +1983,6 @@ extension KMLeftSideViewController {
 
 // MARK: - NSOutlineViewDelegate, NSOutlineViewDataSource
 
-/*
- 
- func outlineView(_ outlineView: NSOutlineView, child index: Int, ofItem item: Any?) -> Any {
-     if item is KMBOTAAnnotationSection {
-         let section = item as? KMBOTAAnnotationSection
-         return section!.annotations?[index] as Any
-     } else if item is KMBOTAAnnotationItem {
-         return item as Any
-     } else {
-         var tempArray: [KMBOTAAnnotationSection] = []
-         for temp in self.data {
-             if temp.annotations?.count != 0 {
-                 tempArray.append(temp)
-             }
-         }
-         let section = tempArray[index]
-         return section as Any
-     }
- }
- 
- func outlineView(_ outlineView: NSOutlineView, viewFor tableColumn: NSTableColumn?, item: Any) -> NSView? {
-     if item is KMBOTAAnnotationItem {
-         let cell : KMAnnotationOutlineCellView = KMAnnotationOutlineCellView.init()
-         cell.delegate = self
-         cell.model = item as? KMBOTAAnnotationItem
-         return cell
-     } else if item is KMBOTAAnnotationSection {
-         let section = item as? KMBOTAAnnotationSection
-         
-         let cell : KMAnnotationOutlineSectionView = KMAnnotationOutlineSectionView.init()
-         cell.model = section
-         return cell
-     }
-     return NSTableCellView()
- }
- 
- func outlineView(_ outlineView: NSOutlineView, rowViewForItem item: Any) -> NSTableRowView? {
-     let rowView = KMAnnotationOutlineRowView()
-     if item is KMBOTAAnnotationItem {
-         rowView.model = (item as? KMBOTAAnnotationItem)
-     } else if item is KMBOTAAnnotationSection {
-         rowView.section = (item as? KMBOTAAnnotationSection)
-     }
-     rowView.mouseDownAction = { [unowned self] view, event in
-         if rowView.section != nil {
-             let expanded = outlineView.isItemExpanded(outlineView.item(atRow: outlineView.selectedRow))
-             if expanded {
-                 outlineView.collapseItem(outlineView.item(atRow: outlineView.selectedRow), collapseChildren: true)
-                 outlineView.reloadItem(outlineView.item(atRow: outlineView.selectedRow))
-             } else {
-                 outlineView.expandItem(outlineView.item(atRow: outlineView.selectedRow), expandChildren: true)
-                 outlineView.reloadItem(outlineView.item(atRow: outlineView.selectedRow))
-             }
-         } else if rowView.model != nil {
-             self.didSelectItem(view: rowView, event: event)
-         }
-     }
-     
-     rowView.rightMouseDownAction = { [unowned self] view, event in
-         if rowView.section != nil {
-             
-         } else if rowView.model != nil {
-             if !KMOCToolClass.arrayContains(array: self.selectItems, annotation: item) ||
-                 self.selectItems.count == 1 {
-                 self.selectItem(item: item as! KMBOTAAnnotationItem)
-             }
-             
-             DispatchQueue.main.async {
-                 self.delegate?.annotationOutlineView(self, rightMouseDownDidSelectView: view, evnet: event)
-             }
-         }
-     }
-     
-     rowView.hoverCallback = { [unowned self] (mouseEntered, mouseBox) in
-         self.outlineView.enumerateAvailableRowViews { view, row in
-             if view is KMAnnotationOutlineRowView {
-                 (view as? KMAnnotationOutlineRowView)?.model?.hover = false
-                 (view as? KMAnnotationOutlineRowView)?.reloadData()
-             }
-         }
-         if mouseEntered {
-             rowView.model?.hover = true
-         } else {
-             rowView.model?.hover = false
-         }
-     }
-     return rowView
- }
- 
- func outlineView(_ outlineView: NSOutlineView, heightOfRowByItem item: Any) -> CGFloat {
-     if item is KMBOTAAnnotationItem {
-         return KMBOTAAnnotationTool.fetchCellHeight(annotation: (item as? KMBOTAAnnotationItem)!.annotation!, maxSize: CGSize(width: self.maxWidth - 16, height: 1000))
-     } else if item is KMBOTAAnnotationSection {
-         return 40
-     } else {
-         return 30
-     }
- }
- 
- func outlineViewSelectionDidChange(_ notification: Notification) {
-     if self.outlineView.selectedRow == -1 {
-         self.cancelSelect()
-     }
- }
- 
- func outlineView(_ outlineView: NSOutlineView, isItemExpandable item: Any) -> Bool {
-     if item is KMBOTAAnnotationItem {
-         return false
-     } else if item is KMBOTAAnnotationSection {
-         let section = item as? KMBOTAAnnotationSection
-         return section!.annotations?.count ?? 0 > 0
-     }
-     return false
- }
- 
- func outlineView(_ outlineView: NSOutlineView, shouldExpandItem item: Any) -> Bool {
-     if let item = item as? KMBOTAAnnotationSection {
-         if !item.isItemExpanded {
-             item.isItemExpanded = true
-             outlineView.animator().expandItem(item, expandChildren: true)
-             return false
-         }
-     }
-     return true
- }
-
- func outlineView(_ outlineView: NSOutlineView, shouldCollapseItem item: Any) -> Bool {
-     if let item = item as? KMBOTAAnnotationSection {
-         if item.isItemExpanded {
-             item.isItemExpanded = false
-             outlineView.animator().collapseItem(item, collapseChildren: true)
-             return false
-         }
-     }
-     return true
- }
- */
-
 extension KMLeftSideViewController: NSOutlineViewDelegate, NSOutlineViewDataSource {
     func outlineView(_ outlineView: NSOutlineView, numberOfChildrenOfItem item: Any?) -> Int {
         if outlineView.isEqual(to: self.tocOutlineView) {
@@ -2111,10 +1993,11 @@ extension KMLeftSideViewController: NSOutlineViewDelegate, NSOutlineViewDataSour
             if item == nil { // 第一层
                 // 获取根
                 guard let outline = self.listView.document.outlineRoot() else {
-                    let view = self.tocOutlineView.enclosingScrollView!
+                    let view = self.tocOutlineView.enclosingScrollView
+                    let viewFrame = view?.frame ?? .zero
                     let emptyVcSize =  self.leftSideEmptyVC.emptyOutlineView.frame.size
 //
-                    self.leftSideEmptyVC.emptyOutlineView.frame = NSMakeRect((view.frame.size.width-emptyVcSize.width)/2.0,(view.frame.size.height-emptyVcSize.height)/2.0, emptyVcSize.width, emptyVcSize.height)
+                    self.leftSideEmptyVC.emptyOutlineView.frame = NSMakeRect((viewFrame.size.width-emptyVcSize.width)/2.0,(viewFrame.size.height-emptyVcSize.height)/2.0, emptyVcSize.width, emptyVcSize.height)
                     self.leftSideEmptyVC.emptyOutlineView.autoresizingMask = [.minXMargin, .maxXMargin, .minYMargin, .maxYMargin]
                     self.tocOutlineView.enclosingScrollView?.documentView?.addSubview(self.leftSideEmptyVC.emptyOutlineView)
                     self.leftSideEmptyVC.deleteOutlineBtn.isEnabled = false
@@ -2136,10 +2019,11 @@ extension KMLeftSideViewController: NSOutlineViewDelegate, NSOutlineViewDataSour
                         self.leftSideEmptyVC.emptyOutlineView.removeFromSuperview()
                         self.leftSideEmptyVC.deleteOutlineBtn.isEnabled = true
                     } else { // 没有数据
-                        let view = self.tocOutlineView.enclosingScrollView!
+                        let view = self.tocOutlineView.enclosingScrollView
+                        let viewFrame = view?.frame ?? .zero
                         let emptyVcSize =  self.leftSideEmptyVC.emptyOutlineView.frame.size
     //
-                        self.leftSideEmptyVC.emptyOutlineView.frame = NSMakeRect((view.frame.size.width-emptyVcSize.width)/2.0,(view.frame.size.height-emptyVcSize.height)/2.0, emptyVcSize.width, emptyVcSize.height)
+                        self.leftSideEmptyVC.emptyOutlineView.frame = NSMakeRect((viewFrame.size.width-emptyVcSize.width)/2.0,(viewFrame.size.height-emptyVcSize.height)/2.0, emptyVcSize.width, emptyVcSize.height)
                         self.leftSideEmptyVC.emptyOutlineView.autoresizingMask = [.minXMargin, .maxXMargin, .minYMargin, .maxYMargin]
                         self.tocOutlineView.enclosingScrollView?.documentView?.addSubview(self.leftSideEmptyVC.emptyOutlineView)
                         self.leftSideEmptyVC.deleteOutlineBtn.isEnabled = false
@@ -2176,8 +2060,7 @@ extension KMLeftSideViewController: NSOutlineViewDelegate, NSOutlineViewDataSour
                 if self.isSearchOutlineMode {
                     if let data = item as? String, data == "Bookmarks" { // 书签group
                         return 0
-                    } else if item is CPDFOutline { // 大纲
-                        let child = item as! CPDFOutline
+                    } else if let child = item as? CPDFOutline { // 大纲
                         if child.numberOfChildren == 0 {
                             return 0
                         }
@@ -2222,9 +2105,10 @@ extension KMLeftSideViewController: NSOutlineViewDelegate, NSOutlineViewDataSour
                     self.noteFilterButton.isEnabled = false
 //                    }
                     self.noteOutlineView.usesAlternatingRowBackgroundColors = false
-                    let view = self.noteOutlineView.enclosingScrollView!
+                    let view = self.noteOutlineView.enclosingScrollView
+                    let viewFrame = view?.frame ?? .zero
                     var emptyVcSize =  self.leftSideEmptyVC.emptyAnnotationView.frame.size
-                    self.leftSideEmptyVC.emptyAnnotationView.frame = NSMakeRect((view.frame.size.width-emptyVcSize.width)/2.0,(view.frame.size.height-emptyVcSize.height)/2.0, emptyVcSize.width, emptyVcSize.height)
+                    self.leftSideEmptyVC.emptyAnnotationView.frame = NSMakeRect((viewFrame.size.width-emptyVcSize.width)/2.0,(viewFrame.size.height-emptyVcSize.height)/2.0, emptyVcSize.width, emptyVcSize.height)
                     
                     self.leftSideEmptyVC.emptyAnnotationView.autoresizingMask = [.minXMargin, .maxXMargin, .minYMargin, .maxYMargin]
                     self.noteOutlineView.enclosingScrollView?.documentView?.addSubview(self.leftSideEmptyVC.emptyAnnotationView)
@@ -2304,17 +2188,13 @@ extension KMLeftSideViewController: NSOutlineViewDelegate, NSOutlineViewDataSour
             } else {
                 if let data = item as? String, data == "Bookmarks" {
                     return array[index]
-                } else if item is CPDFOutline {
+                } else if let ol = item as? CPDFOutline {
                     if self.isSearchOutlineMode == false {
-                        return (item as! CPDFOutline).child(at: UInt(index))
+                        return ol.child(at: UInt(index)) as Any
                     }
-                    let child = item as! CPDFOutline
-//                    if child.numberOfChildren == 0 {
-//                        return 0
-//                    }
                     var array: [CPDFOutline] = []
-                    for i in 0 ..< child.numberOfChildren {
-                        if let _child = child.child(at: i) {
+                    for i in 0 ..< ol.numberOfChildren {
+                        if let _child = ol.child(at: i) {
                             if self._hasContainString(self.outlineSearchField.stringValue, rootOutline: _child) {
                                 array.append(_child)
                             }
@@ -2480,33 +2360,33 @@ extension KMLeftSideViewController: NSOutlineViewDelegate, NSOutlineViewDataSour
             return cell
         } else if outlineView.isEqual(to: self.noteOutlineView) {
             let model = item as? KMBOTAAnnotationItem
-            var note: CPDFAnnotation!
+            var note: CPDFAnnotation?
             if self.noteSearchMode {
-                note = item as! CPDFAnnotation
+                note = item as? CPDFAnnotation
             } else {
-                note = (item as! KMBOTAAnnotationItem).annotation!
+                note = (item as? KMBOTAAnnotationItem)?.annotation
             }
             
             let cell = outlineView.makeView(withIdentifier: NSUserInterfaceItemIdentifier(rawValue: "KMNoteTableViewCell"), owner: self) as! KMNoteTableViewCell
             cell.cellNote = note
             
-            let noteColor = note.color
-            var noteType = note.type ?? ""
-            var noteString = KMBOTAAnnotationTool.fetchContentLabelString(annotation: note)
-//            NSString *pageString = [[note page] displayLabel] ? : @"";
-            var pageString = "\((note.page?.pageIndex() ?? 0) + 1)"
+            let noteColor = note?.color
+            var noteType = note?.type ?? ""
+            var noteString = ""
+            if let data = note {
+                noteString = KMBOTAAnnotationTool.fetchContentLabelString(annotation: data)
+            }
+
+            var pageString = "\((note?.page?.pageIndex() ?? 0) + 1)"
             let formatter = DateFormatter()
             formatter.dateFormat = "hh:mm"
             var dateString = ""
-            if let date = note.modificationDate() {
+            if let date = note?.modificationDate() {
                 dateString = formatter.string(from: date)
             }
-            var authorString = note.userName() ?? ""
-//            NSString *noteTextString = [note noteText].string ? : @"";
-            var noteTextString = note.string() ?? ""
-//
+            var authorString = note?.userName() ?? ""
+            var noteTextString = note?.string() ?? ""
 //            if([noteType isEqualToString:@"Redact"]) {
-            
 //                noteString = @"Redact";
 //            }
 //
@@ -2542,82 +2422,84 @@ extension KMLeftSideViewController: NSOutlineViewDelegate, NSOutlineViewDataSour
             }
 
             let imageView = KMNoteTypeImageView()
-            if note.isKind(of: CPDFStampAnnotation.self) {
-                let annotation_stamp = note as! CPDFStampAnnotation
-                if (annotation_stamp.stampImage() != nil) {
-                    noteType = SKNStampString
-                }
-            } else if note.isKind(of: CPDFLineAnnotation.self) {
-                 let annotation_line = note as! CPDFLineAnnotation
-                if annotation_line.startLineStyle == .none && annotation_line.endLineStyle == .none {
-                    noteType = SKNLine_NoneString
-                } else if annotation_line.startLineStyle == .none && annotation_line.endLineStyle == .openArrow {
-                    noteType = SKNLine_OpenArrowString
-                } else {
-                    noteType = SKNLine_NoneString
-                }
-            } else if note.isKind(of: CPDFButtonWidgetAnnotation.self) {
-                 let buttonWidget = note as! CPDFButtonWidgetAnnotation
-                if buttonWidget.controlType() == .radioButtonControl {
-                    noteType = KMAnnotationFormRadioButtonKey
-                } else if buttonWidget.controlType() == .checkBoxControl {
-                    noteType = KMAnnotationFormCheckBoxKey
-                } else if buttonWidget.controlType() == .pushButtonControl {
-                    noteType = KMAnnotationFormActionButtonKey
-                }
-            } else if note.isKind(of: CPDFTextWidgetAnnotation.self) {
-                noteType = KMAnnotationFormTextFieldKey
-            } else if note.isKind(of: CPDFChoiceWidgetAnnotation.self) {
-                let choiceWidget = note as! CPDFChoiceWidgetAnnotation
-                if choiceWidget.isListChoice {
-                    noteType = KMAnnotationFormListMenuKey
-                } else {
-                    noteType = KMAnnotationFormComboBoxKey
-                }
-            } else if note.isKind(of: KMTableAnnotation.self) {
-                noteType = "Ink_Table"
-            } else if note.isKind(of: KMSelfSignAnnotation.self) {
-                let selfSignNote = note as! KMSelfSignAnnotation
-                if selfSignNote.annotationType == .signFalse {
-                    noteType = "KMSelfSignTypeFalseActionButtonKey"
-                } else if (selfSignNote.annotationType == .signature) {
-                    noteType = "KMSelfSignTypeTureActionButtonKey"
-                } else if (selfSignNote.annotationType == .signCircle) {
-                    noteType = "KMSelfSignTypeCircleActionButtonKey"
-                } else if (selfSignNote.annotationType == .signLine) {
-                    noteType = "KMSelfSignTypeLineActionButtonKey"
-                } else if (selfSignNote.annotationType == .signDot) {
-                    noteType = "KMSelfSignTypeDotActionButtonKey"
-                } else if (selfSignNote.annotationType == .signText) {
-                    noteType = "KMSelfSignTypeTextActionButtonKey"
-                }
-            } else if note.isKind(of: CPDFSquareAnnotation.self) {
-                noteType = SKNSquareString
-            } else if note.isKind(of: CPDFTextAnnotation.self) {
-                noteType = SKNNoteString
-            } else if note.isKind(of: CPDFFreeTextAnnotation.self) {
-                noteType = SKNFreeTextString
-            } else if note.isKind(of: CPDFCircleAnnotation.self) {
-                noteType = SKNCircleString
-            } else if note.isKind(of: CPDFSignatureAnnotation.self) {
-                noteType = SKNSignatureString
-            } else if note.isKind(of: CPDFInkAnnotation.self) {
-                noteType = SKNInkString
-            } else if note.isKind(of: CPDFMarkupAnnotation.self) {
-                let anno = note as! CPDFMarkupAnnotation
-                if anno.markupType() == .highlight {
-                    noteType = SKNHighlightString
-                } else if anno.markupType() == .underline {
-                    noteType = SKNUnderlineString
-                } else if anno.markupType() == .strikeOut {
-                    noteType = SKNStrikeOutString
+            if let data = note {
+                if data.isKind(of: CPDFStampAnnotation.self) {
+                    let annotation_stamp = data as! CPDFStampAnnotation
+                    if (annotation_stamp.stampImage() != nil) {
+                        noteType = SKNStampString
+                    }
+                } else if data.isKind(of: CPDFLineAnnotation.self) {
+                    let annotation_line = data as! CPDFLineAnnotation
+                    if annotation_line.startLineStyle == .none && annotation_line.endLineStyle == .none {
+                        noteType = SKNLine_NoneString
+                    } else if annotation_line.startLineStyle == .none && annotation_line.endLineStyle == .openArrow {
+                        noteType = SKNLine_OpenArrowString
+                    } else {
+                        noteType = SKNLine_NoneString
+                    }
+                } else if data.isKind(of: CPDFButtonWidgetAnnotation.self) {
+                    let buttonWidget = data as! CPDFButtonWidgetAnnotation
+                    if buttonWidget.controlType() == .radioButtonControl {
+                        noteType = KMAnnotationFormRadioButtonKey
+                    } else if buttonWidget.controlType() == .checkBoxControl {
+                        noteType = KMAnnotationFormCheckBoxKey
+                    } else if buttonWidget.controlType() == .pushButtonControl {
+                        noteType = KMAnnotationFormActionButtonKey
+                    }
+                } else if data.isKind(of: CPDFTextWidgetAnnotation.self) {
+                    noteType = KMAnnotationFormTextFieldKey
+                } else if data.isKind(of: CPDFChoiceWidgetAnnotation.self) {
+                    let choiceWidget = data as! CPDFChoiceWidgetAnnotation
+                    if choiceWidget.isListChoice {
+                        noteType = KMAnnotationFormListMenuKey
+                    } else {
+                        noteType = KMAnnotationFormComboBoxKey
+                    }
+                } else if data.isKind(of: KMTableAnnotation.self) {
+                    noteType = "Ink_Table"
+                } else if data.isKind(of: KMSelfSignAnnotation.self) {
+                    let selfSignNote = data as! KMSelfSignAnnotation
+                    if selfSignNote.annotationType == .signFalse {
+                        noteType = "KMSelfSignTypeFalseActionButtonKey"
+                    } else if (selfSignNote.annotationType == .signature) {
+                        noteType = "KMSelfSignTypeTureActionButtonKey"
+                    } else if (selfSignNote.annotationType == .signCircle) {
+                        noteType = "KMSelfSignTypeCircleActionButtonKey"
+                    } else if (selfSignNote.annotationType == .signLine) {
+                        noteType = "KMSelfSignTypeLineActionButtonKey"
+                    } else if (selfSignNote.annotationType == .signDot) {
+                        noteType = "KMSelfSignTypeDotActionButtonKey"
+                    } else if (selfSignNote.annotationType == .signText) {
+                        noteType = "KMSelfSignTypeTextActionButtonKey"
+                    }
+                } else if data.isKind(of: CPDFSquareAnnotation.self) {
+                    noteType = SKNSquareString
+                } else if data.isKind(of: CPDFTextAnnotation.self) {
+                    noteType = SKNNoteString
+                } else if data.isKind(of: CPDFFreeTextAnnotation.self) {
+                    noteType = SKNFreeTextString
+                } else if data.isKind(of: CPDFCircleAnnotation.self) {
+                    noteType = SKNCircleString
+                } else if data.isKind(of: CPDFSignatureAnnotation.self) {
+                    noteType = SKNSignatureString
+                } else if data.isKind(of: CPDFInkAnnotation.self) {
+                    noteType = SKNInkString
+                } else if data.isKind(of: CPDFMarkupAnnotation.self) {
+                    let anno = data as! CPDFMarkupAnnotation
+                    if anno.markupType() == .highlight {
+                        noteType = SKNHighlightString
+                    } else if anno.markupType() == .underline {
+                        noteType = SKNUnderlineString
+                    } else if anno.markupType() == .strikeOut {
+                        noteType = SKNStrikeOutString
+                    }
                 }
             }
             
             cell.typeImageView.image = imageView.noteTypeImage(withType: noteType, color: noteColor ?? .red)
             cell.typeImageView.isHidden = false
 
-            if note.isKind(of: CPDFMarkupAnnotation.self) {
+            if note is CPDFMarkupAnnotation {
                 cell.isFold = true
             }
 
@@ -2630,136 +2512,140 @@ extension KMLeftSideViewController: NSOutlineViewDelegate, NSOutlineViewDataSour
 
             cell.contentView.isHidden = false
             cell.contentViewHidden(false)
-            if note.isKind(of: CPDFMarkupAnnotation.self) {
-                let  markup = note as! CPDFMarkupAnnotation
-                var contentString = KMBOTAAnnotationTool.fetchText(text: markup.markupContent() ?? "")
-                contentString = contentString.replacingOccurrences(of: "\r", with: "")
-                contentString = contentString.replacingOccurrences(of: "\n", with: "")
-                cell.noteContentLabel.stringValue = contentString
-                if(contentString.isEmpty == false) {
-                    cell.foldButton.isHidden = false
-                }
-                var attributeStr = NSMutableAttributedString(string: contentString)
-                if (markup.markupType() == .highlight) {
-                    attributeStr.addAttribute(.backgroundColor, value: noteColor as Any, range: NSMakeRange(0, contentString.count))
-                } else if (markup.markupType() == .strikeOut) {
-                    attributeStr.addAttribute(.strikethroughStyle, value: NSUnderlineStyle.single.rawValue, range: NSMakeRange(0, contentString.count))
-                    attributeStr.addAttribute(.strikethroughColor, value: noteColor as Any, range: NSMakeRange(0, contentString.count))
-                } else if (markup.markupType() == .underline) {
-                    attributeStr.addAttribute(.underlineStyle, value: NSUnderlineStyle.single.rawValue, range: NSMakeRange(0, contentString.count))
-                    attributeStr.addAttribute(.underlineColor, value: noteColor as Any, range: NSMakeRange(0, contentString.count))
-                }
-                cell.annotationContentLabel.attributedStringValue = attributeStr
-
-                if self.foldType == .unfold {
-//                if let data = model?.foldType, data == .unfold { // 全部展开
-                    cell.isFold = false
-                } else if self.foldType == .fold {
-//                else if let data = model?.foldType, data == .fold { // 全部折叠
-                    cell.isFold = true
-                } else { // 混合
-                    if self.allFoldNotes.isEmpty == false && self.allFoldNotes.contains(note) {
+            if let data = note {
+                if data.isKind(of: CPDFMarkupAnnotation.self) {
+                    let  markup = data as! CPDFMarkupAnnotation
+                    var contentString = KMBOTAAnnotationTool.fetchText(text: markup.markupContent() ?? "")
+                    contentString = contentString.replacingOccurrences(of: "\r", with: "")
+                    contentString = contentString.replacingOccurrences(of: "\n", with: "")
+                    cell.noteContentLabel.stringValue = contentString
+                    if(contentString.isEmpty == false) {
+                        cell.foldButton.isHidden = false
+                    }
+                    var attributeStr = NSMutableAttributedString(string: contentString)
+                    if (markup.markupType() == .highlight) {
+                        attributeStr.addAttribute(.backgroundColor, value: noteColor as Any, range: NSMakeRange(0, contentString.count))
+                    } else if (markup.markupType() == .strikeOut) {
+                        attributeStr.addAttribute(.strikethroughStyle, value: NSUnderlineStyle.single.rawValue, range: NSMakeRange(0, contentString.count))
+                        attributeStr.addAttribute(.strikethroughColor, value: noteColor as Any, range: NSMakeRange(0, contentString.count))
+                    } else if (markup.markupType() == .underline) {
+                        attributeStr.addAttribute(.underlineStyle, value: NSUnderlineStyle.single.rawValue, range: NSMakeRange(0, contentString.count))
+                        attributeStr.addAttribute(.underlineColor, value: noteColor as Any, range: NSMakeRange(0, contentString.count))
+                    }
+                    cell.annotationContentLabel.attributedStringValue = attributeStr
+                    
+                    if self.foldType == .unfold {
+                        //                if let data = model?.foldType, data == .unfold { // 全部展开
                         cell.isFold = false
-                    } else {
+                    } else if self.foldType == .fold {
+                        //                else if let data = model?.foldType, data == .fold { // 全部折叠
                         cell.isFold = true
+                    } else { // 混合
+                        if self.allFoldNotes.isEmpty == false && self.allFoldNotes.contains(data) {
+                            cell.isFold = false
+                        } else {
+                            cell.isFold = true
+                        }
                     }
-                }
-                // noteString.isEmpty == false &&
-                if (contentString.isEmpty == false) {
-                    cell.contentViewHidden(false)
-                } else {
-                    cell.contentViewHidden(true)
-                }
-            } else if note.isKind(of: CPDFLineAnnotation.self) || noteType == SKNSquareString || noteType == SKNCircleString || noteType == SKNInkString {
-                cell.annotationContentLabel.stringValue = noteString
-                if (noteString.isEmpty == false) {
-                    cell.contentViewHidden(false)
-                } else {
-                    cell.contentViewHidden(true)
-                }
-            } else if note.isKind(of: CPDFStampAnnotation.self) {
-                if note.isKind(of: KMSelfSignAnnotation.self) {
-                     let newAnnotation = note as! KMSelfSignAnnotation
-                    let type = newAnnotation.annotationType
-                    var returnString = ""
-                    if (type == .signFalse) {
-                       returnString = KMLocalizedString("X", nil)
-                    } else if (type == .signature) {
-                       returnString = KMLocalizedString("Check mark", nil)
-                    } else if (type == .signCircle) {
-                       returnString = KMLocalizedString("Circle", nil)
-                    } else if (type == .signLine) {
-                       returnString = KMLocalizedString("Line", nil)
-                    } else if (type == .signDot) {
-                       returnString = KMLocalizedString("Dot", nil)
-                    } else if (type == .signText) {
-                       returnString = KMLocalizedString("Text", nil)
-                    }
-                    cell.annotationContentLabel.stringValue = returnString
-                } else {
-                    cell.annotationContentLabel.isHidden = true
-
-                    cell.noteImageView.isHidden = false
-                    let anno = note as! CPDFStampAnnotation
-                    cell.noteImageView.image = anno.stampImage()
-                }
-            } else if note.isKind(of: CPDFTextAnnotation.self) {
-                cell.foldButton.isHidden = false
-                if noteString.isEmpty {
-                    cell.annotationContentLabel.stringValue = noteTextString
-                }else{
+                    // noteString.isEmpty == false &&
+                    if (contentString.isEmpty == false) {
+                        cell.contentViewHidden(false)
+                    } else {
+                        cell.contentViewHidden(true)
+                    }
+                } else if data.isKind(of: CPDFLineAnnotation.self) || noteType == SKNSquareString || noteType == SKNCircleString || noteType == SKNInkString {
                     cell.annotationContentLabel.stringValue = noteString
-                    cell.noteContentLabel.stringValue = noteTextString
-                }
-
-                if (self.foldType == .unfold) {
-                    cell.isFold = false
-                } else if (self.foldType == .fold) {
-                    cell.isFold = true
-                } else {
-                    if self.allFoldNotes.isEmpty == false && self.allFoldNotes.contains(note) {
-                        cell.isFold = false
+                    if (noteString.isEmpty == false) {
+                        cell.contentViewHidden(false)
                     } else {
-                        cell.isFold = true
+                        cell.contentViewHidden(true)
                     }
-                }
-                if (noteString.isEmpty == false || noteTextString.isEmpty == false) {
-                    cell.contentView.isHidden = false
-                } else {
-                    cell.contentView.isHidden = true
-                    cell.contentViewHidden(true)
-                }
-                // noteString.isEmpty == false &&
-                if (noteTextString.isEmpty == false) {
+                } else if data.isKind(of: CPDFStampAnnotation.self) {
+                    if data.isKind(of: KMSelfSignAnnotation.self) {
+                        let newAnnotation = note as! KMSelfSignAnnotation
+                        let type = newAnnotation.annotationType
+                        var returnString = ""
+                        if (type == .signFalse) {
+                            returnString = KMLocalizedString("X", nil)
+                        } else if (type == .signature) {
+                            returnString = KMLocalizedString("Check mark", nil)
+                        } else if (type == .signCircle) {
+                            returnString = KMLocalizedString("Circle", nil)
+                        } else if (type == .signLine) {
+                            returnString = KMLocalizedString("Line", nil)
+                        } else if (type == .signDot) {
+                            returnString = KMLocalizedString("Dot", nil)
+                        } else if (type == .signText) {
+                            returnString = KMLocalizedString("Text", nil)
+                        }
+                        cell.annotationContentLabel.stringValue = returnString
+                    } else {
+                        cell.annotationContentLabel.isHidden = true
+                        
+                        cell.noteImageView.isHidden = false
+                        let anno = note as! CPDFStampAnnotation
+                        cell.noteImageView.image = anno.stampImage()
+                    }
+                } else if data.isKind(of: CPDFTextAnnotation.self) {
                     cell.foldButton.isHidden = false
-                }else{
-                    cell.foldButton.isHidden = true
-                }
-
-            } else {
-                cell.annotationContentLabel.stringValue = noteString
-                cell.imageViewHeightConstraint.constant = cell.contentView.frame.size.height
-                if (noteString.isEmpty == false) {
-                    cell.contentViewHidden(false)
+                    if noteString.isEmpty {
+                        cell.annotationContentLabel.stringValue = noteTextString
+                    }else{
+                        cell.annotationContentLabel.stringValue = noteString
+                        cell.noteContentLabel.stringValue = noteTextString
+                    }
+                    
+                    if (self.foldType == .unfold) {
+                        cell.isFold = false
+                    } else if (self.foldType == .fold) {
+                        cell.isFold = true
+                    } else {
+                        if self.allFoldNotes.isEmpty == false && self.allFoldNotes.contains(data) {
+                            cell.isFold = false
+                        } else {
+                            cell.isFold = true
+                        }
+                    }
+                    if (noteString.isEmpty == false || noteTextString.isEmpty == false) {
+                        cell.contentView.isHidden = false
+                    } else {
+                        cell.contentView.isHidden = true
+                        cell.contentViewHidden(true)
+                    }
+                    // noteString.isEmpty == false &&
+                    if (noteTextString.isEmpty == false) {
+                        cell.foldButton.isHidden = false
+                    }else{
+                        cell.foldButton.isHidden = true
+                    }
+                    
                 } else {
-                    cell.contentViewHidden(true)
+                    cell.annotationContentLabel.stringValue = noteString
+                    cell.imageViewHeightConstraint.constant = cell.contentView.frame.size.height
+                    if (noteString.isEmpty == false) {
+                        cell.contentViewHidden(false)
+                    } else {
+                        cell.contentViewHidden(true)
+                    }
                 }
             }
 
             cell.autherLayoutConstraint.constant = cell.autherLabel.isHidden ? -(cell.autherLabel.bounds.size.width) + 10.0 : 10.0
             cell.typeImageViewLayoutConstraint.constant = cell.typeImageView.isHidden ? -(cell.typeImageView.bounds.size.width) : 0.0
             cell.contentBoxLayoutConstraint.constant = cell.noteContentBox.isHidden ? -(cell.noteContentBox.bounds.size.height+8.0) : 8.0
-            if note.isKind(of: CPDFStampAnnotation.self) && note.isKind(of: KMSelfSignAnnotation.self) == false {
-
-            } else {
-                if note.isKind(of: CPDFMarkupAnnotation.self) {
-                    if (!cell.isFold) {
-                        self.allFoldNotes.append(note)
+            if let data = note {
+                if data.isKind(of: CPDFStampAnnotation.self) && data.isKind(of: KMSelfSignAnnotation.self) == false {
+                    
+                } else {
+                    if data.isKind(of: CPDFMarkupAnnotation.self) {
+                        if (!cell.isFold) {
+                            self.allFoldNotes.append(data)
+                        } else {
+                            cell.imageViewHeightConstraint.constant = 18.0 + 8
+                        }
                     } else {
                         cell.imageViewHeightConstraint.constant = 18.0 + 8
                     }
-                } else {
-                    cell.imageViewHeightConstraint.constant = 18.0 + 8
                 }
             }
             cell.isUnFoldNote = { [unowned self] cellNote, isUnfold in
@@ -2781,8 +2667,10 @@ extension KMLeftSideViewController: NSOutlineViewDelegate, NSOutlineViewDataSour
                     model?.foldH = isUnfold ? 30 : (cell.noteContentHeightConstraint.constant + cell.maltlineLabelLayoutConstraint.constant + 85)
                 }
                 if (isUnfold) {
-                    if (self.allFoldNotes.contains(note)) {
-                        self.allFoldNotes.removeObject(note)
+                    if let data = note {
+                        if (self.allFoldNotes.contains(data)) {
+                            self.allFoldNotes.removeObject(data)
+                        }
                     }
 
                     if (self.allFoldNotes.count == 0) {
@@ -2791,8 +2679,10 @@ extension KMLeftSideViewController: NSOutlineViewDelegate, NSOutlineViewDataSour
                         self.foldType = .none
                     }
                 } else {
-                    if self.allFoldNotes.contains(note) == false {
-                        self.allFoldNotes.append(note)
+                    if let data = note {
+                        if self.allFoldNotes.contains(data) == false {
+                            self.allFoldNotes.append(data)
+                        }
                     }
 
 //                    if (rightSideController.allFoldNotes.count == rightSideController.canFoldNotes.count) {
@@ -2809,17 +2699,17 @@ extension KMLeftSideViewController: NSOutlineViewDelegate, NSOutlineViewDataSour
     
     func outlineView(_ outlineView: NSOutlineView, heightOfRowByItem item: Any) -> CGFloat {
         if outlineView.isEqual(self.noteOutlineView) {
-            if item is KMBOTAAnnotationItem {
-                let model = item as! KMBOTAAnnotationItem
+            if let model = item as? KMBOTAAnnotationItem {
                 if model.foldType == .fold {
                     return model.foldH
                 }
-                return KMBOTAAnnotationTool.fetchCellHeight(annotation: (item as? KMBOTAAnnotationItem)!.annotation!, maxSize: CGSize(width: 260+40 - 16, height: 1000))
+                if let anno = model.annotation {
+                    return KMBOTAAnnotationTool.fetchCellHeight(annotation: anno, maxSize: CGSize(width: 260+40 - 16, height: 1000))
+                }
             }
             return 30
         } else if outlineView.isEqual(self.tocOutlineView) {
-            if item is CPDFOutline {
-                let tempItem = item as! CPDFOutline
+            if let tempItem = item as? CPDFOutline {
                 let string: NSString = tempItem.label as NSString
                 let paragraphStyle = NSMutableParagraphStyle()
                 paragraphStyle.lineHeightMultiple = 1.32
@@ -2843,7 +2733,7 @@ extension KMLeftSideViewController: NSOutlineViewDelegate, NSOutlineViewDataSour
             if let data = item as? String, data == "Bookmarks" {
                 return true
             } else if item is CPDFOutline {
-                return ((item as! CPDFOutline).numberOfChildren ?? 0) != 0
+                return ((item as? CPDFOutline)?.numberOfChildren ?? 0) != 0
             } else if item is CPDFBookmark {
                 return false
             }

+ 4 - 5
PDF Office/PDF Master/Class/PDFWindowController/ViewController/KMMainViewController+Action.swift

@@ -479,11 +479,10 @@ extension KMMainViewController {
         _ = stypeMenu.addItem(withTitle: NSLocalizedString("Crop Current Page", comment: ""), action: #selector(cropCurrentPageItem), target: self, tag: 1)
         _ = stypeMenu.addItem(withTitle: NSLocalizedString("Auto Crop – Separate", comment: ""), action: #selector(autoCropAllItem), target: self, tag: 2)
         _ = stypeMenu.addItem(withTitle: NSLocalizedString("Auto Crop – Combined", comment: ""), action: #selector(smartAutoCropAllItem), target: self, tag: 3)
-        //        if(NSIsEmptyRect(selectionRect)) {
-        _ = stypeMenu.addItem(withTitle: NSLocalizedString("Select Area", comment: ""), action: #selector(selectToolModel), target: self, tag: 4)
-        _ = stypeMenu.addItem(withTitle: NSLocalizedString("Crop Options...", comment: ""), action: #selector(customCropModel), target: self, tag: 5)
-        //
-        //        }
+        if NSIsEmptyRect(listView.selectionRect){
+            _ = stypeMenu.addItem(withTitle: NSLocalizedString("Select Area", comment: ""), action: #selector(selectToolModel), target: self, tag: 4)
+            _ = stypeMenu.addItem(withTitle: NSLocalizedString("Crop Options...", comment: ""), action: #selector(customCropModel), target: self, tag: 5)
+        }
         
         stypItem.submenu = stypeMenu
         //        if self.toolbarController.toolbarType == .Annatiton {

+ 10 - 2
PDF Office/PDF Master/Class/PDFWindowController/ViewController/KMMainViewController+UI.swift

@@ -626,7 +626,10 @@ extension KMMainViewController {
         self.leftView.isHidden = true
         
         //弹出提示框
-        let alertView = CustomAlertView.alertView(message: NSLocalizedString("Read mode on, you can press ESC to exit.", comment: ""), fromView: self.view, withStyle: .blue, backgroundColor: NSColor.km_init(hex: "#36383B"))
+        if readAlertView != nil {
+            readAlertView?.removeFromSuperview()
+        }
+        readAlertView = CustomAlertView.alertView(message: NSLocalizedString("Read mode on, you can press ESC to exit.", comment: ""), fromView: self.view, withStyle: .blue, backgroundColor: NSColor.km_init(hex: "#36383B"))
     }
     
     @objc func closeReadModel() {
@@ -666,10 +669,15 @@ extension KMMainViewController {
             self.toolbarController.view.isHidden = false
             self.listView.toolMode = readToolMode
             self.listView.annotationType = readAnnotationType
+            self.toolbarController.toolbarType = .viewSetting
         } else {
             self.toolbarController.toolbarType = .None
         }
-        let alertView = CustomAlertView.alertView(message: NSLocalizedString("Read Mode Off", comment: ""), fromView: self.view, withStyle: .blue, backgroundColor: NSColor.km_init(hex: "#36383B"))
+        
+        if readAlertView != nil {
+            readAlertView?.removeFromSuperview()
+        }
+        readAlertView = CustomAlertView.alertView(message: NSLocalizedString("Read Mode Off", comment: ""), fromView: self.view, withStyle: .blue, backgroundColor: NSColor.km_init(hex: "#36383B"))
     }
     
     @objc func addOutLineItemAction() {

+ 1 - 0
PDF Office/PDF Master/Class/PDFWindowController/ViewController/KMMainViewController.swift

@@ -56,6 +56,7 @@ let LOCKED_KEY  = "locked"
     @IBOutlet weak var bottomAreaView: KMBox!
     @IBOutlet weak var readModelViewWidthConstraint: NSLayoutConstraint!
     var isReadMode: Bool = false
+    var readAlertView: CustomAlertView?
     
     var readLeftMethodType: BotaType = .None
     var readLeftPanelOpen = false

+ 21 - 5
PDF Office/PDF Reader Pro.xcodeproj/xcuserdata/kdanmobile.xcuserdatad/xcdebugger/Breakpoints_v2.xcbkptlist

@@ -263,16 +263,32 @@
       <BreakpointProxy
          BreakpointExtensionID = "Xcode.Breakpoint.FileBreakpoint">
          <BreakpointContent
-            uuid = "835506E2-BAB9-4B07-811B-120DC0EA9881"
+            uuid = "56395C92-3A00-4FEB-947F-91EE3A0B02AA"
             shouldBeEnabled = "Yes"
             ignoreCount = "0"
             continueAfterRunningActions = "No"
-            filePath = "PDF Master/Class/Home/ViewController/KMHomeViewController+Action.swift"
+            filePath = "PDF Master/AppDelegate.swift"
             startingColumnNumber = "9223372036854775807"
             endingColumnNumber = "9223372036854775807"
-            startingLineNumber = "454"
-            endingLineNumber = "454"
-            landmarkName = "openFile(withFilePath:)"
+            startingLineNumber = "310"
+            endingLineNumber = "310"
+            landmarkName = "applicationShouldHandleReopen(_:hasVisibleWindows:)"
+            landmarkType = "7">
+         </BreakpointContent>
+      </BreakpointProxy>
+      <BreakpointProxy
+         BreakpointExtensionID = "Xcode.Breakpoint.FileBreakpoint">
+         <BreakpointContent
+            uuid = "6B9373DD-1A2D-449E-8B52-CAB5C3223C22"
+            shouldBeEnabled = "Yes"
+            ignoreCount = "0"
+            continueAfterRunningActions = "No"
+            filePath = "PDF Master/Class/ChromiumTabs/KMBrowserWindowController.swift"
+            startingColumnNumber = "9223372036854775807"
+            endingColumnNumber = "9223372036854775807"
+            startingLineNumber = "350"
+            endingLineNumber = "350"
+            landmarkName = "reopenDocument(forPaths:)"
             landmarkType = "7">
          </BreakpointContent>
       </BreakpointProxy>