package org.jcodec.movtool;
import java.io.File;
import java.io.IOException;
import java.nio.ByteBuffer;
import org.jcodec.common.Assert;
import org.jcodec.common.NIOUtils;
import org.jcodec.common.SeekableByteChannel;
import org.jcodec.containers.mp4.MP4Util;
import org.jcodec.containers.mp4.MP4Util.Atom;
import org.jcodec.containers.mp4.boxes.BoxFactory;
import org.jcodec.containers.mp4.boxes.Header;
import org.jcodec.containers.mp4.boxes.MovieBox;
import org.jcodec.containers.mp4.boxes.NodeBox;
/**
* This class is part of JCodec ( www.jcodec.org ) This software is distributed
* under FreeBSD License
*
* @author The JCodec project
*
*/
public abstract class InplaceEdit {
protected abstract void apply(MovieBox mov);
public boolean save(File f) throws IOException, Exception {
SeekableByteChannel fi = null;
try {
fi = NIOUtils.rwFileChannel(f);
Atom moov = getMoov(fi);
Assert.assertNotNull(moov);
fi.position(moov.getOffset());
ByteBuffer oldMov = NIOUtils.fetchFrom(fi, (int) moov.getHeader().getSize());
Header header = Header.read(oldMov);
MovieBox movBox = (MovieBox) NodeBox.parseBox(oldMov, header, BoxFactory.getDefault());
apply(movBox);
oldMov.clear();
try {
movBox.write(oldMov);
} catch (Exception e) {
return false;
}
if (oldMov.hasRemaining()) {
if (oldMov.remaining() < 8)
return false;
oldMov.putInt(oldMov.remaining());
oldMov.put(new byte[] { 'f', 'r', 'e', 'e' });
}
oldMov.flip();
fi.position(moov.getOffset());
fi.write(oldMov);
return true;
} finally {
if (fi != null)
fi.close();
}
}
private Atom getMoov(SeekableByteChannel f) throws IOException {
for (Atom atom : MP4Util.getRootAtoms(f)) {
if ("moov".equals(atom.getHeader().getFourcc())) {
return atom;
}
}
return null;
}
}