From e1910fdff28332a14f2fe3c99f9282845b31c214 Mon Sep 17 00:00:00 2001 From: shadowislord Date: Wed, 19 Nov 2014 23:59:52 -0500 Subject: [PATCH] Fix OGG/Vorbis stream looping Previously, a discontinuity occurred when looping an OGG/Vorbis stream, this happens due to a bug in J-Ogg library. To work around this issue, we load the logical ogg stream and vorbis stream from scratch based on the already loaded existing OGG pages instead of using the buggy setTime(0) call. --- .../jme3/audio/plugins/CachedOggStream.java | 23 ++++- .../com/jme3/audio/plugins/OGGLoader.java | 95 +++++++++---------- 2 files changed, 62 insertions(+), 56 deletions(-) diff --git a/jme3-jogg/src/main/java/com/jme3/audio/plugins/CachedOggStream.java b/jme3-jogg/src/main/java/com/jme3/audio/plugins/CachedOggStream.java index 956d4af51..9ac18a602 100644 --- a/jme3-jogg/src/main/java/com/jme3/audio/plugins/CachedOggStream.java +++ b/jme3-jogg/src/main/java/com/jme3/audio/plugins/CachedOggStream.java @@ -62,6 +62,7 @@ public class CachedOggStream implements PhysicalOggStream { private OggPage lastPage; private int pageNumber; + private int serialno; public CachedOggStream(InputStream in) throws IOException { sourceStream = in; @@ -106,6 +107,19 @@ public class CachedOggStream implements PhysicalOggStream { } } + public LogicalOggStream reloadLogicalOggStream() { + logicalStreams.clear(); + LogicalOggStreamImpl los = new LogicalOggStreamImpl(this, serialno); + logicalStreams.put(serialno, los); + + for (IntMap.Entry entry : oggPages) { + los.addPageNumberMapping(entry.getKey()); + los.addGranulePosition(entry.getValue().getAbsoluteGranulePosition()); + } + + return los; + } + private int readOggNextPage() throws IOException { if (eos) return -1; @@ -120,10 +134,11 @@ public class CachedOggStream implements PhysicalOggStream { } LogicalOggStreamImpl los = (LogicalOggStreamImpl) logicalStreams.get(op.getStreamSerialNumber()); - if(los == null) { - los = new LogicalOggStreamImpl(this, op.getStreamSerialNumber()); - logicalStreams.put(op.getStreamSerialNumber(), los); - los.checkFormat(op); + if (los == null) { + serialno = op.getStreamSerialNumber(); + los = new LogicalOggStreamImpl(this, op.getStreamSerialNumber()); + logicalStreams.put(op.getStreamSerialNumber(), los); + los.checkFormat(op); } los.addPageNumberMapping(pageNumber); diff --git a/jme3-jogg/src/main/java/com/jme3/audio/plugins/OGGLoader.java b/jme3-jogg/src/main/java/com/jme3/audio/plugins/OGGLoader.java index 5fb030981..10da62aec 100644 --- a/jme3-jogg/src/main/java/com/jme3/audio/plugins/OGGLoader.java +++ b/jme3-jogg/src/main/java/com/jme3/audio/plugins/OGGLoader.java @@ -49,8 +49,6 @@ import java.io.IOException; import java.io.InputStream; import java.nio.ByteBuffer; import java.util.Collection; -import java.util.logging.Level; -import java.util.logging.Logger; public class OGGLoader implements AssetLoader { @@ -66,9 +64,13 @@ public class OGGLoader implements AssetLoader { private static class JOggInputStream extends InputStream { private boolean endOfStream = false; - protected final VorbisStream vs; + protected PhysicalOggStream ps; + protected LogicalOggStream ls; + protected VorbisStream vs; - public JOggInputStream(VorbisStream vs){ + public JOggInputStream(PhysicalOggStream ps, LogicalOggStream ls, VorbisStream vs){ + this.ps = ps; + this.ls = ls; this.vs = vs; } @@ -83,35 +85,34 @@ public class OGGLoader implements AssetLoader { } @Override - public int read(byte[] buf, int offset, int length) throws IOException{ - if (endOfStream) + public int read(byte[] buf, int offset, int length) throws IOException { + if (endOfStream) { return -1; + } int bytesRead = 0, cnt = 0; assert length % 2 == 0; // read buffer should be even - - while (bytesRead