draw()的Swift回调函数?

时间:2017-09-15 17:35:40

标签: ios swift uiview ondraw

我有customView我覆盖drawRect:。我也有一些情况,我希望在customView上显示UILabel ontop:

if self.ticks.count < 50 {
    self.label.frame = self.bounds
    self.label.text = "This chart requires 50 or more ticks.\nKeep Ticking."
    self.addSubview(label)
}

但是,如果我在调用drawRect之前调用此代码,则我的标签不会显示。是否有像viewDidDraw之类的回调方法?

修改

有人要求它,所以现在所有的代码都在做我需要做的事情。我认为问题的答案是覆盖layoutSubviews

@IBDesignable open class  CustomView: UIView {
    @objc open var ticks:[Tick] = []
    let label = UILabel()

    required public init?(coder: NSCoder) {
        super.init(coder: coder)
        setup()
    }
    required public override init(frame: CGRect) {
        super.init(frame: frame)
        setup()
    }
    func setup(){
        self.backgroundColor = UIColor.clear
        self.label.frame = self.bounds
        self.label.text = "This chart requires 50 or more ticks.\nKeep Ticking."
        self.label.numberOfLines = 0
        self.label.textAlignment = .center
        self.addSubview(label)
    }

    override open func layoutSubviews() {
        self.label.frame = self.bounds
    }

    @objc open func setSessions(sessions:[Session]){
        self.ticks = []
        for session in sessions.reversed(){
            if self.ticks.count < 250{
                self.ticks = self.ticks + (session.getShots() as! [Shot])
            }else{
                break
            }
        }
        if self.ticks.count < 50 {
            self.label.isHidden = false
        }else{
            self.label.isHidden = true
        }
        self.bringSubview(toFront: self.label)
    }

    override open func draw(_ rect: CGRect) {
        let context = UIGraphicsGetCurrentContext()!
        let width = rect.width - 10;
        let height = rect.height - 10;
        let center = CGPoint(x: width/2+5, y: height/2+5)
        let big_r = min(width, height)/2

        context.setLineWidth(1.5)
        UIColor.white.setStroke()

        //draw the rings
        for i in stride(from: 1, to: 7, by: 1){
            let r = big_r * CGFloat(i) / 6.0;
            context.addArc(center:center, radius:r, startAngle: 0, endAngle: CGFloat(2*Double.pi), clockwise: false)
            context.strokePath()
        }

        //draw the ticks
        if self.ticks.count > 49 {
            UIColor.red().setFill()
            for (i, tick) in self.ticks.prefix(250).enumerated(){
                let radius = min((100.0-CGFloat(shot.score))/30.0 * big_r, big_r);

                let x = Utilities.calculateX(tick, radius)
                let y = Utilities.calculateY(tick, radius)

                let point = CGPoint(x: x+center.x,y: y+center.y)
                context.addArc(center:point, radius:CGFloat(DOT_WIDTH/2), startAngle: 0, endAngle: CGFloat(2*Double.pi), clockwise: false)
                context.fillPath()
            }
        }
    }
}

2 个答案:

答案 0 :(得分:1)

您可以在需要时通过调用setNeedsDisplay()来重绘自定义视图。之后,您可以添加标签

答案 1 :(得分:0)

您可以为View类设置委托,并在draw函数的末尾调用委托方法。但是,似乎如果直接调用该函数,则绘图函数将仅在处理委托函数之前结束。这意味着代码将在屏幕上刷新新图形之前执行。在这种情况下,您可能需要异步调用它。

// at end of draw function
DispatchQueue.main.async {
    self.delegate?.drawEnd()
}