I have an array of characters "." and "-" which is a translated text to morse code. They are of course in a extacly specified order because of the morse code. Now i want to convert this array to long and short flashes from flashlight in iPhone, after button is tapped. I tried of course looping through this array with 'if' statement, with scheduledTimers just like below, but obviously that doesnt worked out, loop was executing immediately and flashlight was launching only once.
let dash: Character = "-"
let dot: Character = "."
for i in translatedArray {
if i == dash{
//two sec delay at the beggining because of the pause beetween each flash which is equal to one dot
timer1 = Timer.scheduledTimer(timeInterval: 2, target: self, selector: #selector(toggleFlashlightOn), userInfo: nil, repeats: false)
timer2 = Timer.scheduledTimer(timeInterval: 6, target: self, selector: #selector(toggleFlashlightOff), userInfo: nil, repeats: false)
print("long flash activated")
}else if i == dot{
timer1 = Timer.scheduledTimer(timeInterval: 2, target: self, selector: #selector(toggleFlashlightOn), userInfo: nil, repeats: false)
timer2 = Timer.scheduledTimer(timeInterval: 4, target: self, selector: #selector(toggleFlashlightOff), userInfo: nil, repeats: false)
print("short flash activated")
} else { return }
}
I also tried to delay separate 'if' iteration with delay() function, but execution of this loop with morse code should have irregular time interval beetween each iteration depending on previous character aka previous lenght of flash, and delay() have only static value of seconds, so this didn't worked either.
Finally i found this thread here. And except updating it to swift4, and changing array of morse code characters to array of time intervals, which i did succesfully this would be a perfect solution for my problem... but it doesn't work. It turns on flashlight in only one mode which is ON, and refresh endlesly printing "ON" regularly with first time interval value in the array, for example every 2 seconds or so. So it never turns off the flashlight.
let shortFlash: Double = 2
let longFlash: Double = 4
let pause: Double = 2
var sequenceOfFlashes: [Double] = []
//this works ok, prints correct values in correct order from sequenceOfFlashes array
func setupMorseFlashesSequence(){
let dot: Character = "•"
let line: Character = "—"
for i in translatedArray {
switch i {
case dot:
sequenceOfFlashes.append(shortFlash)
sequenceOfFlashes.append(pause)
case line:
sequenceOfFlashes.append(longFlash)
sequenceOfFlashes.append(pause)
default:
return
}
}
print(sequenceOfFlashes)
}
var index: Int = 0
weak var timer: Timer?
func scheduleTimer(){
timer = Timer.scheduledTimer(timeInterval: sequenceOfFlashes[index], target: self, selector: #selector(timerTick), userInfo: nil, repeats: false)
}
@objc func timerTick(){
if index == sequenceOfFlashes.count {
stop()
}
turnFlashlight(on: index % 2 == 0)
scheduleTimer()
}
func start(){
index = 0
turnFlashlight(on: true)
scheduleTimer()
}
func stop(){
timer?.invalidate()
turnFlashlight(on: false)
}
deinit{
timer?.invalidate()
}
how can i achieve executing this flashes one by one with different times?
You forgot to increment index
in timerTick()
:
@objc func timerTick(){
index += 1
if index == sequenceOfFlashes.count {
stop()
}
turnFlashlight(on: index % 2 == 0)
scheduleTimer()
}