Skip to content
Snippets Groups Projects
Commit 79157237 authored by Tomáš Valenta's avatar Tomáš Valenta
Browse files

check for 0 time and allow second tolerance

parent 7d46bda9
No related branches found
No related tags found
1 merge request!9Release
Pipeline #15161 passed
...@@ -12,8 +12,8 @@ const enableInputs = () => { ...@@ -12,8 +12,8 @@ const enableInputs = () => {
$("#pause_play,#minutes,#seconds,#update_time").prop("disabled", false) $("#pause_play,#minutes,#seconds,#update_time").prop("disabled", false)
} }
const updateTimeText = (timer) => { const updateTimeText = () => {
const timeValues = timer.getTimeValues() const timeValues = window.timer.getTimeValues()
const hours = String(timeValues.minutes + timeValues.hours * 60 + timeValues.days * 1440).padStart(2, '0') const hours = String(timeValues.minutes + timeValues.hours * 60 + timeValues.days * 1440).padStart(2, '0')
const seconds = String(timeValues.seconds).padStart(2, '0') const seconds = String(timeValues.seconds).padStart(2, '0')
...@@ -21,15 +21,15 @@ const updateTimeText = (timer) => { ...@@ -21,15 +21,15 @@ const updateTimeText = (timer) => {
$('#timer .timer-values').html(`${hours}:${seconds}`) $('#timer .timer-values').html(`${hours}:${seconds}`)
} }
const assignEventListeners = (timer) => { const assignEventListeners = () => {
timer.addEventListener( window.timer.addEventListener(
'secondsUpdated', 'secondsUpdated',
(event) => { (event) => {
updateTimeText(timer) updateTimeText()
} }
) )
timer.addEventListener( window.timer.addEventListener(
'targetAchieved', 'targetAchieved',
(event) => { (event) => {
$("#is_counting").prop("checked", false) $("#is_counting").prop("checked", false)
...@@ -37,20 +37,41 @@ const assignEventListeners = (timer) => { ...@@ -37,20 +37,41 @@ const assignEventListeners = (timer) => {
} }
) )
updateTimeText(timer) updateTimeText()
} }
const updateTimer = (timer, data, continuePlaying) => { const updateTimer = (data, options) => {
console.info(`Updating timer: ${JSON.stringify(data.sync_time)}`) const timerValues = timer.getTimeValues()
const minutes = data["sync_time"]["minutes"]
const seconds = data["sync_time"]["seconds"]
if (window.timerIsRunning && (minutes === 0 && seconds <= 5)) {
// Don't update the time if we're running in the final 5 seconds.
return
}
if (options.minuteTolerance !== undefined && options.secondTolerance !== undefined) {
if (
(Math.abs(timerValues.minutes - minutes) < options.minuteTolerance)
&& (Math.abs(timerValues.seconds - seconds) < options.secondTolerance)
) {
// Don't annoy the user with time changes when there is only a 1-2 second difference.
return
} else {
console.warn("Timer out of sync!")
}
}
console.info(`Updating timer: ${minutes}:${seconds}, used to be ${timerValues.minutes}:${timerValues.seconds}`)
window.startingTime = { window.startingTime = {
minutes: data["sync_time"]["minutes"], minutes: minutes,
seconds: data["sync_time"]["seconds"] seconds: seconds
} }
timer.removeAllEventListeners() window.timer.removeAllEventListeners()
timer = new Timer({ window.timer = new Timer({
countdown: true, countdown: true,
startValues: { startValues: {
minutes: window.startingTime.minutes, minutes: window.startingTime.minutes,
...@@ -58,18 +79,16 @@ const updateTimer = (timer, data, continuePlaying) => { ...@@ -58,18 +79,16 @@ const updateTimer = (timer, data, continuePlaying) => {
} }
}) })
assignEventListeners(timer) assignEventListeners()
if (window.timerIsRunning) { if (window.timerIsRunning) {
timer.start() window.timer.start()
} }
return timer
} }
const syncTime = (timerSocket, timer) => { const syncTime = (timerSocket) => {
timerSocket.send(JSON.stringify({ timerSocket.send(JSON.stringify({
"sync": timer.getTimeValues() "sync": window.timer.getTimeValues()
})) }))
} }
...@@ -80,8 +99,7 @@ $(window).ready( ...@@ -80,8 +99,7 @@ $(window).ready(
// --- BEGIN Timer --- // --- BEGIN Timer ---
window.timerIsRunning = false window.timerIsRunning = false
window.timer = new Timer({
let timer = new Timer({
countdown: true, countdown: true,
startValues: { startValues: {
minutes: window.startingTime.minutes, minutes: window.startingTime.minutes,
...@@ -118,25 +136,22 @@ $(window).ready( ...@@ -118,25 +136,22 @@ $(window).ready(
const data = JSON.parse(event.data) const data = JSON.parse(event.data)
if ("sync_time" in data) { if ("sync_time" in data) {
// Only update if there is any real difference. updateTimer(
data,
const remainingTime = timer.getTimeValues() {
minuteTolerance: 1,
if ( secondTolerance: 2
data.sync_time.minutes !== remainingTime.minutes ||
data.sync_time.seconds !== remainingTime.seconds
) {
timer = updateTimer(timer, data)
} }
)
} }
if ("is_running" in data) { if ("is_running" in data) {
if (data["is_running"]) { if (data["is_running"]) {
// Reset if we are playing again. // Reset if we are playing again.
const remainingTime = timer.getTimeValues() const remainingTime = window.timer.getTimeValues()
if (remainingTime.seconds === 0 && remainingTime.minutes === 0) { if (remainingTime.seconds === 0 && remainingTime.minutes === 0) {
timer = new Timer({ window.timer = new Timer({
countdown: true, countdown: true,
startValues: { startValues: {
minutes: window.startingTime.minutes, minutes: window.startingTime.minutes,
...@@ -144,16 +159,16 @@ $(window).ready( ...@@ -144,16 +159,16 @@ $(window).ready(
} }
}) })
assignEventListeners(timer) assignEventListeners()
} }
timer.start() window.timer.start()
$("#is_counting").prop("checked", true) $("#is_counting").prop("checked", true)
$("#pause_play > .btn__body").html("⏸︎") $("#pause_play > .btn__body").html("⏸︎")
window.timerIsRunning = true window.timerIsRunning = true
} else { } else {
timer.pause() window.timer.pause()
$("#is_counting").prop("checked", false) $("#is_counting").prop("checked", false)
$("#pause_play > .btn__body").html("⏵︎") $("#pause_play > .btn__body").html("⏵︎")
...@@ -165,15 +180,23 @@ $(window).ready( ...@@ -165,15 +180,23 @@ $(window).ready(
let interval = null let interval = null
timerSocket.onopen = () => { timerSocket.onopen = () => {
syncTime(timerSocket, timer) syncTime(timerSocket)
interval = setInterval(syncTime, 5000, timerSocket, timer) interval = setInterval(syncTime, 1000, timerSocket)
// --- BEGIN Controls --- // --- BEGIN Controls ---
$("#pause_play").on( $("#pause_play").on(
"click", "click",
(event) => { (event) => {
const timeValues = window.timer.getTimeValues()
if (timeValues.minutes == 0 && timeValues.seconds == 0) {
alertify.error("Prosím, nastav čas.")
return
}
$("#is_counting").click() $("#is_counting").click()
} }
) )
...@@ -206,7 +229,7 @@ $(window).ready( ...@@ -206,7 +229,7 @@ $(window).ready(
(event) => { (event) => {
disableInputs() disableInputs()
timer.pause() window.timer.pause()
let minutes = Number($("#minutes").val()) let minutes = Number($("#minutes").val())
let seconds = Number($("#seconds").val()) let seconds = Number($("#seconds").val())
...@@ -231,14 +254,14 @@ $(window).ready( ...@@ -231,14 +254,14 @@ $(window).ready(
alertify.error("Ztráta spojení, pokoušíme se o zpětné připojení.") alertify.error("Ztráta spojení, pokoušíme se o zpětné připojení.")
setTimeout(connectToSocket, 5000) setTimeout(connectToSocket, 1000)
clearInterval(interval) clearInterval(interval)
$("#is_counting,#pause_play,#update_time").unbind("click") $("#is_counting,#pause_play,#update_time").unbind("click")
} }
} }
connectToSocket() connectToSocket()
assignEventListeners(timer) assignEventListeners()
// --- END Timer --- // --- END Timer ---
} }
......
...@@ -3,7 +3,7 @@ import datetime ...@@ -3,7 +3,7 @@ import datetime
import json import json
import threading import threading
import time import time
from timeit import default_timer import timeit
from asgiref.sync import sync_to_async from asgiref.sync import sync_to_async
from channels.generic.websocket import AsyncWebsocketConsumer from channels.generic.websocket import AsyncWebsocketConsumer
...@@ -12,16 +12,20 @@ running_timer_threads = [] ...@@ -12,16 +12,20 @@ running_timer_threads = []
def tick_timer(timer, iteration: int, total_seconds: int) -> None: def tick_timer(timer, iteration: int, total_seconds: int) -> None:
print("ticking", timer)
second_compensation = 0 second_compensation = 0
start_time = default_timer() start_time = timeit.default_timer()
timer.refresh_from_db() timer.refresh_from_db()
end_time = default_timer() end_time = timeit.default_timer()
second_compensation = end_time - start_time second_compensation = end_time - start_time
while not timer.is_running: while not timer.is_running:
print("waiting to run ...")
time.sleep(0.05) time.sleep(0.05)
timer.refresh_from_db() timer.refresh_from_db()
...@@ -32,15 +36,30 @@ def tick_timer(timer, iteration: int, total_seconds: int) -> None: ...@@ -32,15 +36,30 @@ def tick_timer(timer, iteration: int, total_seconds: int) -> None:
running_timer_threads.remove(timer.id) running_timer_threads.remove(timer.id)
return return
start_time = default_timer() if timer.minutes == 0 and timer.seconds == 0:
# Stop the thread if we have reached the end
if iteration != timer.iteration: running_timer_threads.remove(timer.id)
# Stop the thread if there is a new timer return
start_time = timeit.default_timer()
print(timer.minutes, timer.seconds)
if timer.minutes == 0 and timer.seconds == 0:
# Stop the thread if we have reached the end
timer.is_running = False
timer.save()
running_timer_threads.remove(timer.id) running_timer_threads.remove(timer.id)
return return
if total_seconds < 1: if iteration != timer.iteration:
# Stop the thread if there is a new timer
running_timer_threads.remove(timer.id)
return return
total_seconds -= 1 total_seconds -= 1
...@@ -53,11 +72,11 @@ def tick_timer(timer, iteration: int, total_seconds: int) -> None: ...@@ -53,11 +72,11 @@ def tick_timer(timer, iteration: int, total_seconds: int) -> None:
timer.save() timer.save()
end_time = default_timer() end_time = timeit.default_timer()
second_compensation += end_time - start_time second_compensation += end_time - start_time
threading.Timer( threading.Timer(
interval=1 - second_compensation, interval=max(0, 1 - second_compensation),
function=tick_timer, function=tick_timer,
args=( args=(
timer, timer,
...@@ -118,6 +137,8 @@ class TimerConsumer(AsyncWebsocketConsumer): ...@@ -118,6 +137,8 @@ class TimerConsumer(AsyncWebsocketConsumer):
).start() ).start()
async def receive(self, text_data: str) -> None: async def receive(self, text_data: str) -> None:
await sync_to_async(self.timer.refresh_from_db)()
json_data = json.loads(text_data) json_data = json.loads(text_data)
response = {} response = {}
...@@ -141,8 +162,6 @@ class TimerConsumer(AsyncWebsocketConsumer): ...@@ -141,8 +162,6 @@ class TimerConsumer(AsyncWebsocketConsumer):
if reset_timer or (self.timer.id not in running_timer_threads and self.timer.is_running): if reset_timer or (self.timer.id not in running_timer_threads and self.timer.is_running):
await self.run_timer() await self.run_timer()
await sync_to_async(self.timer.refresh_from_db)()
response.update( response.update(
{ {
"sync_time": { "sync_time": {
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment