Timer

How can I start a timer when a ball’s in a ellipse?

Your gonna have to be a bit more clear :-?

I’m making my firstn app where you have to put a small ball in a ellipse.
My question is: how can I make a stopwatch or something in my app if the ball is in the ellipse?
Does this is clear enough? :slight_smile:

@pepijnpp , First, I will help you with Timer.

function setup()
    timer = 0
end

function draw()
    if timer == 100 then
        text("timer reached 100", WIDTH/2, HEIGHT/2)
    else
        timer = timer + 1
        text("fdsfdsfs", WIDTH/2, HEIGHT/2)
    end
end

I will try help you to solve the problem with detecting collision between ball and ellipse.

You fella’s are tough!

@pepijnpp - here are some hints to get you started. Setup a global timer variable, something like:

function setup()
 timer = 0
end

Then as @West points out you need to detect that your ball is in the ellipse. To make it easier, assume you are looking for a circle in another circle, for which you could use something like:

function circleInCircle( centerX1, centerY1, radius1, centerX2, centerY2, radius2 )
        if radius1 > radius2 then 
            return false  
        end

        local dX, dY, radii = centerX1 - centerX2, centerY1 - centerY2, radius2 - radius1

        if dX * dX + dY * dY <= radii * radii then 
            return true
        else                                       
            return false 
        end
end

Finally, in draw() you check if the ball is in the circle and start incrementing the timer. Use DeltaTime which tells you how long in seconds since the last time draw() was called. You will need to join the dots in the following to get it to work in your App.

function draw()
    if circleInCircle(stick the appropriate bits in here) then
        timer = timer + DeltaTime
    else
        timer = 0      -- if you want to reset the timer every time the ball leaves the circle
    end
end

@pepijnpp, no it still isn’t really that clear. The more details you give, then the easier it is to help. If you have tried coding then great, post it as it makes it far more likely that you will get useful help. There are several ways in which you could start a timer when a ball enters an ellipse, but the right way for you will depend upon your own specific needs.

Have you tried coding anything yet? If not, I suggest sitting down and breaking down what you want to do into smaller chunks. A starter for 10 might be:

OK, we have a ball and an ellipse so we will need to use information about both these, such as the size, dimension and location. As the ball’s location will change then we will need a variable (or variables) store it’s location (x, y and possibly z coordinates - being pedantic a ball is a 3D object and an ellipse is a 2D one). Is the ellipse a fixed size? Will it stay in one place? If the answer is yes to both of these, then you could get away with “hard coding” the position and size, but it’s good practice to store anything that might change as a variable.

Next, the ball needs to move so I guess you’ve already thought about how this will move (e.g. controlled by a directional pad, tilting the ipad, touch select and dragging the object, motion based on a pre-defined algorithm which variables can be manually configured) and written the code to do this. So for every loop of the main program the current position of the ball is calculated and drawn in the appropriate place on the screen (as a default, the centre of your object will be drawn at your specified location).

Now for the collision detection - I’ll assume your constraining it to a 2D environment. Each loop of the main program, take the newly calculated position of the ball and compare it to the position of the ellipse (perhaps using an if statement along the lines of "if the ball’s x position equals the ellipse’s x position and the ball’s y position equals the ellipses y position then the ball is in the ellipse). If they are the same then start your timer. This will only check to see that centres of both the ball and ellipse line up. You’ll probably need more clarity on what you mean by “the ball is in the ellipse”. Do you mean the whole of the ball needs to be inside the ellipse or just some of it? This will allow you to modify your check statement to include the size of the ball and the ellipse - for example: if the ball’s x position is greater than (the ellipse’s x position subtracting half the width of the ellipse) AND the ball’s x position is less than (the ellipse’s x position plus half the width of the ellipse) will check to see if the centre of the ball is within the width of the ellipse. Depending upon how accurate you wish to be, you may prefer to calculate the straight line distance between to the two centres and check to see whether this is less than the radius of the ellipse.

The timer. As @Georgian posted - a timer is just a variable that is incremented each time the desired condition is met. You may also want to expand this to consider other possible situations. What happens if the ball leaves the ellipse? Does the timer reset or will it hold its value until the ball re-enters the ellipse?

Depending upon your design, an overall program design might look something like:

Function to set up the variables (ball start position, ellipse position, set timer to zero)

Main Draw function

  • Get the input from the user
  • Calculate the new position of the ball
  • Check the position of the ball against the ellipse
    – if the ball is inside the ellipse then increment the timer variable
  • If the timer has reached its desired time then execute the next part of the code

I deliberately haven’t supplied you with a chunk of code that does the check, as you will learn much more by doing it yourself (and you also have specified exactly what you want). Have a go, and if it doesn’t work post your code and I’ll be happy to have a look at it.

Here is small timer class and an example program. I’m sure the class can be expanded quite a bit, but I didn’t have a lot of time to spend on it.


function setup()
    print("Example of 3 timers running\
")
    print("program started at ",ElapsedTime)   
    framecount = 0
    
    a=timer()
    b=timer()
    c=timer()
        
    c:startTimer()
    print("\
timer c started at ",ElapsedTime)
end

function draw()
    background(40, 40, 50)  
    framecount = framecount + 1
    
    if framecount == 150 then        -- start timer a after 150 draws
        a:startTimer()
        print("\
timer a started at ",ElapsedTime)
    end 
     
    if a:checkTimer(15) then
        print("timer a stopped 15sec",ElapsedTime)
        b:startTimer()
        print("\
timer b started at ",ElapsedTime)
        print("\
timer c still running",c:running())
        print("timer c run time",c:runTime())
    end
    
    if b:checkTimer(10) then
        print("\
timer b stopped 10sec",ElapsedTime)
        print("\
timer c still running",c:running())
        print("timer c run time",c:runTime())        
    end
    
    if c:checkTimer(40) then
        print("\
timer c stopped 40sec",ElapsedTime)
        print("\
timer a still running",a:running())
        print("timer b still running",b:running())
        print("timer c still running",c:running())               
        print("\
End of example\
program can now be stopped")
    end
end


timer = class()

-- initialize timer
function timer:init()
    self.timer = 0   
end

-- starts the timer
function timer:startTimer()
    self.timer = ElapsedTime
end

-- returns true if timer is still running
function timer:running()
    if self.timer > 0 then
        return true
    end
    return false
end

-- returns amount of time that timer has been running
function timer:runTime()
    if self.timer > 0 then
        return ElapsedTime - self.timer
    end
    return 0
end

-- returns true if timer is equal or greater than stopTime
-- if true, stops the timer by setting it to 0
function timer:checkTimer(stopTime)
    if self.timer > 0 then
        if ElapsedTime - self.timer >= stopTime then
            self.timer=0
            return true
        end
    end
    return false
end

I ported this Stopwatch class from Robert Sedgwick’s java collections. It is very simple and very useful.

Stopwatch = class()

function Stopwatch:init()
– you can accept and set parameters here
self.clock = os.clock()
end

function Stopwatch:elapsedTime()
return os.clock() - self.clock
end

Basic use:

Time = Stopwatch() – creat the time at the current time
Total = time:elapsedTime() – returns the elapsed time.

I use this test my algorithms efficiency.

Sorry, code didn’t post right…

Stopwatch = class()

function Stopwatch:init()
    -- you can accept and set parameters here
    self.clock = os.clock()
end

function Stopwatch:elapsedTime()
    return os.clock() - self.clock
end

@blmacbeth

You don’t have to do multiple posts if you make a mistake. There is an edit option at the top of each post so you can re-edit the original post and make any corrections. Believe me, I have had to use it many times.