CPDFEditToolBar.swift 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345
  1. //
  2. // CPDFEditToolBar.swift
  3. // ComPDFKit_Tools
  4. //
  5. // Copyright © 2014-2024 PDF Technologies, Inc. All Rights Reserved.
  6. //
  7. // THIS SOURCE CODE AND ANY ACCOMPANYING DOCUMENTATION ARE PROTECTED BY INTERNATIONAL COPYRIGHT LAW
  8. // AND MAY NOT BE RESOLD OR REDISTRIBUTED. USAGE IS BOUND TO THE ComPDFKit LICENSE AGREEMENT.
  9. // UNAUTHORIZED REPRODUCTION OR DISTRIBUTION IS SUBJECT TO CIVIL AND CRIMINAL PENALTIES.
  10. // This notice may not be removed from this file.
  11. //
  12. import UIKit
  13. import ComPDFKit
  14. public enum CPDFEditMode: UInt {
  15. case text
  16. case image
  17. case all
  18. }
  19. public enum CPDFEditToolMode: UInt {
  20. case setting
  21. case undo
  22. case redo
  23. }
  24. @objc public protocol CPDFEditToolBarDelegate: AnyObject {
  25. @objc optional func editClick(in toolBar: CPDFEditToolBar, editMode mode: Int)
  26. @objc optional func propertyEditDidClick(in toolBar: CPDFEditToolBar)
  27. @objc optional func redoDidClick(in toolBar: CPDFEditToolBar)
  28. @objc optional func undoDidClick(in toolBar: CPDFEditToolBar)
  29. }
  30. public class CPDFEditToolBar: UIView {
  31. public weak var delegate: CPDFEditToolBarDelegate?
  32. public var pdfView: CPDFListView?
  33. public var contentEditorTypes: [CPDFEditMode] = []
  34. public var undoButton: UIButton?
  35. public var redoButton: UIButton?
  36. public var propertyButton: UIButton?
  37. public var textEditButton: UIButton?
  38. public var imageEditButton: UIButton?
  39. public var leftView: UIView?
  40. public var rightView: UIView?
  41. public var splitView: UIView?
  42. public var editToolBarSelectType: CPDFEditMode = .all
  43. required init?(coder: NSCoder) {
  44. fatalError("init(coder:) has not been implemented")
  45. }
  46. public init(pdfView: CPDFListView) {
  47. super.init(frame: CGRect.zero)
  48. self.pdfView = pdfView
  49. self.setUp()
  50. NotificationCenter.default.addObserver(self, selector: #selector(pageChangedNotification(_:)), name: NSNotification.Name.CPDFViewPageChanged, object: nil)
  51. NotificationCenter.default.addObserver(self, selector: #selector(pageEditingDidChanged(_:)), name: NSNotification.Name.CPDFPageEditingDidChanged, object: nil)
  52. }
  53. public override func layoutSubviews() {
  54. super.layoutSubviews()
  55. rightView?.frame = CGRect(x: self.bounds.size.width - (rightView?.frame.size.width ?? 0), y: 0, width: (rightView?.frame.size.width ?? 0), height: 44)
  56. leftView?.frame = CGRect(x: 0, y: 0, width: self.bounds.size.width - (rightView?.frame.size.width ?? 0), height: 44)
  57. if contentEditorTypes.count > 0 {
  58. let with = ((leftView?.bounds.width ?? 0) - (30 * CGFloat(contentEditorTypes.count))) / CGFloat(contentEditorTypes.count + 1)
  59. var x: CGFloat = with
  60. for contentEditorType in contentEditorTypes {
  61. switch contentEditorType {
  62. case .text:
  63. textEditButton?.frame = CGRect(x:x, y: textEditButton?.frame.origin.y ?? 0, width: textEditButton?.frame.size.width ?? 0, height: textEditButton?.frame.size.height ?? 0)
  64. x = x + (textEditButton?.frame.size.width ?? 0) + with
  65. case .image:
  66. imageEditButton?.frame = CGRect(x: x, y: imageEditButton?.frame.origin.y ?? 0, width: imageEditButton?.frame.size.width ?? 0, height: imageEditButton?.frame.size.height ?? 0)
  67. x = x + (imageEditButton?.frame.size.width ?? 0) + with
  68. case .all:
  69. break
  70. }
  71. }
  72. }
  73. }
  74. func removeViews() {
  75. if((self.leftView) != nil) {
  76. self.leftView?.removeFromSuperview()
  77. }
  78. if((self.rightView) != nil) {
  79. self.rightView?.removeFromSuperview()
  80. }
  81. if((self.splitView) != nil) {
  82. self.splitView?.removeFromSuperview()
  83. }
  84. }
  85. func setUp() {
  86. contentEditorTypes = self.pdfView?.configuration?.contentEditorTypes ?? []
  87. let contentEditorTools = self.pdfView?.configuration?.contentEditorTools ?? []
  88. leftView = UIView(frame: CGRect(x: 0, y: 0, width: 110, height: 44))
  89. if contentEditorTypes.count > 0 {
  90. for contentEditorType in contentEditorTypes {
  91. switch contentEditorType {
  92. case .text:
  93. textEditButton = UIButton(frame: CGRect(x: 10, y: 7, width: 30, height: 30))
  94. textEditButton?.addTarget(self, action: #selector(textEditAction(_:)), for: .touchUpInside)
  95. textEditButton?.setImage(UIImage(named: "CPDFEditAddText", in: Bundle(for: type(of: self)), compatibleWith: nil), for: .normal)
  96. if(textEditButton != nil) {
  97. leftView?.addSubview(textEditButton!)
  98. }
  99. case .image:
  100. imageEditButton = UIButton(frame: CGRect(x: 10, y: 7, width: 30, height: 30))
  101. imageEditButton?.addTarget(self, action: #selector(imageEditAction(_:)), for: .touchUpInside)
  102. imageEditButton?.setImage(UIImage(named: "CPDFEditAddImage", in: Bundle(for: type(of: self)), compatibleWith: nil), for: .normal)
  103. if(imageEditButton != nil) {
  104. leftView?.addSubview(imageEditButton!)
  105. }
  106. default:
  107. break
  108. }
  109. }
  110. }
  111. if(leftView != nil) {
  112. self.addSubview(leftView!)
  113. }
  114. if contentEditorTools.count > 0 {
  115. var offset: CGFloat = 10
  116. let buttonSize: CGFloat = 30
  117. let prWidth = buttonSize * CGFloat(contentEditorTools.count) + offset
  118. rightView = UIView(frame: CGRect(x: self.bounds.size.width - prWidth, y: 0, width: prWidth, height: 44))
  119. if(rightView != nil) {
  120. self.addSubview(rightView!)
  121. }
  122. let lineView = UIView(frame: CGRect(x: 10, y: 12, width: 1, height: 20))
  123. if #available(iOS 13.0, *) {
  124. if UITraitCollection.current.userInterfaceStyle == .dark {
  125. lineView.backgroundColor = UIColor.white
  126. } else {
  127. lineView.backgroundColor = UIColor(red: 0, green: 0, blue: 0, alpha: 0.1)
  128. }
  129. } else {
  130. lineView.backgroundColor = UIColor.black
  131. }
  132. rightView?.addSubview(lineView)
  133. offset += lineView.frame.size.width
  134. for contentEditorTool in contentEditorTools {
  135. switch contentEditorTool {
  136. case .setting:
  137. propertyButton = UIButton(frame: CGRect(x: offset, y: 7, width: 30, height: 30))
  138. propertyButton?.setImage(UIImage(named: "CPDFAnnotationBarImageProperties", in: Bundle(for: self.classForCoder), compatibleWith: nil), for: .normal)
  139. propertyButton?.addTarget(self, action: #selector(propertyAction(_:)), for: .touchUpInside)
  140. if(propertyButton != nil) {
  141. rightView?.addSubview(propertyButton!)
  142. }
  143. offset += propertyButton?.frame.size.width ?? 0
  144. case .undo:
  145. undoButton = UIButton(frame: CGRect(x: offset, y: 7, width: 30, height: 30))
  146. undoButton?.addTarget(self, action: #selector(undoAction(_:)), for: .touchUpInside)
  147. undoButton?.setImage(UIImage(named: "CPDFAnnotationBarImageUndo", in: Bundle(for: self.classForCoder), compatibleWith: nil), for: .normal)
  148. if(undoButton != nil) {
  149. rightView?.addSubview(undoButton!)
  150. }
  151. offset += undoButton?.frame.size.width ?? 0
  152. case .redo:
  153. redoButton = UIButton(frame: CGRect(x: offset, y: 7, width: 30, height: 30))
  154. redoButton?.addTarget(self, action: #selector(redoAction(_:)), for: .touchUpInside)
  155. redoButton?.setImage(UIImage(named: "CPDFAnnotationBarImageRedo", in: Bundle(for: self.classForCoder), compatibleWith: nil), for: .normal)
  156. if(redoButton != nil) {
  157. rightView?.addSubview(redoButton!)
  158. }
  159. offset += redoButton?.frame.size.width ?? 0
  160. }
  161. }
  162. }
  163. self.backgroundColor = UIColor(red: 0.98, green: 0.99, blue: 1.0, alpha: 1.0)
  164. self.updateButtonState()
  165. self.backgroundColor = CPDFColorUtils.CPDFViewControllerBackgroundColor()
  166. editToolBarSelectType = .all
  167. }
  168. @objc func textEditAction(_ sender: UIButton) {
  169. self.textEditButton?.isSelected = !(self.textEditButton?.isSelected ?? false)
  170. if self.textEditButton?.isSelected == true {
  171. self.imageEditButton?.isSelected = false
  172. self.imageEditButton?.backgroundColor = UIColor.clear
  173. }
  174. if sender.isSelected == false && self.imageEditButton?.isSelected == false {
  175. self.pdfView?.changeEditingLoadType([.text, .image])
  176. self.pdfView?.setShouAddEdit([])
  177. self.delegate?.editClick?(in: self, editMode:2)
  178. self.editToolBarSelectType = .all
  179. } else {
  180. self.pdfView?.changeEditingLoadType(.text)
  181. self.pdfView?.setShouAddEdit(.text)
  182. self.delegate?.editClick?(in: self, editMode: 0)
  183. self.editToolBarSelectType = .text
  184. }
  185. updateButtonState()
  186. if sender.isSelected {
  187. self.textEditButton?.backgroundColor = UIColor(red: 221/255, green: 233/255, blue: 255/255, alpha: 1)
  188. } else {
  189. self.textEditButton?.backgroundColor = UIColor.clear
  190. }
  191. }
  192. @objc func imageEditAction(_ sender: UIButton) {
  193. self.imageEditButton?.isSelected = !(self.imageEditButton?.isSelected ?? false)
  194. if self.imageEditButton?.isSelected == true {
  195. self.textEditButton?.isSelected = false
  196. self.textEditButton?.backgroundColor = UIColor.clear
  197. }
  198. if sender.isSelected == false && self.textEditButton?.isSelected == false {
  199. self.pdfView?.changeEditingLoadType([.text, .image])
  200. self.pdfView?.setShouAddEdit([])
  201. self.delegate?.editClick?(in: self, editMode: 2)
  202. self.editToolBarSelectType = .all
  203. } else {
  204. self.pdfView?.changeEditingLoadType(.image)
  205. self.pdfView?.setShouAddEdit(.image)
  206. self.delegate?.editClick?(in: self, editMode: 1)
  207. self.editToolBarSelectType = .image
  208. }
  209. updateButtonState()
  210. if sender.isSelected {
  211. self.imageEditButton?.backgroundColor = UIColor(red: 221/255, green: 233/255, blue: 255/255, alpha: 1)
  212. } else {
  213. self.imageEditButton?.backgroundColor = UIColor.clear
  214. }
  215. }
  216. @objc func redoAction(_ sender: UIButton) {
  217. self.delegate?.redoDidClick?(in: self)
  218. }
  219. @objc func undoAction(_ sender: UIButton) {
  220. self.delegate?.undoDidClick?(in: self)
  221. }
  222. @objc func propertyAction(_ sender: UIButton) {
  223. self.delegate?.propertyEditDidClick?(in: self)
  224. }
  225. public func updateButtonState() {
  226. if self.pdfView?.editingLoadType == .text {
  227. // Text
  228. self.textEditButton?.isSelected = true
  229. self.imageEditButton?.isSelected = false
  230. } else if self.pdfView?.editingLoadType == .image {
  231. self.textEditButton?.isSelected = false
  232. self.imageEditButton?.isSelected = true
  233. } else {
  234. self.textEditButton?.isSelected = false
  235. self.imageEditButton?.isSelected = false
  236. }
  237. if self.textEditButton?.isSelected == true {
  238. self.textEditButton?.backgroundColor = UIColor(red: 221/255, green: 233/255, blue: 255/255, alpha: 1)
  239. } else {
  240. self.textEditButton?.backgroundColor = UIColor.clear
  241. }
  242. if self.imageEditButton?.isSelected == true {
  243. self.imageEditButton?.backgroundColor = UIColor(red: 221/255, green: 233/255, blue: 255/255, alpha: 1)
  244. } else {
  245. self.imageEditButton?.backgroundColor = UIColor.clear
  246. }
  247. let stayy = self.pdfView?.editStatus()
  248. if self.pdfView?.shouAddEditAreaType() == .text {
  249. self.propertyButton?.isEnabled = true
  250. } else if stayy == .empty {
  251. self.propertyButton?.isEnabled = false
  252. } else {
  253. self.propertyButton?.isEnabled = true
  254. }
  255. if ((self.pdfView?.canEditTextRedo()) == true) {
  256. self.redoButton?.isEnabled = true
  257. } else {
  258. self.redoButton?.isEnabled = false
  259. }
  260. if ((self.pdfView?.canEditTextUndo()) == true) {
  261. self.undoButton?.isEnabled = true
  262. } else {
  263. self.undoButton?.isEnabled = false
  264. }
  265. }
  266. @objc func pageChangedNotification(_ notification: Notification) {
  267. guard let pdfview = notification.object as? CPDFView else {
  268. return
  269. }
  270. if pdfview.document == self.pdfView?.document {
  271. updateButtonState()
  272. }
  273. }
  274. @objc func pageEditingDidChanged(_ notification: Notification) {
  275. guard let page = notification.object as? CPDFPage else {
  276. return
  277. }
  278. if page.document == self.pdfView?.document {
  279. updateButtonState()
  280. }
  281. }
  282. }