mirror of
https://gitlab.com/kelteseth/ScreenPlay.git
synced 2024-09-15 06:52:34 +02:00
Add ability to save wallpapers
Add preview Cleanup
This commit is contained in:
parent
0d12c84107
commit
22ef3494e0
@ -3,14 +3,16 @@ import QtGraphicalEffects 1.0
|
|||||||
import QtQuick.Controls 2.2
|
import QtQuick.Controls 2.2
|
||||||
import QtQuick.Controls.Material 2.3
|
import QtQuick.Controls.Material 2.3
|
||||||
import Qt.labs.platform 1.0
|
import Qt.labs.platform 1.0
|
||||||
import QtQuick.Layouts 1.3
|
import QtQuick.Layouts 1.12
|
||||||
|
|
||||||
import net.aimber.create 1.0
|
import net.aimber.create 1.0
|
||||||
|
|
||||||
Item {
|
Item {
|
||||||
id: wrapperContent
|
id: wrapperContent
|
||||||
|
|
||||||
|
property bool conversionFinishedSuccessful: false
|
||||||
property string customVideoPreviewPath: ""
|
property bool canSave: false
|
||||||
|
signal save
|
||||||
|
|
||||||
Text {
|
Text {
|
||||||
id: txtHeadline
|
id: txtHeadline
|
||||||
@ -96,18 +98,15 @@ Item {
|
|||||||
imgPreview.source = "file:///"
|
imgPreview.source = "file:///"
|
||||||
+ screenPlayCreate.workingDir + "/preview.png"
|
+ screenPlayCreate.workingDir + "/preview.png"
|
||||||
imgPreview.visible = true
|
imgPreview.visible = true
|
||||||
txtConvert.text = qsTr(
|
txtConvert.text = qsTr("Converting Video preview mp4")
|
||||||
"Converting Video preview mp4")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (state === CreateImportVideo.State.ConvertingPreviewVideo) {
|
if (state === CreateImportVideo.State.ConvertingPreviewVideo) {
|
||||||
txtConvert.text = qsTr(
|
txtConvert.text = qsTr("Generating preview video...")
|
||||||
"Generating preview video...")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (state === CreateImportVideo.State.ConvertingPreviewGif) {
|
if (state === CreateImportVideo.State.ConvertingPreviewGif) {
|
||||||
txtConvert.text = qsTr(
|
txtConvert.text = qsTr("Generating preview gif...")
|
||||||
"Generating preview gif...")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (state === CreateImportVideo.State.ConvertingPreviewGifFinished) {
|
if (state === CreateImportVideo.State.ConvertingPreviewGifFinished) {
|
||||||
@ -124,8 +123,9 @@ Item {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (state === CreateImportVideo.State.Finished) {
|
if (state === CreateImportVideo.State.Finished) {
|
||||||
imgSuccess.source = "file:///"
|
txtConvert.text = ""
|
||||||
+ screenPlayCreate.workingDir + "/preview.gif"
|
conversionFinishedSuccessful = true
|
||||||
|
busyIndicator.running = false
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
onProgressChanged: {
|
onProgressChanged: {
|
||||||
@ -151,16 +151,17 @@ Item {
|
|||||||
Rectangle {
|
Rectangle {
|
||||||
height: 50
|
height: 50
|
||||||
color: "#eeeeee"
|
color: "#eeeeee"
|
||||||
Layout.fillWidth: true
|
Layout.preferredWidth: imgWrapper.width
|
||||||
|
|
||||||
Text {
|
Text {
|
||||||
id: txtCustomPreviewPath
|
id: txtCustomPreviewPath
|
||||||
color: "#333333"
|
color: "#333333"
|
||||||
|
|
||||||
text: qsTr("Add custom preview image")
|
text: qsTr("Add custom preview image")
|
||||||
anchors {
|
anchors {
|
||||||
verticalCenter: parent.verticalCenter
|
verticalCenter: parent.verticalCenter
|
||||||
left: parent.left
|
left: parent.left
|
||||||
leftMargin: 10
|
leftMargin: 20
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -176,10 +177,9 @@ Item {
|
|||||||
onClicked: fileDialogOpenFile.open()
|
onClicked: fileDialogOpenFile.open()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
FileDialog {
|
FileDialog {
|
||||||
id: fileDialogOpenFile
|
id: fileDialogOpenFile
|
||||||
nameFilters: ["*.png *.jpg"]
|
nameFilters: []
|
||||||
onAccepted: {
|
onAccepted: {
|
||||||
var file = fileDialogOpenFile.file.toString()
|
var file = fileDialogOpenFile.file.toString()
|
||||||
|
|
||||||
@ -207,44 +207,44 @@ Item {
|
|||||||
right: parent.right
|
right: parent.right
|
||||||
left: parent.left
|
left: parent.left
|
||||||
margins: 30
|
margins: 30
|
||||||
top:parent.top
|
top: parent.top
|
||||||
topMargin: 0
|
topMargin: 0
|
||||||
bottom: column1.top
|
bottom: column1.top
|
||||||
bottomMargin: 50
|
bottomMargin: 50
|
||||||
}
|
}
|
||||||
|
|
||||||
TextField {
|
TextField {
|
||||||
id: textField
|
id: textFieldName
|
||||||
placeholderText: qsTr("Name")
|
placeholderText: qsTr("Name")
|
||||||
width:parent.width
|
width: parent.width
|
||||||
Layout.fillWidth: true
|
Layout.fillWidth: true
|
||||||
onTextChanged: {
|
onTextChanged: {
|
||||||
if (textField.text.length >= 3) {
|
if (textFieldName.text.length >= 3) {
|
||||||
canNext = true
|
canSave = true
|
||||||
} else {
|
} else {
|
||||||
canNext = false
|
canSave = false
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
TextField {
|
TextField {
|
||||||
id: textField1
|
id: textFieldDescription
|
||||||
placeholderText: qsTr("Description")
|
placeholderText: qsTr("Description")
|
||||||
width:parent.width
|
width: parent.width
|
||||||
Layout.fillWidth: true
|
Layout.fillWidth: true
|
||||||
}
|
}
|
||||||
|
|
||||||
TextField {
|
TextField {
|
||||||
id: textField2
|
id: textFieldYoutubeURL
|
||||||
placeholderText: qsTr("Youtube URL")
|
placeholderText: qsTr("Youtube URL")
|
||||||
width:parent.width
|
width: parent.width
|
||||||
Layout.fillWidth: true
|
Layout.fillWidth: true
|
||||||
}
|
}
|
||||||
|
|
||||||
TextField {
|
TextField {
|
||||||
id: textField3
|
id: textFieldTags
|
||||||
width:parent.width
|
width: parent.width
|
||||||
placeholderText: qsTr("Tags")
|
placeholderText: qsTr("Tags (seperate with comma)")
|
||||||
Layout.fillWidth: true
|
Layout.fillWidth: true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -271,33 +271,32 @@ Item {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
NextButton {
|
Button {
|
||||||
id: btnFinish
|
id: btnFinish
|
||||||
onClicked: {
|
text: qsTr("Save")
|
||||||
if (btnFinish.state === "enabled" && canNext) {
|
Material.background: Material.Gray
|
||||||
screenPlayCreate.createWallpaperProjectFile(
|
Material.foreground: "white"
|
||||||
textField.text, textField1.text)
|
enabled: {
|
||||||
utility.setNavigationActive(true)
|
if (canSave && conversionFinishedSuccessful) {
|
||||||
createNew.state = "success"
|
return true
|
||||||
|
} else {
|
||||||
|
return false
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
Connections {
|
onClicked: {
|
||||||
target: screenPlayCreate
|
if (conversionFinishedSuccessful) {
|
||||||
onCreateWallpaperStateChanged: {
|
screenPlayCreate.saveWallpaper(
|
||||||
if (state === CreateImportVideo.State.ConvertingVideoFinished) {
|
textFieldName.text, textFieldDescription.text, textFieldYoutubeURL.text, textFieldTags.text)
|
||||||
btnFinish.state = "enabled"
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*##^## Designer {
|
/*##^## Designer {
|
||||||
D{i:0;autoSize:true;height:480;width:640}
|
D{i:0;autoSize:true;height:480;width:950}
|
||||||
}
|
}
|
||||||
##^##*/
|
##^##*/
|
||||||
|
|
||||||
|
@ -30,12 +30,14 @@ Item {
|
|||||||
Connections {
|
Connections {
|
||||||
target: screenPlayCreate
|
target: screenPlayCreate
|
||||||
onCreateWallpaperStateChanged: {
|
onCreateWallpaperStateChanged: {
|
||||||
|
if (state === CreateImportVideo.State.AnalyseVideoError
|
||||||
if (state === CreateImportVideo.State.ConvertingPreviewGifError
|
|
||||||
|| state === CreateImportVideo.State.ConvertingPreviewVideoError
|
|| state === CreateImportVideo.State.ConvertingPreviewVideoError
|
||||||
|
|| state === CreateImportVideo.State.ConvertingPreviewGifError
|
||||||
|| state === CreateImportVideo.State.ConvertingPreviewImageError
|
|| state === CreateImportVideo.State.ConvertingPreviewImageError
|
||||||
|| state === CreateImportVideo.State.AnalyseVideoError) {
|
|| state === CreateImportVideo.State.ConvertingAudioError
|
||||||
createNew.state = "error"
|
|| state === CreateImportVideo.State.AbortCleanupError
|
||||||
|
|| state === CreateImportVideo.State.ErrorUnknown) {
|
||||||
|
createNew.state = "result"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -84,6 +86,12 @@ Item {
|
|||||||
id: loader_wrapperContent
|
id: loader_wrapperContent
|
||||||
anchors.fill: parent
|
anchors.fill: parent
|
||||||
z: 10
|
z: 10
|
||||||
|
Connections {
|
||||||
|
target: loader_wrapperContent.sourceComponent
|
||||||
|
onSave:{
|
||||||
|
createNew.state = "result"
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
CreateWallpaperResult {
|
CreateWallpaperResult {
|
||||||
@ -275,7 +283,7 @@ Item {
|
|||||||
},
|
},
|
||||||
Transition {
|
Transition {
|
||||||
from: "in"
|
from: "in"
|
||||||
to: "error"
|
to: "result"
|
||||||
SequentialAnimation {
|
SequentialAnimation {
|
||||||
PropertyAnimation {
|
PropertyAnimation {
|
||||||
target: loader_wrapperContent
|
target: loader_wrapperContent
|
||||||
@ -293,21 +301,6 @@ Item {
|
|||||||
easing.type: Easing.OutQuart
|
easing.type: Easing.OutQuart
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
|
||||||
Transition {
|
|
||||||
from: "in"
|
|
||||||
to: "success"
|
|
||||||
SequentialAnimation {
|
|
||||||
PropertyAnimation {
|
|
||||||
target: loader_wrapperContent
|
|
||||||
duration: 600
|
|
||||||
property: "opacity"
|
|
||||||
easing.type: Easing.OutQuart
|
|
||||||
}
|
|
||||||
PauseAnimation {
|
|
||||||
duration: 50
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
@ -55,18 +55,20 @@ void Create::createWallpaperStart(QString videoPath)
|
|||||||
videoPath.remove("file:///");
|
videoPath.remove("file:///");
|
||||||
|
|
||||||
QDir dir;
|
QDir dir;
|
||||||
dir.cd(this->m_settings->localStoragePath().toLocalFile());
|
dir.cd(m_settings->localStoragePath().toLocalFile());
|
||||||
|
|
||||||
// Create a temp dir so we can later alter it to the workshop id
|
// Create a temp dir so we can later alter it to the workshop id
|
||||||
auto folderName = QString("_tmp_" + QTime::currentTime().toString()).replace(":", "");
|
auto folderName = QString("_tmp_" + QTime::currentTime().toString()).replace(":", "");
|
||||||
|
|
||||||
if (!dir.mkdir(folderName)) {
|
if (!dir.mkdir(folderName)) {
|
||||||
|
emit createWallpaperStateChanged(CreateImportVideo::State::CreateTmpFolderError);
|
||||||
emit abortCreateWallpaper();
|
emit abortCreateWallpaper();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
setWorkingDir(dir.path() + "/" + folderName);
|
||||||
|
|
||||||
m_createImportVideoThread = new QThread;
|
m_createImportVideoThread = new QThread;
|
||||||
m_createImportVideo = new CreateImportVideo(videoPath, dir.path() + "/" + folderName);
|
m_createImportVideo = new CreateImportVideo(videoPath, workingDir());
|
||||||
|
|
||||||
connect(m_createImportVideo, &CreateImportVideo::createWallpaperStateChanged, this, &Create::createWallpaperStateChanged);
|
connect(m_createImportVideo, &CreateImportVideo::createWallpaperStateChanged, this, &Create::createWallpaperStateChanged);
|
||||||
connect(m_createImportVideoThread, &QThread::started, m_createImportVideo, &CreateImportVideo::process);
|
connect(m_createImportVideoThread, &QThread::started, m_createImportVideo, &CreateImportVideo::process);
|
||||||
@ -78,8 +80,17 @@ void Create::createWallpaperStart(QString videoPath)
|
|||||||
m_createImportVideoThread->start();
|
m_createImportVideoThread->start();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Create::createWallpaperProjectFile(QString name, QString description, QString youtube, QStringList tags)
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
void Create::abortAndCleanup()
|
void Create::abortAndCleanup()
|
||||||
{
|
{
|
||||||
|
if (m_createImportVideo != nullptr || m_createImportVideoThread != nullptr) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
// Save to export path before aborting to be able to cleanup the tmp folder
|
// Save to export path before aborting to be able to cleanup the tmp folder
|
||||||
QString tmpExportPath = m_createImportVideo->m_exportPath;
|
QString tmpExportPath = m_createImportVideo->m_exportPath;
|
||||||
|
|
||||||
@ -94,6 +105,8 @@ void Create::abortAndCleanup()
|
|||||||
qDebug() << "cleanup " << tmpExportPath;
|
qDebug() << "cleanup " << tmpExportPath;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
m_createImportVideo = nullptr;
|
||||||
|
m_createImportVideoThread = nullptr;
|
||||||
});
|
});
|
||||||
m_createImportVideoThread->requestInterruption();
|
m_createImportVideoThread->requestInterruption();
|
||||||
}
|
}
|
||||||
|
@ -31,6 +31,7 @@ class Create : public QObject {
|
|||||||
public:
|
public:
|
||||||
explicit Create(Settings* st, QMLUtilities* util, QObject* parent = nullptr);
|
explicit Create(Settings* st, QMLUtilities* util, QObject* parent = nullptr);
|
||||||
|
|
||||||
|
Q_PROPERTY(QString workingDir READ workingDir WRITE setWorkingDir NOTIFY workingDirChanged)
|
||||||
Q_PROPERTY(float progress READ progress WRITE setProgress NOTIFY progressChanged)
|
Q_PROPERTY(float progress READ progress WRITE setProgress NOTIFY progressChanged)
|
||||||
|
|
||||||
Create() {}
|
Create() {}
|
||||||
@ -41,17 +42,24 @@ public:
|
|||||||
return m_progress;
|
return m_progress;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QString workingDir() const
|
||||||
|
{
|
||||||
|
return m_workingDir;
|
||||||
|
}
|
||||||
|
|
||||||
signals:
|
signals:
|
||||||
void createWallpaperStateChanged(CreateImportVideo::State state);
|
void createWallpaperStateChanged(CreateImportVideo::State state);
|
||||||
void processOutput(QString text);
|
void processOutput(QString text);
|
||||||
void progressChanged(float progress);
|
void progressChanged(float progress);
|
||||||
void abortCreateWallpaper();
|
void abortCreateWallpaper();
|
||||||
|
void workingDirChanged(QString workingDir);
|
||||||
|
|
||||||
public slots:
|
public slots:
|
||||||
void copyProject(QString relativeProjectPath, QString toPath);
|
void copyProject(QString relativeProjectPath, QString toPath);
|
||||||
bool copyRecursively(const QString& srcFilePath, const QString& tgtFilePath);
|
bool copyRecursively(const QString& srcFilePath, const QString& tgtFilePath);
|
||||||
void abortAndCleanup();
|
|
||||||
void createWallpaperStart(QString videoPath);
|
void createWallpaperStart(QString videoPath);
|
||||||
|
void saveWallpaper(QString name, QString description, QString youtube, QString tags);
|
||||||
|
void abortAndCleanup();
|
||||||
|
|
||||||
void setProgress(float progress)
|
void setProgress(float progress)
|
||||||
{
|
{
|
||||||
@ -62,6 +70,15 @@ public slots:
|
|||||||
emit progressChanged(m_progress);
|
emit progressChanged(m_progress);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void setWorkingDir(QString workingDir)
|
||||||
|
{
|
||||||
|
if (m_workingDir == workingDir)
|
||||||
|
return;
|
||||||
|
|
||||||
|
m_workingDir = workingDir;
|
||||||
|
emit workingDirChanged(m_workingDir);
|
||||||
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
CreateImportVideo* m_createImportVideo;
|
CreateImportVideo* m_createImportVideo;
|
||||||
Settings* m_settings;
|
Settings* m_settings;
|
||||||
@ -69,4 +86,5 @@ private:
|
|||||||
QMLUtilities* m_utils;
|
QMLUtilities* m_utils;
|
||||||
|
|
||||||
float m_progress = 0.0f;
|
float m_progress = 0.0f;
|
||||||
|
QString m_workingDir;
|
||||||
};
|
};
|
||||||
|
@ -14,11 +14,13 @@ CreateImportVideo::CreateImportVideo(QString videoPath, QString exportPath, QObj
|
|||||||
|
|
||||||
void CreateImportVideo::process()
|
void CreateImportVideo::process()
|
||||||
{
|
{
|
||||||
qDebug() << "start converting video" << QThread::currentThreadId();
|
qDebug() << "start converting video in thread: " << QThread::currentThreadId();
|
||||||
createWallpaperInfo();
|
createWallpaperInfo();
|
||||||
createWallpaperVideoPreview();
|
createWallpaperVideoPreview();
|
||||||
createWallpaperGifPreview();
|
createWallpaperGifPreview();
|
||||||
extractWallpaperAudio();
|
extractWallpaperAudio();
|
||||||
|
emit createWallpaperStateChanged(CreateImportVideo::State::Finished);
|
||||||
|
|
||||||
emit finished();
|
emit finished();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -117,20 +119,20 @@ bool CreateImportVideo::createWallpaperVideoPreview()
|
|||||||
{
|
{
|
||||||
|
|
||||||
QStringList args;
|
QStringList args;
|
||||||
// args.append("-loglevel");
|
args.append("-loglevel");
|
||||||
// args.append("error");
|
args.append("error");
|
||||||
// args.append("-y");
|
args.append("-y");
|
||||||
// args.append("-stats");
|
args.append("-stats");
|
||||||
args.append("-i");
|
args.append("-i");
|
||||||
args.append(m_videoPath);
|
args.append(m_videoPath);
|
||||||
|
|
||||||
//args.append("-vf");
|
args.append("-vf");
|
||||||
// We allways want to have a 5 second clip via 24fps -> 120 frames
|
// We allways want to have a 5 second clip via 24fps -> 120 frames
|
||||||
// Divided by the number of frames we can skip (timeInSeconds * Framrate)
|
// Divided by the number of frames we can skip (timeInSeconds * Framrate)
|
||||||
// scale & crop parameter: https://unix.stackexchange.com/a/284731
|
// scale & crop parameter: https://unix.stackexchange.com/a/284731
|
||||||
//args.append("select='not(mod(n," + QString::number((m_length / 5)) + "))',setpts=N/FRAME_RATE/TB,crop=in_h*16/9:in_h,scale=-2:400");
|
args.append("select='not(mod(n," + QString::number((m_length / 5)) + "))',setpts=N/FRAME_RATE/TB,crop=in_h*16/9:in_h,scale=-2:400");
|
||||||
// Disable audio
|
// Disable audio
|
||||||
//args.append("-an");
|
args.append("-an");
|
||||||
args.append(m_exportPath + "/preview.webm");
|
args.append(m_exportPath + "/preview.webm");
|
||||||
QScopedPointer<QProcess> proConvertPreviewWebM(new QProcess());
|
QScopedPointer<QProcess> proConvertPreviewWebM(new QProcess());
|
||||||
|
|
||||||
@ -143,7 +145,6 @@ bool CreateImportVideo::createWallpaperVideoPreview()
|
|||||||
#endif
|
#endif
|
||||||
emit createWallpaperStateChanged(CreateImportVideo::State::ConvertingPreviewVideo);
|
emit createWallpaperStateChanged(CreateImportVideo::State::ConvertingPreviewVideo);
|
||||||
|
|
||||||
|
|
||||||
proConvertPreviewWebM.data()->start();
|
proConvertPreviewWebM.data()->start();
|
||||||
while (!proConvertPreviewWebM.data()->waitForFinished(100)) //Wake up every 100ms and check if we must exit
|
while (!proConvertPreviewWebM.data()->waitForFinished(100)) //Wake up every 100ms and check if we must exit
|
||||||
{
|
{
|
||||||
|
@ -45,6 +45,7 @@ public:
|
|||||||
// ConvertingVideoFinished,
|
// ConvertingVideoFinished,
|
||||||
// ConvertingVideoError,
|
// ConvertingVideoError,
|
||||||
AbortCleanupError,
|
AbortCleanupError,
|
||||||
|
CreateTmpFolderError,
|
||||||
Finished,
|
Finished,
|
||||||
ErrorUnknown,
|
ErrorUnknown,
|
||||||
};
|
};
|
||||||
|
Loading…
Reference in New Issue
Block a user