selimanac / defold-modplayer

MOD/XM Module Player for Defold Engine
https://selimanac.github.io/
10 stars 1 forks source link
chiptune chiptune-player defold defold-game-engine defold-library module-player player

ModPlayer

This is chiptune player native extension for Defold Engine. ModPlayer can load and play .XM and .MOD file formats. Extension supported MacOS, Windows, Linux*, Android, iOS and HTML5.

Caution: This extension is not battle tested yet and you should consider it as alpha release. It may contain bugs.

Installation

Installation requires a few steps.

1- Add Dependency

You can use the ModPlayer extension in your own project by adding this project as a Defold library dependency.
Open your game.project file and in the dependencies field under project add:

https://github.com/selimanac/defold-modplayer/archive/master.zip

2- Bundle Resources Path

Open your game.project file and in the Bundle Resources field under project add:

/res

Bundle

3- Create Folders

Create /res/common/assets folders in your project root. Then you can place your .xm and .mod files here. You can add subfolders as you like; /res/common/assets/musics

Bundle

Notes & Known Issues

Example

See the example folder for simple usage.
For more examples: https://github.com/selimanac/defold-modplayer-examples
Nanowar game example: https://github.com/selimanac/nanowar-modplayer


    player.master_volume(1.0) -- Set master volume for musics ( 0.0 -> 1.0 is max level)
    local music = player.load_music("bb.xm") -- Load mod file and assign it is ID
    player.play_music(music) -- Play mod file
    player.music_volume(music, 0.5) -- Set volume for music ( 0.0 -> 1.0 is max level)
    player.music_pitch(music, 1.0) -- Set pitch for a music (1.0 is base level)
    print("Music length: ", player.music_lenght(music)) -- Get music time length (in seconds)

HTML5 Bundle

Unfortunately, it is not possible to build HTML5 on the Defold Editor with mod music(You can build it for testing, but can't load the musics). But you can bundle as HTML5 from the Editor with mod music.

Bundling for HTML5 is require of editing archive_files.json file. More info about the issue is here..
You can use a script or you can edit it manually.

- Python Script

I wrote a small python script for updating archive_files.jsonfile with music files data. You can find it here: https://github.com/selimanac/modplayer-html5-example/blob/master/mod_file_parser.py

- Manual

{
    "name": "level_1.xm",   <- Name of your file for loading from Defold
    "size": 42940,          <- Actual size of the file (bytes) 
    "pieces": [
        {
            "name": "../assets/audio/level_1.xm", <- Relative path to your mod files
            "offset": 0
        }
    ]
}

Example HTML5 project is here and example archive_files.json is here.

API

player.build_path(full_path:string)

!- Don't set this when bundling -!

Only required when developing on Defold Editor. <FULL_PATH> (absolute path) is the full path of your project folder/directory.
Don't forget to add trailing /.

player.build_path("<FULL_PATH>/res/common/assets/") -- Set build path when working on Editor only s
Examples

Windows:
player.build_path("C:/Users/user_name/your_project_path/res/common/assets/")

*nix:
player.build_path("/Users/user_name/your_project_path/res/common/assets/")

We don't need it when bundling:

local is_development = false -- If you are building on Defold Editor then set it true. If you are bundling set it false
if is_development then
    player.build_path("<FULL_PATH>/res/common/assets/") -- Set build path only for Defold Editor
end

player.master_volume(volume:double)

Set master volume for musics ( 0.0 -> 1.0 is max level)

player.master_volume(1.0)

player.load_music(file_name:string)

Load and parse mod file into memory. Returns ID.

local music = player.load_music("your_file_name.xm") -- Load mod file and assign it is ID[int] 

player.play_music(id:int)

Start music playing.

player.play_music(music) 

player.pause_music(id:int)

Pause music playing.

player.pause_music(music) 

player.resume_music(id:int)

Resume playing "paused" music

player.resume_music(music)

player.music_volume(id:int, volume:double)

Set volume for music ( 0.0 -> 1.0 is max level)

player.music_volume(music, 0.5)

player.music_pitch(id:int, pitch:double)

Set pitch for a music (1.0 is base level).

player.music_pitch(music, 1.0) 

player.music_lenght(id:int)

Get music time length (in seconds)

print("Music length: ", player.music_lenght(music))

player.music_played(id:int)

Get current music time played (in seconds)

print("Played : ", player.music_played(music))

player.music_loop(loop:int)

Set music loop count (loop repeats) NOTE: If set to -1, means infinite loop. Default is -1 (infinite)

player.music_loop(music, 1)

player.is_music_playing(id:int)

Check if music is playing. Also returns false if music is not loaded or unloaded.

print("is Playing:", player.is_music_playing(music)) 

player.stop_music(id:int)

Stop music playing

player.stop_music(music) 

player.unload_music(id:int)

Unload music from memory

player.unload_music(music)

player.xm_volume(id:int, volume:double, amplification:double)

Only for XM files. You can change the samples volume, but it may cause a clipping. You can balance it with amplification. Some bad modules may still clip. Default values; volume 1.0, amplification 0.25. Use it with caution!

player.xm_volume(music, 2.5, 0.15)

Dependencies

Thanks to all Defold team for their great support.