// // KMPageIndicator.swift // PDF Reader Pro // // Created by tangchao on 2023/10/10. // import Cocoa @objc(TCPageIndicatorDelegate) protocol KMPageIndicatorDelegate: AnyObject { func pageIndicator(_ pageIndicator: KMPageIndicator, didSelectPageAt index: UInt) } @objc (TCPageIndicator) @objcMembers class KMPageIndicator: NSView { weak var delegate: KMPageIndicatorDelegate? var selectedColor: NSColor? var normalColor: NSColor? var indicatorMargin: CGFloat = 8.0 { didSet { self.needsDisplay = true } } var currentPage: UInt = 0 { didSet { self.needsDisplay = true } } var numberOfPages: UInt = 0 { didSet { self.needsDisplay = true } } var pageIndicatorSize: NSSize = CGSizeMake(6, 6) { didSet { self.needsDisplay = true } } // 是否响应事件 [默认为 YES ] var enabled = true private var _indicatorRects: [NSValue]? override init(frame frameRect: NSRect) { super.init(frame: frameRect) self.initDefaultValue() } required init?(coder: NSCoder) { super.init(coder: coder) self.initDefaultValue() } func initDefaultValue() { self.selectedColor = NSColor.gray self.normalColor = NSColor.gray.withAlphaComponent(0.5) self._indicatorRects = [NSValue](repeating: NSValue(rect: NSZeroRect), count: 10) } override func draw(_ dirtyRect: NSRect) { super.draw(dirtyRect) var indicatorAreaWidth = 0.0 if (self.numberOfPages > 0) { indicatorAreaWidth = self.pageIndicatorSize.width * self.numberOfPages.cgFloat + self.indicatorMargin * (self.numberOfPages-1).cgFloat } var leftPosition = (self.bounds.size.width - indicatorAreaWidth) * 0.5 let topPadding = (self.bounds.size.height - self.pageIndicatorSize.height) * 0.5 self._indicatorRects?.removeAll() for i in 0 ..< self.numberOfPages { let position = NSMakePoint(leftPosition, topPadding) let rect = CGRectMake(position.x, position.y, self.pageIndicatorSize.width, self.pageIndicatorSize.height) self._indicatorRects?.append(NSValue(rect: rect)) let path = NSBezierPath(ovalIn: rect) if (self.currentPage == i) { self.selectedColor?.setFill() } else { self.normalColor?.setFill() } path.fill() leftPosition += (self.pageIndicatorSize.width + self.indicatorMargin) } } override func mouseDown(with event: NSEvent) { super.mouseDown(with: event) if (self.enabled == false) { return } let eventLocation = event.locationInWindow /// 转换成视图的本地坐标 let pointInView = self.convert(eventLocation, from: nil) for i in 0 ..< self.numberOfPages { if let datas = self._indicatorRects { let rect = CGRectInset(datas[Int(i)].rectValue, -2, -2) if (NSPointInRect(pointInView, rect)) { self.currentPage = i self.delegate?.pageIndicator(self, didSelectPageAt: i) } } } } }