File indexing completed on 2024-05-12 15:59:05

0001 /*
0002  *  SPDX-FileCopyrightText: 2016 Boudewijn Rempt <boud@valdyas.org>
0003  *
0004  *  SPDX-License-Identifier: LGPL-2.0-or-later
0005  */
0006 #ifndef LIBKIS_DOCUMENT_H
0007 #define LIBKIS_DOCUMENT_H
0008 
0009 #include <QObject>
0010 
0011 #include "kritalibkis_export.h"
0012 #include "libkis.h"
0013 
0014 #include "GroupLayer.h"
0015 #include "CloneLayer.h"
0016 #include "FileLayer.h"
0017 #include "FilterLayer.h"
0018 #include "FillLayer.h"
0019 #include "VectorLayer.h"
0020 #include "FilterMask.h"
0021 #include "SelectionMask.h"
0022 #include "TransformMask.h"
0023 
0024 class KisDocument;
0025 
0026 /**
0027  * The Document class encapsulates a Krita Document/Image. A Krita document is an Image with
0028  * a filename. Libkis does not differentiate between a document and an image, like Krita does
0029  * internally.
0030  */
0031 class KRITALIBKIS_EXPORT Document : public QObject
0032 {
0033     Q_OBJECT
0034     Q_DISABLE_COPY(Document)
0035 
0036 public:
0037     explicit Document(KisDocument *document, bool ownsDocument, QObject *parent = 0);
0038     ~Document() override;
0039 
0040     bool operator==(const Document &other) const;
0041     bool operator!=(const Document &other) const;
0042 
0043     /**
0044      * @brief horizontalGuides
0045      * The horizontal guides.
0046      * @return a list of the horizontal positions of guides.
0047      */
0048     QList<qreal> horizontalGuides() const;
0049     /**
0050      * @brief verticalGuides
0051      * The vertical guide lines.
0052      * @return a list of vertical guides.
0053      */
0054     QList<qreal> verticalGuides() const;
0055 
0056     /**
0057      * @brief guidesVisible
0058      * Returns guide visibility.
0059      * @return whether the guides are visible.
0060      */
0061     bool guidesVisible() const;
0062     /**
0063      * @brief guidesLocked
0064      * Returns guide lockedness.
0065      * @return whether the guides are locked.
0066      */
0067     bool guidesLocked() const;
0068 
0069 public Q_SLOTS:
0070 
0071     /**
0072      * @brief clone create a shallow clone of this document.
0073      * @return a new Document that should be identical to this one in every respect.
0074      */
0075     Document *clone() const;
0076 
0077     /**
0078      * Batchmode means that no actions on the document should show dialogs or popups.
0079      * @return true if the document is in batchmode.
0080      */
0081     bool batchmode() const;
0082 
0083     /**
0084      * Set batchmode to @p value. If batchmode is true, then there should be no popups
0085      * or dialogs shown to the user.
0086      */
0087     void setBatchmode(bool value);
0088 
0089     /**
0090      * @brief activeNode retrieve the node that is currently active in the currently active window
0091      * @return the active node. If there is no active window, the first child node is returned.
0092      */
0093     Node* activeNode() const;
0094 
0095     /**
0096      * @brief setActiveNode make the given node active in the currently active view and window
0097      * @param value the node to make active.
0098      */
0099     void setActiveNode(Node* value);
0100 
0101     /**
0102      * @brief toplevelNodes return a list with all top level nodes in the image graph
0103      */
0104     QList<Node*> topLevelNodes() const;
0105 
0106     /**
0107      * @brief nodeByName searches the node tree for a node with the given name and returns it
0108      * @param name the name of the node
0109      * @return the first node with the given name or 0 if no node is found
0110      */
0111     Node *nodeByName(const QString &name) const;
0112 
0113 
0114     /**
0115      * @brief nodeByUniqueID searches the node tree for a node with the given name and returns it.
0116      * @param uuid the unique id of the node
0117      * @return the node with the given unique id, or 0 if no node is found.
0118      */
0119     Node *nodeByUniqueID(const QUuid &id) const;
0120 
0121     /**
0122      * colorDepth A string describing the color depth of the image:
0123      * <ul>
0124      * <li>U8: unsigned 8 bits integer, the most common type</li>
0125      * <li>U16: unsigned 16 bits integer</li>
0126      * <li>F16: half, 16 bits floating point. Only available if Krita was built with OpenEXR</li>
0127      * <li>F32: 32 bits floating point</li>
0128      * </ul>
0129      * @return the color depth.
0130      */
0131     QString colorDepth() const;
0132 
0133     /**
0134      * @brief colorModel retrieve the current color model of this document:
0135      * <ul>
0136      * <li>A: Alpha mask</li>
0137      * <li>RGBA: RGB with alpha channel (The actual order of channels is most often BGR!)</li>
0138      * <li>XYZA: XYZ with alpha channel</li>
0139      * <li>LABA: LAB with alpha channel</li>
0140      * <li>CMYKA: CMYK with alpha channel</li>
0141      * <li>GRAYA: Gray with alpha channel</li>
0142      * <li>YCbCrA: YCbCr with alpha channel</li>
0143      * </ul>
0144      * @return the internal color model string.
0145      */
0146     QString colorModel() const;
0147 
0148     /**
0149      * @return the name of the current color profile
0150      */
0151     QString colorProfile() const;
0152 
0153     /**
0154      * @brief setColorProfile set the color profile of the image to the given profile. The profile has to
0155      * be registered with krita and be compatible with the current color model and depth; the image data
0156      * is <i>not</i> converted.
0157      * @param colorProfile
0158      * @return false if the colorProfile name does not correspond to to a registered profile or if assigning
0159      * the profile failed.
0160      */
0161     bool setColorProfile(const QString &colorProfile);
0162 
0163     /**
0164      * @brief setColorSpace convert the nodes and the image to the given colorspace. The conversion is
0165      * done with Perceptual as intent, High Quality and No LCMS Optimizations as flags and no blackpoint
0166      * compensation.
0167      *
0168      * @param colorModel A string describing the color model of the image:
0169      * <ul>
0170      * <li>A: Alpha mask</li>
0171      * <li>RGBA: RGB with alpha channel (The actual order of channels is most often BGR!)</li>
0172      * <li>XYZA: XYZ with alpha channel</li>
0173      * <li>LABA: LAB with alpha channel</li>
0174      * <li>CMYKA: CMYK with alpha channel</li>
0175      * <li>GRAYA: Gray with alpha channel</li>
0176      * <li>YCbCrA: YCbCr with alpha channel</li>
0177      * </ul>
0178      * @param colorDepth A string describing the color depth of the image:
0179      * <ul>
0180      * <li>U8: unsigned 8 bits integer, the most common type</li>
0181      * <li>U16: unsigned 16 bits integer</li>
0182      * <li>F16: half, 16 bits floating point. Only available if Krita was built with OpenEXR</li>
0183      * <li>F32: 32 bits floating point</li>
0184      * </ul>
0185      * @param colorProfile a valid color profile for this color model and color depth combination.
0186      * @return false the combination of these arguments does not correspond to a colorspace.
0187      */
0188     bool setColorSpace(const QString &colorModel, const QString &colorDepth, const QString &colorProfile);
0189 
0190     /**
0191      * @brief backgroundColor returns the current background color of the document. The color will
0192      * also include the opacity.
0193      *
0194      * @return QColor
0195      */
0196     QColor backgroundColor();
0197 
0198     /**
0199      * @brief setBackgroundColor sets the background color of the document. It will trigger a projection
0200      * update.
0201      *
0202      * @param color A QColor. The color will be converted from sRGB.
0203      * @return bool
0204      */
0205     bool setBackgroundColor(const QColor &color);
0206 
0207     /**
0208      * @brief documentInfo creates and XML document representing document and author information.
0209      * @return a string containing a valid XML document with the right information about the document
0210      * and author. The DTD can be found here:
0211      *
0212      * https://phabricator.kde.org/source/krita/browse/master/krita/dtd/
0213      *
0214      * @code
0215      * <?xml version="1.0" encoding="UTF-8"?>
0216      * <!DOCTYPE document-info PUBLIC '-//KDE//DTD document-info 1.1//EN' 'http://www.calligra.org/DTD/document-info-1.1.dtd'>
0217      * <document-info xmlns="http://www.calligra.org/DTD/document-info">
0218      * <about>
0219      *  <title>My Document</title>
0220      *   <description></description>
0221      *   <subject></subject>
0222      *   <abstract><![CDATA[]]></abstract>
0223      *   <keyword></keyword>
0224      *   <initial-creator>Unknown</initial-creator>
0225      *   <editing-cycles>1</editing-cycles>
0226      *   <editing-time>35</editing-time>
0227      *   <date>2017-02-27T20:15:09</date>
0228      *   <creation-date>2017-02-27T20:14:33</creation-date>
0229      *   <language></language>
0230      *  </about>
0231      *  <author>
0232      *   <full-name>Boudewijn Rempt</full-name>
0233      *   <initial></initial>
0234      *   <author-title></author-title>
0235      *   <email></email>
0236      *   <telephone></telephone>
0237      *   <telephone-work></telephone-work>
0238      *   <fax></fax>
0239      *   <country></country>
0240      *   <postal-code></postal-code>
0241      *   <city></city>
0242      *   <street></street>
0243      *   <position></position>
0244      *   <company></company>
0245      *  </author>
0246      * </document-info>
0247      * @endcode
0248      *
0249      */
0250     QString documentInfo() const;
0251 
0252     /**
0253      * @brief setDocumentInfo set the Document information to the information contained in document
0254      * @param document A string containing a valid XML document that conforms to the document-info DTD
0255      * that can be found here:
0256      *
0257      * https://phabricator.kde.org/source/krita/browse/master/krita/dtd/
0258      */
0259     void setDocumentInfo(const QString &document);
0260 
0261     /**
0262      * @return the full path to the document, if it has been set.
0263      */
0264     QString fileName() const;
0265 
0266     /**
0267      * @brief setFileName set the full path of the document to @param value
0268      */
0269     void setFileName(QString value);
0270 
0271     /**
0272      * @return the height of the image in pixels
0273      */
0274     int height() const;
0275 
0276     /**
0277      * @brief setHeight resize the document to @param value height. This is a canvas resize, not a scale.
0278      */
0279     void setHeight(int value);
0280 
0281     /**
0282      * @return the name of the document. This is the title field in the @ref documentInfo
0283      */
0284     QString name() const;
0285 
0286     /**
0287      * @brief setName sets the name of the document to @p value. This is the title field in the @ref documentInfo
0288      */
0289     void setName(QString value);
0290 
0291     /**
0292      * @return the resolution in pixels per inch
0293      */
0294     int resolution() const;
0295     /**
0296      * @brief setResolution set the resolution of the image; this does not scale the image
0297      * @param value the resolution in pixels per inch
0298      */
0299     void setResolution(int value);
0300 
0301     /**
0302      * @brief rootNode the root node is the invisible group layer that contains the entire node
0303      * hierarchy.
0304      * @return the root of the image
0305      */
0306     Node* rootNode() const;
0307 
0308     /**
0309      * @brief selection Create a Selection object around the global selection, if there is one.
0310      * @return the global selection or None if there is no global selection.
0311      */
0312     Selection* selection() const;
0313 
0314     /**
0315      * @brief setSelection set or replace the global selection
0316      * @param value a valid selection object.
0317      */
0318     void setSelection(Selection* value);
0319 
0320     /**
0321      * @return the width of the image in pixels.
0322      */
0323     int width() const;
0324 
0325     /**
0326      * @brief setWidth resize the document to @param value width. This is a canvas resize, not a scale.
0327      */
0328     void setWidth(int value);
0329 
0330     /**
0331      * @return the left edge of the canvas in pixels.
0332      */
0333     int xOffset() const;
0334 
0335     /**
0336      * @brief setXOffset sets the left edge of the canvas to @p x.
0337      */
0338     void setXOffset(int x);
0339 
0340     /**
0341      * @return the top edge of the canvas in pixels.
0342      */
0343     int yOffset() const;
0344 
0345     /**
0346      * @brief setYOffset sets the top edge of the canvas to @p y.
0347      */
0348     void setYOffset(int y);
0349 
0350     /**
0351      * @return xRes the horizontal resolution of the image in pixels
0352      * per inch
0353      */
0354 
0355     double xRes() const;
0356 
0357     /**
0358      * @brief setXRes set the horizontal resolution of the image to
0359      * xRes in pixels per inch
0360      */
0361     void setXRes(double xRes) const;
0362 
0363     /**
0364      * @return yRes the vertical resolution of the image in pixels per
0365      * inch
0366      */
0367     double yRes() const;
0368 
0369     /**
0370      * @brief setYRes set the vertical resolution of the image to yRes
0371      * in pixels per inch
0372      */
0373     void setYRes(double yRes) const;
0374 
0375     /**
0376      * @brief pixelData reads the given rectangle from the image projection and returns it as a byte
0377      * array. The pixel data starts top-left, and is ordered row-first.
0378      *
0379      * The byte array can be interpreted as follows: 8 bits images have one byte per channel,
0380      * and as many bytes as there are channels. 16 bits integer images have two bytes per channel,
0381      * representing an unsigned short. 16 bits float images have two bytes per channel, representing
0382      * a half, or 16 bits float. 32 bits float images have four bytes per channel, representing a
0383      * float.
0384      *
0385      * You can read outside the image boundaries; those pixels will be transparent black.
0386      *
0387      * The order of channels is:
0388      *
0389      * <ul>
0390      * <li>Integer RGBA: Blue, Green, Red, Alpha
0391      * <li>Float RGBA: Red, Green, Blue, Alpha
0392      * <li>LabA: L, a, b, Alpha
0393      * <li>CMYKA: Cyan, Magenta, Yellow, Key, Alpha
0394      * <li>XYZA: X, Y, Z, A
0395      * <li>YCbCrA: Y, Cb, Cr, Alpha
0396      * </ul>
0397      *
0398      * The byte array is a copy of the original image data. In Python, you can use bytes, bytearray
0399      * and the struct module to interpret the data and construct, for instance, a Pillow Image object.
0400      *
0401      * @param x x position from where to start reading
0402      * @param y y position from where to start reading
0403      * @param w row length to read
0404      * @param h number of rows to read
0405      * @return a QByteArray with the pixel data. The byte array may be empty.
0406      */
0407     QByteArray pixelData(int x, int y, int w, int h) const;
0408 
0409     /**
0410      * @brief close Close the document: remove it from Krita's internal list of documents and
0411      * close all views. If the document is modified, you should save it first. There will be
0412      * no prompt for saving.
0413      *
0414      * After closing the document it becomes invalid.
0415      *
0416      * @return true if the document is closed.
0417      */
0418     bool close();
0419 
0420     /**
0421      * @brief crop the image to rectangle described by @p x, @p y,
0422      * @p w and @p h
0423      * @param x x coordinate of the top left corner
0424      * @param y y coordinate of the top left corner
0425      * @param w width
0426      * @param h height
0427      */
0428     void crop(int x, int y, int w, int h);
0429 
0430     /**
0431      * @brief exportImage export the image, without changing its URL to the given path.
0432      * @param filename the full path to which the image is to be saved
0433      * @param exportConfiguration a configuration object appropriate to the file format.
0434      * An InfoObject will used to that configuration.
0435      *
0436      * The supported formats have specific configurations that must be used when in
0437      * batchmode. They are described below:
0438      *
0439      *\b png
0440      * <ul>
0441      * <li>alpha: bool (True or False)
0442      * <li>compression: int (1 to 9)
0443      * <li>forceSRGB: bool (True or False)
0444      * <li>indexed: bool (True or False)
0445      * <li>interlaced: bool (True or False)
0446      * <li>saveSRGBProfile: bool (True or False)
0447      * <li>transparencyFillcolor: rgb (Ex:[255,255,255])
0448      * </ul>
0449      *
0450      *\b jpeg
0451      * <ul>
0452      * <li>baseline: bool (True or False)
0453      * <li>exif: bool (True or False)
0454      * <li>filters: bool (['ToolInfo', 'Anonymizer'])
0455      * <li>forceSRGB: bool (True or False)
0456      * <li>iptc: bool (True or False)
0457      * <li>is_sRGB: bool (True or False)
0458      * <li>optimize: bool (True or False)
0459      * <li>progressive: bool (True or False)
0460      * <li>quality: int (0 to 100)
0461      * <li>saveProfile: bool (True or False)
0462      * <li>smoothing: int (0 to 100)
0463      * <li>subsampling: int (0 to 3)
0464      * <li>transparencyFillcolor: rgb (Ex:[255,255,255])
0465      * <li>xmp: bool (True or False)
0466      * </ul>
0467      * @return true if the export succeeded, false if it failed.
0468      */
0469     bool exportImage(const QString &filename, const InfoObject &exportConfiguration);
0470 
0471     /**
0472      * @brief flatten all layers in the image
0473      */
0474     void flatten();
0475 
0476     /**
0477      * @brief resizeImage resizes the canvas to the given left edge, top edge, width and height.
0478      * Note: This doesn't scale, use scale image for that.
0479      * @param x the new left edge
0480      * @param y the new top edge
0481      * @param w the new width
0482      * @param h the new height
0483      */
0484     void resizeImage(int x, int y, int w, int h);
0485 
0486     /**
0487     * @brief scaleImage
0488     * @param w the new width
0489     * @param h the new height
0490     * @param xres the new xres
0491     * @param yres the new yres
0492     * @param strategy the scaling strategy. There's several ones amongst these that aren't available in the regular UI.
0493     * The list of filters is extensible and can be retrieved with Krita::filter
0494     * <ul>
0495     * <li>Hermite</li>
0496     * <li>Bicubic - Adds pixels using the color of surrounding pixels. Produces smoother tonal gradations than Bilinear.</li>
0497     * <li>Box - Replicate pixels in the image. Preserves all the original detail, but can produce jagged effects.</li>
0498     * <li>Bilinear - Adds pixels averaging the color values of surrounding pixels. Produces medium quality results when the image is scaled from half to two times the original size.</li>
0499     * <li>Bell</li>
0500     * <li>BSpline</li>
0501     * <li>Kanczos3 - Offers similar results than Bicubic, but maybe a little bit sharper. Can produce light and dark halos along strong edges.</li>
0502     * <li>Mitchell</li>
0503     * </ul>
0504     */
0505    void scaleImage(int w, int h, int xres, int yres, QString strategy);
0506 
0507    /**
0508     * @brief rotateImage
0509     * Rotate the image by the given radians.
0510     * @param radians the amount you wish to rotate the image in radians
0511     */
0512    void rotateImage(double radians);
0513 
0514    /**
0515     * @brief shearImage shear the whole image.
0516     * @param angleX the X-angle in degrees to shear by
0517     * @param angleY the Y-angle in degrees to shear by
0518     */
0519    void shearImage(double angleX, double angleY);
0520 
0521     /**
0522      * @brief save the image to its currently set path. The modified flag of the
0523      * document will be reset
0524      * @return true if saving succeeded, false otherwise.
0525      */
0526     bool save();
0527 
0528     /**
0529      * @brief saveAs save the document under the @p filename. The document's
0530      * filename will be reset to @p filename.
0531      * @param filename the new filename (full path) for the document
0532      * @return true if saving succeeded, false otherwise.
0533      */
0534     bool saveAs(const QString &filename);
0535 
0536     /**
0537      * @brief createNode create a new node of the given type. The node is not added
0538      * to the node hierarchy; you need to do that by finding the right parent node,
0539      * getting its list of child nodes and adding the node in the right place, then
0540      * calling Node::SetChildNodes
0541      *
0542      * @param name The name of the node
0543      *
0544      * @param nodeType The type of the node. Valid types are:
0545      * <ul>
0546      *  <li>paintlayer
0547      *  <li>grouplayer
0548      *  <li>filelayer
0549      *  <li>filterlayer
0550      *  <li>filllayer
0551      *  <li>clonelayer
0552      *  <li>vectorlayer
0553      *  <li>transparencymask
0554      *  <li>filtermask
0555      *  <li>transformmask
0556      *  <li>selectionmask
0557      * </ul>
0558      *
0559      * When relevant, the new Node will have the colorspace of the image by default;
0560      * that can be changed with Node::setColorSpace.
0561      *
0562      * The settings and selections for relevant layer and mask types can also be set
0563      * after the Node has been created.
0564      *
0565 @code
0566 d = Application.createDocument(1000, 1000, "Test", "RGBA", "U8", "", 120.0)
0567 root = d.rootNode();
0568 print(root.childNodes())
0569 l2 = d.createNode("layer2", "paintLayer")
0570 print(l2)
0571 root.addChildNode(l2, None)
0572 print(root.childNodes())
0573 @endcode
0574      *
0575      *
0576      * @return the new Node.
0577      */
0578     Node* createNode(const QString &name, const QString &nodeType);
0579     /**
0580      * @brief createGroupLayer
0581      * Returns a grouplayer object. Grouplayers are nodes that can have
0582      * other layers as children and have the passthrough mode.
0583      * @param name the name of the layer.
0584      * @return a GroupLayer object.
0585      */
0586     GroupLayer* createGroupLayer(const QString &name);
0587     /**
0588      * @brief createFileLayer returns a layer that shows an external image.
0589      * @param name name of the file layer.
0590      * @param fileName the absolute filename of the file referenced. Symlinks will be resolved.
0591      * @param scalingMethod how the dimensions of the file are interpreted
0592      *        can be either "None", "ImageToSize" or "ImageToPPI"
0593      * @return a FileLayer
0594      */
0595     FileLayer* createFileLayer(const QString &name, const QString fileName, const QString scalingMethod);
0596 
0597     /**
0598      * @brief createFilterLayer creates a filter layer, which is a layer that represents a filter
0599      * applied non-destructively.
0600      * @param name name of the filterLayer
0601      * @param filter the filter that this filter layer will us.
0602      * @param selection the selection.
0603      * @return a filter layer object.
0604      */
0605     FilterLayer* createFilterLayer(const QString &name, Filter &filter, Selection &selection);
0606 
0607     /**
0608      * @brief createFillLayer creates a fill layer object, which is a layer
0609      * @param name
0610      * @param generatorName - name of the generation filter.
0611      * @param configuration - the configuration for the generation filter.
0612      * @param selection - the selection.
0613      * @return a filllayer object.
0614      *
0615      * @code
0616      * from krita import *
0617      * d = Krita.instance().activeDocument()
0618      * i = InfoObject();
0619      * i.setProperty("pattern", "Cross01.pat")
0620      * s = Selection();
0621      * s.select(0, 0, d.width(), d.height(), 255)
0622      * n = d.createFillLayer("test", "pattern", i, s)
0623      * r = d.rootNode();
0624      * c = r.childNodes();
0625      * r.addChildNode(n, c[0])
0626      * d.refreshProjection()
0627      * @endcode
0628      */
0629     FillLayer* createFillLayer(const QString &name, const QString generatorName, InfoObject &configuration, Selection &selection);
0630 
0631     /**
0632      * @brief createCloneLayer
0633      * @param name
0634      * @param source
0635      * @return
0636      */
0637     CloneLayer* createCloneLayer(const QString &name, const Node* source);
0638 
0639     /**
0640      * @brief createVectorLayer
0641      * Creates a vector layer that can contain vector shapes.
0642      * @param name the name of this layer.
0643      * @return a VectorLayer.
0644      */
0645     VectorLayer* createVectorLayer(const QString &name);
0646 
0647     /**
0648      * @brief createFilterMask
0649      * Creates a filter mask object that much like a filterlayer can apply a filter non-destructively.
0650      * @param name the name of the layer.
0651      * @param filter the filter assigned.
0652      * @param selection the selection to be used by the filter mask
0653      * @return a FilterMask
0654      */
0655     FilterMask* createFilterMask(const QString &name, Filter &filter, Selection &selection);
0656 
0657     /**
0658      * @brief createFilterMask
0659      * Creates a filter mask object that much like a filterlayer can apply a filter non-destructively.
0660      * @param name the name of the layer.
0661      * @param filter the filter assigned.
0662      * @param selection_source a node from which the selection should be initialized
0663      * @return a FilterMask
0664      */
0665     FilterMask* createFilterMask(const QString &name, Filter &filter, const Node* selection_source);
0666 
0667     /**
0668      * @brief createSelectionMask
0669      * Creates a selection mask, which can be used to store selections.
0670      * @param name - the name of the layer.
0671      * @return a SelectionMask
0672      */
0673     SelectionMask* createSelectionMask(const QString &name);
0674 
0675     /**
0676      * @brief createTransformMask
0677      * Creates a transform mask, which can be used to apply a transformation non-destructively.
0678      * @param name - the name of the layer mask.
0679      * @return a TransformMask
0680      */
0681     TransformMask* createTransformMask(const QString &name);
0682 
0683     /**
0684      * @brief projection creates a QImage from the rendered image or
0685      * a cutout rectangle.
0686      */
0687     QImage projection(int x = 0, int y = 0, int w = 0, int h = 0) const;
0688 
0689     /**
0690      * @brief thumbnail create a thumbnail of the given dimensions.
0691      *
0692      * If the requested size is too big a null QImage is created.
0693      *
0694      * @return a QImage representing the layer contents.
0695      */
0696     QImage thumbnail(int w, int h) const;
0697 
0698 
0699     /**
0700      * [low-level] Lock the image without waiting for all the internal job queues are processed
0701      *
0702      * WARNING: Don't use it unless you really know what you are doing! Use barrierLock() instead!
0703      *
0704      * Waits for all the **currently running** internal jobs to complete and locks the image
0705      * for writing. Please note that this function does **not** wait for all the internal
0706      * queues to process, so there might be some non-finished actions pending. It means that
0707      * you just postpone these actions until you unlock() the image back. Until then, then image
0708      * might easily be frozen in some inconsistent state.
0709      *
0710      * The only sane usage for this function is to lock the image for **emergency**
0711      * processing, when some internal action or scheduler got hung up, and you just want
0712      * to fetch some data from the image without races.
0713      *
0714      * In all other cases, please use barrierLock() instead!
0715      */
0716     void lock();
0717 
0718     /**
0719      * Unlocks the image and starts/resumes all the pending internal jobs. If the image
0720      * has been locked for a non-readOnly access, then all the internal caches of the image
0721      * (e.g. lod-planes) are reset and regeneration jobs are scheduled.
0722      */
0723     void unlock();
0724 
0725     /**
0726      * Wait for all the internal image jobs to complete and return without locking
0727      * the image. This function is handly for tests or other synchronous actions,
0728      * when one needs to wait for the result of his actions.
0729      */
0730     void waitForDone();
0731 
0732     /**
0733      * @brief Tries to lock the image without waiting for the jobs to finish
0734      *
0735      * Same as barrierLock(), but doesn't block execution of the calling thread
0736      * until all the background jobs are finished. Instead, in case of presence of
0737      * unfinished jobs in the queue, it just returns false
0738      *
0739      * @return whether the lock has been acquired
0740      */
0741     bool tryBarrierLock();
0742 
0743     /**
0744      * Starts a synchronous recomposition of the projection: everything will
0745      * wait until the image is fully recomputed.
0746      */
0747     void refreshProjection();
0748 
0749     /**
0750      * @brief setHorizontalGuides
0751      * replace all existing horizontal guides with the entries in the list.
0752      * @param lines a list of floats containing the new guides.
0753      */
0754     void setHorizontalGuides(const QList<qreal> &lines);
0755     /**
0756      * @brief setVerticalGuides
0757      * replace all existing horizontal guides with the entries in the list.
0758      * @param lines a list of floats containing the new guides.
0759      */
0760     void setVerticalGuides(const QList<qreal> &lines);
0761 
0762     /**
0763      * @brief setGuidesVisible
0764      * set guides visible on this document.
0765      * @param visible whether or not the guides are visible.
0766      */
0767     void setGuidesVisible(bool visible);
0768 
0769     /**
0770      * @brief setGuidesLocked
0771      * set guides locked on this document
0772      * @param locked whether or not to lock the guides on this document.
0773      */
0774     void setGuidesLocked(bool locked);
0775 
0776     /**
0777      * @brief modified returns true if the document has unsaved modifications.
0778      */
0779     bool modified() const;
0780 
0781     /**
0782      * @brief setModified sets the modified status of the document
0783      * @param modified if true, the document is considered modified and closing it will ask for saving.
0784      */
0785     void setModified(bool modified);
0786 
0787     /**
0788      * @brief bounds return the bounds of the image
0789      * @return the bounds
0790      */
0791     QRect bounds() const;
0792 
0793     /****
0794      * Animation Related API
0795      *****/
0796 
0797 
0798     /**
0799      * @brief Import an image sequence of files from a directory. This will grab all
0800      * images from the directory and import them with a potential offset (firstFrame)
0801      * and step (images on 2s, 3s, etc)
0802      * @returns whether the animation import was successful
0803      */
0804     bool importAnimation(const QList<QString> &files, int firstFrame, int step);
0805 
0806     /**
0807      * @brief frames per second of document
0808      * @return the fps of the document
0809      */
0810     int framesPerSecond();
0811 
0812     /**
0813      * @brief set frames per second of document
0814      */
0815     void setFramesPerSecond(int fps);
0816 
0817     /**
0818      * @brief set start time of animation
0819      */
0820     void setFullClipRangeStartTime(int startTime);
0821 
0822     /**
0823      * @brief get the full clip range start time
0824      * @return full clip range start time
0825      */
0826     int fullClipRangeStartTime();
0827 
0828 
0829     /**
0830      * @brief set full clip range end time
0831      */
0832     void setFullClipRangeEndTime(int endTime);
0833 
0834     /**
0835      * @brief get the full clip range end time
0836      * @return full clip range end time
0837      */
0838     int fullClipRangeEndTime();
0839 
0840     /**
0841      * @brief get total frame range for animation
0842      * @return total frame range for animation
0843      */
0844     int animationLength();
0845 
0846     /**
0847      * @brief set temporary playback range of document
0848      */
0849     void setPlayBackRange(int start, int stop);
0850 
0851     /**
0852      * @brief get start time of current playback
0853      * @return start time of current playback
0854      */
0855     int playBackStartTime();
0856 
0857     /**
0858      * @brief get end time of current playback
0859      * @return end time of current playback
0860      */
0861     int playBackEndTime();
0862 
0863     /**
0864      * @brief get current frame selected of animation
0865      * @return current frame selected of animation
0866      */
0867     int currentTime();
0868 
0869     /**
0870      * @brief set current time of document's animation
0871      */
0872     void setCurrentTime(int time);
0873 
0874     /**
0875      * @brief annotationTypes returns the list of annotations present in the document.
0876      * Each annotation type is unique.
0877      */
0878     QStringList annotationTypes() const;
0879 
0880     /**
0881      * @brief annotationDescription gets the pretty description for the current annotation
0882      * @param type the type of the annotation
0883      * @return a string that can be presented to the user
0884      */
0885     QString annotationDescription(const QString &type) const;
0886 
0887     /**
0888      * @brief annotation the actual data for the annotation for this type. It's a simple
0889      * QByteArray, what's in it depends on the type of the annotation
0890      * @param type the type of the annotation
0891      * @return a bytearray, possibly empty if this type of annotation doesn't exist
0892      */
0893     QByteArray annotation(const QString &type);
0894 
0895     /**
0896      * @brief setAnnotation Add the given annotation to the document
0897      * @param type the unique type of the annotation
0898      * @param description the user-visible description of the annotation
0899      * @param annotation the annotation itself
0900      */
0901     void setAnnotation(const QString &type, const QString &description, const QByteArray &annotation);
0902 
0903     /**
0904      * @brief removeAnnotation remove the specified annotation from the image
0905      * @param type the type defining the annotation
0906      */
0907     void removeAnnotation(const QString &type);
0908 private:
0909 
0910     friend class Krita;
0911     friend class Window;
0912     friend class Filter;
0913     friend class View;
0914     friend class VectorLayer;
0915     friend class Shape;
0916     QPointer<KisDocument> document() const;
0917     void setOwnsDocument(bool ownsDocument);
0918 
0919 private:
0920     struct Private;
0921     Private *const d;
0922 
0923 };
0924 
0925 #endif // LIBKIS_DOCUMENT_H