6

I want to draw a UIView layer but when I do it the layer frame is not equal(In Preview) to UIView frame. enter image description here

class ViewController: UIViewController {

    var graphHeight:CGFloat = 100
    var graphSize:CGFloat!

    override func viewDidLoad() {
        super.viewDidLoad()
        graphSize = self.view.frame.height/CGFloat(M_PI)
        let graphRect:CGRect = CGRectMake(0, graphHeight, self.view.frame.width, graphSize)
        let background = blueGardient()
        var theView:UIView = UIView(frame: graphRect)
        background.frame = theView.frame
        theView.backgroundColor = UIColor.yellowColor()
        theView.layer.cornerRadius = 8
        theView.layer.borderWidth = 1
        theView.layer.borderColor = UIColor.redColor().CGColor
        theView.layer.insertSublayer(background, atIndex: 0)
        self.view.addSubview(theView)

    }

    func blueGardient()->CAGradientLayer{
        let topColor = UIColor(red: 0, green: 0, blue: 255, alpha: 0.7)
        let bottomColor = UIColor(red: 0, green: 0, blue: 255, alpha: 0.9)
        let gradientColors: [CGColor] = [topColor.CGColor, bottomColor.CGColor]
        let gradientLocations: [Float] = [0.0, 1.0]
        let gradientLayer: CAGradientLayer = CAGradientLayer()
        gradientLayer.colors = gradientColors
        gradientLayer.locations = gradientLocations
        return gradientLayer
    }
}

The frame is equal

(0.0,100.0,320.0,180.800015352393)
(0.0,100.0,320.0,180.800015352393)

but not shown eauql. I try with theView.layer.frame but unsuccessfully...

Bogdan Bogdanov
  • 882
  • 11
  • 36
  • 79

1 Answers1

10

The problem is because the context of each frame is different. Your view frame (theView.frame) is in the context of its superview, so the (0,100) origin means it is offset by 100 points downward from the top left of the screen. The layer's frame (background.frame) is in the context of the view it belongs to (theView), so the same (0,100) origin means the blue layer is offset by 100 points from the top left of the view.

Instead of using the view's frame, create a new rect using the size of the view's bounds and a (0,0) origin:

background.frame = CGRect(origin: CGPointZero, size: theView.bounds.size)
Nate Cook
  • 92,417
  • 32
  • 217
  • 178
  • 1
    +1. Technically, though, [`bounds.origin` might not always be (0, 0)](http://oleb.net/blog/2014/04/understanding-uiscrollview/), so I think your second solution is better. – Aaron Brager Nov 17 '14 at 17:18
  • 2
    In addition to @AaronBrager, [`frame` might be invalidated by `transform`](https://developer.apple.com/library/ios/documentation/uikit/reference/UIView_Class/index.html#//apple_ref/occ/instp/UIView/frame), it preferable to use `bounds.size`. – rintaro Nov 17 '14 at 17:22