I want to create a function in MATLAB (2020) that displays a countdown in the console. Using e.g., periodic timers, this can be easily achieved (see below), however I cannot delete the timer when the user presses CTRL+C
during the pause(3.1)
(and the continued execution of update_countdown
would lead to confusing results, deleting characters in the console instead of just displaying the update time)
Since timers seem to run asynchronously, my idea is to detect whether the timer-spawning function main()
is still running or has been terminated - however I can't seem to find a way to detect this from within the periodic timer function update_countdown
.
Based on my knowledge about figures that have
CloseRequestFcn()
- a function that can be specified to run after a figure has been closed,I suspect something like this ought to exist for functions.
(How) can I detect whether main()
is currently running within my MATLAB processs (from within the periodic timer function update_countdown()
)?
%save as script and run
main
function main()
timeout = 3;
t1 = timer('ExecutionMode', 'singleShot', 'StartDelay', timeout, 'TimerFcn', @finish);
t2 = timer('ExecutionMode', 'fixedRate','Period', 1, 'TimerFcn', {@update_countdown,datetime,timeout});
%^datetime is a built-in function that passes the current time
fprintf('countdown: %1i',timeout)
start(t2); start(t1); %start timers
pause(3.1); %<= arbitrary function
stop([t1 t2]); %stop timers
delete([t1 t2]); %delete timers
disp('Main: do more stuff!')
end
function update_countdown(src,ev,starttime,timeout)
%delete last displayed time, add new time (remaining)
t=round(seconds(datetime-starttime)); % time running: current time - start time
t=timeout - t;
fprintf('\b%i',t); %delete last character and replace it with currently remaining time
end
function finish(src,ev)
disp(' done!');
end
You can use the function onCleanup
for this. It registers a function to call when the function exits (whether normally or through Ctrl-C). See also this documentation page.
function main()
timeout = 3;
t1 = timer('ExecutionMode', 'singleShot', 'StartDelay', timeout, 'TimerFcn', @finish);
t2 = timer('ExecutionMode', 'fixedRate','Period', 1, 'TimerFcn', {@update_countdown,datetime,timeout});
%^datetime is a built-in function that passes the current time
obj = onCleanup(@() delete([t1 t2])); %delete timers when function terminates
fprintf('countdown: %1i',timeout)
start(t2); start(t1); %start timers
pause(3.1); %<= arbitrary function
stop([t1 t2]); %stop timers
disp('Main: do more stuff!')
end