1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3  * This file is part of the LibreOffice project.
4  *
5  * This Source Code Form is subject to the terms of the Mozilla Public
6  * License, v. 2.0. If a copy of the MPL was not distributed with this
7  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8  *
9  * This file incorporates work covered by the following license notice:
10  *
11  *   Licensed to the Apache Software Foundation (ASF) under one or more
12  *   contributor license agreements. See the NOTICE file distributed
13  *   with this work for additional information regarding copyright
14  *   ownership. The ASF licenses this file to you under the Apache
15  *   License, Version 2.0 (the "License"); you may not use this file
16  *   except in compliance with the License. You may obtain a copy of
17  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
18  */
19 
20 #pragma once
21 
22 #include <com/sun/star/uno/Reference.h>
23 #include <com/sun/star/uno/Sequence.h>
24 
25 #include <vector>
26 #include <memory>
27 #include <map>
28 
29 class SvXMLExport;
30 namespace com::sun::star {
31     namespace beans { class XPropertySet; }
32     namespace beans { struct PropertyValue; }
33     namespace text { class XText; }
34     namespace text { class XTextContent; }
35     namespace text { class XTextSection; }
36 }
37 
38 // store a list of redline properties
39 typedef ::std::vector<
40             css::uno::Reference<css::beans::XPropertySet> > ChangesVectorType;
41 
42 // store a list of redline properties for each XText
43 typedef ::std::map<
44             css::uno::Reference< css::text::XText>,
45             std::unique_ptr<ChangesVectorType> > ChangesMapType;
46 
47 
48 /**
49  * This class handles the export of redline portions.
50  * It is to be called from XMLTextParagraphExport.
51  */
52 class XMLRedlineExport
53 {
54     const OUString sDeletion;
55     const OUString sFormatChange;
56     const OUString sInsertion;
57 
58     SvXMLExport& rExport;
59 
60 
61     // handling of change recording:
62 
63     // To support change tracking in headers and footers we need to
64     // write these changes separately. To do this, we record the
65     // changes for headers and footers. For the main document body, we
66     // get the complete list of changes from the document, which
67     // should be much more efficient than recording all of those.
68 
69     ChangesMapType aChangeMap;              /// map of recorded changes
70 
71     /// list of current changes; is NULL or points to member of aChangeMap
72     ChangesVectorType* pCurrentChangesList;
73 
74 
75 public:
76     explicit XMLRedlineExport(SvXMLExport& rExp);
77 
78     ~XMLRedlineExport();
79 
80     /// export a change
81     void ExportChange(
82         /// PropertySet of RedlinePortion
83         const css::uno::Reference<css::beans::XPropertySet> & rPropSet,
84         bool bAutoStyle);
85 
86     /// export the list of changes (complete list minus recorded changed)
87     void ExportChangesList(bool bAutoStyles);
88 
89     /// export the list of changes (recorded changes for this XText only)
90     void ExportChangesList(
91         const css::uno::Reference<css::text::XText> & rText,
92         bool bAutoStyles);
93 
94     /// set the current XText for which changes should be recorded.
95     /// An empty XText means: don't record changes
96     void SetCurrentXText(
97         const css::uno::Reference<css::text::XText> & rText);
98 
99     /// Do not record changes.
100     /// Same as SetCurrentXText(Reference<XText>) with empty argument.
101     void SetCurrentXText();
102 
103     /// export redline marks which start or end at start nodes,
104     /// i.e. that include the complete paragraph/table/section
105     void ExportStartOrEndRedline(
106         const css::uno::Reference<
107                     css::beans::XPropertySet> & rPropSet,
108         bool bStart);   /// start or end of text entity (e.g. paragraph)?
109 
110     /// convenience method, calls XPropertySet-version of this method
111     void ExportStartOrEndRedline(
112         /// XTextContent; must also be an XPropertySet
113         const css::uno::Reference<css::text::XTextContent> & rContent,
114         bool bStart);
115 
116     /// convenience method, calls XPropertySet-version of this method
117     void ExportStartOrEndRedline(
118         /// XTextSection; must also be an XPropertySet
119         const css::uno::Reference<css::text::XTextSection> & rSection,
120         bool bStart);
121 
122 private:
123 
124     /// export the change mark contained in the text body
125     void ExportChangeInline(
126         /// PropertySet of RedlinePortion
127         const css::uno::Reference<css::beans::XPropertySet> & rPropSet);
128 
129     /// export the auto styles used in this change
130     void ExportChangeAutoStyle(
131         /// PropertySet of RedlinePortion
132         const css::uno::Reference<css::beans::XPropertySet> & rPropSet);
133 
134     /// export the changes list (<text:tracked-changes>)
135     void ExportChangesListElements();
136 
137     /// export the auto styles needed by the changes list
138     void ExportChangesListAutoStyles();
139 
140     /// export the changed-region element
141     void ExportChangedRegion(
142         const css::uno::Reference<css::beans::XPropertySet> & rPropSet);
143 
144     /// export a change-info element (from a PropertySet)
145     void ExportChangeInfo(
146         const css::uno::Reference<css::beans::XPropertySet> & rPropSet);
147 
148     /// export a change-info element (from PropertyValues)
149     void ExportChangeInfo(
150         const css::uno::Sequence<css::beans::PropertyValue> & rValues);
151 
152     /// convert the change type from API to XML names
153     OUString const & ConvertTypeName(std::u16string_view sApiName);
154 
155     /// Get ID string!
156     static OUString GetRedlineID(
157         const css::uno::Reference<css::beans::XPropertySet> & rPropSet);
158 
159     /// write a comment string as sequence of <text:p> elements
160     void WriteComment(std::u16string_view rComment);
161 };
162 
163 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
164