If/ elif with an interval, no loop?

Hi everyone.

I would like to ask if there is a possibility to do a if - phrase with an interval, and only 1 result is given? Because i know it will keep being triggered in something like this:


own[‘offset’] = some integer value

preoffset = own[‘offset’] + 3

if own[‘offset’] >= 100 and own[‘offset’] < preoffset:
GameLogic.sendMessage(“haselnuss”)

elif own[‘offset’] >= 105 and own[‘offset’] < preoffset:
GameLogic.sendMessage(“haselnuss”)

elif own[‘offset’] >= 108 and own[‘offset’] < preoffset:
GameLogic.sendMessage(“haselnuss”)


the value offset is an integer that is generated from a float timer value and this increases really really fast, so there will be several gaps in the value list it gives. To ensure that the value i want to “catch” , still functions nicely and problemless, i want to bring it into an interval, as you can see.

‘offset’ is a value that keeps growing quickly, so

if offset is bettween its own value and its future value +3, the game logic will creates the message haselnuss.

I hope you could help me to solve this problem. The code lines should just generate 1 message and stop, then next statement

Thank you in advance

The typical statements to create one instance only:


...
if not isDone():
   if isConditionMet():
      doWhatYouWantToDo()
      markAsDone()

...

There are several ways to implement that concept:

  • end the object after done
  • switch to another state
  • ensure to measure the “done” condition e.g. by checking a property

I usually set a property with True when some thing has finished.

if not own.get("finished"):
    result = do_something()
    if result:
        own['finished'] = True

Then as soon as do_something() returns a useful result, the function no longer gets called.

If you’re trying to check == with a float you could try multiplying it and turning it in to an integer.

If you want to play an action when the timer == 0.0012

then:

time = int(own['timer'] * 10000)
if time == 12:
do_something()

However, float objects don’t always behave exactly as we’d like because of the problems with floating point numbers and binary numbers. It’s best not to rely too much on being able to get the exact value of a float.

if offset is bettween its own value and its future value +3, the game logic will creates the message haselnuss.

If I understand correctly you want it to activate every 3<insert value>, right? You should be able to use Always sensor to adjust the interval or through the timer property/time function


own['offset'] = # timer property
interval = 3 # set your interval here

if own['offset'] &gt; interval:
    own['offset'] = 0 # reset timer
    GameLogic.sendMessage("haselnuss")

Thank you very much!

I will soon try out the ways you suggested today.

@smoking mirror

I already converted that float value into an integer and i still can use the exact values it gives. Howhever, it always gives gaps and i have to keep reediting the value to make it work.

For example, the float runs to 1.0000 to 1.90000 ===> integer 10 to 19, but the value will mostly have 11, 13, 15, 16, 19. So if i decide to use int 18, i have to adjust it into 19, or 16. This way still works in BGE flawlessly even with low framerate. I think there is other easier way to do than this. Thats why i pick an interval for less work.

If I’m understanding what you want to do, you’re trying to test if a property “crosses” a value, even if it’s increasing too quickly to ever hit that value exactly? In that case you might do well to remember the previous value of the increasing property, and test if your target value is between the current and previous value (EG if you want something to happen when a timer hits 100, but there’s some lag and the timer skips from 99 to 101, this will still catch it)

Of course if I’ve misunderstood what you’re trying to do, just go ahead and ignore this!

You did understand the methode i want to archieve.

In this video i just input the offset values for the rhythm notes (manually). I had to adjust the values very often to fit with the integer from the timer. As you can see there, it works flawlessly. But really it takes like a day to enter and adjust every timing of each note

The timing where the note appears i s always 3 beats earlier than the timing, where player should press the key.

There is a ghost timer (offset), that runs 3 beats earlier than the real timer, with this i can receive the ghost timer from any song with different tempo (bpm)

own[‘offset’] = own[‘timer’] + 180 / own[‘realbpm’]

the offset value is then converted into an integer value

This kind synchronization I advice use better timer. Blender’s timers is based for screen updates, and they can be little untrusty in long time.

There are time module, with gives accurate time in millisecodns.
Just see:

import time
print (time.time())

You see time from computer clock, in miiliseconds. Example we have song beat is 120 BPM. Then beat rate is 5000 Ms per 1/4 quarter note.
We need just pick time from start and negates it from current time, and we have exact time from music running. Division that by 1000 gives it in seconds. Then no need to know framerates etc…
Then you need only make list of beats and give tolerance when player hit buttons to accept hit score.

Edit:
You seems make elif for every beats from video.
Make just list of beat times and compare them with for loops, read that list from file, It is not so hard, just little Python basics. Else you have hard debugged ‘hardcoded’ script for just one music.

Interesting idea byt to way.


It gives me a long columm of float values like this @.@

Okkey, I remember wrong, it gives seconds in integer and milliseconds for mantissa.
Anyway, this is time experinced from (1.1.1982) in seconds. You just get start time and negate it current time to get song time.

That’s the computer clock time.

Use monotonic (from the the time module), and then you can take the difference of a start timestamp, and the current time (time.monotonic()) and that’s the elapsed time.

stc=1

I just started the code with (time.monotonic()) ,after 1 second, it showed this

anyway, i thank you alot for your support. I will try to fix t his timing issue in future. There is another problem with loop clause i am having too.

I made a script that can send messages with different properties. Like this:

import GameLogic

cont = GameLogic.getCurrentController()
own = cont.owner

if own[‘mapnber’] == 1:

own['mapname'] = str("MightySoya")
GameLogic.sendMessage("changemap1","none","Mapchanger")

elif own[‘mapnber’] == 2:

own['mapname'] = str("B2ST")   
GameLogic.sendMessage("changemap2","none","Mapchanger")

If the mapnber is 1 , it will send “changemap1” , if 2, then “changemap2”. The problem i am having is, the scene which receives the message will keep being set/ restarted to its scene over and over again. I cannot really start anything with this. Could anyone explain to me, how i could use the methode of smoking mirror in my script like above?

if not own.get(“finished”): result = do_something()
if result: own[‘finished’] = True

Here is somekind example if you still interested for musical game.
I made this “Drumhero” in few minutes, but you may get some idea what I mean.

Drumhero.zip (1.96 MB)

wow , i like it. I saw it automaticly generates beat using midi values of it.

That demo uses pre calculated data from midi data, bequese I am writing midi parser just now, and it it another program.
It generates keyframes to animation from midi. Now just test with game engine. Basically I can apply my midiparser to directly ge:
Just need some time.

really advanced how you do it. I will sure look at this blendfile often in future.

I want to challenge the player with my kind of beat maps so i need to input the timing of everything manually. It should be complex like this: ( this is a video from my gaming channel)

Hmm… Now wondering has anybody used dance mat in Blender game. :smiley:

Whoo, now we see “Pianohero”, Actually there are piano teacher in freeware programs. It get midi track and shows bars in keyboard,
and uses real midi keyboard as playcontroller.

I have my own program (Midiani), with I used for generating blender keyframes with many variations from midi tracks.(Yep, I seen Animusic years ago)
If I compose own music, it is easy to get midi tracks for certain instruments.
There are even pitchfollower in daw, with can generate midi notes from acoustic tracks.
And beat to midi plug (That can do for drum tracks)

So I think we need allways use mp3 music for audio and same song midi files for making musical animation data.

If everybody doesn’t know?
mp3, wav, etc… They consists raw acoustic audio.
when midi consists notes and information for instruments to play. Midifiles allso saves separate tracks for every instruments.

Thanks for the info. My talents don’t stretch to music at all so the most I do with sound is editing WAVs in Audacity.
I think if someone knows a bit of python and has some musical skill you could make a good music game in Blender.