palace icon indicating copy to clipboard operation
palace copied to clipboard

Decoder.seek() always return False

Open caliuf opened this issue 4 years ago • 3 comments

Hi Everyone, on my system Decoder.seek() doesn't seem to work, details below.

As usual, thanks in advance!

How to Reproduce

This code:

from palace import Device, Source, Context, Buffer, decode

with Device() as dev, Context(dev) as ctx, Source(ctx) as src:
    src.spatialize = True
    src.relative = True
    dec = decode(PROJECT_DIR + "/samples/sample1.mp3")
    with Buffer.from_decoder(dec, "myname") as buf:
        print(f"length_seconds={dec.length_seconds}, length={dec.length}")
        ret = dec.seek(12 * 44100)
        if not ret:
            raise RuntimeError()
        else:
            print("seek ok")
        
        buf.play(src)
        while src.playing:
            time.sleep(1)

Prints:

length_seconds=12.434285714285714, length=548352
seek ok

But no matter what I put in the seek pos, the track starts always from the beginning (but if I put for instance 13 secs that is more than the track length it correctly returns False)

Is there something I'm missing? Is there something I could do to fiddle with the Decoder factory or the Decoder object returned in order to make it work?

System info

  • Palace Version: 0.2.1
  • platform.platform() = Linux-4.15.0-112-generic-x86_64-with-LinuxMint-19.1-tessa
  • platform.python_version() = 3.7.5
  • platform.python_compiler() = GCC 8.3.0

caliuf avatar Sep 14 '20 21:09 caliuf

Hello there, you tried to seek the decoder after feeding it to the buffer, the playback position was not affected. You can tried Source.offset instead. In addition, usually you can .play decoders directly or load the file directly to a buffer, Buffer.from_decoder is usually only needed for customly defined decoders.

McSinyx avatar Sep 15 '20 04:09 McSinyx

Sorry @McSinyx after a first trial I forgot to answer.

Your solution fix my test case actually, but for some reason doesn't fix this problem in my app, and I still have to figure out why, but I think this issue could be closed, should be something on my side (any possible idea of what can make offset fail, though?)

For answering your suggestions: playing decoder directly will not benefit from buffering (correct?), that is something very useful for having a smooth start, while using source.offset will require to set it after .play() call, that I think will vanish the initial buffering.

Thanks for your help!

caliuf avatar Sep 18 '20 10:09 caliuf

Sorry for the late reply, I've been burnt out a bit for quite a while :smile:

any possible idea of what can make offset fail, though?

Which kind of file were you trying to play and how exactly you used palace to play it? AFAIK setting offset simply either point to the new location in memory (for buffers) or perform file system calls (for decoders). If I may have my hands on a reproducible case, I might be able to help figuring out why it might fail.

playing decoder directly will not benefit from buffering

Playing decoders does buffer, but their buffers are relatively small, depending on what you give [Decoder.play](playing decoder directly will not benefit from buffering).

while using source.offset will require to set it after .play() call, that I think will vanish the initial buffering

IIUC your point, then setting offset of a source playing either decoders or buffers would jump directly to the point you want to play thanks to random access. The only advantage of Buffer is to avoid loading the audio the second time (think of it as caching the whole track). My earlier point was that you should play decoders or buffer directly and avoid loading redundantly creating buffers from decoders (unless the decoders are programmatically defined in Python&emdash;see GH-10).

McSinyx avatar Sep 30 '20 14:09 McSinyx