14#include <config-mlt.h>
40#include <QScopedPointer>
42#include <QRegularExpression>
45#include <klocalizedstring.h>
48#include <kconfiggroup.h>
49#include <QKeySequence>
51#include <QApplication>
52#include <QDomDocument>
54#include <QGlobalStatic>
95 , animationCachePopulator(_part)
96 , playbackEngine(nullptr)
114 bool closingSession{
false};
120 Q_FOREACH(
auto view, views) {
121 if (view && view->isVisible() && view->document() == document) {
122 return view->queryClose();
139 const int busyWaitDelay = 1000;
142 dialog.blockIfImageIsBusy();
163 connect(&
d->idleWatcher, SIGNAL(startedIdleMode()),
164 &
d->animationCachePopulator, SLOT(slotRequestRegeneration()));
165 connect(&
d->idleWatcher, SIGNAL(startedIdleMode()),
172 d->animationCachePopulator.slotRequestRegeneration();
178 while (!
d->documents.isEmpty()) {
179 delete d->documents.takeFirst();
182 while (!
d->views.isEmpty()) {
183 delete d->views.takeFirst();
186 while (!
d->mainWindows.isEmpty()) {
187 delete d->mainWindows.takeFirst();
198 if (document->image()) {
199 images << document->image();
203 d->idleWatcher.setTrackedImages(images);
208 d->idleWatcher.forceImageModified();
215 if (!
d->documents.contains(document)) {
216 d->documents.append(document);
221 connect(document, SIGNAL(sigSavingFinished(QString)), SLOT(
slotDocumentSaved(QString)));
245 return d->documents.size();
251 d->documents.removeAll(document);
254 if (deleteDocument) {
255 document->deleteLater();
263 dbgUI <<
"mainWindow" << (
void*)mw <<
"added to view" <<
this;
264 d->mainWindows.append(mw);
283 KConfigGroup grp( KSharedConfig::openConfig(),
"crashprevention");
284 if (grp.readEntry(
"CreatingCanvas",
false)) {
290 grp.writeEntry(
"CreatingCanvas",
true);
295 KisCursorOverrideLock cursorLock(Qt::WaitCursor);
296 view =
new KisView(document, viewManager, parent);
300 grp.writeEntry(
"CreatingCanvas",
false);
313 if (!
d->views.contains(view)) {
314 d->views.append(view);
335 d->views.removeAll(view);
340 if (view && view->document() == doc) {
359 return d->views.count();
364 if (view && view->isVisible() && view->document() == doc) {
374 return d->closingSession;
379 return s_instance.exists();
384 d->closingSession =
true;
386 Q_FOREACH(
auto document,
d->documents) {
387 if (!
d->queryCloseDocument(document.data())) {
388 d->closingSession =
false;
393 if (
d->currentSession) {
397 d->currentSession->storeCurrentWindows();
402 KConfigGroup cfg = KSharedConfig::openConfig()->group(
"session");
403 cfg.writeEntry(
"previousSession",
d->currentSession->name());
406 d->currentSession =
nullptr;
410 Q_FOREACH (
auto window,
d->mainWindows) {
414 if (
d->sessionManager) {
415 d->sessionManager->close();
419 d->closingSession =
false;
431 QUrl url = QUrl::fromLocalFile(filePath);
433 if (!
d->pendingAddRecentUrlMap.contains(url)) {
436 QUrl oldUrl =
d->pendingAddRecentUrlMap.take(url);
442 dbgUI <<
"mainWindow" << (
void*)mainWindow <<
"removed from doc" <<
this;
444 d->mainWindows.removeAll(mainWindow);
450 return d->mainWindows;
455 return d->mainWindows.count();
461 QWidget *widget = qApp->activeWindow();
462 KisMainWindow *mainWindow = qobject_cast<KisMainWindow*>(widget);
463 while (!mainWindow && widget) {
464 widget = widget->parentWidget();
465 mainWindow = qobject_cast<KisMainWindow*>(widget);
483 if (mainWindow->id() ==
id) {
493 return &
d->idleWatcher;
498 return &
d->animationCachePopulator;
503 return d->playbackEngine.data();
509 d->animationCachePopulator.requestRegenerationWithPriorityFrame(image, frame);
536 KisCursorOverrideLock cursorLock(Qt::BusyCursor);
540 bool ok = document->loadNativeFormat(url.toLocalFile());
541 document->setModified(
false);
542 document->undoStack()->clear();
543 document->documentInfo()->resetMetaData();
548 mimeType.remove( QRegularExpression(
"-template$" ) );
549 document->setMimeTypeAfterLoading(mimeType);
550 document->resetPath();
551 document->setReadWrite(
true);
554 if (document->errorMessage().isEmpty()) {
555 QMessageBox::critical(qApp->activeWindow(), i18nc(
"@title:window",
"Krita"), i18n(
"Could not create document from template\n%1", document->localFilePath()));
558 QMessageBox::critical(qApp->activeWindow(), i18nc(
"@title:window",
"Krita"), i18n(
"Could not create document from template\n%1\nReason: %2", document->localFilePath(), document->errorMessage()));
563 QMap<QString, QString> dictionary;
566 document->image()->rootLayer()->accept(
v);
578 if (!url.isEmpty()) {
580 if (url.isLocalFile()) {
581 QString path = url.adjusted(QUrl::StripTrailingSlash).toLocalFile();
582 const QStringList tmpDirs = QStandardPaths::locateAll(QStandardPaths::TempLocation,
"", QStandardPaths::LocateDirectory);
583 for (QStringList::ConstIterator it = tmpDirs.begin() ; ok && it != tmpDirs.end() ; ++it) {
584 if (path.contains(*it)) {
590 for (QStringList::ConstIterator it = templateDirs.begin() ; ok && it != templateDirs.end() ; ++it) {
591 if (path.contains(*it)) {
598 if (!oldUrl.isEmpty()) {
608 d->pendingAddRecentUrlMap.insert(url, oldUrl);
628 if (
d->sessionManager.isNull()) {
632 d->sessionManager->show();
633 d->sessionManager->activateWindow();
646 if (sessionName.isNull())
return false;
650 if (!session || !session->valid())
return false;
658 d->currentSession = session;
664 d->currentSession = session;
673 if (
d->playbackEngine->supportsAudio()) {
680 d->playbackEngine->setObservedCanvas(
canvas);
690 d->playbackEngine.reset();
699 QScopedPointer backup(p_playbackEngine);
700 d->playbackEngine.swap(backup);
704 KisUsageLogger::log(
"Audio Playback Engine: " + QString(p_playbackEngine->metaObject()->className()));
709#include "moc_KisPart.cpp"
quint64 part(quint64 n1, quint64 n2, int p)
Q_GLOBAL_STATIC(KisStoragePluginRegistry, s_instance)
static KisActionRegistry * instance()
void setFeedbackCallback(std::function< void(KisImageSP)> callback)
static KisBusyWaitBroker * instance()
static KisColorManager * instance()
void disableOpenGL() const
QString canvasState(bool defaultValue=false) const
bool saveSessionOnQuit(bool defaultValue) const
const KisTimeSpan & documentPlaybackRange() const
documentPlaybackRange
KisImageAnimationInterface * animationInterface() const
A container for a set of QAction objects.
virtual KisKActionCollection * actionCollection() const
bool openDocument(const QString &path, OpenFlags flags)
KisView * addViewAndNotifyLoadingCompleted(KisDocument *document, QMdiSubWindow *subWindow=0)
KisViewManager * viewManager
bool hackIsSaving() const
void initializeGeometry()
void synchronizeDynamicActions()
static QString mimeTypeForFile(const QString &file, bool checkExistingFiles=true)
Find the mimetype for the given filename. The filename must include a suffix.
KisAnimationCachePopulator animationCachePopulator
bool closeSession(bool keepWindows=false)
void sigDocumentSaved(const QString &url)
QList< QPointer< KisDocument > > documents
void sigViewAdded(KisView *view)
void removeMainWindow(KisMainWindow *mainWindow)
bool queryCloseDocument(KisDocument *document)
void upgradeToPlaybackEngineMLT(class KoCanvasBase *canvas)
QList< QPointer< KisMainWindow > > mainWindows
void addRecentURLToAllMainWindows(QUrl url, QUrl oldUrl=QUrl())
void setPlaybackEngine(KisPlaybackEngine *p_playbackEngine)
void documentClosed(const QString &ref)
KisView * createView(KisDocument *document, KisViewManager *viewManager, QWidget *parent)
void openTemplate(const QUrl &url)
KisInputManager * currentInputManager()
QScopedPointer< KisSessionManagerDialog > sessionManager
KisSessionResourceSP currentSession
static KisPart * instance()
void sigDocumentAdded(KisDocument *document)
QScopedPointer< KisPlaybackEngine > playbackEngine
bool restoreSession(const QString &sessionName)
void slotDocumentSaved(const QString &filePath)
void addView(KisView *view)
void removeView(KisView *view)
QMap< QUrl, QUrl > pendingAddRecentUrlMap
void addDocument(KisDocument *document, bool notify=true)
void queueAddRecentURLToAllMainWindowsOnFileSaved(QUrl url, QUrl oldUrl=QUrl())
int documentCount() const
int viewCount(KisDocument *doc) const
void playbackEngineChanged(KisPlaybackEngine *newPlaybackEngine)
KisAnimationCachePopulator * cachePopulator() const
KisMainWindow * currentMainwindow() const
void prioritizeFrameForCache(KisImageSP image, int frame)
KisIdleWatcher idleWatcher
KisMainWindow * windowById(QUuid id) const
void removeDocument(KisDocument *document, bool deleteDocument=true)
KisDocument * createTemporaryDocument() const
void sigViewRemoved(KisView *view)
QWidget * currentMainwindowAsQWidget() const
void startCustomDocument(KisDocument *doc)
startCustomDocument adds the given document to the document list and deletes the sender()
KisDocument * createDocument() const
QList< QPointer< KisView > > views
void setCurrentSession(KisSessionResourceSP session)
void documentOpened(const QString &ref)
void updateIdleWatcherConnections()
void openExistingFile(const QString &path)
void sigDocumentRemoved(const QString &filename)
int mainwindowCount() const
void unloadPlaybackEngine()
void showSessionManager()
void sigMainWindowIsBeingCreated(KisMainWindow *window)
void notifyMainWindowIsBeingCreated(KisMainWindow *mainWindow)
notifyMainWindowIsBeingCreated emits the sigMainWindowCreated signal
KisMainWindow * createMainWindow(QUuid id=QUuid())
The KisPlaybackEngineMLT class is an implementation of KisPlaybackEngine that uses MLT (Media Lovin' ...
The KisPlaybackEngineQT class is an implementation of KisPlaybackEngine that drives animation playbac...
Krita's base animation playback engine for producing image frame changes and associated audio.
static KisRecentFileIconCache * instance()
void reloadFileIcon(const QUrl &url)
void add(const QUrl &url)
void remove(const QUrl &url)
static KisRecentFilesManager * instance()
The KisResourceModel class provides the main access to resources. It is possible to filter the resour...
bool updateResource(KoResourceSP resource) override
updateResource creates a new version of the resource in the storage and in the database....
static KisResourceServerProvider * instance()
KoResourceServer< KisSessionResource > * sessionServer()
bool contains(int time) const
KisTranslateLayerNamesVisitor::KisTranslateLayerNamesVisitor translates layer names from templates.
static void log(const QString &message)
Logs with date/time.
KisInputManager * inputManager() const
Filters events and sends them to canvas actions.
KisMainWindow * mainWindow() const
QPointer< KisDocument > document
static QStringList findDirs(const QString &type)
QSharedPointer< T > resource(const QString &md5, const QString &fileName, const QString &name)
resource retrieves a resource. If the md5sum is not empty, the resource will only be retrieved if a r...
#define KIS_SAFE_ASSERT_RECOVER_RETURN(cond)
#define KIS_ASSERT_RECOVER_RETURN(cond)
static KisMemoryStatisticsServer * instance()
static KoResourceServerProvider * instance()