File indexing completed on 2024-05-12 04:34:58

0001 /* This file is part of Spectacle, the KDE screenshot utility
0002  * SPDX-FileCopyrightText: 2019 Boudhayan Gupta <bgupta@kde.org>
0003  * SPDX-License-Identifier: LGPL-2.0-or-later
0004  */
0005 
0006 #pragma once
0007 
0008 #include <QEventLoopLocker>
0009 #include <QObject>
0010 #include <QQmlEngine>
0011 #include <QQuickItem>
0012 #include <QVariantAnimation>
0013 
0014 #include "CaptureModeModel.h"
0015 #include "CommandLineOptions.h"
0016 #include "ExportManager.h"
0017 #include "Gui/Annotations/AnnotationDocument.h"
0018 #include "Gui/CaptureWindow.h"
0019 #include "Gui/ViewerWindow.h"
0020 #include "Platforms/PlatformLoader.h"
0021 #include "RecordingModeModel.h"
0022 #include "VideoFormatModel.h"
0023 #include "settings.h"
0024 
0025 #include <array>
0026 #include <memory>
0027 
0028 class SpectacleCore : public QObject
0029 {
0030     Q_OBJECT
0031     Q_PROPERTY(ImagePlatform *imagePlatform READ imagePlatform CONSTANT FINAL)
0032     Q_PROPERTY(CaptureModeModel *captureModeModel READ captureModeModel CONSTANT FINAL)
0033     Q_PROPERTY(RecordingModeModel *recordingModeModel READ recordingModeModel CONSTANT FINAL)
0034     Q_PROPERTY(QUrl screenCaptureUrl READ screenCaptureUrl NOTIFY screenCaptureUrlChanged FINAL)
0035     Q_PROPERTY(int captureTimeRemaining READ captureTimeRemaining NOTIFY captureTimeRemainingChanged FINAL)
0036     Q_PROPERTY(qreal captureProgress READ captureProgress NOTIFY captureProgressChanged FINAL)
0037     Q_PROPERTY(QString recordedTime READ recordedTime NOTIFY recordedTimeChanged)
0038     Q_PROPERTY(bool videoMode READ videoMode NOTIFY videoModeChanged)
0039     Q_PROPERTY(QUrl currentVideo READ currentVideo NOTIFY currentVideoChanged)
0040 
0041 public:
0042     enum class StartMode {
0043         Gui = 0,
0044         DBus = 1,
0045         Background = 2,
0046     };
0047 
0048     explicit SpectacleCore(QObject *parent = nullptr);
0049     ~SpectacleCore() override;
0050 
0051     static SpectacleCore *instance();
0052 
0053     ImagePlatform *imagePlatform() const;
0054 
0055     CaptureModeModel *captureModeModel() const;
0056     RecordingModeModel *recordingModeModel() const;
0057     VideoFormatModel *videoFormatModel() const;
0058 
0059     AnnotationDocument *annotationDocument() const;
0060 
0061     QUrl screenCaptureUrl() const;
0062     void setScreenCaptureUrl(const QUrl &url);
0063     // Used when setting the URL from CLI
0064     void setScreenCaptureUrl(const QString &filePath);
0065 
0066     QUrl outputUrl() const;
0067 
0068     int captureTimeRemaining() const;
0069     qreal captureProgress() const;
0070 
0071     void initGuiNoScreenshot();
0072 
0073     void syncExportImage();
0074 
0075     Q_INVOKABLE void startRecording(VideoPlatform::RecordingMode mode, bool withPointer = Settings::videoIncludePointer());
0076     Q_INVOKABLE void finishRecording();
0077     bool videoMode() const;
0078     QUrl currentVideo() const;
0079     QString recordedTime() const;
0080     Q_INVOKABLE QString timeFromMilliseconds(qint64 milliseconds) const;
0081 
0082     ExportManager::Actions autoExportActions() const;
0083 
0084     void activateAction(const QString &actionName, const QVariant &parameter);
0085 
0086 public Q_SLOTS:
0087     void activate(const QStringList &arguments, const QString &workingDirectory);
0088     void takeNewScreenshot(int captureMode = Settings::captureMode(),
0089                            int timeout = Settings::captureOnClick() ? -1 : Settings::captureDelay() * 1000,
0090                            bool includePointer = Settings::includePointer(),
0091                            bool includeDecorations = Settings::includeDecorations(),
0092                            bool includeShadow = Settings::includeShadow());
0093     void cancelScreenshot();
0094     void showErrorMessage(const QString &message);
0095     void onScreenshotFailed();
0096 
0097 Q_SIGNALS:
0098     void screenCaptureUrlChanged();
0099     void captureTimeRemainingChanged();
0100     void captureProgressChanged();
0101 
0102     void allDone();
0103     void dbusScreenshotFailed();
0104     void dbusRecordingFailed();
0105     void videoModeChanged(bool videoMode);
0106     void currentVideoChanged(const QUrl &currentVideo);
0107     void recordedTimeChanged();
0108 
0109 private:
0110     enum class ScreenCapture {
0111         Screenshot,
0112         Recording,
0113     };
0114 
0115     void takeNewScreenshot(ImagePlatform::GrabMode grabMode, int timeout, bool includePointer, bool includeDecorations, bool includeShadow);
0116     void setExportImage(const QImage &image);
0117     void showViewerIfGuiMode(bool minimized = false);
0118     void doNotify(ScreenCapture type, const ExportManager::Actions &actions, const QUrl &saveUrl);
0119     ImagePlatform::GrabMode toGrabMode(CaptureModeModel::CaptureMode captureMode, bool transientOnly) const;
0120     CaptureModeModel::CaptureMode toCaptureMode(ImagePlatform::GrabMode grabMode) const;
0121     bool isGuiNull() const;
0122     QQmlEngine *getQmlEngine();
0123     void initCaptureWindows(CaptureWindow::Mode mode);
0124     void initViewerWindow(ViewerWindow::Mode mode);
0125     void deleteWindows();
0126     void unityLauncherUpdate(const QVariantMap &properties) const;
0127     void setVideoMode(bool enabled);
0128     void setCurrentVideo(const QUrl &currentVideo);
0129     QUrl videoOutputUrl() const;
0130 
0131     static SpectacleCore *s_self;
0132     std::unique_ptr<AnnotationDocument> m_annotationDocument = nullptr;
0133     StartMode m_startMode = StartMode::Gui;
0134     QUrl m_screenCaptureUrl;
0135     std::unique_ptr<ImagePlatform> m_imagePlatform;
0136     std::unique_ptr<VideoPlatform> m_videoPlatform;
0137     std::unique_ptr<CaptureModeModel> m_captureModeModel;
0138     std::unique_ptr<RecordingModeModel> m_recordingModeModel;
0139     std::unique_ptr<VideoFormatModel> m_videoFormatModel;
0140     std::unique_ptr<QQmlEngine> m_engine;
0141     std::unique_ptr<QTimer> m_annotationSyncTimer;
0142     std::unique_ptr<QVariantAnimation> m_delayAnimation;
0143     std::unique_ptr<QEventLoopLocker> m_eventLoopLocker;
0144 
0145     // Use ViewerWindow::instance() to get the viewer window.
0146     ViewerWindow::UniquePointer m_viewerWindow = {nullptr, nullptr};
0147 
0148     // Use CaptureWindow::instances() to get the capture windows.
0149     // Don't assume that this will never have entries that are null.
0150     // For some reason, removeIf/erase_if/find_if then erase doesn't work with QList/QList,
0151     // so we have to use std::vector. Something about use of a deleted unique_ptr function.
0152     std::vector<CaptureWindow::UniquePointer> m_captureWindows;
0153 
0154     bool m_copyImageToClipboard = false;
0155     bool m_copyLocationToClipboard = false;
0156     bool m_saveToOutput = false;
0157     std::array<bool, CommandLineOptions::TotalOptions> m_cliOptions = {};
0158 
0159     QUrl m_editExistingUrl;
0160     QUrl m_outputUrl;
0161 
0162     ImagePlatform::GrabMode m_lastGrabMode = ImagePlatform::GrabMode::NoGrabModes;
0163     bool m_lastIncludePointer = false; // cli default value
0164     bool m_lastIncludeDecorations = true; // cli default value
0165     bool m_lastIncludeShadow = true; // cli default value
0166     VideoPlatform::RecordingMode m_lastRecordingMode = VideoPlatform::NoRecordingModes;
0167     bool m_videoMode = false;
0168     QUrl m_currentVideo;
0169 };