Swift 3.1 CALayer

Created By: Debasis Das (15-May-2017)

An introduction to CALayer and Swift Sample code to create CALayer and modify its properties.
Layers are backing store for views and also can be used without a view to display content.
We can modify the visual attributes of a layer such as background color, border width, border color, shadow, opacity etc
In addition to the visual content, layers also maintain its position, size and transforms.
Animations can be initiated by modifying the properties of a layer
There are different types of layers such as

  • CALayer
  • CAGradientLayer
  • CATextLayer
  • CAShapeLayer
  • CAReplicatorLayer
  • CATiledLayer etc

In this article we will focus on creating a simple CALayer and setting it as the layer of the view and change the property of the layers on click of buttons

CALayer-gif

CAGradientLayer_gif2

//  ViewController.swift
//  CALayerSample
//  Created by Debasis Das on 5/15/17.
//  Copyright © 2017 Knowstack.com All rights reserved.

import Cocoa

class ViewController: NSViewController {

    @IBOutlet weak var placeholderView: NSView!
    
    override func viewDidLoad() {
        super.viewDidLoad()
        
        let layer = CALayer()
        layer.frame = self.placeholderView.frame
        layer.backgroundColor = NSColor.black.cgColor
        layer.borderWidth = 10.0
        layer.borderColor = NSColor.random().cgColor
        self.placeholderView.layer = layer
        self.placeholderView.wantsLayer = true
    }


    @IBAction func changeViewBackgroundColor(_ sender: Any) {
        self.placeholderView.layer?.backgroundColor = NSColor.random().cgColor
    }
    
    
    @IBAction func changeBorderWidth(_ sender: Any) {
        if (self.placeholderView.layer?.borderWidth)! >= CGFloat(10.0){
           self.placeholderView.layer?.borderWidth = 0.0
        }
        else{
           self.placeholderView.layer?.borderWidth = 10.0
        }
    }
    
    @IBAction func changeBorderColor(_ sender: Any) {
        self.placeholderView.layer?.borderColor = NSColor.random().cgColor
    }

    @IBAction func changeViewSize(_ sender: Any) {
        var layerBounds = self.placeholderView.layer?.bounds
        if (layerBounds?.size.height)! > CGFloat(200){
            layerBounds?.size.height = 100.0
        }
        else{
            layerBounds?.size.height = 230.0
            
        }
        self.placeholderView.layer?.bounds = layerBounds!
    }
    
    @IBAction func changeViewCornerRadius(_ sender: Any) {
        if (self.placeholderView.layer?.cornerRadius)! >= CGFloat(20.0){
            self.placeholderView.layer?.cornerRadius = 0.0
        }
        else{
            self.placeholderView.layer?.cornerRadius = 20.0
        }

    }
    
    @IBAction func changeViewOpacity(_ sender: Any) {
        let opacity = self.placeholderView.layer?.opacity
        if opacity == 1.0{
            self.placeholderView.layer?.opacity = 0.5
        }
        else{
            self.placeholderView.layer?.opacity = 1.0
        }
    }
    
    @IBAction func showHideShadow(_ sender: Any) {
        let shadowOpacity = self.placeholderView.layer?.shadowOpacity
        if shadowOpacity == 0.0{
            self.placeholderView.layer?.shadowOpacity = 1.0
            self.placeholderView.layer?.shadowRadius = 10.0
        }
        else{
            self.placeholderView.layer?.shadowOpacity = 0.0
            self.placeholderView.layer?.shadowRadius = 0.0
            
        }
    }
    
    @IBAction func changeAll(_ sender: Any) {
        changeViewSize(self)
        changeViewBackgroundColor(self)
        changeBorderWidth(self)
        changeBorderColor(self)
        changeViewCornerRadius(self)
        changeViewOpacity(self)
        showHideShadow(self)
        
    }
}

//We will extend the CGFloat class to generate a random float
extension CGFloat{
    static func random() -> CGFloat {
        return CGFloat(arc4random()) / CGFloat(UInt32.max)
    }
    
}

//In the below extension we are generating a random NSColor
extension NSColor{
    static func random()->NSColor{
        return NSColor(calibratedRed: .random(), green: .random(), blue: .random(), alpha: 1.0)
    }
}

Download the code here CALayerSample Sample Code

Swift 3.1 CAGradientLayer Sample Code

CAGradientLayer_gif2
CAGradientLayer has a colors property which accepts an array of CGColorRef.
In this sample we will initialize a CAGradientLayer with 2 Gradient Color generated at random and then subsequently change the gradience or add new CGColorRef to the gradient

//  ViewController.swift
//  GradientLayerSample
//  Created by Debasis Das on 5/15/17.
//  Copyright © 2017 Knowstack. All rights reserved.

import Cocoa

class ViewController: NSViewController {

    @IBOutlet weak var placeholderView: NSView!
    override func viewDidLoad() {
        super.viewDidLoad()
        let gradientLayer = CAGradientLayer()
        let colorRef1 = NSColor.random().cgColor
        let colorRef2 = NSColor.random().cgColor
        let colors = [colorRef1, colorRef2]
        gradientLayer.colors = colors
        gradientLayer.frame = self.placeholderView.frame
        self.placeholderView.layer = gradientLayer
        self.placeholderView.wantsLayer = true
    }
    
    @IBAction func changeGradientColor(_ sender: Any) {
        let colorRef1 = NSColor.random().cgColor
        let colorRef2 = NSColor.random().cgColor
        let colors = [colorRef1, colorRef2]
        (self.placeholderView.layer as! CAGradientLayer).colors = colors
    }

    @IBAction func addGradientColor(_ sender: Any) {
        
        var colors = (self.placeholderView.layer as! CAGradientLayer).colors
        colors?.append(NSColor.random().cgColor)
        (self.placeholderView.layer as! CAGradientLayer).colors = colors
    }

}

extension CGFloat{
    static func random() -> CGFloat {
        return CGFloat(arc4random()) / CGFloat(UInt32.max)
    }
    
}

extension NSColor{
    static func random()->NSColor{
        return NSColor(calibratedRed: .random(), green: .random(), blue: .random(), alpha: 1.0)
    }
}

You can download the code here CAGradientLayer Sample Code

Swift 3.1 Playing Card using CALayer

In the below sample we will create a Playing Card in Swift using CALayer
Playing Card Swift 3.1 CALayer

//  ViewController.swift
//  CALayer-PlayingCards
//  Created by Debasis Das on 5/15/17.
//  Copyright © 2017 Knowstack. All rights reserved.

import Cocoa

class ViewController: NSViewController {
    @IBOutlet weak var placeholderView: NSView!
    override func viewDidLoad() {
        super.viewDidLoad()
        
        //Set the card layer base
        let cardLayer = CALayer()
        cardLayer.frame = self.placeholderView.frame
        cardLayer.backgroundColor = NSColor.white.cgColor
        cardLayer.cornerRadius = 10.0
        cardLayer.borderWidth = 5.0
        cardLayer.borderColor = NSColor.black.cgColor
        cardLayer.shadowOpacity = 1.0
        cardLayer.shadowRadius = 10.0
        self.placeholderView.layer = cardLayer
        self.placeholderView.wantsLayer = true

        let topTextLayer = CATextLayer()
        topTextLayer.string = "A"
        topTextLayer.alignmentMode = "center"
        topTextLayer.frame = CGRect(x: cardLayer.bounds.width/8, y: cardLayer.bounds.size.height - 50.0, width: 50 , height: 50)
        topTextLayer.fontSize = 45
        topTextLayer.foregroundColor = NSColor.black.cgColor
        topTextLayer.contentsScale = (NSScreen.main()?.backingScaleFactor)!
        cardLayer.addSublayer(topTextLayer)
        
        let topImageLayer = CALayer()
        topImageLayer.frame = CGRect(x: cardLayer.bounds.size.width/8, y: cardLayer.bounds.size.height - 100, width: 50, height: 50)
        topImageLayer.contents = NSImage(named: "spade")
        cardLayer.addSublayer(topImageLayer)

        let centerImageLayer = CALayer()
        centerImageLayer.frame = CGRect(x: cardLayer.bounds.size.width/2 - 50.0, y: cardLayer.bounds.size.height/2 - 50.0, width: 100, height: 100)
        centerImageLayer.contents = NSImage(named: "spade")
        cardLayer.addSublayer(centerImageLayer)

        let bottomImageLayer = CALayer()
        bottomImageLayer.frame = CGRect(x: (cardLayer.bounds.size.width * CGFloat(6.0/8)), y: 50, width: 50, height: 50)
        bottomImageLayer.contents = NSImage(named: "spade")
        bottomImageLayer.transform = CATransform3DScale(CATransform3DMakeRotation(CGFloat(Double.pi), 0, 0, 1),
                                                         1.0, 1.0, 1);
        cardLayer.addSublayer(bottomImageLayer)

        
        let bottomTextLayer = CATextLayer()
        bottomTextLayer.string = "A"
        bottomTextLayer.alignmentMode = "center"
        bottomTextLayer.frame = CGRect(x: (cardLayer.bounds.size.width * CGFloat(6.0/8)), y: 0.0 , width: 50 , height: 50)
        bottomTextLayer.fontSize = 45
        bottomTextLayer.foregroundColor = NSColor.black.cgColor
        bottomTextLayer.transform = CATransform3DMakeRotation(CGFloat(Double.pi), 0.0, 0.0, 1.0);
        bottomTextLayer.contentsScale = (NSScreen.main()?.backingScaleFactor)!
        cardLayer.addSublayer(bottomTextLayer)

    }
}

You can download the code here CALayer-PlayingCards Sample Code

Posted in Swift 3.1 Tagged with: , , , ,

Leave a Reply

Your email address will not be published. Required fields are marked *

*

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>

Recent Posts


Hit Counter provided by technology news