Typewriter effect text animation

I have written a subclass of UILabel called CLTypingLabel, available on GitHub. This should do what you want.

After installing CocoaPods, add the following like to your Podfile to use it:

pod 'CLTypingLabel'

Sample Code

Change the class of a label from UILabel to CLTypingLabel; enter image description here

@IBOutlet weak var myTypeWriterLabel: CLTypingLabel!

At runtime, set text of the label will trigger animation automatically:

myTypeWriterLabel.text = "This is a demo of typing label animation..."

You can customize time interval between each character:

myTypeWriterLabel.charInterval = 0.08 //optional, default is 0.1

You can pause the typing animation at any time:

myTypeWriterLabel.pauseTyping() //this will pause the typing animation
myTypeWriterLabel.continueTyping() //this will continue paused typing animation

Also there is a sample project that comes with cocoapods


update: Xcode 7.0 GM • Swift 2.0

import UIKit

class ViewController: UIViewController {
    @IBOutlet weak var myTypeWriter: UITextField!
    let myText = Array("Hello World !!!".characters)
    var myCounter = 0
    var timer:NSTimer?
    func fireTimer(){
        timer = NSTimer.scheduledTimerWithTimeInterval(0.5, target: self, selector: "typeLetter", userInfo: nil, repeats: true)
    }
    func typeLetter(){
        if myCounter < myText.count {
            myTypeWriter.text = myTypeWriter.text! + String(myText[myCounter])
            let randomInterval = Double((arc4random_uniform(8)+1))/20
            timer?.invalidate()
            timer = NSTimer.scheduledTimerWithTimeInterval(randomInterval, target: self, selector: "typeLetter", userInfo: nil, repeats: false)
        } else {
            timer?.invalidate()
        }
        myCounter++
    }
    override func viewDidLoad() {
        super.viewDidLoad()
        fireTimer()
        // Do any additional setup after loading the view, typically from a nib.
    }
    override func didReceiveMemoryWarning() {
        super.didReceiveMemoryWarning()
        // Dispose of any resources that can be recreated.
    }
}

Based on this Answer: Letter by letter animation for UILabel?

I've updated it to Swift 4 and solved the CPU animation problem with DispatchWorkItem in order to create a queue.

Swift 4

extension UILabel {
    func setTextWithTypeAnimation(typedText: String, characterDelay: TimeInterval = 5.0) {
        text = ""
        var writingTask: DispatchWorkItem?
        writingTask = DispatchWorkItem { [weak weakSelf = self] in
            for character in typedText {
                DispatchQueue.main.async {
                    weakSelf?.text!.append(character)
                }
                Thread.sleep(forTimeInterval: characterDelay/100)
            }
        }
        
        if let task = writingTask {
            let queue = DispatchQueue(label: "typespeed", qos: DispatchQoS.userInteractive)
            queue.asyncAfter(deadline: .now() + 0.05, execute: task)
        }
    }
    
}

Usage

label.setTextWithTypeAnimation(typedText: text, characterDelay:  10) //less delay is faster

Swift 5

func setTyping(text: String, characterDelay: TimeInterval = 5.0) {
  self.text = ""
    
  let writingTask = DispatchWorkItem { [weak self] in
    text.forEach { char in
      DispatchQueue.main.async {
        self?.text?.append(char)
      }
      Thread.sleep(forTimeInterval: characterDelay/100)
    }
  }
    
  let queue: DispatchQueue = .init(label: "typespeed", qos: .userInteractive)
  queue.asyncAfter(deadline: .now() + 0.05, execute: writingTask)
}

Usage

label.setTyping(text: "Your text")

Tags:

Ios

Swift