13#include <QRegularExpression>
17const QString keyAnimationExport =
"ANIMATION_EXPORT";
18const QString keyFfmpegPath =
"ffmpeg_path";
19const QString keyVideoDirectory =
"recorder_export/videodirectory";
20const QString keyInputFps =
"recorder_export/inputfps";
21const QString keyFps =
"recorder_export/fps";
22const QString keyResultPreview=
"recorder_export/resultpreview";
23const QString keyFirstFrameSec =
"recorder_export/firstframesec";
24const QString keyExtendResult =
"recorder_export/extendresult";
25const QString keyLastFrameSec =
"recorder_export/lastframesec";
26const QString keyResize =
"recorder_export/resize";
27const QString keySize =
"recorder_export/size";
28const QString keyLockRatio =
"recorder_export/lockratio";
29const QString keyLockFps =
"recorder_export/lockfps";
30const QString keyProfileIndex =
"recorder_export/profileIndex";
31const QString keyProfiles =
"recorder_export/profiles";
32const QString keyEditedProfiles =
"recorder_export/editedprofiles";
34const QString profilePrefix =
"-reinit_filter 0\n-framerate $IN_FPS\n-i \"$INPUT_DIR%07d.$EXT\"\n-framerate $OUT_FPS\n-start_number $FRAMES-1\n-i \"$INPUT_DIR%07d.$EXT\"\n";
37 {
"MP4 x264",
"mp4", profilePrefix %
"-filter_complex \"\n"
45 " [1]scale='min($WIDTH, iw*($HEIGHT/ih))':'min($HEIGHT, ih*($WIDTH/iw))'[hold1];\n"
46 " [hold1]pad=$WIDTH:$HEIGHT:(ow-iw)/2:(oh-ih)/2[hold2];\n"
47 " [hold2]setsar=1:1[hold3];\n"
48 " [hold3]split=3[preview1][transition1][end1];\n"
50 " [preview1]tpad=stop_mode=clone:stop_duration=$FIRST_FRAME_SEC[preview2];\n"
51 " [preview2]setpts=PTS-STARTPTS[preview3];\n"
53 " [transition1]tpad=stop_mode=clone:stop_duration=$TRANSITION_LENGTH[transition2];\n"
54 " [transition2]setpts=PTS-STARTPTS[transition3];\n"
55 " [transition3]framerate=$OUT_FPS[transition4];\n"
57 " [0]fps=$OUT_FPS[main1];\n"
58 " [main1]scale='min($WIDTH, iw*($HEIGHT/ih))':'min($HEIGHT, ih*($WIDTH/iw))':eval=frame[main2];\n"
59 " [main2]pad=$WIDTH:$HEIGHT:(ow-iw)/2:(oh-ih)/2:eval=frame[main3];\n"
60 " [main3]setsar=1:1[main4];\n"
61 " [transition4][main4]xfade=transition=smoothright:duration=$TRANSITION_LENGTH:offset=0[main5];\n"
63 " [end1]tpad=stop_mode=clone:stop_duration=$LAST_FRAME_SEC[end2];\n"
64 " [end2]setpts=PTS-STARTPTS[end3];\n"
66 " [preview3][main5][end3]concat=n=3:v=1:a=0[final1];\n"
67 " [final1]setpts=PTS-STARTPTS\n"
69 "\"\n-stats\n-loglevel error\n-c:v $H264_ENCODER\n-r $OUT_FPS\n-pix_fmt yuv420p" },
70 {
"GIF",
"gif", profilePrefix %
"-filter_complex \"\n"
71 " [1]scale='min($WIDTH, iw*($HEIGHT/ih))':'min($HEIGHT, ih*($WIDTH/iw))'[hold1];\n"
72 " [hold1]pad=$WIDTH:$HEIGHT:(ow-iw)/2:(oh-ih)/2[hold2];\n"
73 " [hold2]setsar=1:1[hold3];\n"
74 " [hold3]split=3[preview1][transition1][end1];\n"
76 " [preview1]tpad=stop_mode=clone:stop_duration=$FIRST_FRAME_SEC[preview2];\n"
77 " [preview2]setpts=PTS-STARTPTS[preview3];\n"
79 " [transition1]tpad=stop_mode=clone:stop_duration=$TRANSITION_LENGTH[transition2];\n"
80 " [transition2]setpts=PTS-STARTPTS[transition3];\n"
81 " [transition3]framerate=$OUT_FPS[transition4];\n"
83 " [0]fps=$OUT_FPS[main1];\n"
84 " [main1]scale='min($WIDTH, iw*($HEIGHT/ih))':'min($HEIGHT, ih*($WIDTH/iw))':eval=frame[main2];\n"
85 " [main2]pad=$WIDTH:$HEIGHT:(ow-iw)/2:(oh-ih)/2:eval=frame[main3];\n"
86 " [main3]setsar=1:1[main4];\n"
87 " [transition4][main4]xfade=transition=smoothright:duration=$TRANSITION_LENGTH:offset=0[main5];\n"
89 " [end1]tpad=stop_mode=clone:stop_duration=$LAST_FRAME_SEC[end2];\n"
90 " [end2]setpts=PTS-STARTPTS[end3];\n"
92 " [preview3][main5][end3]concat=n=3:v=1:a=0[final1];\n"
93 " [final1]setpts=PTS-STARTPTS[final2];\n"
94 " [final2]split[final3][final4];\n"
95 " [final3]palettegen[palettegen];\n"
96 " [final4][palettegen]paletteuse\n"
97 "\"\n-stats\n-loglevel error\n-r $OUT_FPS" },
98 {
"Matroska",
"mkv", profilePrefix %
"-filter_complex \"\n"
99 " [1]scale='min($WIDTH, iw*($HEIGHT/ih))':'min($HEIGHT, ih*($WIDTH/iw))'[hold1];\n"
100 " [hold1]pad=$WIDTH:$HEIGHT:(ow-iw)/2:(oh-ih)/2[hold2];\n"
101 " [hold2]setsar=1:1[hold3];\n"
102 " [hold3]split=3[preview1][transition1][end1];\n"
104 " [preview1]tpad=stop_mode=clone:stop_duration=$FIRST_FRAME_SEC[preview2];\n"
105 " [preview2]setpts=PTS-STARTPTS[preview3];\n"
107 " [transition1]tpad=stop_mode=clone:stop_duration=$TRANSITION_LENGTH[transition2];\n"
108 " [transition2]setpts=PTS-STARTPTS[transition3];\n"
109 " [transition3]framerate=$OUT_FPS[transition4];\n"
111 " [0]fps=$OUT_FPS[main1];\n"
112 " [main1]scale='min($WIDTH, iw*($HEIGHT/ih))':'min($HEIGHT, ih*($WIDTH/iw))':eval=frame[main2];\n"
113 " [main2]pad=$WIDTH:$HEIGHT:(ow-iw)/2:(oh-ih)/2:eval=frame[main3];\n"
114 " [main3]setsar=1:1[main4];\n"
115 " [transition4][main4]xfade=transition=smoothright:duration=$TRANSITION_LENGTH:offset=0[main5];\n"
117 " [end1]tpad=stop_mode=clone:stop_duration=$LAST_FRAME_SEC[end2];\n"
118 " [end2]setpts=PTS-STARTPTS[end3];\n"
120 " [preview3][main5][end3]concat=n=3:v=1:a=0[final1];\n"
121 " [final1]setpts=PTS-STARTPTS\n"
122 "\"\n-stats\n-loglevel error\n-pix_fmt yuv420p\n-r $OUT_FPS" },
123 {
"WebM",
"webm", profilePrefix %
"-filter_complex \"\n"
124 " [1]scale='min($WIDTH, iw*($HEIGHT/ih))':'min($HEIGHT, ih*($WIDTH/iw))'[hold1];\n"
125 " [hold1]pad=$WIDTH:$HEIGHT:(ow-iw)/2:(oh-ih)/2[hold2];\n"
126 " [hold2]setsar=1:1[hold3];\n"
127 " [hold3]split=3[preview1][transition1][end1];\n"
129 " [preview1]tpad=stop_mode=clone:stop_duration=$FIRST_FRAME_SEC[preview2];\n"
130 " [preview2]setpts=PTS-STARTPTS[preview3];\n"
132 " [transition1]tpad=stop_mode=clone:stop_duration=$TRANSITION_LENGTH[transition2];\n"
133 " [transition2]setpts=PTS-STARTPTS[transition3];\n"
134 " [transition3]framerate=$OUT_FPS[transition4];\n"
136 " [0]fps=$OUT_FPS[main1];\n"
137 " [main1]scale='min($WIDTH, iw*($HEIGHT/ih))':'min($HEIGHT, ih*($WIDTH/iw))':eval=frame[main2];\n"
138 " [main2]pad=$WIDTH:$HEIGHT:(ow-iw)/2:(oh-ih)/2:eval=frame[main3];\n"
139 " [main3]setsar=1:1[main4];\n"
140 " [transition4][main4]xfade=transition=smoothright:duration=$TRANSITION_LENGTH:offset=0[main5];\n"
142 " [end1]tpad=stop_mode=clone:stop_duration=$LAST_FRAME_SEC[end2];\n"
143 " [end2]setpts=PTS-STARTPTS[end3];\n"
145 " [preview3][main5][end3]concat=n=3:v=1:a=0[final1];\n"
146 " [final1]setpts=PTS-STARTPTS\n"
147 "\"\n-stats\n-loglevel error\n-r $OUT_FPS" },
148 {
"MP4 x264 (Flash Effect)",
"mp4", profilePrefix %
"-filter_complex \"\n"
149 " [1]scale='min($WIDTH, iw*($HEIGHT/ih))':'min($HEIGHT, ih*($WIDTH/iw))'[hold1];\n"
150 " [hold1]pad=$WIDTH:$HEIGHT:(ow-iw)/2:(oh-ih)/2[hold2];\n"
151 " [hold2]setsar=1:1[hold3];\n"
152 " [hold3]split=3[preview1][fade1][end1];\n"
154 " [preview1]tpad=stop_mode=clone:stop_duration=$FIRST_FRAME_SEC[preview2];\n"
155 " [preview2]setpts=PTS-STARTPTS[preview3];\n"
157 " [fade1]tpad=stop_mode=clone:stop_duration=$TRANSITION_LENGTH[fade2];\n"
158 " [fade2]setpts=PTS-STARTPTS[fade3];\n"
159 " [fade3]fade=out:duration=$TRANSITION_LENGTH:color=white[fade4];\n"
161 " [0]fps=$OUT_FPS[main1];\n"
162 " [main1]scale='min($WIDTH, iw*($HEIGHT/ih))':'min($HEIGHT, ih*($WIDTH/iw))':eval=frame[main2];\n"
163 " [main2]pad=$WIDTH:$HEIGHT:(ow-iw)/2:(oh-ih)/2:eval=frame[main3];\n"
164 " [main3]setsar=1:1[main4];\n"
165 " [fade4][main4]concat[main5];\n"
167 " [end1]tpad=stop_mode=clone:stop_duration=$LAST_FRAME_SEC[end2];\n"
168 " [end2]setpts=PTS-STARTPTS[end3];\n"
170 " [preview3][main5][end3]concat=n=3:v=1:a=0[final1];\n"
171 " [final1]setpts=PTS-STARTPTS\n"
172 "\"\n-stats\n-loglevel error\n-c:v $H264_ENCODER\n-r $OUT_FPS\n-pix_fmt yuv420p" },
173 {
"Custom1",
"editme", profilePrefix %
"-filter_complex \"loop=$LAST_FRAME_SEC:size=1:start=$FRAMES,scale=$WIDTH:$HEIGHT\"\n-r $OUT_FPS" },
174 {
"Custom2",
"editme", profilePrefix %
"-filter_complex \"loop=$LAST_FRAME_SEC:size=1:start=$FRAMES,scale=$WIDTH:$HEIGHT\"\n-r $OUT_FPS" },
175 {
"Custom3",
"editme", profilePrefix %
"-filter_complex \"loop=$LAST_FRAME_SEC:size=1:start=$FRAMES,scale=$WIDTH:$HEIGHT\"\n-r $OUT_FPS" },
176 {
"Custom4",
"editme", profilePrefix %
"-filter_complex \"loop=$LAST_FRAME_SEC:size=1:start=$FRAMES,scale=$WIDTH:$HEIGHT\"\n-r $OUT_FPS" }
326 const QString &profilesStr =
config->
readEntry(keyProfiles, QString());
327 if (profilesStr.isEmpty())
328 return ::defaultProfiles;
332 const QStringList &profilesList = profilesStr.split(
"\n");
334 for (
const QString &profileStr : profilesList) {
337 const QStringList& profileList = profileStr.split(
"|");
338 if (profileList.size() == 3) {
339 profiles.append({profileList[0], profileList[1], QString(profileList[2]).replace(
"\\n",
"\n")});
358 const QRegularExpression cleanUp(
"[\n|]");
362 if (profile != defaultProfile) {
368 outValue += QString(profile.name).replace(cleanUp,
" ") %
"|"
369 % QString(profile.extension).replace(cleanUp,
" ") %
"|"
370 % QString(profile.arguments).replace(
"\n",
"\\n").replace(
"|",
" ") %
"\n";
384 return ::defaultProfiles;
389 const QVariantList &readValue =
config->
readEntry(keyEditedProfiles, QVariantList());
391 for (
const QVariant &item : readValue) {
392 result.insert(item.toInt());
399 QVariantList writeValue;
400 for (
int index :
value) {
401 writeValue.append(index);
438 return !(left == right);
float value(const T *src, size_t ch)
void setFFMpegLocation(const QString &value)
void writeEntry(const QString &name, const T &value)
QString ffmpegLocation(bool defaultValue=false) const
T readEntry(const QString &name, const T &defaultValue=T())
void setFirstFrameSec(int value)
void setProfiles(const QList< RecorderProfile > &value)
void setLockFps(bool value)
void setVideoDirectory(const QString &value)
void setResize(bool value)
QString ffmpegPath() const
void setLockRatio(bool value)
void loadConfiguration(RecorderExportSettings *settings, bool loadLockFps=true) const
void setResultPreview(bool value)
int firstFrameSec() const
RecorderExportConfig(bool readOnly)
bool resultPreview() const
void setInputFps(int value)
void setFfmpegPath(const QString &value)
QString videoDirectory() const
QList< RecorderProfile > defaultProfiles() const
QSet< int > editedProfilesIndexes() const
QList< RecorderProfile > profiles() const
void setProfileIndex(int value)
void setSize(const QSize &value)
void setExtendResult(bool value)
void setLastFrameSec(int value)
bool extendResult() const
void setEditedProfilesIndexes(const QSet< int > &value)
bool operator!=(const RecorderProfile &left, const RecorderProfile &right)
bool operator==(const RecorderProfile &left, const RecorderProfile &right)
QList< RecorderProfile > profiles
QList< RecorderProfile > defaultProfiles