0

Basics of CALayer

Khi bạn lần đầu nghe về Core animation, bạn có thể nghĩ tất cả thành phần trong nó đều là animation. Tuy nhiên, animation chỉ là 1 phần của framework này. Nó sử dụng GPU để tăng tốc render các đối tượng trên màn hình. Nó chia nội dung trên màn hình thành một đối tượng độc lập gọi là layers, và sắp xếp chúng trong một hệ thống cây (được gọi là layer tree). Bạn đã quen thuộc với hệ thống phân cấp cây UIView, được xây dựng trên layer tree. Nói cách khác, Core Animation cho tất cả mọi thứ bạn thấy trên màn hình. Trong bài viết này chúng ta sẽ đi tìm hiểu về CALayer- một thành phần quan trọng trong Core Animation. Hy vọng với bài viết này bạn sẽ biết được cơ bản về CALayer, làm thế nào để sử dụng các thuộc tính của nó để tạo ra các hiệu ứng hình ảnh một cách dễ dàng, và ở phần cuối của hướng dẫn này, bạn sẽ học được lớp phụ quan trọng nhất của CALayer - CAShapeLayer.

What Is CALayer?

CALayers là các đối tượng hình chữ nhật có thể chứa nội dung trực quan. Chúng được lưu trữ trong một hệ thống cấp bậc cây (tree hierarchy), và quản lý vị trí các sublayers con của nó. Nghe có vẻ quen? Bạn có thể nói, "Nó giống như UIView!"

Đó là sự thật, nhưng đó không chỉ là một sự trùng hợp ngẫu nhiên. Mỗi UIView có một thuộc tính lớp được gọi là backing layer, là một thể hiện của CALayer. UIView chỉ đảm bảo các back layer tương ứng được kết nối chính xác trong tree layer khi các subvieưs được thêm hoặc xoá khỏi view. Back layer có trách nhiệm hiển thị và show animation của view. Các tính năng duy nhất mà back layer không xử lý là tương tác người dùng.

Exploring CALayer

Tạo một CALayer instance rất đơn giản.

let redLayer = CALayer()

Chúng ta có thể thiết lập frame, backgroundColor, và thêm nó vào một superlayer giống như chúng ta làm với UIView.

redLayer.frame = CGRect(x: 50, y: 50, width: 100, height: 100)
redLayer.backgroundColor = UIColor.redColor().CGColor
layer.addSublayer(redLayer)

Thêm đoạn code này vào function được gọi là setup trong ViewController.swift, and gọi method này trong viewDidLoad. Ta sẽ có:

import UIKit
 
class ViewController: UIViewController {
    override func viewDidLoad() {
        super.viewDidLoad()
         
        setup()
    }
    func setup() {
        let redLayer = CALayer()
         
        redLayer.frame = CGRect(x: 50, y: 50, width: 50, height: 50)
        redLayer.backgroundColor = UIColor.redColor().CGColor
        self.view.layer.addSublayer(redLayer)
    }
}

Lưu ý rằng thuộc tính bạckgroundColor của CALayer là một CGColor thay vì UIColor. Bạn cũng có thể thiết lập một hình ảnh như là một nội dung. Nội dung đó được gọi là backing image.

func setup() {
    let redLayer = CALayer()
     
    redLayer.frame = CGRect(x: 50, y: 50, width: 50, height: 50)
    redLayer.backgroundColor = UIColor.redColor().CGColor
    self.view.layer.addSublayer(redLayer)
     
     
    let imageLayer = CALayer()
    let image = UIImage(named: "ButterflySmall.jpg")!
    imageLayer.contents = image.CGImage
     
    imageLayer.frame = CGRect(x: 0, y: 100, width: image.size.width, height: image.size.height)
    imageLayer.contentsGravity = kCAGravityResizeAspect
    imageLayer.contentsScale = UIScreen.mainScreen().scale
     
    self.view.layer.addSublayer(imageLayer)
}

ContentsGravity là một hằng số chỉ định vị trí và scale theo bounds của nó cho layer contents contentsScale định nghĩa tỷ lệ ánh xạ giữa kích thước của layer (đo bằng points) và kích thước của bitmap được sử dụng để hiển thị nội dung của layer (được gọi là backing image, được đo bằng pixel). Giá trị mặc định là 1.0. Thông thường chúng ta đặt giá trị như tỷ lệ như hình ảnh, như được hiển thị ở trên. Tuy nhiên, khi làm việc với hình ảnh được tạo ra bằng code, hoặc hình ảnh thiếu hậu tố @2x/@3x , bạn phải nhớ để tự thiết lập contentScale phù hợp với screen scale.

Corners and Border

CALayer có một thuộc tính gọi là cornerRadius, nó áp dụng các góc tròn cho background và border của layer. Khi thuộc tính masksToBounds được thiết lập là true, backing image và layer con của layer đó được cắt bớt vào đường cong này. Trên redLayer ta sẽ áp dụng một số góc tròn và làm cho border có thể nhìn thấy được.

func setup() {
    let redLayer = CALayer()
     
    redLayer.frame = CGRect(x: 50, y: 50, width: 50, height: 50)
    redLayer.backgroundColor = UIColor.redColor().CGColor
     
    // Round corners
    redLayer.cornerRadius = 25
     
    // Set border
    redLayer.borderColor = UIColor.blackColor().CGColor
    redLayer.borderWidth = 10
    ...

BorderWidth, borderColor xác định chiều rộng và màu sắc border của layer.

Drop Shadow

Có bốn thuộc tính mà bạn có thể cấu hình drop shadow cho layer, shadowOpacity, shadowColor, shadowOffset and shadowRadius. ShadowRadius kiểm soát độ mờ của bóng. Giá trị lớn có thể tạo ra bóng mềm hơn, giống với tự nhiên hơn. Chúng ta sẽ add shadow cho redLayer.

redLayer.shadowColor = UIColor.blackColor().CGColor
redLayer.shadowOpacity = 0.8
redLayer.shadowOffset = CGSizeMake(2, 2)
redLayer.shadowRadius = 3

Không giống như layer border. Shadow của layer bắt nguồn từ hình dạng chính xác của contents, không dựa vào bounds và cornerRadius. Để thuận tiện trong việc chuyển tải nội dung bài viết, giúp các bạn nắm bắt được phương pháp, các ví dụ mình sử dụng rất đơn giản. Hi vọng bài viết sẽ giúp ích được cho mọi người.


All rights reserved

Viblo
Hãy đăng ký một tài khoản Viblo để nhận được nhiều bài viết thú vị hơn.
Đăng kí