/** * Decompresses the list of entries and returns the list of decoding times. * * @param entries compressed entries * @return decoding time per sample */ public static synchronized long[] blowupTimeToSamples(List<TimeToSampleBox.Entry> entries) { SoftReference<long[]> cacheEntry; if ((cacheEntry = cache.get(entries)) != null) { long[] cacheVal; if ((cacheVal = cacheEntry.get()) != null) { return cacheVal; } } long numOfSamples = 0; for (TimeToSampleBox.Entry entry : entries) { numOfSamples += entry.getCount(); } assert numOfSamples <= Integer.MAX_VALUE; long[] decodingTime = new long[(int) numOfSamples]; int current = 0; for (TimeToSampleBox.Entry entry : entries) { for (int i = 0; i < entry.getCount(); i++) { decodingTime[current++] = entry.getDelta(); } } cache.put(entries, new SoftReference<long[]>(decodingTime)); return decodingTime; }
inputStream.read(data); samples.add(ByteBuffer.wrap(data)); stts.add(new TimeToSampleBox.Entry(1, 1024)); inputStream.mark(15);
static List<TimeToSampleBox.Entry> adjustTts(List<TimeToSampleBox.Entry> source, double timeScaleFactor, long[] syncSample, long[] syncSampleTimes) { long[] sourceArray = TimeToSampleBox.blowupTimeToSamples(source); long summedDurations = 0; LinkedList<TimeToSampleBox.Entry> entries2 = new LinkedList<TimeToSampleBox.Entry>(); for (int i = 1; i <= sourceArray.length; i++) { long duration = sourceArray[i - 1]; long x = Math.round(timeScaleFactor * duration); TimeToSampleBox.Entry last = entries2.peekLast(); int ssIndex; if ((ssIndex = Arrays.binarySearch(syncSample, i + 1)) >= 0) { // we are at the sample before sync point if (syncSampleTimes[ssIndex] != summedDurations) { long correction = syncSampleTimes[ssIndex] - (summedDurations + x); LOG.finest(String.format("Sample %d %d / %d - correct by %d", i, summedDurations, syncSampleTimes[ssIndex], correction)); x += correction; } } summedDurations += x; if (last == null) { entries2.add(new TimeToSampleBox.Entry(1, x)); } else if (last.getDelta() != x) { entries2.add(new TimeToSampleBox.Entry(1, x)); } else { last.setCount(last.getCount() + 1); } } return entries2; }
if (trun.isSampleDurationPresent()) { if (decodingTimeEntries.size() == 0 || decodingTimeEntries.get(decodingTimeEntries.size() - 1).getDelta() != entry.getSampleDuration()) { decodingTimeEntries.add(new TimeToSampleBox.Entry(1, entry.getSampleDuration())); } else { TimeToSampleBox.Entry e = decodingTimeEntries.get(decodingTimeEntries.size() - 1); e.setCount(e.getCount() + 1); decodingTimeEntries.add(new TimeToSampleBox.Entry(1, tfhd.getDefaultSampleDuration())); } else { decodingTimeEntries.add(new TimeToSampleBox.Entry(1, trex.getDefaultSampleDuration()));
if (trun.isSampleDurationPresent()) { if (decodingTimeEntries.size() == 0 || decodingTimeEntries.get(decodingTimeEntries.size() - 1).getDelta() != entry.getSampleDuration()) { decodingTimeEntries.add(new TimeToSampleBox.Entry(1, entry.getSampleDuration())); } else { TimeToSampleBox.Entry e = decodingTimeEntries.get(decodingTimeEntries.size() - 1); e.setCount(e.getCount() + 1); decodingTimeEntries.add(new TimeToSampleBox.Entry(1, tfhd.getDefaultSampleDuration())); } else { decodingTimeEntries.add(new TimeToSampleBox.Entry(1, trex.getDefaultSampleDuration()));
if (trun.isSampleDurationPresent()) { if (decodingTimeEntries.size() == 0 || decodingTimeEntries.get(decodingTimeEntries.size() - 1).getDelta() != entry.getSampleDuration()) { decodingTimeEntries.add(new TimeToSampleBox.Entry(1, entry.getSampleDuration())); } else { TimeToSampleBox.Entry e = decodingTimeEntries.get(decodingTimeEntries.size() - 1); e.setCount(e.getCount() + 1); decodingTimeEntries.add(new TimeToSampleBox.Entry(1, tfhd.getDefaultSampleDuration())); } else { decodingTimeEntries.add(new TimeToSampleBox.Entry(1, trex.getDefaultSampleDuration()));
long curEntryLeft = timeQueue.peek().getCount(); while (left > curEntryLeft) { left -= curEntryLeft; timeQueue.remove(); curEntryLeft = timeQueue.peek().getCount(); entry.setSampleDuration(timeQueue.peek().getDelta()); if (--curEntryLeft == 0 && timeQueue.size() > 1) { timeQueue.remove(); curEntryLeft = timeQueue.peek().getCount();
double stretch = (double) sc / refSampleCount; TimeToSampleBox.Entry sttsEntry = testTrack.getDecodingTimeEntries().get(0); long samplesPerFrame = sttsEntry.getDelta(); // Assuming all audio tracks have the same number of samples per frame, which they do for all known types long samplesPerFrame = sttsEntry.getDelta(); // Assuming all audio tracks have the same number of samples per frame, which they do for all known types double factor = (double) ase.getSampleRate() / (double) minSampleRate; if (factor != Math.rint(factor)) { // Not an integer
double stretch = (double) sc / refSampleCount; TimeToSampleBox.Entry sttsEntry = testTrack.getDecodingTimeEntries().get(0); long samplesPerFrame = sttsEntry.getDelta(); // Assuming all audio tracks have the same number of samples per frame, which they do for all known types long samplesPerFrame = sttsEntry.getDelta(); // Assuming all audio tracks have the same number of samples per frame, which they do for all known types double factor = (double) ase.getSampleRate() / (double) minSampleRate; if (factor != Math.rint(factor)) { // Not an integer
long curEntryLeft = timeQueue.peek().getCount(); while (left > curEntryLeft) { left -= curEntryLeft; timeQueue.remove(); curEntryLeft = timeQueue.peek().getCount(); entry.setSampleDuration(timeQueue.peek().getDelta()); if (--curEntryLeft == 0 && timeQueue.size() > 1) { timeQueue.remove(); curEntryLeft = timeQueue.peek().getCount();
buffered.clear(); samples.add(bb); stts.add(new TimeToSampleBox.Entry(1, frametick)); if (nal_unit_type == 5) { // IDR Picture stss.add(frameNr);
buffered.clear(); samples.add(bb); stts.add(new TimeToSampleBox.Entry(1, frametick)); if (nal_unit_type == 5) { // IDR Picture stss.add(frameNr);
inputStream.read(data); samples.add(ByteBuffer.wrap(data)); stts.add(new TimeToSampleBox.Entry(1, 1024)); inputStream.mark(15);
private static long[] getTimes(Track track, Movie m) { final CacheTuple key = new CacheTuple(track, m); final long[] result = getTimesCache.get(key); if (result != null) { return result; } long[] syncSamples = track.getSyncSamples(); long[] syncSampleTimes = new long[syncSamples.length]; Queue<TimeToSampleBox.Entry> timeQueue = new LinkedList<TimeToSampleBox.Entry>(track.getDecodingTimeEntries()); int currentSample = 1; // first syncsample is 1 long currentDuration = 0; long currentDelta = 0; int currentSyncSampleIndex = 0; long left = 0; final long scalingFactor = calculateTracktimesScalingFactor(m, track); while (currentSample <= syncSamples[syncSamples.length - 1]) { if (currentSample++ == syncSamples[currentSyncSampleIndex]) { syncSampleTimes[currentSyncSampleIndex++] = currentDuration * scalingFactor; } if (left-- == 0) { TimeToSampleBox.Entry entry = timeQueue.poll(); left = entry.getCount() - 1; currentDelta = entry.getDelta(); } currentDuration += currentDelta; } getTimesCache.put(key, syncSampleTimes); return syncSampleTimes; }
private static long[] getTimes(Track track, Movie m) { final CacheTuple key = new CacheTuple(track, m); final long[] result = getTimesCache.get(key); if (result != null) { return result; } long[] syncSamples = track.getSyncSamples(); long[] syncSampleTimes = new long[syncSamples.length]; Queue<TimeToSampleBox.Entry> timeQueue = new LinkedList<TimeToSampleBox.Entry>(track.getDecodingTimeEntries()); int currentSample = 1; // first syncsample is 1 long currentDuration = 0; long currentDelta = 0; int currentSyncSampleIndex = 0; long left = 0; final long scalingFactor = calculateTracktimesScalingFactor(m, track); while (currentSample <= syncSamples[syncSamples.length - 1]) { if (currentSample++ == syncSamples[currentSyncSampleIndex]) { syncSampleTimes[currentSyncSampleIndex++] = currentDuration * scalingFactor; } if (left-- == 0) { TimeToSampleBox.Entry entry = timeQueue.poll(); left = entry.getCount() - 1; currentDelta = entry.getDelta(); } currentDuration += currentDelta; } getTimesCache.put(key, syncSampleTimes); return syncSampleTimes; }
static List<TimeToSampleBox.Entry> getDecodingTimeEntries(List<TimeToSampleBox.Entry> origSamples, long fromSample, long toSample) { if (origSamples != null && !origSamples.isEmpty()) { long current = 0; ListIterator<TimeToSampleBox.Entry> e = origSamples.listIterator(); LinkedList<TimeToSampleBox.Entry> nuList = new LinkedList<TimeToSampleBox.Entry>(); // Skip while not yet reached: TimeToSampleBox.Entry currentEntry; while ((currentEntry = e.next()).getCount() + current <= fromSample) { current += currentEntry.getCount(); } // Take just a bit from the next if (currentEntry.getCount() + current >= toSample) { nuList.add(new TimeToSampleBox.Entry(toSample - fromSample, currentEntry.getDelta())); return nuList; // done in one step } else { nuList.add(new TimeToSampleBox.Entry(currentEntry.getCount() + current - fromSample, currentEntry.getDelta())); } current += currentEntry.getCount(); while (e.hasNext() && (currentEntry = e.next()).getCount() + current < toSample) { nuList.add(currentEntry); current += currentEntry.getCount(); } nuList.add(new TimeToSampleBox.Entry(toSample - current, currentEntry.getDelta())); return nuList; } else { return null; } }
static List<TimeToSampleBox.Entry> adjustTts(List<TimeToSampleBox.Entry> source, double timeScaleFactor, long[] syncSample, long[] syncSampleTimes) { long[] sourceArray = TimeToSampleBox.blowupTimeToSamples(source); long summedDurations = 0; LinkedList<TimeToSampleBox.Entry> entries2 = new LinkedList<TimeToSampleBox.Entry>(); for (int i = 1; i <= sourceArray.length; i++) { long duration = sourceArray[i - 1]; long x = Math.round(timeScaleFactor * duration); TimeToSampleBox.Entry last = entries2.peekLast(); int ssIndex; if ((ssIndex = Arrays.binarySearch(syncSample, i + 1)) >= 0) { // we are at the sample before sync point if (syncSampleTimes[ssIndex] != summedDurations) { long correction = syncSampleTimes[ssIndex] - (summedDurations + x); LOG.finest(String.format("Sample %d %d / %d - correct by %d", i, summedDurations, syncSampleTimes[ssIndex], correction)); x += correction; } } summedDurations += x; if (last == null) { entries2.add(new TimeToSampleBox.Entry(1, x)); } else if (last.getDelta() != x) { entries2.add(new TimeToSampleBox.Entry(1, x)); } else { last.setCount(last.getCount() + 1); } } return entries2; }