diff --git a/MVMCoreUI/Atoms/Views/Arrow.swift b/MVMCoreUI/Atoms/Views/Arrow.swift index 59e6f6f9..7e1a510a 100644 --- a/MVMCoreUI/Atoms/Views/Arrow.swift +++ b/MVMCoreUI/Atoms/Views/Arrow.swift @@ -14,8 +14,10 @@ open class Arrow: View { //-------------------------------------------------- var arrowLayer = CAShapeLayer() - var lineWidth: CGFloat = 1 - var color: UIColor = .black + + public var arrowModel: ArrowModel? { + return model as? ArrowModel + } //-------------------------------------------------- // MARK: - Lifecycle @@ -24,8 +26,8 @@ open class Arrow: View { open override func setupView() { super.setupView() - heightAnchor.constraint(equalToConstant: 12).isActive = true - widthAnchor.constraint(equalToConstant: 12).isActive = true + heightAnchor.constraint(equalToConstant: 40).isActive = true + widthAnchor.constraint(equalToConstant: 40).isActive = true drawShapeLayer() isOpaque = false @@ -33,66 +35,54 @@ open class Arrow: View { arrowLayer.strokeEnd = 1 } - override open func layoutSubviews() { - super.layoutSubviews() - - drawShapeLayer() -// layer.cornerRadius = isRound ? cornerRadiusValue : 0 - } - //-------------------------------------------------- // MARK: - Drawing //-------------------------------------------------- + open override func draw(_ rect: CGRect) { + super.draw(rect) + + arrowLayer.transform = CATransform3DIdentity + drawShapeLayer() + + if let degrees = arrowModel?.degrees { + let radians = CGFloat(degrees * Float.pi / 180) + arrowLayer.transform = CATransform3DMakeRotation(-radians, 0.0, 0.0, 1.0) + } + } + private func drawShapeLayer() { arrowLayer.frame = bounds - arrowLayer.strokeColor = color.cgColor + arrowLayer.strokeColor = arrowModel?.color.cgColor arrowLayer.fillColor = UIColor.clear.cgColor arrowLayer.path = arrowPath() arrowLayer.lineJoin = .miter arrowLayer.lineCap = .butt - arrowLayer.lineWidth = lineWidth + arrowLayer.lineWidth = arrowModel?.lineWidth ?? 1 } private func arrowPath() -> CGPath { - let length = max(bounds.size.height, bounds.size.width) - 1 -// let xInsetLeft = length * 0.25 -// let yInsetTop = length * 0.3 -// let innerWidth = length - (xInsetLeft + length * 0.25) // + Right X Inset -// let innerHeight = length - (yInsetTop + length * 0.35) // + Bottom Y Inset + let length = max(bounds.size.height, bounds.size.width) + let inset = (arrowModel?.lineWidth ?? 1) / 2 + let midLength = length / 2 - var startPoint = CGPoint(x: length * 0.5, y: 1) - let pivotPoint = CGPoint(x: length, y: length * 0.5) - var endPoint = CGPoint(x: length * 0.5, y: length) + var startPoint = CGPoint(x: midLength, y: inset) + let pivotPoint = CGPoint(x: length - inset, y: midLength) + var endPoint = CGPoint(x: midLength, y: length - inset) let bezierPath = UIBezierPath() bezierPath.move(to: startPoint) bezierPath.addLine(to: pivotPoint) bezierPath.addLine(to: endPoint) - startPoint = CGPoint(x: 1, y: length * 0.5) - endPoint = CGPoint(x: length, y: length * 0.5) + startPoint = CGPoint(x: inset, y: midLength) + endPoint = CGPoint(x: length - inset, y: midLength) bezierPath.move(to: startPoint) bezierPath.addLine(to: pivotPoint) return bezierPath.cgPath } - - //-------------------------------------------------- - // MARK: - MVMCoreMoleculeViewProtocol - //-------------------------------------------------- - - public override func setWithModel(_ model: MoleculeModelProtocol?, _ delegateObject: MVMCoreUIDelegateObject?, _ additionalData: [AnyHashable: Any]?) { - guard let model = model as? ArrowModel else { return } - - arrowLayer.transform = CATransform3DIdentity - - if let degrees = model.direction { - let radians = CGFloat(degrees * Double.pi / 180) - arrowLayer.transform = CATransform3DMakeRotation(-radians, 0.0, 0.0, 1.0) - } - } } diff --git a/MVMCoreUI/Atoms/Views/ArrowModel.swift b/MVMCoreUI/Atoms/Views/ArrowModel.swift index 62bf5c05..926a9ea7 100644 --- a/MVMCoreUI/Atoms/Views/ArrowModel.swift +++ b/MVMCoreUI/Atoms/Views/ArrowModel.swift @@ -17,7 +17,8 @@ open class ArrowModel: MoleculeModelProtocol { public var backgroundColor: Color? public var color: Color = Color(uiColor: .mvmBlack) - public var direction: Double? + public var degrees: Float = 0 + public var lineWidth: CGFloat = 1 //-------------------------------------------------- // MARK: - Keys @@ -27,8 +28,9 @@ open class ArrowModel: MoleculeModelProtocol { case moleculeName case backgroundColor case color - case direction + case degrees case size + case lineWidth } //-------------------------------------------------- @@ -37,20 +39,27 @@ open class ArrowModel: MoleculeModelProtocol { required public init(from decoder: Decoder) throws { let typeContainer = try decoder.container(keyedBy: CodingKeys.self) + backgroundColor = try typeContainer.decodeIfPresent(Color.self, forKey: .backgroundColor) if let color = try typeContainer.decodeIfPresent(Color.self, forKey: .color) { self.color = color } - backgroundColor = try typeContainer.decodeIfPresent(Color.self, forKey: .backgroundColor) - direction = try typeContainer.decodeIfPresent(Double.self, forKey: .direction) + if let degrees = try typeContainer.decodeIfPresent(Float.self, forKey: .degrees) { + self.degrees = degrees + } + + if let lineWidth = try typeContainer.decodeIfPresent(CGFloat.self, forKey: .lineWidth) { + self.lineWidth = lineWidth + } } public func encode(to encoder: Encoder) throws { var container = encoder.container(keyedBy: CodingKeys.self) try container.encode(moleculeName, forKey: .moleculeName) - try container.encode(color, forKey: .color) - try container.encode(direction, forKey: .direction) try container.encodeIfPresent(backgroundColor, forKey: .backgroundColor) + try container.encode(color, forKey: .color) + try container.encode(degrees, forKey: .degrees) + try container.encodeIfPresent(backgroundColor, forKey: .lineWidth) } }