How to set a timer to enable/disable buttons - ios

I got an issue.
I want to set a timer that could disable the 6 large buttons of my ViewController2.
For example : Until the timer reach 100, it's not possible to click on the buttons Clue1Button,Clue2Button,Clue3Button,Clue4Button,Clue5Button,Clue6Button
Until the timer reach 200, it's not possible to click on the buttons 2,3,4,5,6 ...
How should I do it ? I tried several times, but I failed each time. Thanks for your help
Code of my ViewController2 :
// ViewController2.swift
// PROJET X
//
// Created by Alexis Decloedt on 22/12/2019.
// Copyright © 2019 Alexis Decloedt. All rights reserved.
//
import UIKit
class ViewController2: UIViewController {
#IBOutlet weak var Clue1Button: UIButton!
#IBOutlet weak var Clue2Button: UIButton!
#IBOutlet weak var Clue3Button: UIButton!
#IBOutlet weak var Clue4Button: UIButton!
#IBOutlet weak var Clue5Button: UIButton!
#IBOutlet weak var Clue6Button: UIButton!
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
}
#IBAction func ChestButton(_ sender: Any) {
dismiss(animated: false, completion: nil)
}
}
//
// ViewController2.swift
// PROJET X
//
// Created by Alexis Decloedt on 22/12/2019.
// Copyright © 2019 Alexis Decloedt. All rights reserved.
//
import UIKit
var currentCount : Int?
var maxCount : Int?
var mytimer : Timer?
let ValeurStock = "ValeurStock"
class ViewController2: UIViewController {
#IBOutlet weak var Clue1Button: UIButton!
#IBOutlet weak var Clue2Button: UIButton!
#IBOutlet weak var Clue3Button: UIButton!
#IBOutlet weak var Clue4Button: UIButton!
#IBOutlet weak var Clue5Button: UIButton!
#IBOutlet weak var Clue6Button: UIButton!
override func viewDidLoad() {
super.viewDidLoad()
currentCount = 0
self.mytimer = Timer.scheduledTimer(timeInterval: 2, target: self, selector: #selector(increase), userInfo: nil, repeats: true)
}
#IBAction func ChestButton(_ sender: Any) {
dismiss(animated: false, completion: nil)
}
func increase() {
currentCount! += 1
}
func buttonStatus() {
if currentCount ?? <#default value#> >= 100 {
//I'm stuck ?? How to continue ?
}
}
}
Try to make my button disable/enable

What you may want to do is:
//Add variable that will count how many times Timer was repeated.
var timerCount = 0
//Create timer
Timer.scheduledTimer(withTimeInterval: 100, repeats: true) { t in
//After first 100 sec passed, timer will get triggered and enable the buttons you want.
button1.isEnabled = true
button2.isEnabled = true
//After another 100 passed, timer will enable other buttons
if timerCount == 1 {
button3.isEnabled = true
button4.isEnabled = true
t.invalidate()
}
//Adds 1 to timer count
timerCount += 1
}

Related

Make variable equal to UserDefaults for timer

I have a UIProgress view that takes 60 seconds to go across the screen, but how do I make it where rather than having a set time 'var seconds = 60' I have the UserDefault string be the time? (Not all the code is included.)
import UIKit
class MinuteMeditation: UIViewController {
#IBOutlet weak var progressController: UIProgressView!
#IBOutlet weak var statusLabel: UILabel!
#IBOutlet weak var timeLabel: UILabel!
let savedTime = UserDefaults.standard.string(forKey: "time")
var seconds = 60 // THIS IS WHERE I WANT THE USER DEFAULTS ^
var timer = Timer()
var isTimerRunning = false
var resumeTapped = false
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
runTimer()
One way is to assign the value at some point in the UIViewControllers life-cycle, for example, you could use viewWillLoad if you want to use the saved value EVERY time the view is shown, or viewLoaded if you only want to set when the view is first loaded by the system, for example...
class MinuteMeditation: UIViewController {
#IBOutlet weak var progressController: UIProgressView!
#IBOutlet weak var statusLabel: UILabel!
#IBOutlet weak var timeLabel: UILabel!
var seconds: TimeInterval = 60.0 // THIS IS WHERE I WANT THE USER DEFAULTS ^
var timer = Timer()
var isTimerRunning = false
var resumeTapped = false
override func viewWillAppear(_ animated: Bool) {
super.viewWillAppear(animated)
if let savedTime = UserDefaults.standard.string(forKey: "time"), let time = Double(savedTime) {
seconds = time
}
}
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
runTimer()
}
}
Just remember, this will ALWAYS override any value previous set. If you prefer to only use the saved value if the value hasn't previously been set, you will need to make seconds optional and assign a default value when it hasn't previously been set and there is no saved value
Another option is to make seconds a computed value...
class MinuteMeditation: UIViewController {
#IBOutlet weak var progressController: UIProgressView!
#IBOutlet weak var statusLabel: UILabel!
#IBOutlet weak var timeLabel: UILabel!
var seconds: TimeInterval {
guard let savedTime = UserDefaults.standard.string(forKey: "time"), let time = Double(savedTime) else {
return 60.0
}
return time
}
var timer = Timer()
var isTimerRunning = false
var resumeTapped = false
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
runTimer()
}
}
This does mean that the value will never be settable directly, it will only be settable via the UserDefaults

How do I change what property to use in function of action based off of sender in Swift 4

#IBOutlet weak var weekdaysHoursSliderOutlet: UISlider!
#IBOutlet weak var weekdaysHoursLabelOutlet: UILabel!
#IBOutlet weak var weekdaysHoursNumberLabel: UILabel!
#IBOutlet weak var weekdendsHoursSliderOutlet: UISlider!
#IBOutlet weak var weekendsHoursLabelOutlet: UILabel!
#IBOutlet weak var weekendsHoursNumberLabel: UILabel!
#IBAction func weekendsHoursSliderChange(_ sender: UISlider) {
let currentValue: Int = Int(sender.value)
weekendsHoursNumberLabel.text = ("\(currentValue)")
if(currentValue == 1){
weekendsHoursLabelOutlet.text = ("Hour Per Day")
}
else{
weekendsHoursLabelOutlet.text = ("Hours Per Day")
}
}
I would want to change that to weekdays if say the weekdaysHourSliderOutlet called an on change Action. I plan on implementing more than just weekends and weekdays so I don't want a bunch of redundant code. I was thinking of using a dictionary of some sort but couldn't get it hooked up correctly. Thank you in advance!
func viewDidLoad() {
weekdaysHoursSliderOutlet.tag = 1
weekdendsHoursSliderOutlet.tag = 2
}
#IBAction func sliderChanged(_ sender: UISlider) {
if sender.tag == 1 {
//handle weekdaysHoursSliderOutlet
}
else {
//handle weekdendsHoursSliderOutlet
}
}

Swift Add float value to UISlider.value

import UIKit
class ViewController: UIViewController {
// Khai bao bien
var time:Float = 0
var timer:NSTimer!
var sliTime:Float!
// End khai bao
#IBOutlet weak var sldTime: UISlider!
#IBOutlet weak var lblScore: UILabel!
#IBOutlet weak var lblNum1: UILabel!
#IBOutlet weak var lblOperator: UILabel!
#IBOutlet weak var lblNum2: UILabel!
#IBOutlet weak var lblResult: UILabel!
#IBAction func btnOK(sender: AnyObject) {
}
#IBAction func btnCan(sender: AnyObject) {
}
override func viewDidLoad() {
super.viewDidLoad()
sldTime.minimumValue = 0
sldTime.maximumValue = 10
timer = NSTimer.scheduledTimerWithTimeInterval(1, target: self, selector: Selector("Run") ,userInfo: nil, repeats: true)
}
func Run()
{
if time == 0{
time = 10
}else{
time = time - 1
sldTime.value = time
}
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
}
When I run app in simulator , the app show:
"Thread 1 breakpoint 1.1" in line sldTime.value = time
What does the debugger console say? Thread 1: signal SIGABRT error if that's what the console says that mean you made a bad connection from the Main Story board to the ViewController Go to the Outlet Connection > and delete a connection you made but it's no longer in use. And try to run it again. Just keep in mind that Thread 1: signal SIGABRT Error is due to a connection problem between the Storyboard and ViewController mostly.
time = sldTime.floatValue

Error - 'ViewController' does not have a member named 'seconds'

I am making an app where a textfield input is shown on a label for the amount of time (in seconds) indicated on an other textfield. My app only runs when var seconds is set to an integer and not to the textfield input. When I set var seconds to the textfield input, I get the following error on the indicated lines of code: 'ViewController' does not have a member named 'seconds' Can anyone help? Thanks.
Here is all of my code, the lines of code with the error have //Error beside them:
class ViewController: UIViewController {
#IBOutlet weak var chronometre: UILabel!
#IBOutlet weak var prochainpointLabel: UILabel!
#IBOutlet weak var pointactuelLabel: UILabel!
#IBOutlet weak var point1Textfield: UITextField!
#IBOutlet weak var point1tempsTextfield: UITextField!
#IBOutlet weak var point2Textfield: UITextField!
#IBOutlet weak var point2tempsTextfield: UITextField!
var timer = NSTimer()
var seconds = point1tempsTextfield.text.toInt()
func subtractTime(dt:NSTimer){
seconds-- //Error
chronometre.text = "\(seconds)" //Error
if(seconds == 0) { //Error
seconds = point2tempsTextfield.text.toInt()
pointactuelLabel.text = point2Textfield.text
prochainpointLabel.text = nil
}
}
override func viewDidLoad() {
super.viewDidLoad()
// 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.
}
#IBAction func presenterButton(sender: AnyObject) {
pointactuelLabel.text = point1Textfield.text
prochainpointLabel.text = point2Textfield.text
chronometre.text = "\(seconds)" //Error
timer = NSTimer.scheduledTimerWithTimeInterval(1.0, target: self, selector: ("subtractTime:"), userInfo: nil, repeats: true)
}
}
Thank you for your help, I am very new to coding and really appreciate it!
Forget about using a timer to calculate time. You should use NSTimeInterval between two dates to measure elapsed time.
ElapsedTime
extension NSTimeInterval {
var time:String {
return String(format:"%02d:%02d", Int((self/60.0)%60), Int((self) % 60 ))
}
}
var startTime:NSTimeInterval = 0
var elapsedTime:NSTimeInterval = 0
startTime = NSDate().timeIntervalSinceReferenceDate // 446644854.4675
sleep(3) //
elapsedTime = NSDate().timeIntervalSinceReferenceDate - startTime // 3.005680024623871
println(elapsedTime.time) "00:03"
// applying this concept to your code would look like this:
class ViewController: UIViewController {
#IBOutlet weak var chronometre: UILabel!
#IBOutlet weak var prochainpointLabel: UILabel!
#IBOutlet weak var pointactuelLabel: UILabel!
#IBOutlet weak var point1Textfield: UITextField!
#IBOutlet weak var point1tempsTextfield: UITextField!
#IBOutlet weak var point2Textfield: UITextField!
#IBOutlet weak var point2tempsTextfield: UITextField!
var timer = NSTimer()
var startTime:NSTimeInterval = 0
func updateTime(){
chronometre.text = (NSDate().timeIntervalSinceReferenceDate - startTime).time
}
override func viewDidLoad() {
super.viewDidLoad()
// 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.
}
#IBAction func presenterButton(sender: AnyObject) {
pointactuelLabel.text = point1Textfield.text
prochainpointLabel.text = point2Textfield.text
timer = NSTimer.scheduledTimerWithTimeInterval(1/10, target: self, selector: ("updateTime:"), userInfo: nil, repeats: true)
startTime = NSDate().timeIntervalSinceReferenceDate
}
}

Error - Thread 1: signal SIGABRT (unrecognized selector sent to instance) [duplicate]

This question already has answers here:
Unrecognized selector sent to instance NSTimer Swift
(3 answers)
Closed 8 years ago.
I'm making an app where you need to indicate the amount of time that a label appears for and that amount of time is counted down at the bottom of the page.
When I run my app on the Xcode simulator, the chronometre label displays "Optional (*indicated number)" when I want it to only display the indicated number. Once it's displayed for a second, I get taken to my App Delegate and it says Thread 1: signal SIGABRT.
The following error is also shown: 2015-02-22 21:05:50.860 MemoPres.New[71008:12980314] -[MemoPres_New.ViewController subtractTime:]: unrecognized selector sent to instance 0x7fbab24299c0
2015-02-22 21:05:50.862 MemoPres.New[71008:12980314] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[MemoPres_New.ViewController subtractTime:]: unrecognized selector sent to instance 0x7fbab24299c0'.
Help would be greatly appreciated.
The following is all of my code:
class ViewController: UIViewController {
#IBOutlet weak var chronometre: UILabel!
#IBOutlet weak var prochainpointLabel: UILabel!
#IBOutlet weak var pointactuelLabel: UILabel!
#IBOutlet weak var point1Textfield: UITextField!
#IBOutlet weak var point1tempsTextfield: UITextField!
#IBOutlet weak var point2Textfield: UITextField!
#IBOutlet weak var point2tempsTextfield: UITextField!
override func viewDidLoad() {
super.viewDidLoad()
// 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.
}
#IBAction func presenterButton(sender: AnyObject) {
var timer = NSTimer()
var seconds = point1tempsTextfield.text.toInt()
pointactuelLabel.text = point1Textfield.text
prochainpointLabel.text = point2Textfield.text
chronometre.text = "\(seconds)"
timer = NSTimer.scheduledTimerWithTimeInterval(1.0, target: self, selector: ("subtractTime:"), userInfo: nil, repeats: true)
func subtractTime(dt:NSTimer){
seconds!--
chronometre.text = "\(seconds)"
}
}
}
You need to declare your method subtractTime() outside your IBAction. The same applies to your timer and second vars.
import UIKit
class ViewController: UIViewController {
#IBOutlet weak var progressView: UIProgressView!
#IBOutlet weak var strTimer: UILabel!
#IBOutlet weak var btnStartCancel: UIButton!
#IBOutlet weak var btnPauseResume: UIButton!
var timer = Timer()
var startTime: TimeInterval = 0
var timeLeft: TimeInterval = 45
var isTimerON = false
var isPaused = false
func updateTimer() {
if isTimerON && !isPaused {
strTimer.text = (startTime - Date().timeIntervalSinceReferenceDate).time
progressView.progress = (1 - Float(startTime - Date().timeIntervalSinceReferenceDate) / 45)
}
}
override func viewDidLoad() {
super.viewDidLoad()
timer = .scheduledTimerWithTimeInterval(1/20, target: self, selector: "updateTimer", userInfo: nil, repeats: true)
RunLoop.main.addTimer(timer, forMode: .common)
}
#IBAction func pauseResumeAction(_ sender: Any) {
isPaused = !isPaused
if isPaused {
timeLeft = startTime - Date().timeIntervalSinceReferenceDate
}
startTime = Date().dateByAddingTimeInterval(timeLeft).timeIntervalSinceReferenceDate
btnPauseResume.setTitle( !isPaused ? "Pause" : "Resume", forState: .normal)
}
#IBAction func startCancelAction(_ sender: Any) {
isTimerON = !isTimerON
isPaused = false
timeLeft = 45
startTime = isTimerON ? Date().dateByAddingTimeInterval(timeLeft).timeIntervalSinceReferenceDate : timeLeft
btnStartCancel.setTitle(!isTimerON ? "Start" : "Cancel", forState: .normal)
progressView.progress = 0
btnPauseResume.setTitle("Pause", forState: .normal)
strTimer.text = "00:45"
btnPauseResume.enabled = isTimerON
}
}
extension TimeInterval {
var time: String {
String(format: "%02d:%02d", Int((self/60)%60), Int(self%60))
}
}

Resources