Currently I am making a rhythm game which needs to be in-sync as precisely as possible.
So I programmed to get music’s position every frame using “FMOD.Studio.EventInstance.getTimelinePosition” and use it to sync with the game.
It was working great as intended.
The problem came when implementing pause system on it.
Everytime the game pause and resume music again, “getTimelinePosition”'s value seems to go out of sync. The off-sync gets worse as the music is paused and resumed repeatly. For example, with multiple execution of pause/resume music, I’ve debugged to find out the system returns 51s when the song actually playing around 53s.
The game currently pause/resume music using “FMOD.Studio.EventInstance.setPause” method. Is there anyway the off-sync problem can be solved?
It’s difficult to reason about how the timeline position is going out of sync with the game without understanding what in-sync with the game means.
I’m guessing you have some sort of timer in your game which you pause at the same time that you call FMOD.Studio.EventInstance.setPaused?
FMOD.Studio.EventInstance.setPaused is an asynchronous operation - calling setPaused posts a command to the FMOD studio update thread and returns immediately, there is then some latency before the command is processed by FMOD studio and the event instance actually changes pause state. If your game pauses and unpauses immediately while the FMOD studio event pause state changes several milliseconds later this would introduce some drift.
To avoid this issue I would suggest using the DSP clock to synchronise your game when pausing/unpausing. FMOD.Studio.EventInstance.getChannelGroup can be used to get the low level channel group belonging to the event instance and then FMOD.ChannelGroup.getDSPClock can be used to retrieve the current DSP clock value.