Krita Source Code Documentation
Loading...
Searching...
No Matches
KisAsyncAnimationFramesSaveDialog Class Reference

#include <KisAsyncAnimationFramesSaveDialog.h>

+ Inheritance diagram for KisAsyncAnimationFramesSaveDialog:

Classes

struct  Private
 

Public Member Functions

QList< int > getUniqueFrames () const
 
 KisAsyncAnimationFramesSaveDialog (KisImageSP image, const KisTimeSpan &range, const QString &baseFilename, int startNumberingAt, bool onlyNeedsUniqueFrames, KisPropertiesConfigurationSP exportConfiguration)
 
Result regenerateRange (KisViewManager *viewManager) override
 start generation of frames and (if not in batch mode) show the dialog
 
QStringList savedFiles () const
 
QString savedFilesMask () const
 
QString savedFilesMaskWildcard () const
 
QStringList savedUniqueFiles () const
 
 ~KisAsyncAnimationFramesSaveDialog ()
 
- Public Member Functions inherited from KisAsyncAnimationRenderDialogBase
bool batchMode () const
 
 KisAsyncAnimationRenderDialogBase (const QString &actionTitle, KisImageSP image, int busyWait=200)
 construct and initialize the dialog
 
KisRegion regionOfInterest () const
 
void setBatchMode (bool value)
 setting batch mode to true will prevent any dialogs or message boxes from showing on screen. Please take it into account that using batch mode prevents some potentially dangerous recovery execution paths (e.g. delete the existing frames in the destination folder). In such case the rendering will be stopped with RenderFailed result.
 
void setRegionOfInterest (const KisRegion &roi)
 
virtual ~KisAsyncAnimationRenderDialogBase ()
 

Protected Member Functions

QList< int > calcDirtyFrames () const override
 returns a list of frames that should be regenerated by the dialog
 
KisAsyncAnimationRendererBasecreateRenderer (KisImageSP image) override
 create a renderer object linked to image
 
void initializeRendererForFrame (KisAsyncAnimationRendererBase *renderer, KisImageSP image, int frame) override
 

Private Attributes

const QScopedPointer< Privatem_d
 

Additional Inherited Members

- Public Types inherited from KisAsyncAnimationRenderDialogBase
enum  Result { RenderComplete , RenderCancelled , RenderFailed , RenderTimedOut }
 

Detailed Description

Definition at line 14 of file KisAsyncAnimationFramesSaveDialog.h.

Constructor & Destructor Documentation

◆ KisAsyncAnimationFramesSaveDialog()

KisAsyncAnimationFramesSaveDialog::KisAsyncAnimationFramesSaveDialog ( KisImageSP image,
const KisTimeSpan & range,
const QString & baseFilename,
int startNumberingAt,
bool onlyNeedsUniqueFrames,
KisPropertiesConfigurationSP exportConfiguration )

Definition at line 58 of file KisAsyncAnimationFramesSaveDialog.cpp.

64 : KisAsyncAnimationRenderDialogBase(i18n("Saving frames..."), originalImage, 0),
65 m_d(new Private(originalImage, range, baseFilename, qMax(startNumberingAt - range.start(), range.start() * -1), onlyNeedsUniqueFrames, exportConfiguration))
66{
67
68
69}
KisAsyncAnimationRenderDialogBase(const QString &actionTitle, KisImageSP image, int busyWait=200)
construct and initialize the dialog
int start() const

◆ ~KisAsyncAnimationFramesSaveDialog()

KisAsyncAnimationFramesSaveDialog::~KisAsyncAnimationFramesSaveDialog ( )

Definition at line 71 of file KisAsyncAnimationFramesSaveDialog.cpp.

72{
73}

Member Function Documentation

◆ calcDirtyFrames()

QList< int > KisAsyncAnimationFramesSaveDialog::calcDirtyFrames ( ) const
overrideprotectedvirtual

returns a list of frames that should be regenerated by the dialog

Called by the dialog in the very beginning of regenerateRange()

Implements KisAsyncAnimationRenderDialogBase.

Definition at line 175 of file KisAsyncAnimationFramesSaveDialog.cpp.

176{
177 QList<int> result;
178 for (int frame = m_d->range.start(); frame <= m_d->range.end(); frame++) {
179 KisTimeSpan heldFrameTimeRange = KisTimeSpan::calculateIdenticalFramesRecursive(m_d->originalImage->root(), frame);
180
181 if (!m_d->onlyNeedsUniqueFrames) {
182 // Clamp holds that begin before the rendered range onto it
183 heldFrameTimeRange &= m_d->range;
184 }
185
186 KIS_SAFE_ASSERT_RECOVER_RETURN_VALUE(heldFrameTimeRange.isValid(), result);
187
188 result.append(heldFrameTimeRange.start());
189
190 if (heldFrameTimeRange.isInfinite()) {
191 break;
192 } else {
193 frame = heldFrameTimeRange.end();
194 }
195 }
196 return result;
197}
bool isInfinite() const
static KisTimeSpan calculateIdenticalFramesRecursive(const KisNode *node, int time)
int end() const
bool isValid() const
#define KIS_SAFE_ASSERT_RECOVER_RETURN_VALUE(cond, val)
Definition kis_assert.h:129

References KisTimeSpan::calculateIdenticalFramesRecursive(), KisTimeSpan::end(), KisTimeSpan::isInfinite(), KisTimeSpan::isValid(), KIS_SAFE_ASSERT_RECOVER_RETURN_VALUE, m_d, and KisTimeSpan::start().

◆ createRenderer()

KisAsyncAnimationRendererBase * KisAsyncAnimationFramesSaveDialog::createRenderer ( KisImageSP image)
overrideprotectedvirtual

create a renderer object linked to image

Renderer are special objects that connect to the individual image signals, react on them and fetch the final frames data

See also
KisAsyncAnimationRendererBase

Implements KisAsyncAnimationRenderDialogBase.

Definition at line 199 of file KisAsyncAnimationFramesSaveDialog.cpp.

200{
202 m_d->filenamePrefix,
203 m_d->filenameSuffix,
204 m_d->outputMimeType,
205 m_d->range,
206 m_d->sequenceNumberingOffset,
207 m_d->onlyNeedsUniqueFrames,
208 m_d->exportConfiguration);
209}

References m_d.

◆ getUniqueFrames()

QList< int > KisAsyncAnimationFramesSaveDialog::getUniqueFrames ( ) const

Definition at line 258 of file KisAsyncAnimationFramesSaveDialog.cpp.

259{
260 return this->calcDirtyFrames();
261}
QList< int > calcDirtyFrames() const override
returns a list of frames that should be regenerated by the dialog

References calcDirtyFrames().

◆ initializeRendererForFrame()

void KisAsyncAnimationFramesSaveDialog::initializeRendererForFrame ( KisAsyncAnimationRendererBase * renderer,
KisImageSP image,
int frame )
overrideprotectedvirtual

Implements KisAsyncAnimationRenderDialogBase.

Definition at line 211 of file KisAsyncAnimationFramesSaveDialog.cpp.

212{
213 Q_UNUSED(renderer);
214 Q_UNUSED(image);
215 Q_UNUSED(frame);
216}

◆ regenerateRange()

KisAsyncAnimationRenderDialogBase::Result KisAsyncAnimationFramesSaveDialog::regenerateRange ( KisViewManager * viewManager)
overridevirtual

start generation of frames and (if not in batch mode) show the dialog

The link to view manager is used to barrier lock with visual feedback in the end of the operation

Since this method can be called from the places where no view manager is available, we need this manually crafted ugly construction to "try-lock-cancel" the image.

Reimplemented from KisAsyncAnimationRenderDialogBase.

Definition at line 75 of file KisAsyncAnimationFramesSaveDialog.cpp.

76{
77 QString dirPath;
78 QString fileWildcard;
79#ifdef Q_OS_ANDROID
80 // QFileInfo can't manage to manipulate content URIs on Android, most
81 // functions either just hand you the entire input or an empty string, so
82 // we have to do the name mangling by hand.
83 {
84 QString wildcardPath = savedFilesMaskWildcard();
85 int lastSlashIndex = wildcardPath.lastIndexOf(QChar('/'));
87 dirPath = wildcardPath.mid(0, lastSlashIndex);
88 fileWildcard = wildcardPath.mid(lastSlashIndex + 1);
89 }
90#else
91 {
92 QFileInfo fileInfo(savedFilesMaskWildcard());
93 dirPath = fileInfo.absolutePath();
94 fileWildcard = fileInfo.fileName();
95 }
96#endif
97 QDir dir(dirPath);
98
99 // On Android, directory existence checks are unreliable and creating
100 // directories is not allowed. We'll just have to take what we're given and
101 // hope that works out for us.
102#ifndef Q_OS_ANDROID
103 if (!dir.exists()) {
104 dir.mkpath(dirPath);
105 }
106 KIS_SAFE_ASSERT_RECOVER_NOOP(dir.exists());
107#endif
108
109 // Check for overwrite. (Batch mode always overwrites.)
110 QStringList preexistingFileNames = dir.entryList({ fileWildcard });
111 if (!preexistingFileNames.isEmpty() && !batchMode()) {
112 QStringList truncatedList = preexistingFileNames;
113
114 while (truncatedList.size() > 3) {
115 truncatedList.takeLast();
116 }
117
118 QString exampleFiles = truncatedList.join(", ");
119 if (truncatedList.size() != preexistingFileNames.size()) {
120 exampleFiles += QString(", ...");
121 }
122
123 QMessageBox::StandardButton result =
124 QMessageBox::warning(qApp->activeWindow(),
125 i18n("Delete old frames?"),
126 i18n("Frames with the same naming "
127 "scheme exist in the destination "
128 "directory. They are going to be "
129 "deleted, continue?\n\n"
130 "Directory: %1\n"
131 "Files: %2",
132 dirPath, exampleFiles),
133 QMessageBox::Yes | QMessageBox::No,
134 QMessageBox::No);
135
136 if (result == QMessageBox::No) {
137 return RenderCancelled;
138 }
139 }
140
141 // Remove any preexisting files.
142 Q_FOREACH (const QString &file, preexistingFileNames) {
143 if (!dir.remove(file)) {
144 if (!batchMode()) {
145 QMessageBox::critical(qApp->activeWindow(),
146 i18n("Failed to delete"),
147 i18n("Failed to delete an old frame file:\n\n"
148 "%1\n\n"
149 "Rendering cancelled.", dir.absoluteFilePath(file)));
150 }
151
152 qWarning() << "WARNING: KisAsyncAnimFramesSaveDialog: Failed to delete old frame file(s):" << dir.absoluteFilePath(file);
153 return RenderFailed;
154 }
155 }
156
157 // Save new frame files.
159
160 // If we cancel rendering or fail rendering process,
161 // lets clean up any files that may have been created
162 // to keep the next render from having artifacts.
163 preexistingFileNames = savedFiles();
164 if (renderingResult != RenderComplete) {
165 Q_FOREACH (const QString &file, preexistingFileNames) {
166 if (dir.exists(file)) {
167 (void)dir.remove(file);
168 }
169 }
170 }
171
172 return renderingResult;
173}
virtual Result regenerateRange(KisViewManager *viewManager)
start generation of frames and (if not in batch mode) show the dialog
#define KIS_SAFE_ASSERT_RECOVER_NOOP(cond)
Definition kis_assert.h:130
typedef void(QOPENGLF_APIENTRYP PFNGLINVALIDATEBUFFERDATAPROC)(GLuint buffer)

References KisAsyncAnimationRenderDialogBase::batchMode(), KIS_SAFE_ASSERT_RECOVER_NOOP, KIS_SAFE_ASSERT_RECOVER_RETURN_VALUE, KisAsyncAnimationRenderDialogBase::regenerateRange(), KisAsyncAnimationRenderDialogBase::RenderCancelled, KisAsyncAnimationRenderDialogBase::RenderComplete, KisAsyncAnimationRenderDialogBase::RenderFailed, savedFiles(), savedFilesMaskWildcard(), and void().

◆ savedFiles()

QStringList KisAsyncAnimationFramesSaveDialog::savedFiles ( ) const

Definition at line 228 of file KisAsyncAnimationFramesSaveDialog.cpp.

229{
230 QStringList files;
231
232 for (int i = m_d->range.start(); i <= m_d->range.end(); i++) {
233 const int num = m_d->sequenceNumberingOffset + i;
234 QString name = QString("%1").arg(num, 4, 10, QChar('0'));
235 name = m_d->filenamePrefix + name + m_d->filenameSuffix;
236 files.append(QFileInfo(name).fileName());
237 }
238
239 return files;
240}
const char * name(StandardAction id)

References m_d.

◆ savedFilesMask()

QString KisAsyncAnimationFramesSaveDialog::savedFilesMask ( ) const

Definition at line 218 of file KisAsyncAnimationFramesSaveDialog.cpp.

219{
220 return m_d->filenamePrefix + "%04d" + m_d->filenameSuffix;
221}

References m_d.

◆ savedFilesMaskWildcard()

QString KisAsyncAnimationFramesSaveDialog::savedFilesMaskWildcard ( ) const

Definition at line 223 of file KisAsyncAnimationFramesSaveDialog.cpp.

224{
225 return m_d->filenamePrefix + "????" + m_d->filenameSuffix;
226}

References m_d.

◆ savedUniqueFiles()

QStringList KisAsyncAnimationFramesSaveDialog::savedUniqueFiles ( ) const

Definition at line 242 of file KisAsyncAnimationFramesSaveDialog.cpp.

243{
244 QStringList files;
245
246 const QList<int> frames = calcDirtyFrames();
247
248 Q_FOREACH (int frame, frames) {
249 const int num = m_d->sequenceNumberingOffset + frame;
250 QString name = QString("%1").arg(num, 4, 10, QChar('0'));
251 name = m_d->filenamePrefix + name + m_d->filenameSuffix;
252 files.append(QFileInfo(name).fileName());
253 }
254
255 return files;
256}

References calcDirtyFrames(), and m_d.

Member Data Documentation

◆ m_d

const QScopedPointer<Private> KisAsyncAnimationFramesSaveDialog::m_d
private

Definition at line 43 of file KisAsyncAnimationFramesSaveDialog.h.


The documentation for this class was generated from the following files: