0
$\begingroup$

I'm making music for my Blender game. After the song ends, I want it to start or loop from another portion of the song rather than the very beginning. I notice some games do that with music, but is it possible to do that with Blender?

Let's say the song starts off with a drum beat and then a melody later. When the song ends, I want it to start from the melody rather than the drum beat (the very beginning of the song).

$\endgroup$
0
$\begingroup$

It's possible, and you should use Python. Example blend file can be downloaded here, the code is fully commented.

Notes:

  • I've made this song especially for this answer. ;)
  • For moderators: The zip file is needed as I can't pack the music file on blend if I want to load it through Python. It's not possible to upload zip files on Blend-Exchange, so I posted the example file on my Google Drive. Sorry for the inconvenience.
import bge
import aud
from bge.logic import expandPath, globalDict

# Load music factory to memory at start, if not already
if not 'music' in globalDict.keys():

    # Self explanatory
    music_path = expandPath('//example_music.ogg')

    # Load at globalDict the buffered music factory
    # Buffering allows lower delay on playing a new loop
    globalDict['music'] = aud.Factory(music_path).buffer()

def main(cont):

    own = cont.owner

    # Sensors
    always = cont.sensors[0]

    # Other
    device = aud.device()

    # Constants
    START_POS = 0.0
    LOOP_POS = 8.0

    # If sensor activated and music factory is loaded in globalDict
    if always.positive and 'music' in globalDict.keys():

        # If playback handle is not present in current object
        # After handle is created, this block will not run anymore
        if not 'music' in own:

            # Create a property in current object with playback handle
            own['music'] = device.play(globalDict['music'])

            # Set starting position of first playback
            own['music'].position = START_POS

            # Warning message
            print('Song not playing, playing it from start', START_POS)

        # If playback handle is present in current object
        if 'music' in own:

            # If music stopped playing
            if own['music'].status == False:

                # Play and save a new handle in place of the older one
                own['music'] = device.play(globalDict['music'])

                # Set starting position of loop playback
                own['music'].position = LOOP_POS

                # Warning message
                print('Loop song at position', LOOP_POS)
$\endgroup$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.