I have a problem. How can I make the button stop receiving clicks until the action inside it is finished?

LiveCode is the premier environment for creating multi-platform solutions for all major operating systems - Windows, Mac OS X, Linux, the Web, Server environments and Mobile platforms. Brand new to LiveCode? Welcome!

Moderators: FourthWorld, heatherlaine, Klaus, kevinmiller, robinmiller

crokyweb
Posts: 14
Joined: Fri Apr 15, 2022 1:55 pm

Re: I have a problem. How can I make the button stop receiving clicks until the action inside it is finished?

Post by crokyweb » Tue Nov 07, 2023 11:37 am

so there is a gap in LC in the calculation of seconds and how it serves me hundredths of a second.
Does anyone see a solution or should I tell my client that at the moment I cannot continue the development of the program he commissioned me?

richmond62
Livecode Opensource Backer
Livecode Opensource Backer
Posts: 9389
Joined: Fri Feb 19, 2010 10:17 am
Location: Bulgaria

Re: I have a problem. How can I make the button stop receiving clicks until the action inside it is finished?

Post by richmond62 » Tue Nov 07, 2023 12:31 pm

If the discrepancy between LC's 'seconds' and real world seconds is constant then you can make adjustments for that, and you can keep your client happy.

IF, however (as has been suggested) the discrepancy may vary according to processor load you are in the sh*t, I am afraid.

It is also not clear whether the discrepancy comes about in your computer's operating system, or in you LC stack.

If the discrepancy comes about in your LC stack I would suppose it would be constant.

I also wonder if, instead of "counting its own fingers" whether (and this depends on your client having a constant internet connexion) it cannot get its seconds from some external source, e.g. the internet, where you do not have to worry about LC having 9 fingers, or the computer having 11.

Many long years ago (about 45) I remember a teacher telling me at school that there was an international clock that worked out time from the decay of radioactive Caesium . . . whether that is just a "memory" or a real memory, I am just not sure . . . but I am sure there must be something like that that is used over the internet and LC can hook into.

[Wow! Not quite as 'past it' as I thought: https://www.sciencedirect.com/topics/engineering/cesium]

https://en.wikipedia.org/wiki/Network_Time_Protocol

Oh, and should you go out in the woods picking mushrooms, be careful to take a Geiger counter with you, as boletus edulis (one of my favourites) is a great accumulator of caesium: and a caesium-filled cep will give you more than an upset stomach.
-
boletus.jpg
boletus.jpg (11.54 KiB) Viewed 5480 times
-
SShot 2023-11-07 at 13.44.40.png
-
I see that nowadays these mushrooms are called 'Porcini' and are all the rage in fancy food shops . . . when I was picking them with my Mum in about 1968 they were unavailable in the shops and people thought we were bonkers eating them as "everyone knows that toadstools are poisonous": but England in the 1960 is only remarkable in my mem0ry in terms of the amazingly high levels of ignorance about lots and lots of things.
Last edited by richmond62 on Tue Nov 07, 2023 1:19 pm, edited 1 time in total.

richmond62
Livecode Opensource Backer
Livecode Opensource Backer
Posts: 9389
Joined: Fri Feb 19, 2010 10:17 am
Location: Bulgaria

Re: I have a problem. How can I make the button stop receiving clicks until the action inside it is finished?

Post by richmond62 » Tue Nov 07, 2023 1:18 pm

Part of this has been discussed before:

https://forums.livecode.com/viewtopic.php?t=3494

dunbarx
VIP Livecode Opensource Backer
VIP Livecode Opensource Backer
Posts: 9670
Joined: Wed May 06, 2009 2:28 pm
Location: New York, NY

Re: I have a problem. How can I make the button stop receiving clicks until the action inside it is finished?

Post by dunbarx » Tue Nov 07, 2023 3:16 pm

Richmond.

The issue is not constant at all. As Jacque mentioned, other processes run hand in hand with an executing LC handler, and the results vary from run to run.

One can scale my little offering, waiting 11 mS, for example, instead of 10, but that does not improve repeatability at all.

So I guess I can assume that the answer to my "real" question is that there is no mystery why adding stuff to a handler makes the result faster than it "should". There is no "should", and faster or slower is not pertinent.

As I mentioned, and Jacque concurred,, one has to pull the time from some accurate source, but the ability to do that every hundredth of a second is likely not feasible. LC could post such data quickly enough, assuming the handler did not have its own burdens, but it lives in a burdensome world.

Craig

dunbarx
VIP Livecode Opensource Backer
VIP Livecode Opensource Backer
Posts: 9670
Joined: Wed May 06, 2009 2:28 pm
Location: New York, NY

Re: I have a problem. How can I make the button stop receiving clicks until the action inside it is finished?

Post by dunbarx » Tue Nov 07, 2023 3:28 pm

I made a simple test:

Code: Select all

on mouseUp
   put 0 into temp
   put the milliseconds into x
   repeat 1000000  -- one million
      add 1 to temp --can comment out later
   end repeat
   answer the milliseconds - x
end mouseUp
This does a little math a million times. I got 54 mS at the end. That is 18 million passes per second through that loop. Commenting out the "add" line gave 12 mS. or 80 million passes per second through the loop.

Well, that is fast enough if one stays inside a loop inside LC in a single handler. But I have a feeling those numbers will plummet if one queries an outside time server.

Mac Mini M2, 3.49 GHz.

Craig

LCMark
Livecode Staff Member
Livecode Staff Member
Posts: 1209
Joined: Thu Apr 11, 2013 11:27 am

Re: I have a problem. How can I make the button stop receiving clicks until the action inside it is finished?

Post by LCMark » Tue Nov 07, 2023 3:50 pm

The system clock on modern machine is highly accurate - it has to be otherwise a lot of things we rely on day in day out would not work. (By accurate I mean the drift over a course of a period of time between when it is synchronized with an external source is exceptionally small - most systems automatically sync with a time server periodically to keep them as accurate as possible).

The problem with the approaches above is that the countdown is being computed *relatively* - i.e. by making an assumption that it takes exactly a known amount of time to execute some code (whether that be wait, or wait combined with a number of other statements) and then updating a countdown variable iteratively. This is hugely inaccurate because on modern computers there is no guarantee any code will run in any particular time.

Instead, the solution is to compute the countdown by 'polling' at a fixed interval and comparing a start time with the current time. Roughly:

Code: Select all

local sStartTime

on mouseUp
   /* Record the start time - this is done in a script local so that when completed
     * its easy to verify the amount of time the countdown took. */
   put the milliseconds into sStartTime
 
   /* Compute the end time - 10000ms is 10seconds, so this will countdown for
     * 10 seconds. */
   local tEndTime
   put 10000 + sStartTime into tEndTime
   
   /* Start polling the system clock. */
   send "countDown tEndTime" to me in 0 milliseconds
end mouseUp

on countDown pEndTime
   /* Fetch the time *now* in milliseconds. */
   local tCurrentTime
   put the milliseconds into tCurrentTime
 
   /* Compute the time remaining. If the remaining time is zero (or indeed
     * less than zero because there has been a tiny overshoot) then exit. */
   local tRemaining
   put pEndTime - tCurrentTime into tRemaining
   if tRemaining <= 0 then
      /* This displays the amount of time (in seconds) which were actually spent
        * counting down. */
      put "DONE" && (tCurrentTime - sStartTime) / 1000
      exit countDown
   end if
   
   /* Log the time remaining in the countdown - in MM:SS.HH. (HH is hundredths of a second) */
   put "REMAINING:" && format("%d:%02d:%02d", (tRemaining div 60000), (tRemaining div 1000) mod 60, ((tRemaining div 10) mod 100))
   
   /* We poll every 10 milliseconds to ensure we get hundred of a second accuracy. */
   send "countDown pEndTime" to me in 10 milliseconds
end countDown
If you put this script in a button and click on it, you'll see a count down in the message box and then 'DONE' after 10 seconds when its complete - after DONE will be printed the *actual* time it took.

Note: This will be potentially quite CPU intensive as its polling every 10 milliseconds - as this is probably unnecessary (you can't actually see a number change 100 times a second!) so a better approach would probably be to poll every 50 milliseconds until you get within 200 milliseconds of the goal, and then poll at 10 milliseconds.

bn
VIP Livecode Opensource Backer
VIP Livecode Opensource Backer
Posts: 4003
Joined: Sun Jan 07, 2007 9:12 pm
Location: Bochum, Germany

Re: I have a problem. How can I make the button stop receiving clicks until the action inside it is finished?

Post by bn » Fri Nov 10, 2023 10:51 am

crokyweb wrote:
Tue Nov 07, 2023 11:37 am
so there is a gap in LC in the calculation of seconds and how it serves me hundredths of a second.
Does anyone see a solution or should I tell my client that at the moment I cannot continue the development of the program he commissioned me?
Hi,

Mark Waddingham posted a very nifty solution to your problem. It is very accurate and would solve your problem.
While counting down it might skip the display or intermediate hundreds of a second but when you stop it displays the correct time elapsed.

I adapted this to your sample stack for you to incorporate it into your stack keeping your naming conventions.
I put the logic into the mouseDown handler to reduce latency.

If you have questions feel free to ask.

Kind regards
Bernd
Attachments
TimerTestWaddingham.livecode.zip
(1.97 KiB) Downloaded 55 times

Post Reply

Return to “Getting Started with LiveCode - Experienced Developers”