1 /* This file is part of the KDE project
2    Copyright (C) 2004-2006 David Faure <faure@kde.org>
3    Copyright (C) 2007-2008 Thorsten Zachmann <zachmann@kde.org>
4    Copyright (C) 2007 Jan Hambrecht <jaham@gmx.net>
5    Copyright (C) 2010 Benjamin Port <port.benjamin@gmail.com>
6 
7    This library is free software; you can redistribute it and/or
8    modify it under the terms of the GNU Library General Public
9    License as published by the Free Software Foundation; either
10    version 2 of the License, or (at your option) any later version.
11 
12    This library is distributed in the hope that it will be useful,
13    but WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15    Library General Public License for more details.
16 
17    You should have received a copy of the GNU Library General Public License
18    along with this library; see the file COPYING.LIB.  If not, write to
19    the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
20  * Boston, MA 02110-1301, USA.
21 */
22 
23 #ifndef KOSHAPESAVINGCONTEXT_H
24 #define KOSHAPESAVINGCONTEXT_H
25 
26 #include "flake_export.h"
27 
28 #include <KoElementReference.h>
29 #include <QMap>
30 
31 class KoShape;
32 class KoXmlWriter;
33 class KoGenStyles;
34 class KoDataCenterBase;
35 class KoEmbeddedDocumentSaver;
36 class KoImageData;
37 class KoMarker;
38 class KoShapeLayer;
39 class KoStore;
40 class KoSharedSavingData;
41 class KoShapeSavingContextPrivate;
42 
43 class QImage;
44 class QTransform;
45 
46 /**
47  * The set of data for the ODF file format used during saving of a shape.
48  */
49 class FLAKE_EXPORT KoShapeSavingContext
50 {
51 public:
52     /// The Style used for saving the shape
53     enum ShapeSavingOption {
54         /**
55          * If set the style of family presentation ('pr') is used,
56          * See OpenDocument 9.2.15 Common Drawing Shape Attributes / Style
57          */
58         PresentationShape = 1,
59         /**
60          * Save the draw:id used for referencing the shape. If draw:id is saved, xml:id is also
61          * saved.
62          * See OpenDocument 9.2.15 Common Drawing Shape Attributes / ID
63          */
64         DrawId = 2,
65         /**
66          * If set the automatic style will be marked as being needed in styles.xml
67          */
68         AutoStyleInStyleXml = 4,
69         /**
70          * If set duplicate master pages will be merged to one
71          */
72         UniqueMasterPages = 8,
73         /**
74          * If set the z-index is saved in the shape
75          */
76         ZIndex = 16
77     };
78     Q_DECLARE_FLAGS(ShapeSavingOptions, ShapeSavingOption)
79 
80     /**
81      * @brief Constructor
82      * @param xmlWriter used for writing the xml
83      * @param mainStyles for saving the styles
84      * @param embeddedSaver for saving embedded documents
85      */
86     KoShapeSavingContext(KoXmlWriter &xmlWriter, KoGenStyles &mainStyles,
87                          KoEmbeddedDocumentSaver &embeddedSaver);
88     virtual ~KoShapeSavingContext();
89 
90     /**
91      * @brief Get the xml writer
92      *
93      * @return xmlWriter
94      */
95     KoXmlWriter &xmlWriter();
96 
97     /**
98      * @brief Set the xml writer
99      *
100      * Change the xmlWriter that is used in the Context e.g. for saving to styles.xml
101      * instead of content.xml
102      *
103      * @param xmlWriter to use
104      */
105     void setXmlWriter(KoXmlWriter &xmlWriter);
106 
107     /**
108      * @brief Get the main styles
109      *
110      * @return main styles
111      */
112     KoGenStyles &mainStyles();
113 
114     /**
115      * @brief Get the embedded document saver
116      *
117      * @return embedded document saver
118      */
119     KoEmbeddedDocumentSaver &embeddedSaver();
120 
121     /**
122      * @brief Check if an option is set
123      *
124      * @return ture if the option is set, false otherwise
125      */
126     bool isSet(ShapeSavingOption option) const;
127 
128     /**
129      * @brief Set the options to use
130      *
131      * @param options to use
132      */
133     void setOptions(ShapeSavingOptions options);
134 
135     /// add an option to the set of options stored on this context, will leave the other options intact.
136     void addOption(ShapeSavingOption option);
137 
138     /// remove an option, will leave the other options intact.
139     void removeOption(ShapeSavingOption option);
140 
141     /**
142      * @brief Get the options used
143      *
144      * @return options used
145      */
146     ShapeSavingOptions options() const;
147 
148 
149     /**
150      * @brief xmlid returns an element reference that can be related to the given referent. If there is a
151      *   prefix given, this prefix will be used in addition to either the counter or the uuid.
152      * @param referent the object we are referring to
153      * @param prefix a prefix for the xml:id string
154      * @param counter if counter is true, shapesavingcontext will use a counter to create the xml:id
155      * @return a KoElementReference; if insert is false and referent doesn't exist yet in the list, the elementreference will be invalid.
156      */
157     KoElementReference xmlid(const void *referent, const QString& prefix = QString(), KoElementReference::GenerationOption counter = KoElementReference::UUID);
158 
159     /**
160      * @brief existingXmlid retrieve an existing xml id or invalid xml id if the referent object doesn't exist
161      */
162     KoElementReference existingXmlid(const void *referent);
163 
164     /**
165      * @brief Clear out all given draw ids
166      * @param prefix: removes all xml:id's that have the given prefix.
167      *
168      * This is needed for checking if master pages are the same. In normal saving
169      * this should not be called.
170      *
171      * @see KoPAPastePage::process
172      */
173     void clearXmlIds(const QString &prefix);
174 
175     /**
176      * Adds a layer to save into a layer-set in styles.xml according to 9.1.2/9.1.3 odf spec
177      * @param layer the layer to save
178      */
179     void addLayerForSaving(const KoShapeLayer *layer);
180 
181     /**
182      * Saves the layers added with addLayerForSaving to the xml writer
183      */
184     void saveLayerSet(KoXmlWriter &xmlWriter) const;
185 
186     /**
187      * remove all layers
188      *
189      * This can be used for saving different layer sets per page.
190      */
191     void clearLayers();
192 
193     /**
194      * Get the image href under which the image will be saved in the store
195      */
196     QString imageHref(const KoImageData *image);
197 
198     /**
199      * Get the image href under which the image will be save in the store
200      *
201      * This should only be used for temporary images that are onle there during
202      * saving, e.g. a pixmap representation of a draw:frame
203      */
204     QString imageHref(const QImage &image);
205 
206     /**
207      * Get the images that needs to be saved to the store
208      */
209     QMap<qint64, QString> imagesToSave();
210 
211     /**
212      * Get the reference to use for the marker lookup
213      */
214     QString markerRef(const KoMarker *marker);
215 
216     /**
217      * Add data center
218      */
219     void addDataCenter(KoDataCenterBase *dataCenter);
220 
221     /**
222      * Save the data centers
223      *
224      * This calls KoDataCenterBase::completeSaving()
225      * @returns false if an error occurred, which typically cancels the save.
226      */
227     bool saveDataCenter(KoStore *store, KoXmlWriter *manifestWriter);
228 
229     /**
230      * Add shared data
231      *
232      * This can be use to pass data between shapes on saving. E.g. The presentation page layout
233      * styles. With that e.g. the styles only need to be saved once and can be used everywhere
234      * without creating them again.
235      *
236      * The ownership of the added data is passed to the context. The KoShapeSavingContext will
237      * delete the added data when it is destroyed.
238      *
239      * Data inserted for a specific id will not be overwritten by calling addSharedData with
240      * the same id again.
241      *
242      * You get an assertion when the id is already existing.
243      *
244      * @see KoSharedSavingData
245      */
246     void addSharedData(const QString &id, KoSharedSavingData *data);
247 
248     /**
249      * Get the shared data.
250      *
251      * @see KoSharedLoadingData
252      *
253      * @param id The id used to identify the shared data.
254      * @return The shared data for the id or 0 if there is no shared data for the id.
255      */
256     KoSharedSavingData *sharedData(const QString &id) const;
257 
258     /**
259      * Add an offset that will be applied to the shape position when saved
260      *
261      * This is needed e.g. for shapes anchored to a text shape as the position is
262      * saved as offset to the anchor.
263      *
264      * @param shape The shape for which the offset should be added.
265      * @param matrix The offset which should be applied on saving the position.
266      */
267     void addShapeOffset(const KoShape *shape, const QTransform &matrix);
268 
269     /**
270      * Remove an offset from the saved offset list
271      *
272      * @param shape The shape for which the offset should be removed.
273      */
274     void removeShapeOffset(const KoShape *shape);
275 
276     /**
277      * Get the offset that will be applied to the shape position when saved.
278      *
279      * @param shape The shape for which the offset should be get.
280      * @return the saved offset or QTransform() when offset is not set.
281      */
282     QTransform shapeOffset(const KoShape *shape) const;
283 
284     /**
285      * Set stylen family to @p name
286      * E.g "ch" for chart family
287      */
288     void setStyleFamily(const QString &name);
289     /**
290      * @return the style family
291      * If PresentationShape is set the style of family presentation is used,
292      * else if style family is not empty, it is used,
293      * else family graphic is used.
294      * See OpenDocument 9.2.15 Common Drawing Shape Attributes / Style
295      */
296     QString styleFamily() const;
297 
298 private:
299     KoShapeSavingContextPrivate * const d;
300 };
301 
302 Q_DECLARE_OPERATORS_FOR_FLAGS(KoShapeSavingContext::ShapeSavingOptions)
303 
304 #endif // KOSHAPESAVINGCONTEXT_H
305