123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138 |
- //
- // KMPDFAnnotationChoiceWidgetSub.swift
- // PDF Reader Pro
- //
- // Created by wanjun on 2024/1/31.
- //
- import Cocoa
- class KMPDFAnnotationChoiceWidgetSub: CPDFChoiceWidgetAnnotation {
- var formType: CAnnotationType = .unkown
-
- override func draw(with box: CPDFDisplayBox, in context: CGContext!) {
- let listChoice: Bool = isListChoice
- if listChoice {
- if hasAppearanceStream() {
- super.draw(with: box, in: context)
- } else {
- super.draw(with: box, in: context)
- transformContext(for: page, displayBox: box)
-
- context.setStrokeColor(red: 0, green: 0, blue: 0, alpha: 1.0)
- context.setLineWidth(1.0)
- context.addRect(CGRect(x: bounds.origin.x, y: bounds.origin.y, width: bounds.size.width, height: bounds.size.height))
- context.strokePath()
- }
- } else {
- if hasAppearanceStream() {
- super.draw(with: box, in: context)
- } else {
- var stabilizeHeight = bounds.size.height
- if stabilizeHeight > 25.0 {
- stabilizeHeight = 25.0
- }
- var actualRect = CGRect.zero
- actualRect = CGRect(x: bounds.origin.x, y: bounds.minY + (bounds.height - stabilizeHeight) / 2, width: bounds.size.width, height: stabilizeHeight)
-
- let borderWidth: CGFloat = 0.5
- var rightPartWidthChangePointValue = bounds.size.width / 2
- if rightPartWidthChangePointValue > 30 {
- rightPartWidthChangePointValue = 30
- }
- let radius: CGFloat = 2.0
-
- // 画外框
- context.saveGState()
- context.move(to: CGPoint(x: actualRect.maxX - rightPartWidthChangePointValue, y: actualRect.minY + borderWidth))
- context.addLine(to: CGPoint(x: actualRect.minX + borderWidth, y: actualRect.minY + borderWidth))
- context.addLine(to: CGPoint(x: actualRect.minX + borderWidth, y: actualRect.maxY - borderWidth))
- context.addLine(to: CGPoint(x: actualRect.maxX - rightPartWidthChangePointValue + 2 * borderWidth, y: actualRect.maxY - borderWidth))
- context.addLine(to: CGPoint(x: actualRect.maxX - rightPartWidthChangePointValue + 2 * borderWidth, y: actualRect.minY + borderWidth))
- context.setStrokeColor(NSColor.lightGray.cgColor)
- context.setLineWidth(borderWidth)
- context.setFillColor(self.backgroundColor.cgColor)
- context.drawPath(using: .fillStroke)
- context.restoreGState()
-
- context.saveGState()
- context.move(to: CGPoint(x: actualRect.maxX - rightPartWidthChangePointValue, y: actualRect.maxY))
- context.addLine(to: CGPoint(x: actualRect.maxX - rightPartWidthChangePointValue, y: actualRect.minY))
- context.addLine(to: CGPoint(x: actualRect.maxX - radius, y: actualRect.minY))
- context.addArc(center: CGPoint(x: actualRect.maxX - radius, y: actualRect.minY + radius), radius: radius, startAngle: CGFloat(3 * Double.pi / 2), endAngle: CGFloat(2 * Double.pi), clockwise: false)
- context.addLine(to: CGPoint(x: actualRect.maxX, y: actualRect.maxY - radius))
- context.addArc(center: CGPoint(x: actualRect.maxX - radius, y: actualRect.maxY - radius), radius: radius, startAngle: CGFloat(2 * Double.pi), endAngle: CGFloat(Double.pi / 2), clockwise: false)
- context.addLine(to: CGPoint(x: actualRect.maxX - rightPartWidthChangePointValue, y: actualRect.maxY))
- context.setFillColor(NSColor(red: 37/255.0, green: 139/255.0, blue: 251/255.0, alpha: 1.0).cgColor)
- context.drawPath(using: .fill)
- context.restoreGState()
-
- // 画等边三角形
- let triangleWidth = min(rightPartWidthChangePointValue, actualRect.height) / 2.0
- let triangleHeight = triangleWidth * sqrt(3.0) / 2
- let centerPointUpGap = triangleHeight / 3.0
-
- context.saveGState()
- let startPointX = actualRect.maxX - rightPartWidthChangePointValue + (rightPartWidthChangePointValue - triangleWidth) / 2
- let startPointY = actualRect.midY + centerPointUpGap
- context.move(to: CGPoint(x: startPointX, y: startPointY))
- context.addLine(to: CGPoint(x: startPointX + triangleWidth, y: startPointY))
- context.addLine(to: CGPoint(x: startPointX + triangleWidth / 2.0, y: actualRect.midY - 2 * centerPointUpGap))
- context.closePath()
- context.setFillColor(NSColor.white.cgColor)
- context.drawPath(using: .fill)
- context.restoreGState()
-
- context.saveGState()
- // 画文字
- var attributes = [NSAttributedString.Key: Any]()
- if let font = self.font {
- attributes[.font] = font
- }
- if let fontColor = self.fontColor {
- attributes[.foregroundColor] = fontColor
- }
- let stringRect = self.string().boundingRect(with: CGSize(width: actualRect.size.width - rightPartWidthChangePointValue, height: actualRect.size.height), options: .usesLineFragmentOrigin, attributes: attributes)
-
- self.string().draw(in: CGRect(x: actualRect.origin.x, y: (actualRect.size.height - stringRect.size.height) / 2 + actualRect.origin.y, width: stringRect.size.width, height: stringRect.size.height), withAttributes: attributes)
- // context.restoreGState()
- }
- }
- }
-
- func transformContext(for page: CPDFPage, displayBox box: CPDFDisplayBox) {
- var transform = NSAffineTransform()
- // Identity.
- transform = NSAffineTransform()
- // Bounds for page.
- let boxRect = page.bounds(for: box)
- // Handle rotation.
- let rotation = page.rotation
- switch rotation {
- case 90:
- transform.rotate(byDegrees: -90)
- transform.translateX(by: -boxRect.size.width, yBy: 0.0)
- case 180:
- transform.rotate(byDegrees: 180)
- transform.translateX(by: -boxRect.size.width, yBy: -boxRect.size.height)
- case 270:
- transform.rotate(byDegrees: 90)
- transform.translateX(by: 0.0, yBy: -boxRect.size.height)
- default:
- break
- }
- // Origin.
- transform.translateX(by: -boxRect.origin.x, yBy: -boxRect.origin.y)
- // Concatenate.
- transform.concat()
- }
- func keysForValuesToObserveForUndo() -> Set<String> {
- return []
- }
- }
|