# How to add the pause button to that dynamic stopwatch?

Referring to How to make a dynamic stopwatch?

Timers can now be created with timer = makeTimer[] and utilised with actions such as timer["lap"] to get the current lap time. Timers are quiescent unless asked to do something.

You could extend this to handle a pause function if that's required.

How do you add that pause button?

-
What are you talking about? Image Master? makeTimer? What are you quoting? –  Pickett Dec 19 '13 at 12:22
Jim, welcome to Mathematica.SE! In the future please add links to the previous questions you refer to. –  Mr.Wizard Dec 19 '13 at 12:45
Jim, have you tried something that hasn't worked? typically you can get more helpful responses if M.SE users know where you are getting stuck. –  bobthechemist Dec 19 '13 at 14:16
It seems that Jim has placed his question into a wrong page. It seems that it belongs to the page with the question referenced above, and it should be addressed to image_doctor who actually proposed the function makeTimer[] in his answer or to István Zachar, who accepted his answer. –  Alexei Boulbitch Dec 19 '13 at 15:02
@Alexei Respectfully, that is incorrect. Users are encouraged to post questions as questions. This user cannot post comments yet that isn't even an option. Further image_doctor (sadly) hasn't been here since August so it makes more sense to address the community. Jim did the right thing except that he forgot to include the link. –  Mr.Wizard Dec 19 '13 at 15:34

It's not very easy to add a pause button with the approach that image_doctor took. I can't think of any way of doing it without introducing auxiliary variables and it's just not very elegant. I tried a different approach which made it easier instead. I use scheduled tasks since the comment thread in the original question indicates that this is more precise, however in this example the resolution is only one second. Resolution can be changed by changing dt, but then the visualization/the increment would also have to be adapted.

timer[] :=
With[{time = Unique["time"], dt = Unique["dt"], paused = Unique["paused"]},
time = 0; dt = 1; paused = True;
If[! paused, time++]
, dt];
Row[{
Column[{
Button["Start", paused = False;],
Button["Paus", paused = True],
Button["Reset", time = 0; paused = True;],
Button[Dynamic[time]]
}],
Column[{Pane[
Dynamic@
ClockGauge[{Floor[Mod[time, 60 3600]/3600], Floor[Mod[time, 3600]/60], Mod[time, 60]}],
210, Alignment -> Right]
}]
}]
]


The code looks a bit funny with the home-made localization at the beginning, I had to do this because RunScheduledTask does not work inside DynamicModule, and I did not like the fact that Mathematica marked my dynamic variables red when I used Module.

How it looks:

timer[]


When you're done you can remove the scheduled events like this:

RemoveScheduledTask[ScheduledTasks[]]

-

Some variables have to be added to the method of the linked question to keep track of whether the stop watch is paused and the delay accumulated by the pauses.

Here's one way to adapt the method of the linked question. It still needs RunScheduledTask[time = timer["now"], 2] to be executed.

DynamicModule[{start = AbsoluteTime[], paused = 0},
makeTimer[] :=
(start = AbsoluteTime[]; paused = 0;
Switch[#,
"now", If[paused > 0, paused - start, AbsoluteTime[] - start],
"lap", If[paused > 0, paused - start, AbsoluteTime[] - start],
"reset", start = AbsoluteTime[]; If[paused > 0, paused = start]; 0.,
"pause", (paused = AbsoluteTime[]) - start,
"restart",
If[paused > 0, start += AbsoluteTime[] - paused; paused = 0];
AbsoluteTime[] - start
] &)
];


To add a pause button, a variable has to be added to keep track of the state of the timer.

DynamicModule[{state = "Pause"},
Grid[{
{Button["Start", timer = makeTimer[]; time = 0.;
state = "Pause"]}, {Button["Lap", time = timer["lap"]]},
{Button["Reset", time = timer["reset"]]},
{Button[Dynamic@state,
If[state == "Pause",
time = timer["pause"]; state = "Restart",
time = timer["restart"]; state = "Pause"]]},
{Button[Dynamic[ClockGauge@time]]}}]
]


Adding the UpdateInterval option to Refresh can control how often the stopwatch is updated.

Here's a simpler way to make a stopwatch. Clicking on it toggles the run/pause modes. Other commands may be added to the action of the Button.

DynamicModule[{time, offset = 0, stop, update = True},
Button[Dynamic@Refresh[
ClockGauge[If[update, time = Clock[Infinity], time] - offset]],
If[update,
stop = time; update = False,
offset += Clock[Infinity] - stop; update = True]]]


-