ComponentButton.swift 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328
  1. //
  2. // ComponentButton.swift
  3. // KMComponentLibrary
  4. //
  5. // Created by Niehaoyu on 2024/8/22.
  6. //
  7. import Cocoa
  8. import AppKit
  9. public class ComponentButton: ComponentBaseXibView {
  10. @IBOutlet var contendBox: NSBox!
  11. @IBOutlet var leftIcon: NSImageView!
  12. @IBOutlet var label: NSTextField!
  13. @IBOutlet var rightIcon: NSImageView!
  14. @IBOutlet var leftImgLeftConst: NSLayoutConstraint!
  15. @IBOutlet var leftImgWidthConst: NSLayoutConstraint!
  16. @IBOutlet var rightImgWidthConst: NSLayoutConstraint!
  17. @IBOutlet var rightImgRightConst: NSLayoutConstraint!
  18. // MARK: Private Property
  19. private var _properties : ComponentButtonProperty = ComponentButtonProperty()
  20. private var _toolTip: String = "" // 提示文字
  21. private var action: Selector? // 点击事件
  22. private weak var target: AnyObject? // 对象目标
  23. private var mouseDownEnable: Bool = false
  24. open var keyEquivalent: String = ""
  25. open var keyEquivalentModifierMask: NSEvent.ModifierFlags = NSEvent.ModifierFlags()
  26. // MARK: - 初始化
  27. public required init?(coder decoder: NSCoder) {
  28. super.init(coder: decoder)
  29. }
  30. override init(frame frameRect: NSRect) {
  31. super.init(frame: frameRect)
  32. }
  33. public override func awakeFromNib() {
  34. super.awakeFromNib()
  35. label.wantsLayer = true
  36. }
  37. // MARK: - Set & Get
  38. public var properties : ComponentButtonProperty {
  39. get {
  40. return _properties
  41. }
  42. set {
  43. _properties = newValue
  44. ComponentLibrary.shared.configButtonComponent(properties: _properties)
  45. reloadData()
  46. }
  47. }
  48. //MARK: - setupUI
  49. func setupUI() {
  50. leftIcon.isHidden = true
  51. label.isHidden = true
  52. rightIcon.isHidden = true
  53. if properties.onlyIcon == true {
  54. leftIcon.isHidden = false
  55. } else {
  56. label.isHidden = false
  57. if properties.showLeftIcon == true &&
  58. properties.showRightIcon == true {
  59. leftIcon.isHidden = false
  60. rightIcon.isHidden = false
  61. } else if properties.showLeftIcon == true &&
  62. properties.showRightIcon == false {
  63. leftIcon.isHidden = false
  64. } else if properties.showLeftIcon == false &&
  65. properties.showRightIcon == true {
  66. rightIcon.isHidden = false
  67. } else {
  68. }
  69. }
  70. }
  71. func refreshUI() {
  72. var fillColor = properties.propertyInfo.color_nor
  73. var borderWidth = properties.propertyInfo.borderWidth
  74. var borderColor = properties.propertyInfo.borderColor_nor
  75. var textColor = properties.propertyInfo.textColor
  76. var leftImage = properties.icon
  77. var rightImage = properties.icon
  78. if properties.state == .normal {
  79. if let image = properties.propertyInfo.leftIcon_nor {
  80. leftImage = image
  81. }
  82. if let image = properties.propertyInfo.rightIcon_nor {
  83. rightImage = image
  84. }
  85. } else if properties.state == .hover {
  86. fillColor = properties.propertyInfo.color_hov
  87. borderWidth = properties.propertyInfo.borderWidth_hov
  88. borderColor = properties.propertyInfo.borderColor_hov
  89. textColor = properties.propertyInfo.textColor_hov
  90. if let image = properties.propertyInfo.leftIcon_hov {
  91. leftImage = image
  92. }
  93. if let image = properties.propertyInfo.rightIcon_hov {
  94. rightImage = image
  95. }
  96. } else if properties.state == .pressed {
  97. fillColor = properties.propertyInfo.color_active
  98. borderWidth = properties.propertyInfo.borderWidth_active
  99. borderColor = properties.propertyInfo.borderColor_active
  100. textColor = properties.propertyInfo.textColor_Active
  101. if let image = properties.propertyInfo.leftIcon_press {
  102. leftImage = image
  103. }
  104. if let image = properties.propertyInfo.rightIcon_press {
  105. rightImage = image
  106. }
  107. }
  108. if properties.isDisabled == true {
  109. fillColor = properties.propertyInfo.color_dis
  110. borderWidth = properties.propertyInfo.borderWidth
  111. borderColor = properties.propertyInfo.borderColor_dis
  112. textColor = properties.propertyInfo.textColor_dis
  113. if let image = properties.propertyInfo.leftIcon_dis {
  114. leftImage = image
  115. } else {
  116. if let image = properties.propertyInfo.leftIcon_nor?.filled(with: textColor) {
  117. leftImage = image
  118. } else if let image = properties.icon?.filled(with: textColor) {
  119. leftImage = image
  120. }
  121. }
  122. if let image = properties.propertyInfo.rightIcon_dis {
  123. rightImage = image
  124. }
  125. }
  126. contendBox.fillColor = fillColor
  127. contendBox.borderColor = borderColor
  128. contendBox.cornerRadius = properties.propertyInfo.cornerRadius
  129. contendBox.borderWidth = borderWidth
  130. label.textColor = textColor
  131. label.font = properties.propertyInfo.textFont
  132. if let image = leftImage {
  133. leftIcon.image = image
  134. }
  135. if let image = rightImage {
  136. rightIcon.image = image
  137. }
  138. label.stringValue = properties.buttonText ?? ""
  139. // let paragraphStyle = NSMutableParagraphStyle()
  140. // paragraphStyle.maximumLineHeight = 24
  141. // if properties.size == .l {
  142. // paragraphStyle.maximumLineHeight = 20
  143. // } else if properties.size == .m {
  144. // paragraphStyle.maximumLineHeight = 18
  145. // } else if properties.size == .s {
  146. // paragraphStyle.maximumLineHeight = 18
  147. // }
  148. // let attributedString = NSAttributedString(string: self.label.stringValue,
  149. // attributes: [.paragraphStyle: paragraphStyle,
  150. // NSAttributedString.Key.font : label.font as Any,
  151. // NSAttributedString.Key.foregroundColor : label.textColor as Any,
  152. //
  153. // ])
  154. // label.attributedStringValue = attributedString
  155. leftImgWidthConst.constant = properties.propertyInfo.imageWidth
  156. rightImgWidthConst.constant = leftImgWidthConst.constant
  157. if properties.onlyIcon == true {
  158. properties.propertyInfo.viewWidth = properties.propertyInfo.viewHeight
  159. let viewWidth = properties.propertyInfo.viewWidth
  160. leftImgLeftConst.constant = (viewWidth - leftImgWidthConst.constant)/2
  161. } else {
  162. let viewWidth = frame.size.width
  163. let imageWidth = properties.propertyInfo.imageWidth
  164. let layoutGap = properties.propertyInfo.layout_gap
  165. label.sizeToFit()
  166. var labelRect = label.frame
  167. labelRect.origin.y = (CGRectGetHeight(frame) - labelRect.size.height)/2
  168. if properties.showLeftIcon == true && properties.showRightIcon == true {
  169. leftIcon.isHidden = false
  170. rightIcon.isHidden = false
  171. labelRect.origin.x = (viewWidth - labelRect.size.width - imageWidth*2 - layoutGap*2)/2.0 + imageWidth + layoutGap
  172. } else if properties.showLeftIcon == true && properties.showRightIcon == false {
  173. leftIcon.isHidden = false
  174. labelRect.origin.x = (viewWidth - labelRect.size.width - imageWidth - layoutGap)/2.0 + imageWidth + layoutGap
  175. } else if properties.showLeftIcon == false && properties.showRightIcon == true {
  176. rightIcon.isHidden = false
  177. labelRect.origin.x = (viewWidth - labelRect.size.width - imageWidth - layoutGap)/2.0
  178. } else {
  179. labelRect.origin.x = (viewWidth - labelRect.size.width)/2.0
  180. }
  181. label.frame = labelRect
  182. leftImgLeftConst.constant = CGRectGetMinX(labelRect) - leftImgWidthConst.constant - layoutGap
  183. rightImgRightConst.constant = frame.size.width - CGRectGetMaxX(labelRect) - leftImgWidthConst.constant - layoutGap
  184. }
  185. leftIcon.autoresizingMask = [.minXMargin, .maxXMargin, .minYMargin, .maxYMargin]
  186. }
  187. public func reloadData() {
  188. DispatchQueue.main.async {
  189. self.setupUI()
  190. self.refreshUI()
  191. }
  192. }
  193. //MARK: - Public Method
  194. public func setTarget(_ target: AnyObject?, action: Selector?) {
  195. self.target = target!
  196. self.action = action!
  197. }
  198. func sizeOfString(_ string: String, _ font: NSFont, _ width: CGFloat) -> (CGSize) {
  199. let paragraphStyle = NSMutableParagraphStyle()
  200. paragraphStyle.lineBreakMode = .byWordWrapping
  201. let attributes: [NSAttributedString.Key: Any] = [
  202. .font: font,
  203. .paragraphStyle:paragraphStyle
  204. ]
  205. let size = (string as NSString).boundingRect(with: NSSize(width: width, height: CGFloat(MAXFLOAT)),
  206. options: .usesLineFragmentOrigin,
  207. attributes: attributes,
  208. context: nil).size
  209. return size
  210. }
  211. //MARK: - MouseEvent
  212. public override func mouseEntered(with event: NSEvent) {
  213. super.mouseEntered(with: event)
  214. if properties.isDisabled == false && properties.state != .pressed {
  215. properties.state = .hover
  216. }
  217. refreshUI()
  218. }
  219. public override func mouseMoved(with event: NSEvent) {
  220. super.mouseMoved(with: event)
  221. }
  222. public override func mouseExited(with event: NSEvent) {
  223. super.mouseExited(with: event)
  224. if properties.isDisabled == false && properties.state != .pressed {
  225. properties.state = .normal
  226. }
  227. refreshUI()
  228. }
  229. public override func mouseDown(with event: NSEvent) {
  230. if properties.isDisabled == false &&
  231. properties.state != .pressed {
  232. properties.state = .pressed
  233. refreshUI()
  234. }
  235. }
  236. public override func mouseUp(with event: NSEvent) {
  237. if properties.isDisabled == false {
  238. if properties.keepPressState == false {
  239. properties.state = .hover
  240. refreshUI()
  241. }
  242. window?.makeFirstResponder(self)
  243. if let target = target, let action = action {
  244. _ = target.perform(action, with: self)
  245. }
  246. }
  247. }
  248. }