Sorry your browser is not supported!

You are using an outdated browser that does not support modern web technologies, in order to use this site please update to a new browser.

Browsers supported include Chrome, FireFox, Safari, Opera, Internet Explorer 10+ or Microsoft Edge.

DarkBASIC Professional Discussion / Tutorial: How to make an Interrupt Timer in Darkbasic.

Author
Message
Sedit
6
Years of Service
User Offline
Joined: 3rd Sep 2017
Location: Ghetto of NJ
Posted: 15th Nov 2017 08:20 Edited at: 15th Nov 2017 08:22
I needed a Timer system for my little weekend project and noticed I needed a Timer system similar to things that Visual Basic has in which you can set the time and every second , 5 seconds or whatever that function would get called and your Sprite or whatever you were doing would get updated. After looking around to see if they had it since I am Very new to DBPro I ended up seeing ALOT of people asking the question but no real answers other then setting it up inside your loop and manually calling it whenever needed. That is sort of what I have done here except I have taken out the worry of this out of the programmers hands and assigned it to the SYNC function so that we don't have to bother ourselves with it anymore once its all setup.


Entire program is only around 20 lines of code and honestly could be streamlined and made MUCH more powerful with ease but its 3 in the morning and just figured I would share before I went to sleep because It seems like a lot of people could possibly make use out of something like this.

This code simply calls a function once every second that Rotates a Cube so you get a sort of Ticking motion out of its rotation however you can make any function you wish get called so that it does whatever you want it to.



Enjoy hope this helps someone,
~Sedit
Ortu
DBPro Master
16
Years of Service
User Offline
Joined: 21st Nov 2007
Location: Austin, TX
Posted: 15th Nov 2017 18:00
A good start

Now expand it to handle multiple timers, variable ticks/durations, and variable callback functions

Hint: keep a list of timers/timer datas that will be processed by the update and provide functions to add or remove timers from it.
http://games.joshkirklin.com/sulium

A single player RPG featuring a branching, player driven storyline of meaningful choices and multiple endings alongside challenging active combat and intelligent AI.
Sedit
6
Years of Service
User Offline
Joined: 3rd Sep 2017
Location: Ghetto of NJ
Posted: 15th Nov 2017 18:40
Thanks,
Multiple Timers would simply be placed in the Timer function itself. Each one with the TIMER() ... IF statement set to a different value.


There is definitely some potential to this and it is something I just whipped up in the middle of the night out of necessity. It allows for much cleaner code in my opinion then applying all the timer functions in the main game loop. This is essentially that but its more like playing it all into a function called SYNC.


I'm thinking of ways to streamline this and make it more compatible with various situations.

I am thinking I might need some sort of RegisterTimer() function that Creates a Timer objects, Creates a small area of memory like a few bytes to store the amount of time between Ticks, The issue I have now is that I have to make all of the Variables Global which I highly dislike, I think I might be able to Call the function which passes the Pointer to SET POSTSYNC CALLBACK POINTER, and Allocates a bit of memory for the time to point to in order to get the timer duration.

IDK Its all a work in progress at the moment, If you all can help me I will append the original post with a more advanced Version of the Timer since it seems like DBPro users have been screaming for something of this nature for sometime now to no avail.


What are your suggestions on how to arrange the Timer, Should I structure them With a TYPEDEF, an ARRAY, MEMBLOCK etc.

I am thinking that a TYPEDEF similar to

Type _ITimer
Function_PTR as integer
Duration as integer
endtype

DIM Timers() as _ITimer

function Register_Timer(function, duration) etc....
Timers(sizeof(Timers) + 1).Function = function
Timers(sizeof(Timers) + 1).Duration = Duration...


Pseudo-code at the moment but you understand.


Any Ideas? I want to link the Duration and the Function somehow so that I don't have to make Global Variables.
Ortu
DBPro Master
16
Years of Service
User Offline
Joined: 21st Nov 2007
Location: Austin, TX
Posted: 15th Nov 2017 23:10
Quote: "Type _ITimer
Function_PTR as integer
Duration as integer
endtype

DIM Timers() as _ITimer

function Register_Timer(function, duration) etc....
Timers(sizeof(Timers) + 1).Function = function
Timers(sizeof(Timers) + 1).Duration = Duration...
"


Yes, this is along the lines of how I do it, I have a few extra attributes in the type. I will post my functions when I get home.

Matrix1 also implements "Tickers" which do much the same btw.

Keep in mind, all arrays are always global in dbpro. You can access Timers(i).function (and so on) from anywhere, you don't need individual global variables for these.
http://games.joshkirklin.com/sulium

A single player RPG featuring a branching, player driven storyline of meaningful choices and multiple endings alongside challenging active combat and intelligent AI.
Ortu
DBPro Master
16
Years of Service
User Offline
Joined: 21st Nov 2007
Location: Austin, TX
Posted: 16th Nov 2017 01:04 Edited at: 16th Nov 2017 01:11
Here are the relevant functions that I use in my framework:

Please note that this won't compile as is, but you can see how it works. A couple of things:

it uses a number of the matrix1 dlls.
It is extracted from a larger system and makes some calls out to functions not included here, these have just been commented out here.
It also uses [] for arrays, which is invalid syntax, you can do a find and replace to change [ to ( and ] to ). (my preprocessor handles this.)
I initially used the matrix1 'call function' commands to execute the callback, but this causes graphical errors in Advanced Lighting (yeah, its a weird pair to conflict) and so implemented my own version as App_callFunction()
I prefer to work with function name rather than function pointer for readability and for places in which the name is always known, but a runtime pointer cant be (defining callback functions on UI elements in an xml file for instance)
The System_updateIntervals() is called regularly during the main update loop.

Why not just hard code the callbacks into the update function? >> then you are stuck with them as defined at compile time. keep it more abstract and now you can manage them during runtime. you can add a timer that only executes N times then is removed. Maybe you only want to add one after a given event. you get the idea.

http://games.joshkirklin.com/sulium

A single player RPG featuring a branching, player driven storyline of meaningful choices and multiple endings alongside challenging active combat and intelligent AI.
Sedit
6
Years of Service
User Offline
Joined: 3rd Sep 2017
Location: Ghetto of NJ
Posted: 16th Nov 2017 05:54
[QUOTE]
I prefer to work with function name rather than function pointer for readability and for places in which the name is always known...
Why not just hard code the callbacks into the update function? >> then you are stuck with them as defined at compile time. keep it more abstract and now you can manage them during runtime. you can add a timer that only executes N times then is removed. Maybe you only want to add one after a given event. you get the idea.[/QUOTE]


Yeah I would rather use the name as well but I chose to use the pointer because that is indeed a number and makes the whole system more fluid in case the need ever arises to change the Callback function for the timer during Runtime. I figured I would have to assign a value to it anyway if I needed to do so such as making a variable list of Strings or what not but it seemed pointless when a Pointer would be more versatile and if ever needed I could set up something that that Data is allocated along with the function in that area of memory so that everything was nice and tidy in the memory.

I have some code I was going to post but I started getting Runtime Errors when attempting to make multiple times which more then likely will be an easy fix but I got side tracked working on my game and have been at that all day so when I get a chance I will post my version.


Your code is very similar to what I have laid out but a little more advanced I think. Are you passing arguments to the called function? if so how? Its something i wish to setup where i pass my function to the sync command but i dont know how to pass arguments only set it up to be called during sync
Ortu
DBPro Master
16
Years of Service
User Offline
Joined: 21st Nov 2007
Location: Austin, TX
Posted: 16th Nov 2017 07:06 Edited at: 16th Nov 2017 07:13
Yes, I am passing arguments. I am not sure that you can do so with the postsync callback, but both 'call function ptr myPtr, myArgs' and 'call function name myFunc, myArgs' will accept them, up to something like 10.

For my dispatcher workaround, I just pass a single string, which can be type cast or split as needed.

In either case, you can just call your update function in the main loop before or after calling sync without necessarily attaching to sync

http://games.joshkirklin.com/sulium

A single player RPG featuring a branching, player driven storyline of meaningful choices and multiple endings alongside challenging active combat and intelligent AI.
Ortu
DBPro Master
16
Years of Service
User Offline
Joined: 21st Nov 2007
Location: Austin, TX
Posted: 16th Nov 2017 07:08 Edited at: 16th Nov 2017 07:08
duplicate
http://games.joshkirklin.com/sulium

A single player RPG featuring a branching, player driven storyline of meaningful choices and multiple endings alongside challenging active combat and intelligent AI.
Sedit
6
Years of Service
User Offline
Joined: 3rd Sep 2017
Location: Ghetto of NJ
Posted: 16th Nov 2017 09:50
As long as the update function does not carry and perimeters it could be attached to Sync, The way I am doing it now I have the main timer function which is calling an Array that contains any other functions IE timers that I registered. The Main timer function is basically the Dispatcher that calls all other timers and I have embedded that into the Sync command.

I know, It dont need to be in Sync but lets face it, It feels so much cooler and closer to the Ultimate goal of an Interrupt timer anyway . Plus it makes clean code for the main loop. Hell in my little example above the code for the main loop was nothing but sync.

Login to post a reply

Server time is: 2024-04-24 23:26:16
Your offset time is: 2024-04-24 23:26:16