ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • 타이머 앱
    iOS/패스트캠퍼스(앱제작) 2022. 5. 8. 13:41

     

     

    주요기능

    1. DispatchSourceTimer : 반복적 주기로 특정 작업을 수행 (핸들러 호출)

     - Timer클래스 로도 구현 가능

     - GCD api내의 DispatchSourceTimer 메소드로 구현함

     

    2. UIView Animation 

    - view의 알파값을 조정하여 뷰가 사라지고 표시될때 자연스럽게 이동

    - 이미지가 회전하도록 구현

     

     

     

    //
    //  ViewController.swift
    //  pomodoro
    //
    //  Created by YANG on 2022/05/06.
    //
    
    import UIKit
    import AudioToolbox
    
    enum TimerStatus {
        case start
        case pause
        case end
    }
    
    class ViewController: UIViewController {
    
        @IBOutlet weak var datePicker: UIDatePicker!
        @IBOutlet weak var progressView: UIProgressView!
        @IBOutlet weak var timerLabel: UILabel!
        @IBOutlet weak var toggleBtn: UIButton!
        @IBOutlet weak var cancelBtn: UIButton!
        @IBOutlet weak var imageView: UIImageView!
        
        var duration = 60
        var timerStatus: TimerStatus = .end
        var timer: DispatchSourceTimer?
        var currentSeconds = 0
        
        override func viewDidLoad() {
            super.viewDidLoad()
            self.configureToggleBtn()
            
        }
        
        func setTimerInfoViewVisible(isHidden: Bool) {
            self.timerLabel.isHidden = isHidden
            self.progressView.isHidden = isHidden
        }
        
        func configureToggleBtn() {
            self.toggleBtn.setTitle("시작", for: .normal)
            self.toggleBtn.setTitle("일시정지", for: .selected) // 버튼이 클릭되면 title 변경
        }
        
        func startTimer() {
            if self.timer == nil {
                self.timer = DispatchSource.makeTimerSource(flags: [], queue: .main)
                self.timer?.schedule(deadline: .now(), repeating: 1) // 1초마다 반복
                // 타이머가 동작할때마다 즉, 1초마다 handler내의 closure함수가 호출됨
                self.timer?.setEventHandler(handler: { [weak self] in
                    guard let self = self else { return }
                    self.currentSeconds -= 1
                    let hour = self.currentSeconds / 3600
                    let minute = (self.currentSeconds % 3600) / 60
                    let seconds = (self.currentSeconds % 3600) % 60
                    
                    // 화면에 표시
                    self.timerLabel.text = String(format: "%02d:%02d:%02d", hour, minute, seconds)
                    self.progressView.progress = Float(self.currentSeconds) / Float(self.duration)
                    
                    // 이미지가 180도 변화
                    UIView.animate(withDuration: 0.5, delay: 0, animations: {
                        self.imageView.transform = CGAffineTransform(rotationAngle: .pi)
                    })
                    // 180도 변화하는 애니메이션이 끝난 후 360도 회전
                    UIView.animate(withDuration: 0.5, delay: 0.5, animations: {
                        self.imageView.transform = CGAffineTransform(rotationAngle: .pi * 2)
                    })
                    
                    if self.currentSeconds <= 0 {
                        // 타이머가 종료
                        self.stopTimer()
                        AudioServicesPlaySystemSound(1005)
                    }
                })
                self.timer?.resume()
            }
        }
        
        func stopTimer() {
            if self.timerStatus == .pause {
                self.timer?.resume()
            }
    //        self.setTimerInfoViewVisible(isHidden: false)
    //        self.datePicker.isHidden = true
            UIView.animate(withDuration: 0.5, animations: {
                self.timerLabel.alpha = 0
                self.progressView.alpha = 0
                self.datePicker.alpha = 1
                self.imageView.transform = .identity
            })
            
            self.toggleBtn.isSelected = false
            self.cancelBtn.isEnabled = false
            self.timer?.cancel()
            self.timer = nil
            
        }
        
    
        @IBAction func tabCancleBtn(_ sender: Any) {
            switch self.timerStatus {
            case .start, .pause:
                self.timerStatus = .end
                self.cancelBtn.isEnabled = false
                self.setTimerInfoViewVisible(isHidden: true)
                self.datePicker.isHidden = false
                self.toggleBtn.isSelected = false
            default:
                break
            }
        }
        
        @IBAction func tabToggleBtn(_ sender: Any) {
            self.duration = Int(self.datePicker.countDownDuration) // datePicker에서 설정한 시간을 초로 환산
            
            switch self.timerStatus {
            case .end:
                self.currentSeconds = self.duration
                self.timerStatus = .start
    //            self.setTimerInfoViewVisible(isHidden: false)
    //            self.datePicker.isHidden = true
                
                // closure에 최종값 설정: 현재값에서 원하는 최종값으로 변화
                UIView.animate(withDuration: 0.5, animations: {
                    self.timerLabel.alpha = 1
                    self.progressView.alpha = 1
                    self.datePicker.alpha = 0
                })
                self.toggleBtn.isSelected = true
                self.cancelBtn.isEnabled = true
                self.startTimer()
                
            case .start:
                self.timerStatus = .pause
                self.toggleBtn.isSelected = false
                self.timer?.suspend()
                
            case .pause:
                self.timerStatus = .start
                self.toggleBtn.isSelected = true
                self.timer?.resume()
            }
            
        }
        
    }

    'iOS > 패스트캠퍼스(앱제작)' 카테고리의 다른 글

    코로나 현황판 앱  (0) 2022.05.08
    날씨 앱  (0) 2022.05.08
    일기장 앱  (0) 2022.04.20
    할일 리스트(To-Do List) 앱  (0) 2022.04.03
    계산기 앱  (0) 2022.04.03

    댓글

Designed by Tistory.