EpicKnarvik97 80a62cad23
All checks were successful
KnarCraft/FFmpegConvert/master This commit looks good
Fixes conversion of files containing semicolons
2020-03-01 03:14:52 +01:00

133 lines
5.3 KiB
Java

package net.knarcraft.ffmpegconverter.converter;
import net.knarcraft.ffmpegconverter.streams.AudioStream;
import net.knarcraft.ffmpegconverter.streams.StreamObject;
import net.knarcraft.ffmpegconverter.streams.SubtitleStream;
import net.knarcraft.ffmpegconverter.streams.VideoStream;
import java.io.File;
import java.io.IOException;
import java.util.Arrays;
import java.util.List;
public class AnimeConverter extends Converter {
private String[] audioLang;
private String[] subtitleLang;
private boolean toStereo;
private boolean preventSignsAndSongs;
private boolean debug = false;
/**
* @param ffprobePath Path/command to ffprobe
* @param ffmpegPath Path/command to ffmpeg
* @param audioLang List of wanted audio languages in descending order
* @param subtitleLang List of wanted subtitle languages in descending order
* @param toStereo Convert video with several audio channels to stereo
* @param preventSignsAndSongs Prevent subtitles only converting signs and songs (not speech)
*/
public AnimeConverter(String ffprobePath, String ffmpegPath, String[] audioLang, String[] subtitleLang, boolean toStereo, boolean preventSignsAndSongs) {
this.ffprobePath = ffprobePath;
this.ffmpegPath = ffmpegPath;
this.audioLang = audioLang;
this.subtitleLang = subtitleLang;
this.toStereo = toStereo;
this.preventSignsAndSongs = preventSignsAndSongs;
}
public void convert(File file) throws IOException {
processFile(file.getParentFile(), file);
}
/**
* Reads streams from a file, and converts it to an mp4.
*
* @param folder The folder of the file to process
* @param file The file to process
* @throws IOException If the BufferedReader fails
*/
private void processFile(File folder, File file) throws IOException {
List<StreamObject> streams = probeFile(ffprobePath, file);
if (streams.isEmpty()) {
throw new IllegalArgumentException("The file has no valid streams. Please make sure the file exists and is not corrupt.");
}
String newPath = fileCollisionPrevention(folder.getAbsolutePath() + File.separator + stripExtension(file) + ".mp4", "mp4");
printl("Preparing to start process...");
String[] command = builderCommand(ffmpegPath, file.getName(), streams, newPath);
ProcessBuilder processBuilder = new ProcessBuilder(command);
convertProcess(processBuilder, folder);
}
/**
* Generates a command for a ProcessBuilder.
*
* @param executable The executable file for ffmpeg
* @param fileName The input file
* @param streams A list of ffprobe streams
* @param outFile The output file
* @return A list of commands
*/
private String[] builderCommand(String executable, String fileName, List<StreamObject> streams, String outFile) {
List<String> command = ffmpegWebVideo(executable, fileName);
if (this.debug) {
addDebug(command, 50, 120);
}
List<AudioStream> audioStreams = filterStreamsByType(streams, "audio");
List<VideoStream> videoStreams = filterStreamsByType(streams, "video");
List<SubtitleStream> subtitleStreams = filterStreamsByType(streams, "subtitle");
audioStreams = filterAudioStreams(audioStreams, audioLang);
subtitleStreams = filterSubtitleStreams(subtitleStreams, subtitleLang, preventSignsAndSongs);
VideoStream videoStream = null;
AudioStream audioStream = null;
SubtitleStream subtitleStream = null;
if (videoStreams.size() > 0) {
videoStream = videoStreams.get(0);
}
if (audioStreams.size() > 0) {
audioStream = audioStreams.get(0);
}
if (subtitleStreams.size() > 0) {
subtitleStream = subtitleStreams.get(0);
}
if (videoStream == null) {
throw new IllegalArgumentException("The file does not have any valid video streams.");
}
if (audioStream != null) {
command.add("-map");
command.add("0:" + audioStream.getAbsoluteIndex());
if (toStereo && audioStream.getChannels() > 2) {
command.add("-af");
command.add("pan=stereo|FL=FC+0.30*FL+0.30*BL|FR=FC+0.30*FR+0.30*BR");
}
}
if (subtitleStream != null && subtitleStream.getIsImageSubtitle()) {
command.add("-filter_complex");
command.add("[0:v:" + videoStream.getAbsoluteIndex() + "][0:" + subtitleStream.getAbsoluteIndex() + "]overlay");
} else if (subtitleStream != null) {
command.add("-map");
command.add("0:" + videoStream.getAbsoluteIndex());
command.add("-vf");
String safeFileName = escapeSpecialCharactersInFileName(fileName);
String subtitleCommand = String.format("subtitles=\"%s\"", safeFileName);
command.add(subtitleCommand);
} else {
command.add("-map");
command.add("0:" + videoStream.getAbsoluteIndex());
}
command.add(outFile);
return command.toArray(new String[0]);
}
@Override
public String[] getValidFormats() {
return VIDEO_FORMATS;
}
}