// // KMToolbarController.swift // PDF Reader Pro // // Created by wanjun on 2022/12/29. // import Cocoa extension CAnnotationType { func isAdvanced() -> Bool { if (self == .link || self == .stamp || self == .signSignature) { return true } if (self == .signText || self == .signTure || self == .signFalse || self == .signCircle || self == .signLine || self == .signDot || self == .signDate) { return true } if (self == .addText || self == .addImage) { return true } return false } func isMarkup() -> Bool { if self == .highlight || self == .underline || self == .strikeOut || self == .ink || self == .squiggly { return true } return false } func isSquare() -> Bool { if self == .square || self == .circle || self == .line || self == .arrow { return true } return false } } @objc protocol KMToolbarControllerDelegate { @objc optional func toolbarController(_ viewController: KMToolbarController, heightOffsetChange heightOffset: Float, animated: Bool) @objc optional func changeAnnotationModeAction(item:KMToolbarClickButton) @objc optional func showPDFLayoutModeAction(show:Bool) @objc optional func clickChildTool(type: KMToolbarType, index: Int) @objc optional func changePDFViewZoomModelAction(selectedTag:Int) @objc optional func changePDFViewZoomInAction() @objc optional func changePDFViewZoomOutAction() @objc optional func changePDFViewGotoNextPageAction() @objc optional func changePDFViewGoToPreviousPageAction() @objc optional func changePDFViewGotoBackAction() @objc optional func changePDFViewGoToForwardAction() @objc optional func aiTranslationPDFFileAction() @objc optional func toolbarViewController(_ viewController:KMToolbarViewController, zoomModel selectedTag:Int) @objc optional func toolbarViewController(_ viewController:KMToolbarViewController, zoomSting : String) @objc optional func mainToolDidClicked(_ toolController: KMToolbarController, _ beforeType: KMToolbarViewType, _ type: KMToolbarViewType, _ item: KMToolbarItemView, _ pages: [Int]) @objc optional func toolbarViewController(_ viewController:KMToolbarViewController, shareAction toolbarItem: KMToolbarItemView) @objc optional func toolbarViewController(_ viewController:KMToolbarViewController, shareDocument item:NSMenuItem) @objc optional func toolbarViewController(_ viewController:KMToolbarViewController, shareFlatten item:NSMenuItem) @objc optional func toolbarViewController(_ viewController:KMToolbarViewController, shareOriginalPDF item:NSMenuItem) @objc optional func toolbarViewController(_ viewController:KMToolbarViewController, scanOCRModel selectedTag:Int) @objc optional func toolbarViewController(_ viewController:KMToolbarViewController, itemDidClick toolbarItem: KMToolbarItemView) @objc optional func toolbarViewController(_ viewController:KMToolbarViewController, searchAction searchString: String, forward: Bool) @objc optional func toolbarViewController(_ viewController:KMToolbarViewController, findSearchAction searchString: String, forward: Bool) @objc optional func toolbarViewController(_ viewController:KMToolbarViewController, findSearchAllAction searchString: String, forward: Bool) @objc optional func toolbarViewController(_ viewController:KMToolbarViewController, menuItemDidClick toolbarItem: KMToolbarItemView, index: Int, info: Any?) @objc optional func toolbarViewController(_ viewController:KMToolbarViewController, viewItemDidClick toolbarItem: KMToolbarItemView, index: Int, info: Any?) } class KMToolbarController: NSViewController { static let mainToolBarHeight: Float = 48 static let childToolBarHeightValue: Float = 41 static let findBarHeight: Float = 25 @IBOutlet weak var mainToolBarBox: NSBox! @IBOutlet weak var childToolBarBox: NSBox! @IBOutlet weak var secondaryToolBarBox: NSBox! @IBOutlet weak var mainToolBarHeight: NSLayoutConstraint! @IBOutlet weak var childToolBarHeight: NSLayoutConstraint! @IBOutlet weak var secondaryToolBarHeight: NSLayoutConstraint! @IBOutlet weak var bottomOffset: NSLayoutConstraint! var mainToolBarView: KMToolbarViewController? var childToolBarView: KMToolbarViewController? var _toolbarType : KMToolbarViewType = KMToolbarViewType.None weak var mainViewController: KMMainViewController? open weak var delegate: KMToolbarControllerDelegate? var toolbarItems : [NSToolbarItem.Identifier : Any] = [:] var listView : CPDFListView? var lastItemBox : KMToolbarItemView = KMToolbarItemView() var lastChildItemBox : KMToolbarItemView = KMToolbarItemView() var popover: NSPopover? //find seaarch @IBOutlet weak var findSearchView: KMSearchFindView! // 是否显示所有注释 private var _isShowAllAnnotations = true // 是否显示所有注释 var isShowAllAnnotations: Bool { get { return _isShowAllAnnotations } set { _isShowAllAnnotations = newValue self.childToolBarView?.isShowAllAnnotations = newValue let item = self.findChildItem(KMToolbarShowToolbarItemIdentifier) item?.isSelected = !newValue if newValue { item?.titleName = NSLocalizedString("Hide", comment: "") item?.toolTip = NSLocalizedString("Hide", comment: "") item?.menuFormRepresentation?.title = NSLocalizedString("Hide", comment: "") } else { item?.titleName = NSLocalizedString("Display", comment: "") item?.toolTip = NSLocalizedString("Display", comment: "") item?.menuFormRepresentation?.title = NSLocalizedString("Display", comment: "") } for itemId in self._fetchItemIdsForHideNotes() { self.findItem(itemId)?.unEnabled = !self.isShowAllAnnotations } } } private var _ignoreCurrentAnnotationTypeChange = false var ignoreCurrentAnnotationTypeChange: Bool { get { return self._ignoreCurrentAnnotationTypeChange } set { self._ignoreCurrentAnnotationTypeChange = newValue self.childToolBarView?.ignoreCurrentAnnotationTypeChange = self.ignoreCurrentAnnotationTypeChange // 忽略后重置 这个属性是基于单次添加,所以使用后会重置 // self._ignoreCurrentAnnotationTypeChange = false } } var mainToolBarisVisable: Bool { get { return self.mainToolBarBox.isHidden == false } set { let needShow = newValue let currentIsShow = self.mainToolBarisVisable let toolBarH: Float = Self.mainToolBarHeight if needShow { if currentIsShow { // 当前已显示 return } let height = self.view.frame.size.height self.mainToolBarBox.animator().isHidden = false self.mainToolBarHeight.animator().constant = toolBarH.cgFloat self.delegate?.toolbarController?(self, heightOffsetChange: Float(height)+toolBarH, animated: true) } else { if currentIsShow == false { // 当前已隐藏 return } let height = self.view.frame.size.height self.mainToolBarBox.isHidden = true self.mainToolBarHeight.animator().constant = 0 self.delegate?.toolbarController?(self, heightOffsetChange: Float(height)-toolBarH, animated: true) } } } override func viewDidLoad() { super.viewDidLoad() // Do view setup here. updateViewColor() mainToolBarView = KMToolbarViewController.init() mainToolBarView?.view.wantsLayer = true mainToolBarView?.view.layer?.backgroundColor = NSColor.km_init(hex: "#F7F8FA").cgColor mainToolBarBox.contentView = mainToolBarView?.view mainToolBarView?.delegate = self if let data = self.listView { mainToolBarView?.pdfView = data } childToolBarView = KMToolbarViewController.init() childToolBarView?.view.wantsLayer = true childToolBarView?.view.layer?.backgroundColor = NSColor.km_init(hex: "#F7F8FA").cgColor childToolBarBox.contentView = childToolBarView?.view childToolBarView?.view.frame = childToolBarBox.frame childToolBarView?.delegate = self childToolBarView?.view.autoresizingMask = [.width, .height] if let data = self.listView { childToolBarView?.pdfView = data } toolbarType = .None mainToolBarView?.toolbarType = .Main mainToolBarView?.reloadateToolbar() mainToolBarView?.toolbar?.allowsUserCustomization = true self.findSearchView.isHidden = true NotificationCenter.default.addObserver(self, selector: #selector(selectedShapAnnotationChangeNotification(_:)), name: NSNotification.Name.init(rawValue: "KMSelectedShapAnnotationChangeNotification"), object: nil) NotificationCenter.default.addObserver(self, selector: #selector(PDFChangedNotification(_:)), name: NSNotification.Name.init(rawValue: "PDFChangedNotification"), object: nil) NotificationCenter.default.addObserver(self, selector: #selector(PDFTextEditPDFChangedNotification(_:)), name: NSNotification.Name.init(rawValue: "KMPDFTextEditPDFChangedNotification"), object: nil) } // MARK: func updateViewColor() -> Void { } // MARK: Setter&Getter var toolbarType: KMToolbarViewType { set { if newValue == _toolbarType { if newValue == .Move || newValue == .Magnify || newValue == .Select || newValue == .SelectZoom { _toolbarType = .Annatiton } else { _toolbarType = .None } } else { _toolbarType = newValue } mainViewController?.cancelMeasureType() mainToolBarView?.toolbar?.isHidden = false secondaryToolBarBox.isHidden = true secondaryToolBarHeight.constant = 51 let mainToolbarH = self.mainToolBarisVisable ? Self.mainToolBarHeight : 0 if self.mainViewController!.isReadMode { if (_toolbarType == .Annatiton) { let childToolbarH = Self.childToolBarHeightValue bottomOffset.constant = childToolbarH.cgFloat mainToolBarHeight.constant = 0 childToolBarBox.isHidden = false self.delegate?.toolbarController?(self, heightOffsetChange: 41, animated: false) } else { mainToolBarHeight.constant = 0 bottomOffset.constant = 0 childToolBarBox.isHidden = true mainToolBarView?.toolbar?.isHidden = true self.delegate?.toolbarController?(self, heightOffsetChange: 0, animated: false) } } else { if _toolbarType == .None { bottomOffset.constant = 0 childToolBarBox.isHidden = true self.delegate?.toolbarController?(self, heightOffsetChange: mainToolbarH, animated: false) } else if _toolbarType == .Page || _toolbarType == .LeftPanel || _toolbarType == .redact { bottomOffset.constant = 0 childToolBarBox.isHidden = true self.delegate?.toolbarController?(self, heightOffsetChange: mainToolbarH, animated: false) } else { let childToolbarH = Self.childToolBarHeightValue bottomOffset.constant = childToolbarH.cgFloat childToolBarBox.isHidden = false self.delegate?.toolbarController?(self, heightOffsetChange: mainToolbarH + childToolbarH, animated: false) } } childToolBarView?.toolbarType = _toolbarType if self.toolbarType == .Annatiton { childToolBarView?.toolbar?.contentInset = .init(top: 0, left: 0, bottom: 0, right: 44) childToolBarView?.rightItemView.isHidden = false } else { childToolBarView?.toolbar?.contentInset = NSEdgeInsetsZero childToolBarView?.rightItemView.isHidden = true } childToolBarView?.reloadateToolbar() } get { return _toolbarType } } // MARK: - // MARK: Public Methods // 取消选中 [只是取消选中状态,不会执行具体的方法] public func cancelSelected(_ identifier: String) { if (isMainToolItem(identifier)) { self.findMainItem(identifier)?.isSelected = false return } self.findChildItem(identifier)?.isSelected = false } public func clickItem(_ identifier: String) { self.selectItem(identifier) } public func selectItem(_ identifier: String) { if self.isShowAllAnnotations == false { let itemIds = self._fetchItemIdsForHideNotes() if itemIds.contains(identifier) { NSSound.beep() return } } if (isMainToolItem(identifier)) { self.selectMainItem(identifier) return } if let parentItem = self.findItem(parentIdentifier(identifier)), parentItem.isSelected { if (self.trySelectChildItem(identifier)) { // 尝试去选子工具栏 return } } // 当前主工具栏未开启 let mainToolIdentifier = parentIdentifier(identifier) if (mainToolIdentifier.isEmpty) { return } // 找到主工具栏 self.selectMainItem(mainToolIdentifier) DispatchQueue.main.async { // 再去选择子工具栏 self.selectChildItem(identifier) } } public func findItem(_ identifier: String) -> KMToolbarItemView? { if (isMainToolItem(identifier)) { return self.findMainItem(identifier) } return self.findChildItem(identifier) } // MARK: - // MARK: private Methods private func selectMainItem(_ identifier: String) { if (self.mainToolBarView?.toolbarItems == nil) { return } var item: KMToolbarItemView? for (key, value) in self.mainToolBarView?.toolbarItems ?? [:] { if (key == identifier) { item = (value as? KMToolbarItemView) break } } // 主工具栏 item if let data = item { if (identifier == KMDocumentAnnotationToolbarItemIdentifier || identifier == KMDocumentPageToolbarItemIdentifier || identifier == KMDocumentConversonToolbarItemIdentifier || identifier == KMDocumentEditToolbarItemIdentifier || identifier == KMDocumentFormToolbarItemIdentifier || identifier == KMDocumentFillSginToolbarItemIdentifier || identifier == KMDocumentToolToolbarItemIdentifier) { self.mainToolBarView?.leftControllButtonAction(item: data.clickButton) } else if (identifier == KMRightControlToolbarItemIdentifier) { self.mainToolBarView?.itemAction(data) } else if (identifier == KMLeftControlToolbarItemIdentifier) { self.mainToolBarView?.itemAction(data) } else if identifier == KMDocumentRedactToolbarItemIdentifier { self.mainToolBarView?.itemAction(data) } else if identifier == KMDocumentScanOCRToolbarItemIdentifier { self.mainToolBarView?.itemAction(data) } else if identifier == KMDocumentAIToolsToolbarItemIdentifier { self.mainToolBarView?.itemAction(data) } return } } private func trySelectChildItem(_ identifier: String) -> Bool { // 子工具栏 item [当前主工具栏已开启] var item: KMToolbarItemView? if let items = self.childToolBarView?.toolbarItems, items.count > 0 { for (key, value) in items { if (key == identifier) { item = (value as? KMToolbarItemView) break } } // 子工具栏[找到] if (item != nil) { self.selectChildItem(identifier) return true } } return false } private func selectChildItem(_ identifier: String) { // 子工具栏 item [当前主工具栏已开启] var item: KMToolbarItemView? if let items = self.childToolBarView?.toolbarItems, items.count > 0 { for (key, value) in items { if (key == identifier) { item = (value as? KMToolbarItemView) break } } // 子工具栏[找到] if let data = item { if (identifier == KMToolbarMoveToolModeItemIdentifier || identifier == KMToolbarMagnifyToolModeItemIdentifier || identifier == KMToolbarSelectToolModeItemIdentifier || identifier == KMToolbarZoomToSelectionItemIdentifier) { self.childToolBarView?.leftControllButtonAction(item: data.clickButton) } else if identifier == KMToolbarViewSettingIdentifier || identifier == KMAnnotationImageToolbarItemIdentifier || identifier == KMAnnotationTableToolbarItemIdentifier { self.childToolBarView?.itemAction(data) } else { self.childToolBarView?.changeAnnotationMode(item: data.clickButton) } } } } private func findMainItem(_ identifier: String) -> KMToolbarItemView? { if (self.mainToolBarView?.toolbarItems == nil) { return nil } var item: KMToolbarItemView? if (isMainToolItem(identifier)) { for (key, value) in self.mainToolBarView?.toolbarItems ?? [:] { if (key == identifier) { item = (value as? KMToolbarItemView) break } } return item } return nil } private func findChildItem(_ identifier: String) -> KMToolbarItemView? { if (self.childToolBarView?.toolbarItems == nil || self.childToolBarView!.toolbarItems.count == 0) { return nil } var item: KMToolbarItemView? for (key, value) in self.childToolBarView?.toolbarItems ?? [:] { if (key == identifier) { item = (value as? KMToolbarItemView) break } } return item } private func _fetchItemIdsForHideNotes() -> [String] { let itemIds = [KMDocumentEditToolbarItemIdentifier, KMDocumentFormToolbarItemIdentifier, KMDocumentFillSginToolbarItemIdentifier, KMDocumentRedactToolbarItemIdentifier, KMDocumentSignToolbarItemIdentifier] var annoIds = annotationToolIdentifiers if annoIds.contains(KMToolbarShowToolbarItemIdentifier) { annoIds.removeObject(KMToolbarShowToolbarItemIdentifier) } return annoIds + itemIds + editPDFItemIdentifiers + formToolIdentifiers + fillSignToolIdentifiers } func exitPageEdit() -> Void { if let data = self.mainToolBarView { resetToolbarViewController(data) exitPageEditToolbarViewController(data) } } func exitTextEdit() -> Void { secondaryToolBarBox.isHidden = true secondaryToolBarHeight.constant = 50 bottomOffset.constant = 51 childToolBarBox.isHidden = false self.delegate?.toolbarController?(self, heightOffsetChange: 102, animated: false) } func enterWatermarkAdjective(_ type: KMToolbarType, _ itemTitles: Array>) { self.toolbarType = .None let topBarView = KMWatermarkAdjectiveTopBarView() topBarView.frame = (self.mainToolBarView?.toolbar?.bounds) ?? .zero self.mainToolBarView?.toolbar?.addSubview(topBarView) topBarView.autoresizingMask = NSView.AutoresizingMask(rawValue: 18) topBarView.wantsLayer = true topBarView.layer?.backgroundColor = NSColor.white.cgColor topBarView.isCanApply(can: false) var itemModels: Array> = [] for items in itemTitles { var array: Array = [] for title in items { let model = KMWatermarkAdjectiveTopBarItemModel() model.iconName = "" model.itemTitle = title array.append(model) } itemModels.append(array) } topBarView.initItemData(itemArrays: itemModels) topBarView.cancelClick = { [weak self] in self?.delegate?.clickChildTool?(type: type, index: 1) } topBarView.applyClick = { [weak self] in self?.delegate?.clickChildTool?(type: type, index: 2) } topBarView.itemClick = { [weak self] section,item in self?.delegate?.clickChildTool?(type: type, index: 3+item) } } func exitWatermarkAdjective() { let topBarView = self.mainToolBarView?.toolbar?.subviews.last if (topBarView == nil || topBarView?.isKind(of: KMWatermarkAdjectiveTopBarView.self) == false) { return } topBarView?.removeFromSuperview() } func fetchTopBarView() -> NSView? { let topBarView = self.mainToolBarView?.toolbar?.subviews.last if (topBarView == nil) { return nil } if (topBarView?.isKind(of: KMWatermarkAdjectiveTopBarView.self) == true) { return topBarView } if (topBarView?.isKind(of: KMRedactTopToolBar.self) == true) { return topBarView } return nil } func enterRedact() { self.toolbarType = .None let topBarView = KMRedactTopToolBar() topBarView.frame = (self.mainToolBarView?.toolbar?.bounds) ?? .zero self.mainToolBarView?.toolbar?.addSubview(topBarView) topBarView.autoresizingMask = [.width, .height] topBarView.wantsLayer = true topBarView.layer?.backgroundColor = NSColor.white.cgColor topBarView.selectItem(0) self.delegate?.clickChildTool?(type: .redact, index: 4) topBarView.itemClick = { [weak self] index in self?.delegate?.clickChildTool?(type: .redact, index: index) } } func exitRedact() { let topBarView = self.mainToolBarView?.toolbar?.subviews.last if (topBarView == nil || topBarView?.isKind(of: KMRedactTopToolBar.self) == false) { return } topBarView?.removeFromSuperview() } // MARK: NSNotification @objc func selectedShapAnnotationChangeNotification(_ notification: Notification) -> Void { } @objc func PDFChangedNotification(_ notification: Notification) -> Void { } @objc func PDFTextEditPDFChangedNotification(_ notification: Notification) -> Void { } // MARK: func resetToolbarViewController(_ toolbarViewController: KMToolbarViewController) -> Void { self.toolbarType = .None self.mainToolBarView?.resetToolbar() self.mainViewController?.listView.annotationType = .unkown } func exitPageEditToolbarViewController(_ toolbarViewController: KMToolbarViewController) -> Void { } // MARK: item actions @objc func cropItemAction(sender: NSMenuItem) { if (sender.tag == 0) { /// 裁剪当前页面 self.delegate?.clickChildTool?(type: .crop, index: 1) return } if (sender.tag == 1) { /// 裁剪所有页面 self.delegate?.clickChildTool?(type: .crop, index: 2) return } /// 自定义裁剪区域 self.delegate?.clickChildTool?(type: .crop, index: 3) } @objc func secureItemAction(sender: NSMenuItem) { var index: Int = 1 if (sender.tag == 1) { /// 删除安全性设置 index = 2 } self.delegate?.clickChildTool?(type: .secure, index: index) } override func interfaceThemeDidChanged(_ appearance: NSAppearance.Name) { super.interfaceThemeDidChanged(appearance) self.mainToolBarView?.interfaceThemeDidChanged(appearance) self.childToolBarView?.interfaceThemeDidChanged(appearance) for item in self.childToolBarView?.toolbar?.items ?? [] { if item.itemIdentifier == KMToolbarHighlightAnnotationItemIdentifier { let color = KMPreference.shared.markupHighlightColor let imageV = KMNoteTypeImageView() item.image = imageV.noteTypeImage(withType: SKNHighlightString, color: color) } else if item.itemIdentifier == KMToolbarUnderlineAnnotationItemIdentifier { let color = KMPreference.shared.markupUnderlineColor let imageV = KMNoteTypeImageView() item.image = imageV.noteTypeImage(withType: SKNUnderlineString, color: color) } else if item.itemIdentifier == KMToolbarStrikeOutAnnotationItemIdentifier { let color = KMPreference.shared.markupStrikthroughColor let imageV = KMNoteTypeImageView() item.image = imageV.noteTypeImage(withType: SKNStrikeOutString, color: color) } else if item.itemIdentifier == KMToolbarSquigglyAnnotationItemIdentifier { let color = UserDefaults.standard.PDFListViewColor(forKey: CSquigglyNoteColorKey) let imageV = KMNoteTypeImageView() item.image = imageV.noteTypeImage(withType: CPDFAnnotation.kType.squiggly, color: color ?? NSColor(red: 252.0/255.0, green: 31.0/255.0, blue: 31.0/255.0, alpha: 1.0)) } else if item.itemIdentifier == KMToolbarInkAnnotationItemIdentifier { let color = KMPreference.shared.markupPenColor let imageV = KMNoteTypeImageView() item.image = imageV.noteTypeImage(withType: SKNInkString, color: color) } } } } //MARK: Find Search extension KMToolbarController { func showFindBar() { self.findSearchView.isHidden = false let height: Float = self.fetchHeight(type: _toolbarType) self.delegate?.toolbarController?(self, heightOffsetChange: height, animated: false) self.findSearchView.findField.becomeFirstResponder() self.findSearchView.doneAction = { [weak self] view in self?.exitFindBar() } self.findSearchView.searchAction = { [weak self] view, searchString, forward in if let data = self?.mainToolBarView { self?.toolbarViewController(data, findSearchAction: searchString, forward: forward) } return true } self.findSearchView.showAllAction = { [weak self] view, searchString, forward in if let data = self?.mainToolBarView { self?.toolbarViewController(data, findSearchAllAction: searchString, forward: forward) } } } func showFindString(forward: Bool) { if let data = self.mainToolBarView { self.toolbarViewController(data, findSearchAction: self.findSearchView.findString ?? "", forward: forward) } } func showAllAction() { if let data = self.mainToolBarView { self.toolbarViewController(data, findSearchAllAction: self.findSearchView.findString ?? "", forward: true) } } func exitFindBar() { self.findSearchView.isHidden = true let height: Float = self.fetchHeight(type: _toolbarType, isShow: false) self.delegate?.toolbarController?(self, heightOffsetChange: height, animated: false) } func fetchHeight(type: KMToolbarViewType, isShow: Bool = true) -> Float { var height: Float = 0.0 let mainToolbarH = self.mainToolBarisVisable ? Self.mainToolBarHeight : 0 let childToolbarH = Self.childToolBarHeightValue let findBarH = Self.findBarHeight if isShow { if _toolbarType == .None { bottomOffset.constant = findBarH.cgFloat height = mainToolbarH } else if _toolbarType == .Page || _toolbarType == .LeftPanel || _toolbarType == .redact { bottomOffset.constant = findBarH.cgFloat height = mainToolbarH } else { bottomOffset.constant = childToolbarH.cgFloat + findBarH.cgFloat height = mainToolbarH + childToolbarH } height = height + findBarH } else { if _toolbarType == .None { bottomOffset.constant = 0 height = mainToolbarH } else if _toolbarType == .Page || _toolbarType == .LeftPanel || _toolbarType == .redact { bottomOffset.constant = 0 height = mainToolbarH } else { bottomOffset.constant = childToolbarH.cgFloat height = mainToolbarH + childToolbarH } } return height } } extension KMToolbarController: KMToolbarViewControllerDelegate { func changeAnnotationModeAction(item: KMToolbarClickButton) { let type = CAnnotationType(rawValue: item.tag) ?? CAnnotationType.unkown if (type.isAdvanced() == false) { if self.toolbarType == .Magnify || self.toolbarType == .Move || self.toolbarType == .Select || self.toolbarType == .SelectZoom { self.toolbarType = .Annatiton } self.delegate?.changeAnnotationModeAction?(item: item) return } // 高级功能 Task { @MainActor in //文字编辑 图片编辑 选中按钮逻辑(只能同时选中其中一个) if type == .addText || type == .addImage { let boxItem = item.clickObject as? KMToolbarItemView if let data = boxItem { if self.lastChildItemBox != data { self.lastChildItemBox.isSelected = false data.isSelected = true } else { data.isSelected = !data.isSelected } self.lastChildItemBox = data } } if self.toolbarType == .Magnify || self.toolbarType == .Move || self.toolbarType == .Select || self.toolbarType == .SelectZoom { self.toolbarType = .Annatiton } self.trackEvent(type: type) self.delegate?.changeAnnotationModeAction?(item: item) } } func trackEvent(type: CAnnotationType) { var eventStr = "Btn_SubTbr_Fill&Sign_Check" switch type { case .signTure: eventStr = "Btn_SubTbr_Fill&Sign_Check" case .signFalse: eventStr = "Btn_SubTbr_Fill&Sign_X" case .signDate: eventStr = "Btn_SubTbr_Fill&Sign_Date" case .signDot: eventStr = "Btn_SubTbr_Fill&Sign_Dot" case .signCircle: eventStr = "Btn_SubTbr_Fill&Sign_Circle" case .signLine: eventStr = "Btn_SubTbr_Fill&Sign_Line" default: eventStr = "" break } if eventStr.count > 1{ FMTrackEventManager.defaultManager.trackEvent(event: "SubTbr_Fill&Sign", withProperties: ["SubTbr_Btn": eventStr]) } } func toolbarViewController(_ viewController: KMToolbarViewController, clickMode toolMode: KMToolbarViewType, toolbar toolbarItem: KMToolbarItemView, _ pages: [Int]) { let beforeModel = KMToolbarViewType(rawValue: self.lastItemBox.clickButton.tag) ?? .None if toolMode != .redact { // 标记秘文 let mainC = self.delegate as? KMMainViewController var control: KMPDFRedactViewController? for childC in mainC?.children ?? [] { if (childC.isKind(of: KMPDFRedactViewController.self)) { control = (childC as! KMPDFRedactViewController) break } } if let annos = control?.redactPdfView.newAddAnnotation, annos.count > 0 { let alert = NSAlert() alert.informativeText = KMLocalizedString("There are unapplied redactions in this file. Exit will not save redaction.", nil) alert.addButton(withTitle: KMLocalizedString("Exit", nil)) alert.addButton(withTitle: KMLocalizedString("Cancel", nil)) let resp = alert.runModal() if resp != .alertFirstButtonReturn { // 取消 return } control?.redactPdfView.newAddAnnotation.removeAll() } } if self.lastItemBox != nil { if (toolbarItem.isSelected && toolMode.isToolMode()) { // no nothings } else { self.lastItemBox.isSelected = false } } if self.lastChildItemBox != nil { if toolMode == .editPDF { if !self.lastItemBox.isSelected { self.lastChildItemBox.isSelected = false } } } if toolMode != .Magnify && toolMode != .Move && toolMode != .Select && toolMode != .SelectZoom && toolMode != .LeftPanel && toolMode != .RightPanel { if(toolMode == self.toolbarType) { toolbarItem.isSelected = false } else { toolbarItem.isSelected = true self.lastItemBox = toolbarItem self.trackEvent(toolType: toolMode) } } else { if(toolMode != self.toolbarType && toolMode != .LeftPanel) { let item : KMToolbarItemView = (self.mainToolBarView?.toolbarItemFindItemIdentifiers(value: KMDocumentAnnotationToolbarItemIdentifier))! item.isSelected = true self.lastItemBox = item if toolMode == .Select { FMTrackEventManager.defaultManager.trackEvent(event: "SubTbr_Tools", withProperties: ["SubTbr_Btn" : "Btn_SubTbr_Tools_ContentSelection"]) } if toolMode == .SelectZoom { FMTrackEventManager.defaultManager.trackEvent(event: "SubTbr_Tools", withProperties: ["SubTbr_Btn" : "Btn_SubTbr_Tools_Zoom"]) } } else if (toolMode == .LeftPanel) { if(toolMode == self.toolbarType) { toolbarItem.isSelected = false } else { toolbarItem.isSelected = true } } } self.toolbarType = toolMode self.delegate?.mainToolDidClicked?(self, beforeModel, toolMode, toolbarItem, pages) } func trackEvent(toolType type: KMToolbarViewType) -> Void { if (type == .Annatiton) { FMTrackEventManager.defaultManager.trackEvent(event: "Tbr", withProperties: ["Tbr_Btn" : "Btn_Tbr_Tools"]) } else if (type == .editPDF) { FMTrackEventManager.defaultManager.trackEvent(event: "Tbr", withProperties: ["Tbr_Btn" : "Btn_Tbr_EditPDF"]) } else if (type == .Page) { FMTrackEventManager.defaultManager.trackEvent(event: "Tbr", withProperties: ["Tbr_Btn" : "Btn_Tbr_PageEdit"]) } else if (type == .Conversion) { } else if (type == .Tool) { FMTrackEventManager.defaultManager.trackEvent(event: "Tbr", withProperties: ["Tbr_Btn" : "Btn_Tbr_Editor"]) } else if (type == .Conversion) { FMTrackEventManager.defaultManager.trackEvent(event: "Tbr", withProperties: ["Tbr_Btn" : "Btn_Tbr_Converter"]) } else if (type == .Form) { FMTrackEventManager.defaultManager.trackEvent(event: "Tbr", withProperties: ["Tbr_Btn" : "Btn_Tbr_Form"]) } else if (type == .FillSign) { FMTrackEventManager.defaultManager.trackEvent(event: "Tbr", withProperties: ["Tbr_Btn" : "Btn_Tbr_Fill & Sign"]) } else if (type == .redact) { FMTrackEventManager.defaultManager.trackEvent(event: "Tbr", withProperties: ["Tbr_Btn" : "Btn_Tbr_Redact"]) } } func showPDFLayoutModeAction(show: Bool) { self.delegate?.showPDFLayoutModeAction?(show: show) } func toolbarViewController(_ viewController: KMToolbarViewController, clickChaildToolType: KMToolbarType, toolbar toolbarItem: KMToolbarItemView) { if (clickChaildToolType == .crop) { let titles = [NSLocalizedString("Crop Current Page - White Margins", comment: ""), NSLocalizedString("Crop All Pages - Auto", comment: "")] let vc: KMHomePopViewController = KMHomePopViewController().initWithPopViewDataArr(titles) let createFilePopover: NSPopover = NSPopover.init() createFilePopover.contentViewController = vc createFilePopover.animates = true createFilePopover.behavior = .transient createFilePopover.setValue(true, forKey: "shouldHideAnchor") createFilePopover.show(relativeTo: NSZeroRect, of: toolbarItem, preferredEdge: .maxY) self.popover = createFilePopover vc.downCallback = { [weak self] (downEntered: Bool, count: String) -> Void in self?.popover?.close() self?.popover = nil if downEntered { if (count == titles.first) { self?.delegate?.clickChildTool?(type: .crop, index: 1) } else { self?.delegate?.clickChildTool?(type: .crop, index: 2) } } } } else if (clickChaildToolType == .bates || clickChaildToolType == .headerAndFooter || clickChaildToolType == .background || clickChaildToolType == .watermark) { toolbarItem.isSelected = false self.delegate?.clickChildTool?(type: clickChaildToolType, index: 0) } else if (clickChaildToolType == .redact) { toolbarItem.isSelected = false self.enterRedact() } else if (clickChaildToolType == .compress) { self.delegate?.clickChildTool?(type: .compress, index: 0) } else if (clickChaildToolType == .secure) { // toolbarItem.isSelected = fals let titles = [NSLocalizedString("Set Passwords", comment: ""), NSLocalizedString("Remove Security", comment: "")] let vc: KMHomePopViewController = KMHomePopViewController().initWithPopViewDataArr(titles) let createFilePopover: NSPopover = NSPopover.init() createFilePopover.contentViewController = vc createFilePopover.animates = true createFilePopover.behavior = .transient createFilePopover.setValue(true, forKey: "shouldHideAnchor") createFilePopover.show(relativeTo: CGRect(x: toolbarItem.bounds.origin.x, y: 10, width: toolbarItem.bounds.size.width, height: toolbarItem.bounds.size.height), of: toolbarItem, preferredEdge: .minY) vc.downCallback = { [weak self] (downEntered: Bool, count: String) -> Void in if downEntered { if (count == titles.first) { self?.delegate?.clickChildTool?(type: .secure, index: 1) } else { self?.delegate?.clickChildTool?(type: .secure, index: 2) } } } } else if ((KMToolbarType.word.rawValue ... KMToolbarType.conversion_imageToPDF.rawValue).contains(clickChaildToolType.rawValue)) { /// 转档 self.delegate?.clickChildTool?(type: clickChaildToolType, index: 0) } else if (clickChaildToolType == .merge) { self.delegate?.clickChildTool?(type: clickChaildToolType, index: 0) } } func toolbarViewController(_ viewController: KMToolbarViewController, zoomModel selectedTag: Int) { self.delegate?.toolbarViewController?(viewController, zoomModel: selectedTag) } func toolbarViewController(_ viewController:KMToolbarViewController, zoomSting : String) { self.delegate?.toolbarViewController?(viewController, zoomSting: zoomSting) } func changePDFViewZoomInAction() { self.delegate?.changePDFViewZoomInAction?() } func changePDFViewZoomOutAction() { self.delegate?.changePDFViewZoomOutAction?() } func changePDFViewGotoNextPageAction() { self.delegate?.changePDFViewGotoNextPageAction?() } func changePDFViewGoToPreviousPageAction() { self.delegate?.changePDFViewGoToPreviousPageAction?() } func changePDFViewGotoBackAction() { self.delegate?.changePDFViewGotoBackAction?() } func changePDFViewGoToForwardAction() { self.delegate?.changePDFViewGoToForwardAction?() } func aiTranslationPDFFileAction() { self.delegate?.aiTranslationPDFFileAction?() } func toolbarViewController(_ viewController: KMToolbarViewController, shareAction toolbarItem: KMToolbarItemView) { self.delegate?.toolbarViewController?(viewController, shareAction: toolbarItem) } func toolbarViewController(_ viewController: KMToolbarViewController, shareDocument item: NSMenuItem) { self.delegate?.toolbarViewController?(viewController, shareDocument: item) } func toolbarViewController(_ viewController: KMToolbarViewController, shareFlatten item: NSMenuItem) { self.delegate?.toolbarViewController?(viewController, shareFlatten: item) } func toolbarViewController(_ viewController: KMToolbarViewController, shareOriginalPDF item: NSMenuItem) { self.delegate?.toolbarViewController?(viewController, shareOriginalPDF: item) } func toolbarViewController(_ viewController: KMToolbarViewController, scanOCRModel selectedTag: Int) { self.delegate?.toolbarViewController?(viewController, scanOCRModel: selectedTag) } func toolbarViewController(_ viewController: KMToolbarViewController, itemDidClick toolbarItem: KMToolbarItemView) { let itemIdentifier = toolbarItem.itemIdentifier if itemIdentifier != KMRightControlToolbarItemIdentifier { if self.lastItemBox != nil { if (toolbarItem.isSelected) { // no nothings } else { let p_itemIdentifier = parentIdentifier(itemIdentifier ?? "") if p_itemIdentifier != self.lastItemBox.itemIdentifier { self.lastItemBox.isSelected = false } } } } if toolbarItem.itemIdentifier != KMDocumentRedactToolbarItemIdentifier { // 标记秘文 let mainC = self.delegate as? KMMainViewController var control: KMPDFRedactViewController? for childC in mainC?.children ?? [] { if (childC.isKind(of: KMPDFRedactViewController.self)) { control = (childC as! KMPDFRedactViewController) break } } if let annos = control?.redactPdfView.newAddAnnotation, annos.count > 0 { let alert = NSAlert() alert.informativeText = KMLocalizedString("There are unapplied redactions in this file. Exit will not save redaction.", nil) alert.addButton(withTitle: KMLocalizedString("Exit", nil)) alert.addButton(withTitle: KMLocalizedString("Cancel", nil)) let resp = alert.runModal() if resp != .alertFirstButtonReturn { // 取消 return } control?.redactPdfView.newAddAnnotation.removeAll() } } self.delegate?.toolbarViewController?(viewController, itemDidClick: toolbarItem) } func toolbarViewController(_ viewController: KMToolbarViewController, searchAction searchString: String, forward: Bool) { self.delegate?.toolbarViewController?(viewController, searchAction: searchString, forward: forward) } func toolbarViewController(_ viewController: KMToolbarViewController, findSearchAction searchString: String, forward: Bool) { self.delegate?.toolbarViewController?(viewController, findSearchAction: searchString, forward: forward) } func toolbarViewController(_ viewController: KMToolbarViewController, findSearchAllAction searchString: String, forward: Bool) { self.delegate?.toolbarViewController?(viewController, findSearchAllAction: searchString, forward: forward) } func toolbarViewController(_ viewController: KMToolbarViewController, menuItemDidClick toolbarItem: KMToolbarItemView, index: Int, info: Any?) { let itemIdentifier = toolbarItem.itemIdentifier if itemIdentifier != KMRightControlToolbarItemIdentifier { if self.lastItemBox != nil { if (toolbarItem.isSelected) { // no nothings } else { let p_itemIdentifier = parentIdentifier(itemIdentifier ?? "") if p_itemIdentifier != self.lastItemBox.itemIdentifier { self.lastItemBox.isSelected = false } } } } if toolbarItem.itemIdentifier != KMDocumentRedactToolbarItemIdentifier { // 标记秘文 let mainC = self.delegate as? KMMainViewController var control: KMPDFRedactViewController? for childC in mainC?.children ?? [] { if (childC.isKind(of: KMPDFRedactViewController.self)) { control = (childC as! KMPDFRedactViewController) break } } if let annos = control?.redactPdfView.newAddAnnotation, annos.count > 0 { let alert = NSAlert() alert.informativeText = KMLocalizedString("There are unapplied redactions in this file. Exit will not save redaction.", nil) alert.addButton(withTitle: KMLocalizedString("Exit", nil)) alert.addButton(withTitle: KMLocalizedString("Cancel", nil)) let resp = alert.runModal() if resp != .alertFirstButtonReturn { // 取消 return } control?.redactPdfView.newAddAnnotation.removeAll() } } self.delegate?.toolbarViewController?(viewController, menuItemDidClick: toolbarItem, index: index, info: info) } func toolbarViewController(_ viewController: KMToolbarViewController, viewItemDidClick toolbarItem: KMToolbarItemView, index: Int, info: Any?) { self.delegate?.toolbarViewController?(viewController, viewItemDidClick: toolbarItem, index: index, info: info) } } extension KMToolbarController { func updataItemVisible() { guard let isCompareModel = self.mainViewController?.isCompareModel else { return } if isCompareModel { self.toolbarType = .None self.mainToolBarView?.isEnable(isEnable: false) } else { self.mainToolBarView?.isEnable() } } }