Coverage Report

Created: 2026-02-14 09:37

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/libreoffice/sd/source/ui/unoidl/unomodel.cxx
Line
Count
Source
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
#include <memory>
21
22
#include <com/sun/star/presentation/XPresentation2.hpp>
23
24
#include <com/sun/star/drawing/FillStyle.hpp>
25
#include <com/sun/star/drawing/LineStyle.hpp>
26
#include <com/sun/star/lang/DisposedException.hpp>
27
#include <com/sun/star/lang/IndexOutOfBoundsException.hpp>
28
#include <com/sun/star/lang/ServiceNotRegisteredException.hpp>
29
#include <com/sun/star/lang/Locale.hpp>
30
#include <com/sun/star/awt/XDevice.hpp>
31
#include <com/sun/star/document/IndexedPropertyValues.hpp>
32
#include <com/sun/star/beans/PropertyAttribute.hpp>
33
#include <com/sun/star/util/XTheme.hpp>
34
#include <com/sun/star/animations/AnimationFill.hpp>
35
#include <com/sun/star/animations/AnimationRestart.hpp>
36
#include <com/sun/star/animations/AnimationEndSync.hpp>
37
#include <com/sun/star/animations/AnimationCalcMode.hpp>
38
#include <com/sun/star/animations/AnimationAdditiveMode.hpp>
39
#include <com/sun/star/animations/AnimationNodeType.hpp>
40
#include <com/sun/star/animations/AnimationTransformType.hpp>
41
#include <com/sun/star/animations/AnimationColorSpace.hpp>
42
#include <com/sun/star/animations/Event.hpp>
43
#include <com/sun/star/animations/EventTrigger.hpp>
44
#include <com/sun/star/animations/Timing.hpp>
45
#include <com/sun/star/animations/TransitionType.hpp>
46
#include <com/sun/star/animations/TransitionSubType.hpp>
47
#include <com/sun/star/animations/ValuePair.hpp>
48
#include <com/sun/star/animations/XAnimate.hpp>
49
#include <com/sun/star/animations/XAnimateMotion.hpp>
50
#include <com/sun/star/animations/XAnimateColor.hpp>
51
#include <com/sun/star/animations/XAnimateTransform.hpp>
52
#include <com/sun/star/animations/XIterateContainer.hpp>
53
#include <com/sun/star/animations/XTimeContainer.hpp>
54
#include <com/sun/star/animations/XTransitionFilter.hpp>
55
#include <com/sun/star/presentation/EffectNodeType.hpp>
56
#include <com/sun/star/presentation/EffectPresetClass.hpp>
57
#include <com/sun/star/presentation/ParagraphTarget.hpp>
58
#include <com/sun/star/presentation/ShapeAnimationSubType.hpp>
59
#include <com/sun/star/presentation/TextAnimationType.hpp>
60
61
62
#include <com/sun/star/embed/Aspects.hpp>
63
64
#include <animations/animationnodehelper.hxx>
65
66
#include <officecfg/Office/Common.hxx>
67
#include <officecfg/Office/Impress.hxx>
68
#include <comphelper/dispatchcommand.hxx>
69
#include <comphelper/indexedpropertyvalues.hxx>
70
#include <comphelper/lok.hxx>
71
#include <comphelper/propertysequence.hxx>
72
#include <comphelper/propertyvalue.hxx>
73
#include <comphelper/sequence.hxx>
74
#include <comphelper/servicehelper.hxx>
75
#include <cppuhelper/supportsservice.hxx>
76
#include <comphelper/processfactory.hxx>
77
#include <comphelper/profilezone.hxx>
78
79
#include <sal/log.hxx>
80
#include <editeng/unofield.hxx>
81
#include <notifydocumentevent.hxx>
82
#include <tpaction.hxx>
83
#include <unomodel.hxx>
84
#include <sdhtmlfilter.hxx>
85
#include "unopool.hxx"
86
#include <sfx2/lokhelper.hxx>
87
#include <sfx2/dispatch.hxx>
88
#include <vcl/ptrstyle.hxx>
89
#include <vcl/themecolors.hxx>
90
#include <vcl/svapp.hxx>
91
#include <Outliner.hxx>
92
#include <LibreOfficeKit/LibreOfficeKitEnums.h>
93
94
#include <editeng/UnoForbiddenCharsTable.hxx>
95
#include <svx/svdoutl.hxx>
96
#include <o3tl/any.hxx>
97
#include <o3tl/safeint.hxx>
98
#include <o3tl/string_view.hxx>
99
#include <o3tl/test_info.hxx>
100
#include <o3tl/unit_conversion.hxx>
101
#include <svx/UnoNamespaceMap.hxx>
102
#include <svx/svdlayer.hxx>
103
#include <svx/svdsob.hxx>
104
#include <svx/svdundo.hxx>
105
#include <svx/svdomedia.hxx>
106
#include <svx/unoapi.hxx>
107
#include <svx/unofill.hxx>
108
#include <svx/sdrpagewindow.hxx>
109
#include <svx/sdrpaintwindow.hxx>
110
#include <editeng/fontitem.hxx>
111
#include <toolkit/awt/vclxdevice.hxx>
112
#include <svx/svdpool.hxx>
113
#include <svx/svdpagv.hxx>
114
#include <svtools/unoimap.hxx>
115
#include <svx/unoshape.hxx>
116
#include <editeng/unonrule.hxx>
117
#include <editeng/eeitem.hxx>
118
#include <unotools/datetime.hxx>
119
#include <sax/tools/converter.hxx>
120
#include <xmloff/autolayout.hxx>
121
#include <xmloff/xmltoken.hxx>
122
#include <rtl/math.hxx>
123
#include <tools/helpers.hxx>
124
#include <tools/json_writer.hxx>
125
#include <TransitionPreset.hxx>
126
127
// Support creation of GraphicStorageHandler and EmbeddedObjectResolver
128
#include <svx/xmleohlp.hxx>
129
#include <xmloff/xmlgrhlp.hxx>
130
#include <DrawDocShell.hxx>
131
#include <ViewShellBase.hxx>
132
#include "UnoDocumentSettings.hxx"
133
134
#include <Annotation.hxx>
135
#include <drawdoc.hxx>
136
#include <sdmod.hxx>
137
#include <sdresid.hxx>
138
#include <sdpage.hxx>
139
140
#include <strings.hrc>
141
#include <strings.hxx>
142
#include <unolayer.hxx>
143
#include <unopage.hxx>
144
#include "unocpres.hxx"
145
#include "unoobj.hxx"
146
#include <stlpool.hxx>
147
#include "unopback.hxx"
148
#include <unokywds.hxx>
149
150
#include <FrameView.hxx>
151
#include <ClientView.hxx>
152
#include <DrawViewShell.hxx>
153
#include <ViewShell.hxx>
154
#include <Window.hxx>
155
#include <optsitem.hxx>
156
#include <SlideshowLayerRenderer.hxx>
157
158
#include <vcl/pdfextoutdevdata.hxx>
159
#include <vcl/pdf/PDFNote.hxx>
160
161
#include <com/sun/star/presentation/AnimationSpeed.hpp>
162
#include <com/sun/star/presentation/ClickAction.hpp>
163
#include <svx/sdr/contact/viewobjectcontact.hxx>
164
#include <svx/sdr/contact/viewcontact.hxx>
165
#include <svx/sdr/contact/displayinfo.hxx>
166
167
#include <com/sun/star/office/XAnnotation.hpp>
168
#include <com/sun/star/office/XAnnotationAccess.hpp>
169
#include <com/sun/star/office/XAnnotationEnumeration.hpp>
170
#include <com/sun/star/geometry/RealPoint2D.hpp>
171
#include <com/sun/star/util/DateTime.hpp>
172
173
#include <drawinglayer/primitive2d/structuretagprimitive2d.hxx>
174
175
#include <sfx2/lokcomponenthelpers.hxx>
176
#include <sfx2/LokControlHandler.hxx>
177
#include <tools/gen.hxx>
178
#include <tools/debug.hxx>
179
#include <tools/urlobj.hxx>
180
#include <comphelper/diagnose_ex.hxx>
181
#include <tools/UnitConversion.hxx>
182
#include <svx/ColorSets.hxx>
183
#include <docmodel/theme/Theme.hxx>
184
185
#include <frozen/bits/defines.h>
186
#include <frozen/bits/elsa_std.h>
187
#include <frozen/unordered_map.h>
188
#include <SlideSorter.hxx>
189
#include <SlideSorterViewShell.hxx>
190
#include <controller/SlideSorterController.hxx>
191
#include <controller/SlsPageSelector.hxx>
192
193
#include <app.hrc>
194
195
using namespace ::cppu;
196
using namespace ::com::sun::star;
197
using namespace ::sd;
198
199
const TranslateId aTypeResIds[SdLinkTargetType::Count] =
200
{
201
    STR_SD_PAGE,            // SdLinkTargetType::Page
202
    STR_NOTES_MODE,         // SdLinkTargetType::Notes
203
    STR_HANDOUT,            // SdLinkTargetType::Handout
204
    STR_MASTERPAGE_NAME,    // SdLinkTargetType::MasterPage
205
};
206
207
TranslateId SdTPAction::GetClickActionSdResId( presentation::ClickAction eCA )
208
0
{
209
0
    switch( eCA )
210
0
    {
211
0
        case presentation::ClickAction_NONE:             return STR_CLICK_ACTION_NONE;
212
0
        case presentation::ClickAction_PREVPAGE:         return STR_CLICK_ACTION_PREVPAGE;
213
0
        case presentation::ClickAction_NEXTPAGE:         return STR_CLICK_ACTION_NEXTPAGE;
214
0
        case presentation::ClickAction_FIRSTPAGE:        return STR_CLICK_ACTION_FIRSTPAGE;
215
0
        case presentation::ClickAction_LASTPAGE:         return STR_CLICK_ACTION_LASTPAGE;
216
0
        case presentation::ClickAction_BOOKMARK:         return STR_CLICK_ACTION_BOOKMARK;
217
0
        case presentation::ClickAction_DOCUMENT:         return STR_CLICK_ACTION_DOCUMENT;
218
0
        case presentation::ClickAction_PROGRAM:          return STR_CLICK_ACTION_PROGRAM;
219
0
        case presentation::ClickAction_MACRO:            return STR_CLICK_ACTION_MACRO;
220
0
        case presentation::ClickAction_SOUND:            return STR_CLICK_ACTION_SOUND;
221
0
        case presentation::ClickAction_VERB:             return STR_CLICK_ACTION_VERB;
222
0
        case presentation::ClickAction_STOPPRESENTATION: return STR_CLICK_ACTION_STOPPRESENTATION;
223
0
        default: OSL_FAIL( "No StringResource for ClickAction available!" );
224
0
    }
225
0
    return {};
226
0
}
227
228
class SdUnoForbiddenCharsTable : public SvxUnoForbiddenCharsTable,
229
                                 public SfxListener
230
{
231
public:
232
    explicit SdUnoForbiddenCharsTable(SdrModel* pModel);
233
    virtual ~SdUnoForbiddenCharsTable() override;
234
235
    // SfxListener
236
    virtual void Notify( SfxBroadcaster& rBC, const SfxHint& rHint ) noexcept override;
237
protected:
238
    virtual void onChange() override;
239
240
private:
241
    SdrModel*   mpModel;
242
};
243
244
namespace {
245
246
class SlideBackgroundInfo
247
{
248
public:
249
    SlideBackgroundInfo(const uno::Reference<drawing::XDrawPage>& xDrawPage,
250
                        const uno::Reference<drawing::XDrawPage>& xMasterPage);
251
0
    bool slideHasOwnBackground() const { return mbIsCustom; }
252
0
    bool hasBackground() const { return bHasBackground; }
253
0
    bool isSolidColor() const { return mbIsSolidColor; }
254
    ::Color getFillColor() const;
255
    sal_Int32 getFillTransparency() const;
256
    OString getFillColorAsRGBA() const;
257
private:
258
    bool getFillStyleImpl(const uno::Reference<drawing::XDrawPage>& xDrawPage);
259
private:
260
    uno::Reference<beans::XPropertySet> mxBackground;
261
    bool mbIsCustom;
262
    bool bHasBackground;
263
    bool mbIsSolidColor;
264
    drawing::FillStyle maFillStyle;
265
};
266
267
SlideBackgroundInfo::SlideBackgroundInfo(
268
        const uno::Reference<drawing::XDrawPage>& xDrawPage,
269
        const uno::Reference<drawing::XDrawPage>& xMasterPage)
270
0
    : mbIsCustom(false)
271
0
    , bHasBackground(false)
272
0
    , mbIsSolidColor(false)
273
0
    , maFillStyle(drawing::FillStyle_NONE)
274
0
{
275
0
    mbIsCustom = getFillStyleImpl(xDrawPage);
276
0
    bHasBackground = mbIsCustom;
277
0
    if (!bHasBackground)
278
0
    {
279
0
        bHasBackground = getFillStyleImpl(xMasterPage);
280
0
    }
281
0
    if (bHasBackground)
282
0
    {
283
0
        if (maFillStyle == drawing::FillStyle_SOLID)
284
0
        {
285
0
            OUString sGradientName;
286
0
            mxBackground->getPropertyValue("FillTransparenceGradientName") >>= sGradientName;
287
0
            if (sGradientName.isEmpty())
288
0
            {
289
0
                mbIsSolidColor = true;
290
0
            }
291
0
        }
292
0
    }
293
0
}
294
295
sal_Int32 SlideBackgroundInfo::getFillTransparency() const
296
0
{
297
0
    if (!mxBackground.is())
298
0
        return 0;
299
0
    sal_Int32 nFillTransparency = 0;
300
0
    mxBackground->getPropertyValue("FillTransparence") >>= nFillTransparency;
301
0
    return nFillTransparency;
302
0
}
303
304
::Color SlideBackgroundInfo::getFillColor() const
305
0
{
306
0
    if (!mxBackground.is())
307
0
        return {};
308
0
    if (sal_Int32 nFillColor; mxBackground->getPropertyValue("FillColor") >>= nFillColor)
309
0
    {
310
0
        return ::Color(ColorTransparency, nFillColor & 0xffffff);
311
0
    }
312
0
    return {};
313
0
}
314
315
OString SlideBackgroundInfo::getFillColorAsRGBA() const
316
0
{
317
0
    ::Color aColor = getFillColor();
318
0
    OString sColor = aColor.AsRGBHEXString().toUtf8();
319
0
    sal_uInt32 nAlpha = std::round((100 - getFillTransparency()) * 255 / 100.0);
320
0
    std::stringstream ss;
321
0
    ss << std::hex << std::uppercase << std::setfill ('0') << std::setw(2) << nAlpha;
322
0
    sColor += ss.str().c_str();
323
0
    return sColor;
324
0
}
325
326
bool SlideBackgroundInfo::getFillStyleImpl(const uno::Reference<drawing::XDrawPage>& xDrawPage)
327
0
{
328
0
    if( xDrawPage.is() )
329
0
    {
330
0
        uno::Reference< beans::XPropertySet > xPropSet( xDrawPage, uno::UNO_QUERY );
331
0
        if( xPropSet.is() )
332
0
        {
333
0
            uno::Reference< beans::XPropertySet > xBackground;
334
0
            if (xPropSet->getPropertySetInfo()->hasPropertyByName("Background"))
335
0
                xPropSet->getPropertyValue( "Background" ) >>= xBackground;
336
0
            if( xBackground.is() )
337
0
            {
338
0
                drawing::FillStyle aFillStyle;
339
0
                if( xBackground->getPropertyValue( "FillStyle" ) >>= aFillStyle )
340
0
                {
341
0
                    maFillStyle = aFillStyle;
342
0
                    if (aFillStyle != drawing::FillStyle_NONE)
343
0
                    {
344
0
                        mxBackground = std::move(xBackground);
345
0
                        return true;
346
0
                    }
347
0
                }
348
0
            }
349
0
        }
350
0
    }
351
0
    return false;
352
0
}
353
354
using namespace ::css::animations;
355
using namespace ::css::beans;
356
using namespace ::css::container;
357
using namespace ::css::uno;
358
using namespace ::xmloff::token;
359
using namespace ::css::presentation;
360
361
template <typename T, std::size_t N>
362
constexpr auto mapEnumToString(std::pair<T, std::string_view> const (&items)[N])
363
0
{
364
0
    return frozen::make_unordered_map<T, std::string_view, N>(items);
365
0
}
Unexecuted instantiation: unomodel.cxx:auto (anonymous namespace)::mapEnumToString<short, 17ul>(std::__1::pair<short, std::__1::basic_string_view<char, std::__1::char_traits<char> > > const (&) [17ul])
Unexecuted instantiation: unomodel.cxx:auto (anonymous namespace)::mapEnumToString<short, 40ul>(std::__1::pair<short, std::__1::basic_string_view<char, std::__1::char_traits<char> > > const (&) [40ul])
Unexecuted instantiation: unomodel.cxx:auto (anonymous namespace)::mapEnumToString<short, 13ul>(std::__1::pair<short, std::__1::basic_string_view<char, std::__1::char_traits<char> > > const (&) [13ul])
Unexecuted instantiation: unomodel.cxx:auto (anonymous namespace)::mapEnumToString<short, 6ul>(std::__1::pair<short, std::__1::basic_string_view<char, std::__1::char_traits<char> > > const (&) [6ul])
Unexecuted instantiation: unomodel.cxx:auto (anonymous namespace)::mapEnumToString<short, 4ul>(std::__1::pair<short, std::__1::basic_string_view<char, std::__1::char_traits<char> > > const (&) [4ul])
Unexecuted instantiation: unomodel.cxx:auto (anonymous namespace)::mapEnumToString<short, 5ul>(std::__1::pair<short, std::__1::basic_string_view<char, std::__1::char_traits<char> > > const (&) [5ul])
Unexecuted instantiation: unomodel.cxx:auto (anonymous namespace)::mapEnumToString<short, 7ul>(std::__1::pair<short, std::__1::basic_string_view<char, std::__1::char_traits<char> > > const (&) [7ul])
Unexecuted instantiation: unomodel.cxx:auto (anonymous namespace)::mapEnumToString<com::sun::star::animations::Timing, 2ul>(std::__1::pair<com::sun::star::animations::Timing, std::__1::basic_string_view<char, std::__1::char_traits<char> > > const (&) [2ul])
Unexecuted instantiation: unomodel.cxx:auto (anonymous namespace)::mapEnumToString<short, 3ul>(std::__1::pair<short, std::__1::basic_string_view<char, std::__1::char_traits<char> > > const (&) [3ul])
Unexecuted instantiation: unomodel.cxx:auto (anonymous namespace)::mapEnumToString<com::sun::star::drawing::FillStyle, 5ul>(std::__1::pair<com::sun::star::drawing::FillStyle, std::__1::basic_string_view<char, std::__1::char_traits<char> > > const (&) [5ul])
Unexecuted instantiation: unomodel.cxx:auto (anonymous namespace)::mapEnumToString<com::sun::star::drawing::LineStyle, 3ul>(std::__1::pair<com::sun::star::drawing::LineStyle, std::__1::basic_string_view<char, std::__1::char_traits<char> > > const (&) [3ul])
366
367
constexpr auto constTransitionTypeToString = mapEnumToString<sal_Int16>({
368
    { animations::TransitionType::BARWIPE, "BarWipe" }, // Wipe
369
    { animations::TransitionType::PINWHEELWIPE, "PineWheelWipe" }, // Wheel
370
    { animations::TransitionType::SLIDEWIPE, "SlideWipe" }, // Cover, Uncover
371
    { animations::TransitionType::RANDOMBARWIPE, "RandomBarWipe" }, // Bars
372
    { animations::TransitionType::CHECKERBOARDWIPE, "CheckerBoardWipe" }, // Checkers
373
    { animations::TransitionType::FOURBOXWIPE, "FourBoxWipe" }, // Shape
374
    { animations::TransitionType::IRISWIPE, "IrisWipe" }, // Box
375
    { animations::TransitionType::FANWIPE, "FanWipe" }, // Wedge
376
    { animations::TransitionType::BLINDSWIPE, "BlindWipe"}, // Venetian
377
    { animations::TransitionType::FADE, "Fade"},
378
    { animations::TransitionType::DISSOLVE, "Dissolve"},
379
    { animations::TransitionType::PUSHWIPE, "PushWipe"}, // Comb
380
    { animations::TransitionType::ELLIPSEWIPE, "EllipseWipe"}, // Shape
381
    { animations::TransitionType::BARNDOORWIPE, "BarnDoorWipe"}, // Split
382
    { animations::TransitionType::WATERFALLWIPE, "WaterfallWipe"}, // Diagonal
383
    { animations::TransitionType::MISCSHAPEWIPE, "MiscShapeWipe"},
384
    { animations::TransitionType::ZOOM, "Zoom"}
385
});
386
387
constexpr auto constTransitionSubTypeToString = mapEnumToString<sal_Int16>({
388
    { animations::TransitionSubType::LEFTTORIGHT, "LeftToRight" },
389
    { animations::TransitionSubType::TOPTOBOTTOM, "TopToBottom" },
390
    { animations::TransitionSubType::EIGHTBLADE, "8Blade" },
391
    { animations::TransitionSubType::FOURBLADE, "4Blade" },
392
    { animations::TransitionSubType::THREEBLADE, "3Blade" },
393
    { animations::TransitionSubType::TWOBLADEVERTICAL, "2BladeVertical" },
394
    { animations::TransitionSubType::ONEBLADE, "1Blade" },
395
    { animations::TransitionSubType::FROMTOPLEFT, "FromTopLeft" },
396
    { animations::TransitionSubType::FROMTOPRIGHT, "FromTopRight"},
397
    { animations::TransitionSubType::FROMBOTTOMLEFT, "FromBottomLeft"},
398
    { animations::TransitionSubType::FROMBOTTOMRIGHT, "FromBottomRight"},
399
    { animations::TransitionSubType::VERTICAL, "Vertical"},
400
    { animations::TransitionSubType::HORIZONTAL, "Horizontal"},
401
    { animations::TransitionSubType::DOWN, "Down"},
402
    { animations::TransitionSubType::ACROSS, "Across"},
403
    { animations::TransitionSubType::CORNERSOUT, "CornersOut"},
404
    { animations::TransitionSubType::DIAMOND, "Diamond"},
405
    { animations::TransitionSubType::CIRCLE, "Circle"},
406
    { animations::TransitionSubType::RECTANGLE, "Rectangle"},
407
    { animations::TransitionSubType::CENTERTOP, "CenterTop"},
408
    { animations::TransitionSubType::CROSSFADE, "CrossFade"},
409
    { animations::TransitionSubType::FADEOVERCOLOR, "FadeOverColor"},
410
    { animations::TransitionSubType::FROMLEFT, "FromLeft"},
411
    { animations::TransitionSubType::FROMRIGHT, "FromRight"},
412
    { animations::TransitionSubType::FROMTOP, "FromTop"},
413
    { animations::TransitionSubType::HORIZONTALLEFT, "HorizontalLeft"},
414
    { animations::TransitionSubType::HORIZONTALRIGHT, "HorizontalRight"},
415
    { animations::TransitionSubType::COMBVERTICAL, "CombVertical"},
416
    { animations::TransitionSubType::COMBHORIZONTAL, "CombHorizontal"},
417
    { animations::TransitionSubType::TOPLEFT, "TopLeft"},
418
    { animations::TransitionSubType::TOPRIGHT, "TopRight"},
419
    { animations::TransitionSubType::BOTTOMRIGHT, "BottomRight"},
420
    { animations::TransitionSubType::BOTTOMLEFT, "BottomLeft"},
421
    { animations::TransitionSubType::TOPCENTER, "TopCenter"},
422
    { animations::TransitionSubType::RIGHTCENTER, "RightCenter"},
423
    { animations::TransitionSubType::BOTTOMCENTER, "BottomCenter"},
424
    { animations::TransitionSubType::FANOUTHORIZONTAL, "FanOutHorizontal"},
425
    { animations::TransitionSubType::CORNERSIN, "CornersIn"},
426
    { animations::TransitionSubType::HEART, "Heart"},
427
    { animations::TransitionSubType::ROTATEIN, "RotateIn"}
428
});
429
430
constexpr auto constAnimationNodeTypeToString = mapEnumToString<sal_Int16>({
431
    { AnimationNodeType::ANIMATE, "Animate" },
432
    { AnimationNodeType::ANIMATECOLOR, "AnimateColor" },
433
    { AnimationNodeType::ANIMATEMOTION, "AnimateMotion" },
434
    { AnimationNodeType::ANIMATEPHYSICS, "Animate" },
435
    { AnimationNodeType::ANIMATETRANSFORM, "AnimateTransform" },
436
    { AnimationNodeType::AUDIO, "Audio" },
437
    { AnimationNodeType::COMMAND, "Command" },
438
    { AnimationNodeType::CUSTOM, "Custom" },
439
    { AnimationNodeType::ITERATE, "Iterate" },
440
    { AnimationNodeType::PAR, "Par" },
441
    { AnimationNodeType::SEQ, "Seq" },
442
    { AnimationNodeType::SET, "Set" },
443
    { AnimationNodeType::TRANSITIONFILTER, "TransitionFilter" },
444
});
445
446
constexpr auto constFillToString = mapEnumToString<sal_Int16>({
447
    { AnimationFill::DEFAULT, "Default" },
448
    { AnimationFill::REMOVE, "Remove" },
449
    { AnimationFill::FREEZE, "Freeze" },
450
    { AnimationFill::HOLD, "Hold" },
451
    { AnimationFill::TRANSITION, "Transition" },
452
    { AnimationFill::AUTO, "Auto" },
453
});
454
455
constexpr auto constRestartToString = mapEnumToString<sal_Int16>({
456
    { AnimationRestart::DEFAULT, "Default" },
457
    { AnimationRestart::ALWAYS, "Always" },
458
    { AnimationRestart::WHEN_NOT_ACTIVE, "WhenNotActive" },
459
    { AnimationRestart::NEVER, "Never" },
460
});
461
462
constexpr auto constEndSyncToString = mapEnumToString<sal_Int16>({
463
    { AnimationEndSync::FIRST, "First" },
464
    { AnimationEndSync::LAST, "Last" },
465
    { AnimationEndSync::ALL, "All" },
466
    { AnimationEndSync::MEDIA, "Media" },
467
});
468
469
constexpr auto constCalcModeToString = mapEnumToString<sal_Int16>({
470
    { AnimationCalcMode::DISCRETE, "Discrete" },
471
    { AnimationCalcMode::LINEAR, "Linear" },
472
    { AnimationCalcMode::PACED, "Paced" },
473
    { AnimationCalcMode::SPLINE, "Spline" },
474
});
475
476
constexpr auto constAdditiveModeToString = mapEnumToString<sal_Int16>({
477
    { AnimationAdditiveMode::BASE, "Base" },
478
    { AnimationAdditiveMode::SUM, "Sum" },
479
    { AnimationAdditiveMode::REPLACE, "Replace" },
480
    { AnimationAdditiveMode::MULTIPLY, "Multiply" },
481
    { AnimationAdditiveMode::NONE, "None" },
482
});
483
484
constexpr auto constEffectPresetClassToString = mapEnumToString<sal_Int16>({
485
    { EffectPresetClass::CUSTOM, "Custom" },
486
    { EffectPresetClass::ENTRANCE, "Entrance" },
487
    { EffectPresetClass::EXIT, "Exit" },
488
    { EffectPresetClass::EMPHASIS, "Emphasis" },
489
    { EffectPresetClass::MOTIONPATH, "MotionPath" },
490
    { EffectPresetClass::OLEACTION, "OleAction" },
491
    { EffectPresetClass::MEDIACALL, "MediaCall" },
492
});
493
494
constexpr auto constEffectNodeTypeToString = mapEnumToString<sal_Int16>({
495
    { EffectNodeType::DEFAULT, "Default" },
496
    { EffectNodeType::ON_CLICK, "OnClick" },
497
    { EffectNodeType::WITH_PREVIOUS, "WithPrevious" },
498
    { EffectNodeType::AFTER_PREVIOUS, "AfterPrevious" },
499
    { EffectNodeType::MAIN_SEQUENCE, "MainSequence" },
500
    { EffectNodeType::TIMING_ROOT, "TimingRoot" },
501
    { EffectNodeType::INTERACTIVE_SEQUENCE, "InteractiveSequence" },
502
});
503
504
constexpr auto constEventTriggerToString = mapEnumToString<sal_Int16>({
505
    { EventTrigger::BEGIN_EVENT, "BeginEvent" },
506
    { EventTrigger::END_EVENT, "EndEvent" },
507
    { EventTrigger::NONE, "None" },
508
    { EventTrigger::ON_BEGIN, "OnBegin" },
509
    { EventTrigger::ON_CLICK, "OnClick" },
510
    { EventTrigger::ON_DBL_CLICK, "OnDblClick" },
511
    { EventTrigger::ON_END, "OnEnd" },
512
    { EventTrigger::ON_MOUSE_ENTER, "OnMouseEnter" },
513
    { EventTrigger::ON_MOUSE_LEAVE, "OnMouseLeave" },
514
    { EventTrigger::ON_NEXT, "OnNext" },
515
    { EventTrigger::ON_PREV, "OnPrev" },
516
    { EventTrigger::ON_STOP_AUDIO, "OnStopAudio" },
517
    { EventTrigger::REPEAT, "Repeat" },
518
});
519
520
constexpr auto constTimingToString = mapEnumToString<Timing>({
521
    { Timing_INDEFINITE, "indefinite" },
522
    { Timing_MEDIA, "media" },
523
});
524
525
constexpr auto constTransformTypeToString = mapEnumToString<sal_Int16>({
526
    { AnimationTransformType::TRANSLATE, "Translate" },
527
    { AnimationTransformType::SCALE, "Scale" },
528
    { AnimationTransformType::ROTATE, "Rotate" },
529
    { AnimationTransformType::SKEWX, "SkewX" },
530
    { AnimationTransformType::SKEWY, "SkewY" },
531
});
532
533
constexpr auto constSubItemToString = mapEnumToString<sal_Int16>({
534
    { ShapeAnimationSubType::AS_WHOLE, "AsWhole" },
535
    { ShapeAnimationSubType::ONLY_BACKGROUND, "OnlyBackground" },
536
    { ShapeAnimationSubType::ONLY_TEXT, "OnlyText" },
537
});
538
539
constexpr auto constIterateTypeToString = mapEnumToString<sal_Int16>({
540
    { TextAnimationType::BY_PARAGRAPH, "ByParagraph" },
541
    { TextAnimationType::BY_WORD, "ByWord" },
542
    { TextAnimationType::BY_LETTER, "ByLetter" },
543
});
544
545
constexpr auto constFillStyleToString = mapEnumToString<drawing::FillStyle>({
546
    { drawing::FillStyle_NONE, "None" },
547
    { drawing::FillStyle_SOLID, "Solid" },
548
    { drawing::FillStyle_BITMAP, "Bitmap" },
549
    { drawing::FillStyle_GRADIENT, "Gradient" },
550
    { drawing::FillStyle_HATCH, "Hatch" },
551
});
552
553
constexpr auto constLineStyleToString = mapEnumToString<drawing::LineStyle>({
554
    { drawing::LineStyle_NONE, "None" },
555
    { drawing::LineStyle_SOLID, "Solid" },
556
    { drawing::LineStyle_DASH, "Dash" },
557
});
558
559
560
constexpr auto constAttributeNameToXMLEnum
561
    = frozen::make_unordered_map<std::string_view, XMLTokenEnum>({
562
        { "X", XML_X },
563
        { "Y", XML_Y },
564
        { "Width", XML_WIDTH },
565
        { "Height", XML_HEIGHT },
566
        { "Rotate", XML_ROTATE },
567
        { "SkewX", XML_SKEWX },
568
        { "FillColor", XML_FILL_COLOR },
569
        { "FillStyle", XML_FILL },
570
        { "LineColor", XML_STROKE_COLOR },
571
        { "LineStyle",XML_STROKE  },
572
        { "CharColor", XML_COLOR },
573
        { "CharRotation", XML_TEXT_ROTATION_ANGLE },
574
        { "CharWeight", XML_FONT_WEIGHT },
575
        { "CharUnderline", XML_TEXT_UNDERLINE },
576
        { "CharFontName", XML_FONT_FAMILY },
577
        { "CharHeight", XML_FONT_SIZE },
578
        { "CharPosture", XML_FONT_STYLE },
579
        { "Visibility", XML_VISIBILITY },
580
        { "Opacity", XML_OPACITY },
581
        { "DimColor", XML_DIM },
582
});
583
584
class AnimationsExporter
585
{
586
public:
587
    AnimationsExporter(::tools::JsonWriter& rWriter,
588
                       const Reference<drawing::XDrawPage>& xDrawPage);
589
    void exportAnimations();
590
    void exportTriggers() const;
591
0
    [[nodiscard]] bool hasEffects() const { return mbHasEffects; }
592
593
private:
594
    void exportNode(const Reference<XAnimationNode>& xNode);
595
    void exportNodeImpl(const Reference<XAnimationNode>& xNode);
596
    void exportContainer(const Reference<XTimeContainer>& xContainer);
597
598
    void exportAnimate(const Reference<XAnimate>& xAnimate);
599
600
    void convertValue(XMLTokenEnum eAttributeName, OStringBuffer& sTmp, const Any& rValue) const;
601
    void convertTiming(OStringBuffer& sTmp, const Any& rValue);
602
603
    void appendTrigger(const css::uno::Any& rTarget, const OString& rTriggerHash);
604
    void exportTriggersImpl(const uno::Reference<drawing::XShapes>& xShapes) const;
605
606
private:
607
    ::tools::JsonWriter& mrWriter;
608
    Reference<drawing::XDrawPage> mxDrawPage;
609
    Reference<XPropertySet> mxPageProps;
610
    Reference<XAnimationNode> mxRootNode;
611
    bool mbHasEffects;
612
    std::unordered_map<SdrObject*, OString> maEventTriggerSet;
613
};
614
615
AnimationsExporter::AnimationsExporter(::tools::JsonWriter& rWriter,
616
                                       const Reference<drawing::XDrawPage>& xDrawPage)
617
0
    : mrWriter(rWriter)
618
0
    , mxDrawPage(xDrawPage)
619
0
    , mbHasEffects(false)
620
0
{
621
0
    if (!mxDrawPage.is())
622
0
        return;
623
624
0
    try
625
0
    {
626
0
        mxPageProps = Reference<XPropertySet>(xDrawPage, UNO_QUERY);
627
0
        if (!mxPageProps.is())
628
0
            return;
629
630
0
        Reference<XAnimationNodeSupplier> xAnimNodeSupplier(mxDrawPage, UNO_QUERY);
631
0
        if (!xAnimNodeSupplier.is())
632
0
            return;
633
634
0
        Reference<XAnimationNode> xRootNode = xAnimNodeSupplier->getAnimationNode();
635
0
        if (xRootNode.is())
636
0
        {
637
            // first check if there are no animations
638
0
            Reference<XEnumerationAccess> xEnumerationAccess(xRootNode, UNO_QUERY_THROW);
639
0
            Reference<XEnumeration> xEnumeration(xEnumerationAccess->createEnumeration(),
640
0
                                                 css::uno::UNO_SET_THROW);
641
0
            if (xEnumeration->hasMoreElements())
642
0
            {
643
                // first child node may be an empty main sequence, check this
644
0
                Reference<XAnimationNode> xMainNode(xEnumeration->nextElement(), UNO_QUERY_THROW);
645
0
                Reference<XEnumerationAccess> xMainEnumerationAccess(xMainNode, UNO_QUERY_THROW);
646
0
                Reference<XEnumeration> xMainEnumeration(
647
0
                    xMainEnumerationAccess->createEnumeration(), css::uno::UNO_SET_THROW);
648
649
                // only export if the main sequence is not empty or if there are additional
650
                // trigger sequences
651
0
                mbHasEffects
652
0
                    = xMainEnumeration->hasMoreElements() || xEnumeration->hasMoreElements();
653
0
            }
654
0
        }
655
0
        if (mbHasEffects)
656
0
            mxRootNode = std::move(xRootNode);
657
0
    }
658
0
    catch (const RuntimeException&)
659
0
    {
660
0
        TOOLS_WARN_EXCEPTION("sd", "unomodel: AnimationsExporter");
661
0
    }
662
0
}
663
664
template <typename EnumT, size_t N>
665
constexpr bool convertEnum(OStringBuffer& rBuffer, EnumT nValue,
666
                           const frozen::unordered_map<EnumT, std::string_view, N>& rMap)
667
0
{
668
0
    auto iterator = rMap.find(nValue);
669
0
    if (iterator == rMap.end())
670
0
        return false;
671
0
    rBuffer.append(iterator->second);
672
0
    return true;
673
0
}
Unexecuted instantiation: unomodel.cxx:bool (anonymous namespace)::convertEnum<short, 13ul>(rtl::OStringBuffer&, short, frozen::unordered_map<short, std::__1::basic_string_view<char, std::__1::char_traits<char> >, 13ul, frozen::elsa<short>, std::__1::equal_to<short> > const&)
Unexecuted instantiation: unomodel.cxx:bool (anonymous namespace)::convertEnum<short, 6ul>(rtl::OStringBuffer&, short, frozen::unordered_map<short, std::__1::basic_string_view<char, std::__1::char_traits<char> >, 6ul, frozen::elsa<short>, std::__1::equal_to<short> > const&)
Unexecuted instantiation: unomodel.cxx:bool (anonymous namespace)::convertEnum<short, 4ul>(rtl::OStringBuffer&, short, frozen::unordered_map<short, std::__1::basic_string_view<char, std::__1::char_traits<char> >, 4ul, frozen::elsa<short>, std::__1::equal_to<short> > const&)
Unexecuted instantiation: unomodel.cxx:bool (anonymous namespace)::convertEnum<short, 7ul>(rtl::OStringBuffer&, short, frozen::unordered_map<short, std::__1::basic_string_view<char, std::__1::char_traits<char> >, 7ul, frozen::elsa<short>, std::__1::equal_to<short> > const&)
Unexecuted instantiation: unomodel.cxx:bool (anonymous namespace)::convertEnum<short, 3ul>(rtl::OStringBuffer&, short, frozen::unordered_map<short, std::__1::basic_string_view<char, std::__1::char_traits<char> >, 3ul, frozen::elsa<short>, std::__1::equal_to<short> > const&)
Unexecuted instantiation: unomodel.cxx:bool (anonymous namespace)::convertEnum<com::sun::star::drawing::FillStyle, 5ul>(rtl::OStringBuffer&, com::sun::star::drawing::FillStyle, frozen::unordered_map<com::sun::star::drawing::FillStyle, std::__1::basic_string_view<char, std::__1::char_traits<char> >, 5ul, frozen::elsa<com::sun::star::drawing::FillStyle>, std::__1::equal_to<com::sun::star::drawing::FillStyle> > const&)
Unexecuted instantiation: unomodel.cxx:bool (anonymous namespace)::convertEnum<com::sun::star::drawing::LineStyle, 3ul>(rtl::OStringBuffer&, com::sun::star::drawing::LineStyle, frozen::unordered_map<com::sun::star::drawing::LineStyle, std::__1::basic_string_view<char, std::__1::char_traits<char> >, 3ul, frozen::elsa<com::sun::star::drawing::LineStyle>, std::__1::equal_to<com::sun::star::drawing::LineStyle> > const&)
Unexecuted instantiation: unomodel.cxx:bool (anonymous namespace)::convertEnum<short, 5ul>(rtl::OStringBuffer&, short, frozen::unordered_map<short, std::__1::basic_string_view<char, std::__1::char_traits<char> >, 5ul, frozen::elsa<short>, std::__1::equal_to<short> > const&)
Unexecuted instantiation: unomodel.cxx:bool (anonymous namespace)::convertEnum<short, 17ul>(rtl::OStringBuffer&, short, frozen::unordered_map<short, std::__1::basic_string_view<char, std::__1::char_traits<char> >, 17ul, frozen::elsa<short>, std::__1::equal_to<short> > const&)
Unexecuted instantiation: unomodel.cxx:bool (anonymous namespace)::convertEnum<short, 40ul>(rtl::OStringBuffer&, short, frozen::unordered_map<short, std::__1::basic_string_view<char, std::__1::char_traits<char> >, 40ul, frozen::elsa<short>, std::__1::equal_to<short> > const&)
674
675
void convertDouble(OStringBuffer& rBuffer, double fValue)
676
0
{
677
0
        ::rtl::math::doubleToStringBuffer(rBuffer, fValue, rtl_math_StringFormat_Automatic,
678
0
                                          rtl_math_DecimalPlaces_Max, '.', true);
679
0
}
680
681
void convertBool(OStringBuffer& rBuffer, bool bValue)
682
0
{
683
0
    rBuffer.append( bValue );
684
0
}
685
686
void convertPath(OStringBuffer& sTmp, const Any& rPath)
687
0
{
688
0
    OUString aStr;
689
0
    rPath >>= aStr;
690
0
    sTmp = aStr.toUtf8();
691
0
}
692
693
void convertColor(OStringBuffer& rBuffer, sal_Int32 nColor)
694
0
{
695
0
    OUStringBuffer aUBuffer;
696
0
    ::sax::Converter::convertColor(aUBuffer, nColor);
697
0
    rBuffer.append(aUBuffer.makeStringAndClear().toUtf8());
698
0
}
699
700
void convertColor(OStringBuffer& rBuffer, const Any& rValue)
701
0
{
702
0
    sal_Int32 nColor = 0;
703
0
    if (rValue >>= nColor)
704
0
    {
705
0
        convertColor(rBuffer, nColor);
706
0
    }
707
0
    else
708
0
    {
709
0
        Sequence<double> aHSL;
710
0
        if ((rValue >>= aHSL) && (aHSL.getLength() == 3))
711
0
        {
712
0
            rBuffer.append("hsl(" + OString::number(aHSL[0]) + ","
713
0
                           + OString::number(aHSL[1] * 100.0) + "%,"
714
0
                           + OString::number(aHSL[2] * 100.0) + "%)");
715
0
        }
716
0
    }
717
0
}
718
719
bool isValidNode(const Reference<XAnimationNode>& xNode)
720
0
{
721
0
    if (xNode.is())
722
0
    {
723
0
        sal_Int16 nNodeType = xNode->getType();
724
0
        auto iterator = constAnimationNodeTypeToString.find(nNodeType);
725
0
        return iterator != constAnimationNodeTypeToString.end();
726
0
    }
727
0
    return false;
728
0
}
729
730
SdrObject* getObjectForShape(uno::Reference<drawing::XShape> const& xShape)
731
0
{
732
0
    if (!xShape.is())
733
0
        return nullptr;
734
0
    SvxShape* pShape = comphelper::getFromUnoTunnel<SvxShape>(xShape);
735
0
    if (pShape)
736
0
        return pShape->GetSdrObject();
737
0
    return nullptr;
738
0
}
739
740
SdrObject* getTargetObject(const uno::Any& aTargetAny)
741
0
{
742
0
    SdrObject* pObject = nullptr;
743
0
    uno::Reference<drawing::XShape> xShape;
744
745
0
    if ((aTargetAny >>= xShape) && xShape.is())
746
0
    {
747
0
        pObject = getObjectForShape(xShape);
748
0
    }
749
0
    else // if target is not a shape - could be paragraph target containing a shape
750
0
    {
751
0
        presentation::ParagraphTarget aParagraphTarget;
752
0
        if ((aTargetAny >>= aParagraphTarget) && aParagraphTarget.Shape.is())
753
0
        {
754
0
            pObject = getObjectForShape(aParagraphTarget.Shape);
755
0
        }
756
0
    }
757
758
0
    return pObject;
759
0
}
760
761
bool isNodeTargetInShapeGroup(const Reference<XAnimationNode>& xNode)
762
0
{
763
0
    Reference<XAnimate> xAnimate(xNode, UNO_QUERY);
764
0
    if (xAnimate.is())
765
0
    {
766
0
        SdrObject* pObject = getTargetObject(xAnimate->getTarget());
767
0
        if (pObject)
768
0
            return pObject->getParentSdrObjectFromSdrObject() != nullptr;
769
0
    }
770
0
    return false;
771
0
}
772
773
bool isNodeTargetAGroup(const Reference<XAnimationNode>& xNode)
774
0
{
775
0
    Reference<XAnimate> xAnimate(xNode, UNO_QUERY);
776
0
    if (xAnimate.is())
777
0
    {
778
0
        SdrObject* pObject = getTargetObject(xAnimate->getTarget());
779
0
        if (pObject)
780
0
            return pObject->getChildrenOfSdrObject() != nullptr;
781
0
    }
782
0
    return false;
783
0
}
784
785
bool isEffectValidForTarget(const Reference<XAnimationNode>& xNode)
786
0
{
787
0
    const Sequence<NamedValue> aUserData(xNode->getUserData());
788
0
    for (const auto& rValue : aUserData)
789
0
    {
790
0
        if (!IsXMLToken(rValue.Name, XML_PRESET_ID))
791
0
            continue;
792
793
0
        OUString aPresetId;
794
0
        if (rValue.Value >>= aPresetId)
795
0
        {
796
0
            if (constNonValidEffectsForGroupSet.find(aPresetId.toUtf8())
797
0
                != constNonValidEffectsForGroupSet.end())
798
0
            {
799
                // it's in the list, so we need to check if the effect target is a group or not
800
0
                Reference<XTimeContainer> xContainer(xNode, UNO_QUERY);
801
0
                if (xContainer.is())
802
0
                {
803
0
                    Reference<XEnumerationAccess> xEnumerationAccess(xContainer, UNO_QUERY);
804
0
                    Reference<XEnumeration> xEnumeration = xEnumerationAccess->createEnumeration();
805
806
                    // target is the same for all children, check the first one
807
0
                    if (xEnumeration.is() && xEnumeration->hasMoreElements())
808
0
                    {
809
0
                        Reference<XAnimationNode> xChildNode(xEnumeration->nextElement(),
810
0
                                                             UNO_QUERY);
811
0
                        if (isNodeTargetAGroup(xChildNode))
812
0
                            return false;
813
0
                    }
814
0
                }
815
0
            }
816
0
        }
817
        // preset id found and checked, we can exit
818
0
        break;
819
0
    }
820
0
    return true;
821
0
}
822
823
void AnimationsExporter::exportAnimations()
824
0
{
825
0
    if (!mxDrawPage.is() || !mxPageProps.is() || !mxRootNode.is() || !hasEffects())
826
0
        return;
827
828
0
    if (isValidNode(mxRootNode))
829
0
    {
830
0
        auto aNode = mrWriter.startNode("root");
831
0
        exportNodeImpl(mxRootNode);
832
0
    }
833
0
}
834
835
void AnimationsExporter::exportNode(const Reference<XAnimationNode>& xNode)
836
0
{
837
    // afaics, when a shape is part of a group any applied effect is ignored
838
    // moreover, some kind of effect, like the ones based on color animations,
839
    // is ignored when applied to a group
840
0
    if (!isValidNode(xNode) || isNodeTargetInShapeGroup(xNode) || !isEffectValidForTarget(xNode))
841
0
        return;
842
0
    auto aStruct = mrWriter.startStruct();
843
0
    exportNodeImpl(xNode);
844
0
}
845
846
void AnimationsExporter::exportNodeImpl(const Reference<XAnimationNode>& xNode)
847
0
{
848
0
    try
849
0
    {
850
0
        std::string sId = GetInterfaceHash(xNode);
851
0
        mrWriter.put("id", sId);
852
0
        sal_Int16 nNodeType = xNode->getType();
853
0
        auto iterator = constAnimationNodeTypeToString.find(nNodeType);
854
0
        assert(iterator != constAnimationNodeTypeToString.end() && "must be previously checked with isValidNode");
855
0
        mrWriter.put("nodeName", iterator->second);
856
857
        // common properties
858
0
        OStringBuffer sTmp;
859
0
        Any aTemp;
860
0
        double fTemp = 0;
861
0
        sal_Int16 nTemp;
862
863
0
        aTemp = xNode->getBegin();
864
0
        if (aTemp.hasValue())
865
0
        {
866
0
            convertTiming(sTmp, aTemp);
867
0
            mrWriter.put("begin", sTmp.makeStringAndClear());
868
0
        }
869
0
        aTemp = xNode->getDuration();
870
0
        if (aTemp.hasValue())
871
0
        {
872
0
            if (aTemp >>= fTemp)
873
0
            {
874
0
                convertDouble(sTmp, fTemp);
875
0
                sTmp.append('s');
876
0
                mrWriter.put("dur", sTmp.makeStringAndClear());
877
0
            }
878
0
            else
879
0
            {
880
0
                Timing eTiming;
881
0
                if (aTemp >>= eTiming)
882
0
                {
883
0
                    mrWriter.put("dur", eTiming == Timing_INDEFINITE ? "indefinite" : "media");
884
0
                }
885
0
            }
886
0
        }
887
0
        aTemp = xNode->getEnd();
888
0
        if (aTemp.hasValue())
889
0
        {
890
0
            convertTiming(sTmp, aTemp);
891
0
            mrWriter.put("end", sTmp.makeStringAndClear());
892
0
        }
893
0
        nTemp = xNode->getFill();
894
0
        if (nTemp != AnimationFill::DEFAULT)
895
0
        {
896
0
            convertEnum(sTmp, nTemp, constFillToString);
897
0
            mrWriter.put("fill", sTmp.makeStringAndClear());
898
0
        }
899
0
        nTemp = xNode->getFillDefault();
900
0
        if (nTemp != AnimationFill::INHERIT)
901
0
        {
902
0
            convertEnum(sTmp, nTemp, constFillToString);
903
0
            mrWriter.put("fillDefault", sTmp.makeStringAndClear());
904
0
        }
905
0
        nTemp = xNode->getRestart();
906
0
        if (nTemp != AnimationRestart::DEFAULT)
907
0
        {
908
0
            convertEnum(sTmp, nTemp, constRestartToString);
909
0
            mrWriter.put("restart", sTmp.makeStringAndClear());
910
0
        }
911
0
        nTemp = xNode->getRestartDefault();
912
0
        if (nTemp != AnimationRestart::INHERIT)
913
0
        {
914
0
            convertEnum(sTmp, nTemp, constRestartToString);
915
0
            mrWriter.put("restartDefault", sTmp.makeStringAndClear());
916
0
        }
917
0
        fTemp = xNode->getAcceleration();
918
0
        if (fTemp != 0.0)
919
0
        {
920
0
            convertDouble(sTmp, fTemp);
921
0
            mrWriter.put("accelerate", sTmp.makeStringAndClear());
922
0
        }
923
0
        fTemp = xNode->getDecelerate();
924
0
        if (fTemp != 0.0)
925
0
        {
926
0
            convertDouble(sTmp, fTemp);
927
0
            mrWriter.put("decelerate", sTmp.makeStringAndClear());
928
0
        }
929
0
        bool bTemp = xNode->getAutoReverse();
930
0
        if (bTemp)
931
0
        {
932
0
            convertBool(sTmp, bTemp);
933
0
            mrWriter.put("autoreverse", sTmp.makeStringAndClear());
934
0
        }
935
0
        aTemp = xNode->getRepeatCount();
936
0
        if (aTemp.hasValue())
937
0
        {
938
0
            Timing eTiming;
939
0
            if ((aTemp >>= eTiming) && (eTiming == Timing_INDEFINITE))
940
0
            {
941
0
                mrWriter.put("repeatCount", "indefinite");
942
0
            }
943
0
            else if (aTemp >>= fTemp)
944
0
            {
945
0
                convertDouble(sTmp, fTemp);
946
0
                mrWriter.put("repeatCount", sTmp.makeStringAndClear());
947
0
            }
948
0
        }
949
0
        aTemp = xNode->getRepeatDuration();
950
0
        if (aTemp.hasValue())
951
0
        {
952
0
            Timing eTiming;
953
0
            if ((aTemp >>= eTiming) && (eTiming == Timing_INDEFINITE))
954
0
            {
955
0
                mrWriter.put("repeatDur", "indefinite");
956
0
            }
957
0
            else if (aTemp >>= fTemp)
958
0
            {
959
0
                convertDouble(sTmp, fTemp);
960
0
                mrWriter.put("repeatDur", sTmp.makeStringAndClear());
961
0
            }
962
0
        }
963
0
        aTemp = xNode->getEndSync();
964
0
        if (aTemp.hasValue() && (aTemp >>= nTemp))
965
0
        {
966
0
            convertEnum(sTmp, nTemp, constEndSyncToString);
967
0
            mrWriter.put("endSync", sTmp.makeStringAndClear());
968
0
        }
969
970
0
        sal_Int16 nContainerNodeType = EffectNodeType::DEFAULT;
971
0
        const Sequence<NamedValue> aUserData(xNode->getUserData());
972
0
        for (const auto& rValue : aUserData)
973
0
        {
974
0
            if (IsXMLToken(rValue.Name, XML_NODE_TYPE))
975
0
            {
976
0
                if ((rValue.Value >>= nContainerNodeType)
977
0
                    && (nContainerNodeType != EffectNodeType::DEFAULT))
978
0
                {
979
0
                    convertEnum(sTmp, nContainerNodeType, constEffectNodeTypeToString);
980
0
                    mrWriter.put("nodeType", sTmp.makeStringAndClear());
981
0
                }
982
0
            }
983
0
            else if (IsXMLToken(rValue.Name, XML_PRESET_ID))
984
0
            {
985
0
                OUString aPresetId;
986
0
                if (rValue.Value >>= aPresetId)
987
0
                {
988
0
                    mrWriter.put("presetId", aPresetId);
989
0
                }
990
0
            }
991
0
            else if (IsXMLToken(rValue.Name, XML_PRESET_SUB_TYPE))
992
0
            {
993
0
                OUString aPresetSubType;
994
0
                if (rValue.Value >>= aPresetSubType)
995
0
                {
996
0
                    mrWriter.put("presetSubType", aPresetSubType);
997
0
                }
998
0
            }
999
0
            else if (IsXMLToken(rValue.Name, XML_PRESET_CLASS))
1000
0
            {
1001
0
                sal_Int16 nEffectPresetClass = sal_uInt16(0);
1002
0
                if (rValue.Value >>= nEffectPresetClass)
1003
0
                {
1004
0
                    convertEnum(sTmp, nEffectPresetClass, constEffectPresetClassToString);
1005
0
                    mrWriter.put("presetClass", sTmp.makeStringAndClear());
1006
0
                }
1007
0
            }
1008
0
            else if (IsXMLToken(rValue.Name, XML_MASTER_ELEMENT))
1009
0
            {
1010
0
                Reference<XInterface> xMaster;
1011
0
                rValue.Value >>= xMaster;
1012
0
                if (xMaster.is())
1013
0
                {
1014
0
                    const std::string aIdentifier(GetInterfaceHash(xMaster));
1015
0
                    if (!aIdentifier.empty())
1016
0
                        mrWriter.put("masterElement", aIdentifier);
1017
0
                }
1018
0
            }
1019
0
            else if (IsXMLToken(rValue.Name, XML_GROUP_ID))
1020
0
            {
1021
0
                sal_Int32 nGroupId = 0;
1022
0
                if (rValue.Value >>= nGroupId)
1023
0
                    mrWriter.put("groupId", nGroupId);
1024
0
            }
1025
0
            else
1026
0
            {
1027
0
                OUString aTmp;
1028
0
                if (rValue.Value >>= aTmp)
1029
0
                    mrWriter.put(rValue.Name, aTmp);
1030
0
            }
1031
0
        }
1032
1033
0
        switch (nNodeType)
1034
0
        {
1035
0
            case AnimationNodeType::PAR:
1036
0
            case AnimationNodeType::SEQ:
1037
0
            case AnimationNodeType::ITERATE:
1038
0
            {
1039
0
                Reference<XTimeContainer> xContainer(xNode, UNO_QUERY_THROW);
1040
0
                exportContainer(xContainer);
1041
0
            }
1042
0
            break;
1043
1044
0
            case AnimationNodeType::ANIMATE:
1045
0
            case AnimationNodeType::SET:
1046
0
            case AnimationNodeType::ANIMATEMOTION:
1047
0
            case AnimationNodeType::ANIMATEPHYSICS:
1048
0
            case AnimationNodeType::ANIMATECOLOR:
1049
0
            case AnimationNodeType::ANIMATETRANSFORM:
1050
0
            case AnimationNodeType::TRANSITIONFILTER:
1051
0
            {
1052
0
                Reference<XAnimate> xAnimate(xNode, UNO_QUERY_THROW);
1053
0
                exportAnimate(xAnimate);
1054
0
            }
1055
0
            break;
1056
0
            case AnimationNodeType::AUDIO:
1057
0
            {
1058
0
                SAL_WARN("sd", "AnimationsExporter::exportNode(): Audio Node not supported.");
1059
0
            }
1060
0
            break;
1061
0
            case AnimationNodeType::COMMAND:
1062
0
            {
1063
0
                SAL_WARN("sd", "AnimationsExporter::exportNode(): Command Node not supported.");
1064
0
            }
1065
0
            break;
1066
0
            default:
1067
0
            {
1068
0
                OSL_FAIL(
1069
0
                    "sd unomodel: AnimationsExporter::exportNode(), invalid AnimationNodeType!");
1070
0
            }
1071
0
        }
1072
0
    }
1073
0
    catch (const RuntimeException&)
1074
0
    {
1075
0
        TOOLS_WARN_EXCEPTION("sd", "unomodel: AnimationsExporter");
1076
0
    }
1077
0
}
1078
1079
void AnimationsExporter::convertTiming(OStringBuffer& sTmp, const Any& rValue)
1080
0
{
1081
0
    if (!rValue.hasValue())
1082
0
        return;
1083
1084
0
    if (auto pSequence = o3tl::tryAccess<Sequence<Any>>(rValue))
1085
0
    {
1086
0
        const sal_Int32 nLength = pSequence->getLength();
1087
0
        sal_Int32 nElement;
1088
0
        const Any* pAny = pSequence->getConstArray();
1089
1090
0
        OStringBuffer sTmp2;
1091
1092
0
        for (nElement = 0; nElement < nLength; nElement++, pAny++)
1093
0
        {
1094
0
            if (!sTmp.isEmpty())
1095
0
                sTmp.append(';');
1096
0
            convertTiming(sTmp2, *pAny);
1097
0
            sTmp.append(sTmp2);
1098
0
            sTmp2.setLength(0);
1099
0
        }
1100
0
    }
1101
0
    else if (auto x = o3tl::tryAccess<double>(rValue))
1102
0
    {
1103
0
        sTmp.append(*x);
1104
0
        sTmp.append('s');
1105
0
    }
1106
0
    else if (auto pTiming = o3tl::tryAccess<Timing>(rValue))
1107
0
    {
1108
0
        const auto svTiming = (*pTiming == Timing_MEDIA)
1109
0
                                  ? constTimingToString.at(Timing_MEDIA)
1110
0
                                  : constTimingToString.at(Timing_INDEFINITE);
1111
0
        sTmp.append(svTiming);
1112
0
    }
1113
0
    else if (auto pEvent = o3tl::tryAccess<Event>(rValue))
1114
0
    {
1115
0
        OStringBuffer sTmp2;
1116
1117
0
        if (pEvent->Trigger != EventTrigger::NONE)
1118
0
        {
1119
0
            if (pEvent->Source.hasValue())
1120
0
            {
1121
0
                OStringBuffer aTriggerBuffer;
1122
                // hash must not start with a digit or on client it is parsed as a time in seconds
1123
0
                aTriggerBuffer.append("id");
1124
0
                anim::convertTarget(aTriggerBuffer, pEvent->Source);
1125
0
                OString sTriggerHash(aTriggerBuffer.makeStringAndClear());
1126
0
                sTmp.append(sTriggerHash);
1127
0
                sTmp.append('.');
1128
0
                appendTrigger(pEvent->Source, sTriggerHash);
1129
0
            }
1130
1131
0
            convertEnum(sTmp2, pEvent->Trigger, constEventTriggerToString);
1132
1133
0
            sTmp.append(sTmp2);
1134
0
            sTmp2.setLength(0);
1135
0
        }
1136
1137
0
        if (pEvent->Offset.hasValue())
1138
0
        {
1139
0
            convertTiming(sTmp2, pEvent->Offset);
1140
1141
0
            if (!sTmp.isEmpty())
1142
0
                sTmp.append('+');
1143
1144
0
            sTmp.append(sTmp2);
1145
0
            sTmp2.setLength(0);
1146
0
        }
1147
0
    }
1148
0
    else
1149
0
    {
1150
0
        OSL_FAIL("sd.unomodel: AnimationsExporter::convertTiming, invalid value type!");
1151
0
    }
1152
0
}
1153
1154
void AnimationsExporter::appendTrigger(const css::uno::Any& rTarget, const OString& rTriggerHash)
1155
0
{
1156
0
    css::uno::Reference<css::uno::XInterface> xRef;
1157
0
    rTarget >>= xRef;
1158
1159
0
    uno::Reference<drawing::XShape> xShape(xRef, uno::UNO_QUERY);
1160
0
    if (!xShape.is())
1161
0
    {
1162
0
        if (auto xParagraphTarget = o3tl::tryAccess<css::presentation::ParagraphTarget>(rTarget))
1163
0
        {
1164
0
            xShape = xParagraphTarget->Shape;
1165
0
        }
1166
0
    }
1167
0
    if (xShape.is())
1168
0
    {
1169
0
        auto* pObject = SdrObject::getSdrObjectFromXShape(xShape);
1170
0
        maEventTriggerSet[pObject] = rTriggerHash;
1171
0
    }
1172
0
}
1173
1174
void AnimationsExporter::exportTriggersImpl(const uno::Reference<drawing::XShapes>& xShapes) const
1175
0
{
1176
0
    if (!xShapes.is())
1177
0
        return;
1178
1179
0
    sal_Int32 nCount = xShapes->getCount();
1180
0
    for (sal_Int32 i = 0; i < nCount; ++i)
1181
0
    {
1182
0
        auto xObject = xShapes->getByIndex(i);
1183
0
        uno::Reference<drawing::XShape> xShape(xObject, uno::UNO_QUERY);
1184
0
        if (!xShape.is())
1185
0
            continue;
1186
1187
0
        auto* pObject = SdrObject::getSdrObjectFromXShape(xShape);
1188
0
        if (maEventTriggerSet.find(pObject) == maEventTriggerSet.end())
1189
0
            continue;
1190
0
        {
1191
0
            auto aShape = mrWriter.startStruct();
1192
0
            mrWriter.put("hash", maEventTriggerSet.at(pObject));
1193
0
            {
1194
0
                auto const& rRectangle = pObject->GetLogicRect();
1195
0
                auto aRectangle
1196
0
                    = o3tl::convert(rRectangle, o3tl::Length::mm100, o3tl::Length::twip);
1197
0
                auto aRect = mrWriter.startNode("bounds");
1198
0
                mrWriter.put("x", aRectangle.Left());
1199
0
                mrWriter.put("y", aRectangle.Top());
1200
0
                mrWriter.put("width", aRectangle.GetWidth());
1201
0
                mrWriter.put("height", aRectangle.GetHeight());
1202
0
            }
1203
0
        }
1204
0
    }
1205
0
}
1206
1207
void AnimationsExporter::exportTriggers() const
1208
0
{
1209
0
    uno::Reference<drawing::XShapes> const xShapes(mxDrawPage, uno::UNO_QUERY_THROW);
1210
0
    if (!xShapes.is())
1211
0
        return;
1212
1213
0
    auto aTriggerList = mrWriter.startArray("triggers");
1214
0
    exportTriggersImpl(xShapes);
1215
0
}
1216
1217
void AnimationsExporter::convertValue(XMLTokenEnum eAttributeName, OStringBuffer& sTmp,
1218
                                      const Any& rValue) const
1219
0
{
1220
0
    if (!rValue.hasValue())
1221
0
        return;
1222
1223
0
    if (auto pValuePair = o3tl::tryAccess<ValuePair>(rValue))
1224
0
    {
1225
0
        OStringBuffer sTmp2;
1226
0
        convertValue(eAttributeName, sTmp, pValuePair->First);
1227
0
        sTmp.append(',');
1228
0
        convertValue(eAttributeName, sTmp2, pValuePair->Second);
1229
0
        sTmp.append(sTmp2);
1230
0
    }
1231
0
    else if (auto pSequence = o3tl::tryAccess<Sequence<Any>>(rValue))
1232
0
    {
1233
0
        const sal_Int32 nLength = pSequence->getLength();
1234
0
        sal_Int32 nElement;
1235
0
        const Any* pAny = pSequence->getConstArray();
1236
1237
0
        OStringBuffer sTmp2;
1238
1239
0
        for (nElement = 0; nElement < nLength; nElement++, pAny++)
1240
0
        {
1241
0
            if (!sTmp.isEmpty())
1242
0
                sTmp.append(';');
1243
0
            convertValue(eAttributeName, sTmp2, *pAny);
1244
0
            sTmp.append(sTmp2);
1245
0
            sTmp2.setLength(0);
1246
0
        }
1247
0
    }
1248
0
    else
1249
0
    {
1250
0
        switch (eAttributeName)
1251
0
        {
1252
0
            case XML_X:
1253
0
            case XML_Y:
1254
0
            case XML_WIDTH:
1255
0
            case XML_HEIGHT:
1256
0
            case XML_ANIMATETRANSFORM:
1257
0
            case XML_ANIMATEMOTION:
1258
0
            case XML_ANIMATEPHYSICS:
1259
0
            {
1260
0
                if (auto sValue = o3tl::tryAccess<OUString>(rValue))
1261
0
                {
1262
0
                    sTmp.append(sValue->toUtf8());
1263
0
                }
1264
0
                else if (auto aValue = o3tl::tryAccess<double>(rValue))
1265
0
                {
1266
0
                    sTmp.append(*aValue);
1267
0
                }
1268
0
                else
1269
0
                {
1270
0
                    OSL_FAIL("sd::AnimationsExporter::convertValue(), invalid value type!");
1271
0
                }
1272
0
                return;
1273
0
            }
1274
0
            case XML_SKEWX:
1275
0
            case XML_ROTATE:
1276
0
            case XML_OPACITY:
1277
0
            case XML_TRANSITIONFILTER:
1278
0
                if (auto aValue = o3tl::tryAccess<double>(rValue))
1279
0
                {
1280
0
                    sTmp.append(*aValue);
1281
0
                }
1282
0
                break;
1283
0
            case XML_TEXT_ROTATION_ANGLE:
1284
0
                if (auto aValue = o3tl::tryAccess<sal_Int16>(rValue))
1285
0
                {
1286
                    // on win and armv7 platforms compiler complains
1287
                    // that append(sal_Int16) is ambiguous
1288
0
                    sTmp.append(static_cast<sal_Int32>(*aValue));
1289
0
                }
1290
0
                break;
1291
0
            case XML_FILL_COLOR:
1292
0
            case XML_STROKE_COLOR:
1293
0
            case XML_DIM:
1294
0
            case XML_COLOR:
1295
0
            {
1296
0
                convertColor(sTmp, rValue);
1297
0
            }
1298
0
            break;
1299
0
            case XML_FILL:
1300
0
                if (auto aValue = o3tl::tryAccess<drawing::FillStyle>(rValue))
1301
0
                {
1302
0
                    convertEnum(sTmp, *aValue, constFillStyleToString);
1303
0
                }
1304
0
                break;
1305
0
            case XML_STROKE:
1306
0
                if (auto aValue = o3tl::tryAccess<drawing::LineStyle>(rValue))
1307
0
                {
1308
0
                    convertEnum(sTmp, *aValue, constLineStyleToString);
1309
0
                }
1310
0
                break;
1311
0
            case XML_FONTSIZE:
1312
0
                if (auto aValue = o3tl::tryAccess<double>(rValue))
1313
0
                {
1314
0
                    double fValue = *aValue * 100;
1315
0
                    fValue += fValue > 0 ? 0.5 : -0.5;
1316
0
                    auto nValue = static_cast<sal_Int32>(fValue);
1317
0
                    sTmp.append(nValue); // percent
1318
0
                }
1319
0
                break;
1320
0
            case XML_FONT_WEIGHT:
1321
0
            case XML_FONT_STYLE:
1322
0
            case XML_TEXT_UNDERLINE:
1323
0
                SAL_WARN("sd", "AnimationsExporter::convertValue(): value type "
1324
0
                                   << GetXMLToken(eAttributeName) << " not supported");
1325
0
                break;
1326
0
            case XML_VISIBILITY:
1327
0
                if (auto aValue = o3tl::tryAccess<bool>(rValue))
1328
0
                {
1329
0
                    OUString sValue = *aValue ? GetXMLToken(XML_VISIBLE) : GetXMLToken(XML_HIDDEN);
1330
0
                    sTmp.append(sValue.toUtf8());
1331
0
                }
1332
0
                break;
1333
0
            default:
1334
0
                OSL_FAIL("unomodel: AnimationsExporter::convertValue(), invalid AttributeName!");
1335
0
        }
1336
0
    }
1337
0
}
1338
1339
void AnimationsExporter::exportContainer(const Reference<XTimeContainer>& xContainer)
1340
0
{
1341
0
    try
1342
0
    {
1343
0
        const sal_Int32 nNodeType = xContainer->getType();
1344
1345
0
        if (nNodeType == AnimationNodeType::ITERATE)
1346
0
        {
1347
0
            OStringBuffer sTmp;
1348
0
            Reference<XIterateContainer> xIter(xContainer, UNO_QUERY_THROW);
1349
1350
0
            Any aTemp(xIter->getTarget());
1351
0
            if (aTemp.hasValue())
1352
0
            {
1353
0
                anim::convertTarget(sTmp, aTemp);
1354
0
                mrWriter.put("targetElement", sTmp.makeStringAndClear());
1355
0
            }
1356
0
            sal_Int16 nTemp = xIter->getSubItem();
1357
0
            if (nTemp)
1358
0
            {
1359
0
                convertEnum(sTmp, nTemp, constSubItemToString);
1360
0
                mrWriter.put("subItem", sTmp.makeStringAndClear());
1361
0
            }
1362
0
            nTemp = xIter->getIterateType();
1363
0
            if (nTemp)
1364
0
            {
1365
0
                convertEnum(sTmp, nTemp, constIterateTypeToString);
1366
0
                mrWriter.put("iterateType", sTmp.makeStringAndClear());
1367
0
            }
1368
0
            double fTemp = xIter->getIterateInterval();
1369
0
            if (fTemp != 0)
1370
0
            {
1371
0
                OUStringBuffer buf;
1372
0
                ::sax::Converter::convertDuration(buf, fTemp / (24 * 60 * 60));
1373
0
                mrWriter.put("iterateInterval", sTmp.makeStringAndClear());
1374
0
            }
1375
0
        }
1376
1377
0
        auto anArray = mrWriter.startArray("children");
1378
1379
0
        Reference<XEnumerationAccess> xEnumerationAccess(xContainer, UNO_QUERY_THROW);
1380
0
        Reference<XEnumeration> xEnumeration(xEnumerationAccess->createEnumeration(),
1381
0
                                             css::uno::UNO_SET_THROW);
1382
0
        while (xEnumeration->hasMoreElements())
1383
0
        {
1384
0
            Reference<XAnimationNode> xChildNode(xEnumeration->nextElement(), UNO_QUERY_THROW);
1385
0
            exportNode(xChildNode);
1386
0
        }
1387
0
    }
1388
0
    catch (const RuntimeException&)
1389
0
    {
1390
0
        TOOLS_WARN_EXCEPTION("sd", "unomodel: AnimationsExporter");
1391
0
    }
1392
0
}
1393
1394
void AnimationsExporter::exportAnimate(const Reference<XAnimate>& xAnimate)
1395
0
{
1396
0
    try
1397
0
    {
1398
0
        const sal_Int16 nNodeType = xAnimate->getType();
1399
1400
0
        OStringBuffer sTmp;
1401
0
        sal_Int16 nTemp;
1402
0
        bool bTemp;
1403
1404
0
        Any aTemp(xAnimate->getTarget());
1405
0
        if (aTemp.hasValue())
1406
0
        {
1407
0
            anim::convertTarget(sTmp, aTemp);
1408
0
            mrWriter.put("targetElement", sTmp.makeStringAndClear());
1409
0
            SdrObject* pObject = getTargetObject(aTemp);
1410
0
            if (pObject)
1411
0
            {
1412
0
                mrWriter.put("title", pObject->GetTitle());
1413
0
            }
1414
0
        }
1415
0
        nTemp = xAnimate->getSubItem();
1416
0
        if (nTemp)
1417
0
        {
1418
0
            convertEnum(sTmp, nTemp, constSubItemToString);
1419
0
            mrWriter.put("subItem", sTmp.makeStringAndClear());
1420
0
        }
1421
1422
0
        XMLTokenEnum eAttributeName = XML_TOKEN_INVALID;
1423
0
        if (nNodeType == AnimationNodeType::TRANSITIONFILTER)
1424
0
        {
1425
0
            eAttributeName = XML_TRANSITIONFILTER;
1426
0
        }
1427
0
        else if (nNodeType == AnimationNodeType::ANIMATETRANSFORM)
1428
0
        {
1429
0
            eAttributeName = XML_ANIMATETRANSFORM;
1430
0
        }
1431
0
        else if (nNodeType == AnimationNodeType::ANIMATEMOTION)
1432
0
        {
1433
0
            eAttributeName = XML_ANIMATEMOTION;
1434
0
        }
1435
0
        else if (nNodeType == AnimationNodeType::ANIMATEPHYSICS)
1436
0
        {
1437
0
            eAttributeName = XML_ANIMATEPHYSICS;
1438
0
        }
1439
0
        else
1440
0
        {
1441
0
            OString sTemp(xAnimate->getAttributeName().toUtf8());
1442
0
            if (!sTemp.isEmpty())
1443
0
            {
1444
0
                auto iterator = constAttributeNameToXMLEnum.find(sTemp);
1445
0
                if (iterator != constAttributeNameToXMLEnum.end())
1446
0
                {
1447
0
                    eAttributeName = iterator->second;
1448
0
                    mrWriter.put("attributeName", sTemp);
1449
0
                }
1450
0
                else
1451
0
                {
1452
0
                    mrWriter.put("attributeName", "invalid");
1453
0
                }
1454
0
            }
1455
0
        }
1456
1457
0
        Sequence<Any> aValues(xAnimate->getValues());
1458
0
        if (aValues.hasElements())
1459
0
        {
1460
0
            aTemp <<= aValues;
1461
0
            convertValue(eAttributeName, sTmp, aTemp);
1462
0
            mrWriter.put("values", sTmp.makeStringAndClear());
1463
0
        }
1464
0
        else
1465
0
        {
1466
0
            aTemp = xAnimate->getFrom();
1467
0
            if (aTemp.hasValue())
1468
0
            {
1469
0
                convertValue(eAttributeName, sTmp, aTemp);
1470
0
                mrWriter.put("from", sTmp.makeStringAndClear());
1471
0
            }
1472
1473
0
            aTemp = xAnimate->getBy();
1474
0
            if (aTemp.hasValue())
1475
0
            {
1476
0
                convertValue(eAttributeName, sTmp, aTemp);
1477
0
                mrWriter.put("by", sTmp.makeStringAndClear());
1478
0
            }
1479
1480
0
            aTemp = xAnimate->getTo();
1481
0
            if (aTemp.hasValue())
1482
0
            {
1483
0
                convertValue(eAttributeName, sTmp, aTemp);
1484
0
                mrWriter.put("to", sTmp.makeStringAndClear());
1485
0
            }
1486
0
        }
1487
1488
0
        if (nNodeType != AnimationNodeType::SET)
1489
0
        {
1490
0
            const Sequence<double> aKeyTimes(xAnimate->getKeyTimes());
1491
0
            if (aKeyTimes.hasElements())
1492
0
            {
1493
0
                for (const auto& rKeyTime : aKeyTimes)
1494
0
                {
1495
0
                    if (!sTmp.isEmpty())
1496
0
                        sTmp.append(';');
1497
1498
0
                    sTmp.append(rKeyTime);
1499
0
                }
1500
0
                mrWriter.put("keyTimes", sTmp.makeStringAndClear());
1501
0
            }
1502
1503
0
            OUString sTemp(xAnimate->getFormula());
1504
0
            if (!sTemp.isEmpty())
1505
0
            {
1506
0
                mrWriter.put("formula", sTemp);
1507
0
            }
1508
1509
0
            if ((nNodeType != AnimationNodeType::TRANSITIONFILTER)
1510
0
                && (nNodeType != AnimationNodeType::AUDIO))
1511
0
            {
1512
                // calcMode  = "discrete | linear | paced | spline"
1513
0
                nTemp = xAnimate->getCalcMode();
1514
0
                if (((nNodeType == AnimationNodeType::ANIMATEMOTION)
1515
0
                     && (nTemp != AnimationCalcMode::PACED))
1516
0
                    || ((nNodeType != AnimationNodeType::ANIMATEMOTION)
1517
0
                        && (nTemp != AnimationCalcMode::LINEAR)))
1518
0
                {
1519
0
                    convertEnum(sTmp, nTemp, constCalcModeToString);
1520
0
                    mrWriter.put("calcMode", sTmp.makeStringAndClear());
1521
0
                }
1522
1523
0
                bTemp = xAnimate->getAccumulate();
1524
0
                if (bTemp)
1525
0
                {
1526
0
                    mrWriter.put("accumulate", "sum");
1527
0
                }
1528
1529
0
                nTemp = xAnimate->getAdditive();
1530
0
                if (nTemp != AnimationAdditiveMode::REPLACE)
1531
0
                {
1532
0
                    convertEnum(sTmp, nTemp, constAdditiveModeToString);
1533
0
                    mrWriter.put("additive", sTmp.makeStringAndClear());
1534
0
                }
1535
0
            }
1536
1537
0
            const Sequence<TimeFilterPair> aTimeFilter(xAnimate->getTimeFilter());
1538
0
            if (aTimeFilter.hasElements())
1539
0
            {
1540
0
                for (const auto& rPair : aTimeFilter)
1541
0
                {
1542
0
                    if (!sTmp.isEmpty())
1543
0
                        sTmp.append(';');
1544
1545
0
                    sTmp.append(OString::number(rPair.Time) + ","
1546
0
                                + OString::number(rPair.Progress));
1547
0
                }
1548
0
                mrWriter.put("keySplines", sTmp.makeStringAndClear());
1549
0
            }
1550
0
        }
1551
1552
0
        switch (nNodeType)
1553
0
        {
1554
0
            case AnimationNodeType::ANIMATEMOTION:
1555
0
            {
1556
0
                Reference<XAnimateMotion> xAnimateMotion(xAnimate, UNO_QUERY_THROW);
1557
1558
0
                aTemp = xAnimateMotion->getPath();
1559
0
                if (aTemp.hasValue())
1560
0
                {
1561
0
                    convertPath(sTmp, aTemp);
1562
0
                    mrWriter.put("path", sTmp.makeStringAndClear());
1563
0
                }
1564
0
            }
1565
0
            break;
1566
0
            case AnimationNodeType::ANIMATEPHYSICS:
1567
0
            {
1568
0
                SAL_WARN(
1569
0
                    "sd",
1570
0
                    "unomodel: AnimationsExporter::exportAnimate(): AnimatePhysics not supported");
1571
0
            }
1572
0
            break;
1573
0
            case AnimationNodeType::ANIMATECOLOR:
1574
0
            {
1575
0
                Reference<XAnimateColor> xAnimateColor(xAnimate, UNO_QUERY_THROW);
1576
1577
0
                nTemp = xAnimateColor->getColorInterpolation();
1578
0
                mrWriter.put("colorInterpolation",
1579
0
                             (nTemp == AnimationColorSpace::RGB) ? "rgb" : "hsl");
1580
1581
0
                bTemp = xAnimateColor->getDirection();
1582
0
                mrWriter.put("colorInterpolationDirection",
1583
0
                             bTemp ? "clockwise" : "counterClockwise");
1584
0
            }
1585
0
            break;
1586
0
            case AnimationNodeType::ANIMATETRANSFORM:
1587
0
            {
1588
0
                mrWriter.put("attributeName", "transform");
1589
1590
0
                Reference<XAnimateTransform> xTransform(xAnimate, UNO_QUERY_THROW);
1591
0
                nTemp = xTransform->getTransformType();
1592
0
                convertEnum(sTmp, nTemp, constTransformTypeToString);
1593
0
                mrWriter.put("transformType", sTmp.makeStringAndClear());
1594
0
            }
1595
0
            break;
1596
0
            case AnimationNodeType::TRANSITIONFILTER:
1597
0
            {
1598
0
                Reference<XTransitionFilter> xTransitionFilter(xAnimate, UNO_QUERY);
1599
1600
0
                sal_Int16 nTransition = xTransitionFilter->getTransition();
1601
0
                convertEnum(sTmp, nTransition, constTransitionTypeToString);
1602
0
                mrWriter.put("transitionType", sTmp.makeStringAndClear());
1603
1604
0
                sal_Int16 nSubtype = xTransitionFilter->getSubtype();
1605
0
                if (nSubtype != TransitionSubType::DEFAULT)
1606
0
                {
1607
0
                    convertEnum(sTmp, nSubtype, constTransitionSubTypeToString);
1608
0
                    mrWriter.put("transitionSubType", sTmp.makeStringAndClear());
1609
0
                }
1610
1611
0
                bTemp = xTransitionFilter->getMode();
1612
0
                if (!bTemp)
1613
0
                    mrWriter.put("transitionMode", "out");
1614
1615
0
                bTemp = xTransitionFilter->getDirection();
1616
0
                if (!bTemp)
1617
0
                    mrWriter.put("transitionDirection", "reverse");
1618
1619
0
                if ((nTransition == TransitionType::FADE)
1620
0
                    && ((nSubtype == TransitionSubType::FADETOCOLOR)
1621
0
                        || (nSubtype == TransitionSubType::FADEFROMCOLOR)))
1622
0
                {
1623
0
                    sal_Int32 nColor = xTransitionFilter->getFadeColor();
1624
0
                    convertColor(sTmp, nColor);
1625
0
                    mrWriter.put("transitionFadeColor", sTmp.makeStringAndClear());
1626
0
                }
1627
0
            }
1628
0
            break;
1629
0
            default:
1630
0
            {
1631
0
                SAL_WARN("sd",
1632
0
                         "unomodel: AnimationsExporter::exportAnimate(): not supported node type: "
1633
0
                             << nNodeType);
1634
0
            }
1635
0
        }
1636
0
    }
1637
0
    catch (const Exception&)
1638
0
    {
1639
0
        TOOLS_WARN_EXCEPTION("sd", "unomodel: AnimationsExporter");
1640
0
    }
1641
0
}
1642
1643
void GetDocStructureSlides(::tools::JsonWriter& rJsonWriter, const SdXImpressDocument* pDoc,
1644
                           const std::map<OUString, OUString>& rArguments)
1645
0
{
1646
0
    auto it = rArguments.find(u"filter"_ustr);
1647
0
    if (it != rArguments.end())
1648
0
    {
1649
        // If filter is present but we are filtering not to slide information
1650
0
        if (!it->second.equals(u"slides"_ustr))
1651
0
            return;
1652
0
    }
1653
1654
0
    sal_uInt16 nPageCount = pDoc->GetDoc()->GetSdPageCount(PageKind::Standard);
1655
0
    sal_uInt16 nMasterPageCount = pDoc->GetDoc()->GetMasterSdPageCount(PageKind::Standard);
1656
1657
0
    rJsonWriter.put("SlideCount", nPageCount);
1658
0
    rJsonWriter.put("MasterSlideCount", nMasterPageCount);
1659
1660
    // write data of every master slide
1661
0
    if (nMasterPageCount > 0)
1662
0
    {
1663
0
        auto aMasterPagesNode = rJsonWriter.startNode("MasterSlides");
1664
0
        for (int nMPId = 0; nMPId < nMasterPageCount; nMPId++)
1665
0
        {
1666
0
            auto aMasterPageNode = rJsonWriter.startNode("MasterSlide " + std::to_string(nMPId));
1667
0
            const OUString& aMName
1668
0
                = pDoc->GetDoc()->GetMasterSdPage(nMPId, PageKind::Standard)->GetName();
1669
0
            rJsonWriter.put("Name", aMName);
1670
0
        }
1671
0
    }
1672
1673
    // write data of every slide
1674
0
    if (nPageCount > 0)
1675
0
    {
1676
0
        auto aPagesNode = rJsonWriter.startNode("Slides");
1677
0
        for (int nPId = 0; nPId < nPageCount; nPId++)
1678
0
        {
1679
0
            auto aPageNode = rJsonWriter.startNode("Slide " + std::to_string(nPId));
1680
0
            SdPage* pPageStandard = pDoc->GetDoc()->GetSdPage(nPId, PageKind::Standard);
1681
1682
            // Slide Name
1683
0
            rJsonWriter.put("SlideName", pPageStandard->GetName());
1684
1685
            // MasterSlide Name
1686
0
            const FmFormPage* pMasterPage
1687
0
                = dynamic_cast<const FmFormPage*>(&pPageStandard->TRG_GetMasterPage());
1688
1689
0
            if (pMasterPage)
1690
0
            {
1691
0
                rJsonWriter.put("MasterSlideName", pMasterPage->GetName());
1692
0
            }
1693
1694
            // Layout id, and name.
1695
0
            AutoLayout nLayout = pPageStandard->GetAutoLayout();
1696
0
            rJsonWriter.put("LayoutId", static_cast<int>(nLayout));
1697
0
            rJsonWriter.put("LayoutName", SdPage::autoLayoutToString(nLayout));
1698
1699
            // Every Objects in the page
1700
0
            int nObjCount = pPageStandard->GetObjCount();
1701
0
            rJsonWriter.put("ObjectCount", nObjCount);
1702
1703
0
            if (nObjCount > 0)
1704
0
            {
1705
0
                auto aObjectsNode = rJsonWriter.startNode("Objects");
1706
0
                for (int nOId = 0; nOId < nObjCount; nOId++)
1707
0
                {
1708
0
                    auto aObjectNode = rJsonWriter.startNode("Objects " + std::to_string(nOId));
1709
0
                    SdrObject* pSdrObj = pPageStandard->GetObj(nOId);
1710
0
                    SdrTextObj* pSdrTxtObj = DynCastSdrTextObj(pSdrObj);
1711
0
                    if (pSdrTxtObj && pSdrTxtObj->HasText())
1712
0
                    {
1713
0
                        sal_Int32 nTextCount = pSdrTxtObj->getTextCount();
1714
0
                        rJsonWriter.put("TextCount", nTextCount);
1715
0
                        if (nTextCount > 0)
1716
0
                        {
1717
0
                            auto aTextsNode = rJsonWriter.startNode("Texts");
1718
0
                            for (int nTId = 0; nTId < nTextCount; nTId++)
1719
0
                            {
1720
0
                                auto aTextNode
1721
0
                                    = rJsonWriter.startNode("Text " + std::to_string(nTId));
1722
0
                                SdrText* pSdrTxt = pSdrTxtObj->getText(nTId);
1723
0
                                OutlinerParaObject* pOutlinerParaObject
1724
0
                                    = pSdrTxt->GetOutlinerParaObject();
1725
1726
0
                                sal_Int32 nParaCount
1727
0
                                    = pOutlinerParaObject->GetTextObject().GetParagraphCount();
1728
1729
0
                                rJsonWriter.put("ParaCount", nParaCount);
1730
0
                                auto aParasNode = rJsonWriter.startArray("Paragraphs");
1731
0
                                for (int nParaId = 0; nParaId < nParaCount; nParaId++)
1732
0
                                {
1733
0
                                    OUString aParaStr(
1734
0
                                        pOutlinerParaObject->GetTextObject().GetText(nParaId));
1735
1736
0
                                    rJsonWriter.putSimpleValue(aParaStr);
1737
0
                                }
1738
0
                            }
1739
0
                        }
1740
0
                    }
1741
0
                }
1742
0
            }
1743
0
        }
1744
0
    }
1745
0
}
1746
1747
} // end anonymous namespace
1748
1749
SdUnoForbiddenCharsTable::SdUnoForbiddenCharsTable( SdrModel* pModel )
1750
638
: SvxUnoForbiddenCharsTable( pModel->GetForbiddenCharsTable() ), mpModel( pModel )
1751
638
{
1752
638
    StartListening( *pModel );
1753
638
}
1754
1755
void SdUnoForbiddenCharsTable::onChange()
1756
641
{
1757
641
    if( mpModel )
1758
641
    {
1759
641
        mpModel->ReformatAllTextObjects();
1760
641
    }
1761
641
}
1762
1763
SdUnoForbiddenCharsTable::~SdUnoForbiddenCharsTable()
1764
638
{
1765
638
    SolarMutexGuard g;
1766
1767
638
    if( mpModel )
1768
638
        EndListening( *mpModel );
1769
638
}
1770
1771
void SdUnoForbiddenCharsTable::Notify( SfxBroadcaster&, const SfxHint& rHint ) noexcept
1772
0
{
1773
0
    if (rHint.GetId() != SfxHintId::ThisIsAnSdrHint)
1774
0
        return;
1775
0
    const SdrHint* pSdrHint = static_cast<const SdrHint*>( &rHint );
1776
0
    if( SdrHintKind::ModelCleared == pSdrHint->GetKind() )
1777
0
    {
1778
0
        mpModel = nullptr;
1779
0
    }
1780
0
}
1781
1782
const sal_uInt16 WID_MODEL_LANGUAGE           =  1;
1783
const sal_uInt16 WID_MODEL_TABSTOP            =  2;
1784
const sal_uInt16 WID_MODEL_VISAREA            =  3;
1785
const sal_uInt16 WID_MODEL_MAPUNIT            =  4;
1786
const sal_uInt16 WID_MODEL_FORBCHARS          =  5;
1787
const sal_uInt16 WID_MODEL_CONTFOCUS          =  6;
1788
const sal_uInt16 WID_MODEL_DSGNMODE           =  7;
1789
const sal_uInt16 WID_MODEL_BASICLIBS          =  8;
1790
const sal_uInt16 WID_MODEL_RUNTIMEUID         =  9;
1791
const sal_uInt16 WID_MODEL_BUILDID            = 10;
1792
const sal_uInt16 WID_MODEL_HASVALIDSIGNATURES = 11;
1793
const sal_uInt16 WID_MODEL_DIALOGLIBS         = 12;
1794
const sal_uInt16 WID_MODEL_FONTS              = 13;
1795
const sal_uInt16 WID_MODEL_INTEROPGRABBAG     = 14;
1796
const sal_uInt16 WID_MODEL_THEME = 15;
1797
const sal_uInt16 WID_MODEL_ALLOWLINKUPDATE    = 16;
1798
1799
static const SvxItemPropertySet* ImplGetDrawModelPropertySet()
1800
36.3k
{
1801
    // Attention: the first parameter HAS TO BE sorted!!!
1802
36.3k
    const static SfxItemPropertyMapEntry aDrawModelPropertyMap_Impl[] =
1803
36.3k
    {
1804
36.3k
        { u"BuildId"_ustr,                WID_MODEL_BUILDID,            ::cppu::UnoType<OUString>::get(),                      0, 0},
1805
36.3k
        { sUNO_Prop_CharLocale,           WID_MODEL_LANGUAGE,           ::cppu::UnoType<lang::Locale>::get(),                                  0, 0},
1806
36.3k
        { sUNO_Prop_TabStop,              WID_MODEL_TABSTOP,            ::cppu::UnoType<sal_Int32>::get(),                                     0, 0},
1807
36.3k
        { sUNO_Prop_VisibleArea,          WID_MODEL_VISAREA,            ::cppu::UnoType<awt::Rectangle>::get(),                                0, 0},
1808
36.3k
        { sUNO_Prop_MapUnit,              WID_MODEL_MAPUNIT,            ::cppu::UnoType<sal_Int16>::get(),                                     beans::PropertyAttribute::READONLY, 0},
1809
36.3k
        { sUNO_Prop_ForbiddenCharacters,  WID_MODEL_FORBCHARS,          cppu::UnoType<i18n::XForbiddenCharacters>::get(), beans::PropertyAttribute::READONLY, 0},
1810
36.3k
        { sUNO_Prop_AutomContFocus,       WID_MODEL_CONTFOCUS,          cppu::UnoType<bool>::get(),                                                 0, 0},
1811
36.3k
        { sUNO_Prop_ApplyFrmDsgnMode,     WID_MODEL_DSGNMODE,           cppu::UnoType<bool>::get(),                                                 0, 0},
1812
36.3k
        { u"BasicLibraries"_ustr,         WID_MODEL_BASICLIBS,          cppu::UnoType<script::XLibraryContainer>::get(),  beans::PropertyAttribute::READONLY, 0},
1813
36.3k
        { u"DialogLibraries"_ustr,        WID_MODEL_DIALOGLIBS,         cppu::UnoType<script::XLibraryContainer>::get(),  beans::PropertyAttribute::READONLY, 0},
1814
36.3k
        { sUNO_Prop_RuntimeUID,           WID_MODEL_RUNTIMEUID,         ::cppu::UnoType<OUString>::get(),                      beans::PropertyAttribute::READONLY, 0},
1815
36.3k
        { sUNO_Prop_HasValidSignatures,   WID_MODEL_HASVALIDSIGNATURES, ::cppu::UnoType<sal_Bool>::get(),                      beans::PropertyAttribute::READONLY, 0},
1816
36.3k
        { sUNO_Prop_AllowLinkUpdate,      WID_MODEL_ALLOWLINKUPDATE,    ::cppu::UnoType<sal_Bool>::get(),                      beans::PropertyAttribute::READONLY, 0},
1817
36.3k
        { u"Fonts"_ustr,                  WID_MODEL_FONTS,              cppu::UnoType<uno::Sequence<uno::Any>>::get(),                     beans::PropertyAttribute::READONLY, 0},
1818
36.3k
        { sUNO_Prop_InteropGrabBag,       WID_MODEL_INTEROPGRABBAG,     cppu::UnoType<uno::Sequence< beans::PropertyValue >>::get(),       0, 0},
1819
36.3k
        { sUNO_Prop_Theme,                WID_MODEL_THEME,              cppu::UnoType<util::XTheme>::get(),       0, 0},
1820
36.3k
    };
1821
36.3k
    static SvxItemPropertySet aDrawModelPropertySet_Impl( aDrawModelPropertyMap_Impl, SdrObject::GetGlobalDrawObjectItemPool() );
1822
36.3k
    return &aDrawModelPropertySet_Impl;
1823
36.3k
}
1824
1825
// this ctor is used from the DocShell
1826
SdXImpressDocument::SdXImpressDocument(::sd::DrawDocShell* pShell, bool bClipBoard)
1827
36.3k
:   SfxBaseModel( pShell ),
1828
36.3k
    mpDocShell( pShell ),
1829
36.3k
    mpDoc( pShell ? pShell->GetDoc() : nullptr ),
1830
36.3k
    mbDisposed(false),
1831
36.3k
    mbImpressDoc( pShell && pShell->GetDoc() && pShell->GetDoc()->GetDocumentType() == DocumentType::Impress ),
1832
36.3k
    mbClipBoard( bClipBoard ),
1833
36.3k
    mpPropSet( ImplGetDrawModelPropertySet() ),
1834
36.3k
    mbPaintTextEdit( true )
1835
36.3k
{
1836
36.3k
    if( mpDoc )
1837
36.3k
    {
1838
36.3k
        StartListening( *mpDoc );
1839
36.3k
    }
1840
0
    else
1841
0
    {
1842
0
        OSL_FAIL("DocShell is invalid");
1843
0
    }
1844
36.3k
}
1845
1846
SdXImpressDocument::SdXImpressDocument(SdDrawDocument* pDoc, bool bClipBoard)
1847
0
:   SfxBaseModel( nullptr ),
1848
0
    mpDocShell( nullptr ),
1849
0
    mpDoc( pDoc ),
1850
0
    mbDisposed(false),
1851
0
    mbImpressDoc( pDoc && pDoc->GetDocumentType() == DocumentType::Impress ),
1852
0
    mbClipBoard( bClipBoard ),
1853
0
    mpPropSet( ImplGetDrawModelPropertySet() ),
1854
0
    mbPaintTextEdit( true )
1855
0
{
1856
0
    if( mpDoc )
1857
0
    {
1858
0
        StartListening( *mpDoc );
1859
0
    }
1860
0
    else
1861
0
    {
1862
0
        OSL_FAIL("SdDrawDocument is invalid");
1863
0
    }
1864
0
}
1865
1866
/***********************************************************************
1867
*                                                                      *
1868
***********************************************************************/
1869
SdXImpressDocument::~SdXImpressDocument() noexcept
1870
36.3k
{
1871
36.3k
}
1872
1873
// XInterface
1874
uno::Any SAL_CALL SdXImpressDocument::queryInterface( const uno::Type & rType )
1875
895k
{
1876
895k
    uno::Any aAny;
1877
1878
895k
    if (rType == cppu::UnoType<lang::XServiceInfo>::get())
1879
32.3k
        aAny <<= uno::Reference<lang::XServiceInfo>(this);
1880
863k
    else if (rType == cppu::UnoType<beans::XPropertySet>::get())
1881
13.6k
        aAny <<= uno::Reference<beans::XPropertySet>(this);
1882
849k
    else if (rType == cppu::UnoType<lang::XMultiServiceFactory>::get())
1883
224k
        aAny <<= uno::Reference<lang::XMultiServiceFactory>(this);
1884
625k
    else if (rType == cppu::UnoType<drawing::XDrawPageDuplicator>::get())
1885
0
        aAny <<= uno::Reference<drawing::XDrawPageDuplicator>(this);
1886
625k
    else if (rType == cppu::UnoType<drawing::XLayerSupplier>::get())
1887
320
        aAny <<= uno::Reference<drawing::XLayerSupplier>(this);
1888
624k
    else if (rType == cppu::UnoType<drawing::XMasterPagesSupplier>::get())
1889
18.3k
        aAny <<= uno::Reference<drawing::XMasterPagesSupplier>(this);
1890
606k
    else if (rType == cppu::UnoType<drawing::XDrawPagesSupplier>::get())
1891
27.4k
        aAny <<= uno::Reference<drawing::XDrawPagesSupplier>(this);
1892
579k
    else if (rType == cppu::UnoType<presentation::XHandoutMasterSupplier>::get())
1893
289
        aAny <<= uno::Reference<presentation::XHandoutMasterSupplier>(this);
1894
578k
    else if (rType == cppu::UnoType<document::XLinkTargetSupplier>::get())
1895
0
        aAny <<= uno::Reference<document::XLinkTargetSupplier>(this);
1896
578k
    else if (rType == cppu::UnoType<style::XStyleFamiliesSupplier>::get())
1897
85.3k
        aAny <<= uno::Reference<style::XStyleFamiliesSupplier>(this);
1898
493k
    else if (rType == cppu::UnoType<css::ucb::XAnyCompareFactory>::get())
1899
18.5k
        aAny <<= uno::Reference<css::ucb::XAnyCompareFactory>(this);
1900
474k
    else if (rType == cppu::UnoType<view::XRenderable>::get())
1901
0
        aAny <<= uno::Reference<view::XRenderable>(this);
1902
474k
    else if (mbImpressDoc && rType == cppu::UnoType<presentation::XPresentationSupplier>::get())
1903
718
        aAny <<= uno::Reference< presentation::XPresentationSupplier >(this);
1904
474k
    else if (mbImpressDoc && rType == cppu::UnoType<presentation::XCustomPresentationSupplier>::get())
1905
2
        aAny <<= uno::Reference< presentation::XCustomPresentationSupplier >(this);
1906
474k
    else
1907
474k
        return SfxBaseModel::queryInterface(rType);
1908
1909
421k
    return aAny;
1910
895k
}
1911
1912
void SAL_CALL SdXImpressDocument::acquire() noexcept
1913
1.78M
{
1914
1.78M
    SfxBaseModel::acquire();
1915
1.78M
}
1916
1917
void SAL_CALL SdXImpressDocument::release() noexcept
1918
1.78M
{
1919
1.78M
    if (osl_atomic_decrement( &m_refCount ) != 0)
1920
1.74M
        return;
1921
1922
    // restore reference count:
1923
36.3k
    osl_atomic_increment( &m_refCount );
1924
36.3k
    if(!mbDisposed)
1925
0
    {
1926
0
        try
1927
0
        {
1928
0
            dispose();
1929
0
        }
1930
0
        catch (const uno::RuntimeException&)
1931
0
        {
1932
            // don't break throw ()
1933
0
            TOOLS_WARN_EXCEPTION( "sd", "" );
1934
0
        }
1935
0
    }
1936
36.3k
    SfxBaseModel::release();
1937
36.3k
}
1938
1939
// XUnoTunnel
1940
const css::uno::Sequence< sal_Int8 > & SdXImpressDocument::getUnoTunnelId() noexcept
1941
472k
{
1942
472k
    static const comphelper::UnoIdInit theSdXImpressDocumentUnoTunnelId;
1943
472k
    return theSdXImpressDocumentUnoTunnelId.getSeq();
1944
472k
}
1945
1946
sal_Int64 SAL_CALL SdXImpressDocument::getSomething( const css::uno::Sequence< sal_Int8 >& rIdentifier )
1947
236k
{
1948
236k
    if (comphelper::isUnoTunnelId<SdrModel>(rIdentifier))
1949
0
        return comphelper::getSomething_cast(mpDoc);
1950
1951
236k
    if (comphelper::isUnoTunnelId<SfxObjectShell>(rIdentifier))
1952
0
        return comphelper::getSomething_cast(mpDocShell);
1953
1954
236k
    return comphelper::getSomethingImpl(rIdentifier, this,
1955
236k
                                        comphelper::FallbackToGetSomethingOf<SfxBaseModel>{});
1956
236k
}
1957
1958
// XTypeProvider
1959
uno::Sequence< uno::Type > SAL_CALL SdXImpressDocument::getTypes(  )
1960
0
{
1961
0
    ::SolarMutexGuard aGuard;
1962
1963
0
    if( !maTypeSequence.hasElements() )
1964
0
    {
1965
0
        uno::Sequence< uno::Type > aTypes( SfxBaseModel::getTypes() );
1966
0
        aTypes = comphelper::concatSequences(aTypes,
1967
0
            uno::Sequence {
1968
0
                cppu::UnoType<beans::XPropertySet>::get(),
1969
0
                cppu::UnoType<lang::XServiceInfo>::get(),
1970
0
                cppu::UnoType<lang::XMultiServiceFactory>::get(),
1971
0
                cppu::UnoType<drawing::XDrawPageDuplicator>::get(),
1972
0
                cppu::UnoType<drawing::XLayerSupplier>::get(),
1973
0
                cppu::UnoType<drawing::XMasterPagesSupplier>::get(),
1974
0
                cppu::UnoType<drawing::XDrawPagesSupplier>::get(),
1975
0
                cppu::UnoType<document::XLinkTargetSupplier>::get(),
1976
0
                cppu::UnoType<style::XStyleFamiliesSupplier>::get(),
1977
0
                cppu::UnoType<css::ucb::XAnyCompareFactory>::get(),
1978
0
                cppu::UnoType<view::XRenderable>::get() });
1979
0
        if( mbImpressDoc )
1980
0
        {
1981
0
            aTypes = comphelper::concatSequences(aTypes,
1982
0
                uno::Sequence {
1983
0
                    cppu::UnoType<presentation::XPresentationSupplier>::get(),
1984
0
                    cppu::UnoType<presentation::XCustomPresentationSupplier>::get(),
1985
0
                    cppu::UnoType<presentation::XHandoutMasterSupplier>::get() });
1986
0
        }
1987
0
        maTypeSequence = std::move(aTypes);
1988
0
    }
1989
1990
0
    return maTypeSequence;
1991
0
}
1992
1993
uno::Sequence< sal_Int8 > SAL_CALL SdXImpressDocument::getImplementationId(  )
1994
0
{
1995
0
    return css::uno::Sequence<sal_Int8>();
1996
0
}
1997
1998
/***********************************************************************
1999
*                                                                      *
2000
***********************************************************************/
2001
void SdXImpressDocument::Notify( SfxBroadcaster& rBC, const SfxHint& rHint )
2002
11.2M
{
2003
11.2M
    if( mpDoc )
2004
11.2M
    {
2005
11.2M
        if (rHint.GetId() == SfxHintId::ThisIsAnSdrHint)
2006
2.16M
        {
2007
2.16M
            const SdrHint* pSdrHint = static_cast<const SdrHint*>( &rHint );
2008
2.16M
            if( hasEventListeners() )
2009
0
            {
2010
0
                document::EventObject aEvent;
2011
0
                if( SvxUnoDrawMSFactory::createEvent( mpDoc, pSdrHint, aEvent ) )
2012
0
                    notifyEvent( aEvent );
2013
0
            }
2014
2015
2.16M
            if( pSdrHint->GetKind() == SdrHintKind::ModelCleared )
2016
0
            {
2017
0
                if( mpDoc )
2018
0
                    EndListening( *mpDoc );
2019
0
                mpDoc = nullptr;
2020
0
                mpDocShell = nullptr;
2021
0
            }
2022
2.16M
        }
2023
9.04M
        else
2024
9.04M
        {
2025
            // did our SdDrawDocument just died?
2026
9.04M
            if(rHint.GetId() == SfxHintId::Dying)
2027
0
            {
2028
                // yes, so we ask for a new one
2029
0
                if( mpDocShell )
2030
0
                {
2031
0
                    SdDrawDocument *pNewDoc = mpDocShell->GetDoc();
2032
2033
                    // is there a new one?
2034
0
                    if( pNewDoc != mpDoc )
2035
0
                    {
2036
0
                        mpDoc = pNewDoc;
2037
0
                        if(mpDoc)
2038
0
                            StartListening( *mpDoc );
2039
0
                    }
2040
0
                }
2041
0
            }
2042
9.04M
        }
2043
11.2M
    }
2044
11.2M
    SfxBaseModel::Notify( rBC, rHint );
2045
11.2M
}
2046
2047
void SdXImpressDocument::getCommandValues(::tools::JsonWriter& rJsonWriter, std::string_view rCommand)
2048
0
{
2049
0
    static constexpr OStringLiteral aExtractDocStructure(".uno:ExtractDocumentStructure");
2050
2051
0
    std::map<OUString, OUString> aMap
2052
0
        = SfxLokHelper::parseCommandParameters(OUString::fromUtf8(rCommand));
2053
2054
0
    if (o3tl::starts_with(rCommand, aExtractDocStructure))
2055
0
    {
2056
0
        auto commentsNode = rJsonWriter.startNode("DocStructure");
2057
0
        GetDocStructureSlides(rJsonWriter, this, aMap);
2058
0
    }
2059
0
}
2060
2061
/******************************************************************************
2062
*                                                                             *
2063
******************************************************************************/
2064
SdPage* SdXImpressDocument::InsertSdPage( sal_uInt16 nPage, bool bDuplicate )
2065
169k
{
2066
169k
    sal_uInt16 nPageCount = mpDoc->GetSdPageCount( PageKind::Standard );
2067
169k
    SdrLayerAdmin& rLayerAdmin = mpDoc->GetLayerAdmin();
2068
169k
    SdrLayerID aBckgrnd = rLayerAdmin.GetLayerID(sUNO_LayerName_background);
2069
169k
    SdrLayerID aBckgrndObj = rLayerAdmin.GetLayerID(sUNO_LayerName_background_objects);
2070
2071
169k
    rtl::Reference<SdPage> pStandardPage;
2072
2073
169k
    if( 0 == nPageCount )
2074
0
    {
2075
        // this is only used for clipboard where we only have one page
2076
0
        pStandardPage = mpDoc->AllocSdPage(false);
2077
2078
0
        Size aDefSize(21000, 29700);   // A4 portrait orientation
2079
0
        pStandardPage->SetSize( aDefSize );
2080
0
        mpDoc->InsertPage(pStandardPage.get(), 0);
2081
0
    }
2082
169k
    else
2083
169k
    {
2084
        // here we determine the page after which we should insert
2085
169k
        SdPage* pPreviousStandardPage = mpDoc->GetSdPage( std::min( static_cast<sal_uInt16>(nPageCount - 1), nPage ), PageKind::Standard );
2086
169k
        SdrLayerIDSet aVisibleLayers = pPreviousStandardPage->TRG_GetMasterPageVisibleLayers();
2087
169k
        bool bIsPageBack = aVisibleLayers.IsSet( aBckgrnd );
2088
169k
        bool bIsPageObj = aVisibleLayers.IsSet( aBckgrndObj );
2089
2090
        // AutoLayouts must be ready
2091
169k
        mpDoc->StopWorkStartupDelay();
2092
2093
        /* First we create a standard page and then a notes page. It is
2094
           guaranteed, that after a standard page the corresponding notes page
2095
           follows. */
2096
2097
169k
        sal_uInt16 nStandardPageNum = pPreviousStandardPage->GetPageNum() + 2;
2098
169k
        SdPage* pPreviousNotesPage = static_cast<SdPage*>( mpDoc->GetPage( nStandardPageNum - 1 ) );
2099
169k
        sal_uInt16 nNotesPageNum = nStandardPageNum + 1;
2100
2101
        /**************************************************************
2102
        * standard page
2103
        **************************************************************/
2104
169k
        if( bDuplicate )
2105
0
            pStandardPage = static_cast<SdPage*>( pPreviousStandardPage->CloneSdrPage(*mpDoc).get() );
2106
169k
        else
2107
169k
            pStandardPage = mpDoc->AllocSdPage(false);
2108
2109
169k
        pStandardPage->SetSize( pPreviousStandardPage->GetSize() );
2110
169k
        pStandardPage->SetBorder( pPreviousStandardPage->GetLeftBorder(),
2111
169k
                                    pPreviousStandardPage->GetUpperBorder(),
2112
169k
                                    pPreviousStandardPage->GetRightBorder(),
2113
169k
                                    pPreviousStandardPage->GetLowerBorder() );
2114
169k
        pStandardPage->SetOrientation( pPreviousStandardPage->GetOrientation() );
2115
169k
        pStandardPage->SetName(OUString());
2116
2117
        // insert page after current page
2118
169k
        mpDoc->InsertPage(pStandardPage.get(), nStandardPageNum);
2119
2120
169k
        if( !bDuplicate )
2121
169k
        {
2122
            // use MasterPage of the current page
2123
169k
            pStandardPage->TRG_SetMasterPage(pPreviousStandardPage->TRG_GetMasterPage());
2124
169k
            pStandardPage->SetLayoutName( pPreviousStandardPage->GetLayoutName() );
2125
169k
            pStandardPage->SetAutoLayout(AUTOLAYOUT_NONE, true );
2126
169k
        }
2127
2128
169k
        aBckgrnd = rLayerAdmin.GetLayerID(sUNO_LayerName_background);
2129
169k
        aBckgrndObj = rLayerAdmin.GetLayerID(sUNO_LayerName_background_objects);
2130
169k
        aVisibleLayers.Set(aBckgrnd, bIsPageBack);
2131
169k
        aVisibleLayers.Set(aBckgrndObj, bIsPageObj);
2132
169k
        pStandardPage->TRG_SetMasterPageVisibleLayers(aVisibleLayers);
2133
2134
        /**************************************************************
2135
        * notes page
2136
        **************************************************************/
2137
169k
        rtl::Reference<SdPage> pNotesPage;
2138
2139
169k
        if( bDuplicate )
2140
0
            pNotesPage = static_cast<SdPage*>( pPreviousNotesPage->CloneSdrPage(*mpDoc).get() );
2141
169k
        else
2142
169k
            pNotesPage = mpDoc->AllocSdPage(false);
2143
2144
169k
        pNotesPage->SetSize( pPreviousNotesPage->GetSize() );
2145
169k
        pNotesPage->SetBorder( pPreviousNotesPage->GetLeftBorder(),
2146
169k
                                pPreviousNotesPage->GetUpperBorder(),
2147
169k
                                pPreviousNotesPage->GetRightBorder(),
2148
169k
                                pPreviousNotesPage->GetLowerBorder() );
2149
169k
        pNotesPage->SetOrientation( pPreviousNotesPage->GetOrientation() );
2150
169k
        pNotesPage->SetName(OUString());
2151
169k
        pNotesPage->SetPageKind(PageKind::Notes);
2152
2153
        // insert page after current page
2154
169k
        mpDoc->InsertPage(pNotesPage.get(), nNotesPageNum);
2155
2156
169k
        if( !bDuplicate )
2157
169k
        {
2158
            // use MasterPage of the current page
2159
169k
            pNotesPage->TRG_SetMasterPage(pPreviousNotesPage->TRG_GetMasterPage());
2160
169k
            pNotesPage->SetLayoutName( pPreviousNotesPage->GetLayoutName() );
2161
169k
            pNotesPage->SetAutoLayout(AUTOLAYOUT_NOTES, true );
2162
169k
        }
2163
169k
    }
2164
2165
169k
    SetModified();
2166
2167
169k
    return pStandardPage.get();
2168
169k
}
2169
2170
void SdXImpressDocument::SetModified() noexcept
2171
1.62M
{
2172
1.62M
    if( mpDoc )
2173
1.62M
        mpDoc->SetChanged();
2174
1.62M
}
2175
2176
// XModel
2177
void SAL_CALL SdXImpressDocument::lockControllers(  )
2178
21.0k
{
2179
21.0k
    ::SolarMutexGuard aGuard;
2180
2181
21.0k
    if( nullptr == mpDoc )
2182
0
        throw lang::DisposedException();
2183
2184
21.0k
    mpDoc->setLock(true);
2185
21.0k
}
2186
2187
void SAL_CALL SdXImpressDocument::unlockControllers(  )
2188
21.0k
{
2189
21.0k
    ::SolarMutexGuard aGuard;
2190
2191
21.0k
    if( nullptr == mpDoc )
2192
0
        throw lang::DisposedException();
2193
2194
21.0k
    if( mpDoc->isLocked() )
2195
21.0k
    {
2196
21.0k
        mpDoc->setLock(false);
2197
21.0k
    }
2198
21.0k
}
2199
2200
sal_Bool SAL_CALL SdXImpressDocument::hasControllersLocked(  )
2201
18.3k
{
2202
18.3k
    ::SolarMutexGuard aGuard;
2203
2204
18.3k
    if( nullptr == mpDoc )
2205
0
        throw lang::DisposedException();
2206
2207
18.3k
    return mpDoc->isLocked();
2208
18.3k
}
2209
2210
uno::Reference < container::XIndexAccess > SAL_CALL SdXImpressDocument::getViewData()
2211
24
{
2212
24
    ::SolarMutexGuard aGuard;
2213
2214
24
    if( nullptr == mpDoc )
2215
0
        throw lang::DisposedException();
2216
2217
24
    uno::Reference < container::XIndexAccess > xRet( SfxBaseModel::getViewData() );
2218
2219
24
    if( !xRet.is() )
2220
24
    {
2221
24
        const std::vector<std::unique_ptr<sd::FrameView>> &rList = mpDoc->GetFrameViewList();
2222
2223
24
        if( !rList.empty() )
2224
0
        {
2225
0
            xRet = new comphelper::IndexedPropertyValuesContainer();
2226
2227
0
            uno::Reference < container::XIndexContainer > xCont( xRet, uno::UNO_QUERY );
2228
0
            DBG_ASSERT( xCont.is(), "SdXImpressDocument::getViewData() failed for OLE object" );
2229
0
            if( xCont.is() )
2230
0
            {
2231
0
                for( sal_uInt32 i = 0, n = rList.size(); i < n; i++ )
2232
0
                {
2233
0
                    ::sd::FrameView* pFrameView = rList[ i ].get();
2234
2235
0
                    uno::Sequence< beans::PropertyValue > aSeq;
2236
0
                    pFrameView->WriteUserDataSequence( aSeq );
2237
0
                    xCont->insertByIndex( i, uno::Any( aSeq ) );
2238
0
                }
2239
0
            }
2240
0
        }
2241
24
    }
2242
2243
24
    return xRet;
2244
24
}
2245
2246
void SAL_CALL SdXImpressDocument::setViewData( const uno::Reference < container::XIndexAccess >& xData )
2247
767
{
2248
767
    ::SolarMutexGuard aGuard;
2249
2250
767
    if( nullptr == mpDoc )
2251
0
        throw lang::DisposedException();
2252
2253
767
    SfxBaseModel::setViewData( xData );
2254
767
    if( !(mpDocShell && (mpDocShell->GetCreateMode() == SfxObjectCreateMode::EMBEDDED) && xData.is()) )
2255
24
        return;
2256
2257
743
    const sal_Int32 nCount = xData->getCount();
2258
2259
743
    std::vector<std::unique_ptr<sd::FrameView>> &rViews = mpDoc->GetFrameViewList();
2260
2261
743
    rViews.clear();
2262
2263
743
    uno::Sequence< beans::PropertyValue > aSeq;
2264
1.49k
    for( sal_Int32 nIndex = 0; nIndex < nCount; nIndex++ )
2265
748
    {
2266
748
        if( xData->getByIndex( nIndex ) >>= aSeq )
2267
748
        {
2268
748
            std::unique_ptr<::sd::FrameView> pFrameView(new ::sd::FrameView( mpDoc ));
2269
748
            pFrameView->ReadUserDataSequence( aSeq );
2270
748
            rViews.push_back( std::move(pFrameView) );
2271
748
        }
2272
748
    }
2273
743
}
2274
2275
// XDrawPageDuplicator
2276
uno::Reference< drawing::XDrawPage > SAL_CALL SdXImpressDocument::duplicate( const uno::Reference< drawing::XDrawPage >& xPage )
2277
0
{
2278
0
    ::SolarMutexGuard aGuard;
2279
2280
0
    if( nullptr == mpDoc )
2281
0
        throw lang::DisposedException();
2282
2283
    // get pPage from xPage and determine the Id (nPos ) afterwards
2284
0
    SvxDrawPage* pSvxPage = comphelper::getFromUnoTunnel<SvxDrawPage>( xPage );
2285
0
    if( pSvxPage )
2286
0
    {
2287
0
        SdPage* pPage = static_cast<SdPage*>( pSvxPage->GetSdrPage() );
2288
0
        sal_uInt16 nPos = pPage->GetPageNum();
2289
0
        nPos = ( nPos - 1 ) / 2;
2290
0
        pPage = InsertSdPage( nPos, true );
2291
0
        if( pPage )
2292
0
        {
2293
0
            uno::Reference< drawing::XDrawPage > xDrawPage( pPage->getUnoPage(), uno::UNO_QUERY );
2294
0
            return xDrawPage;
2295
0
        }
2296
0
    }
2297
2298
0
    uno::Reference< drawing::XDrawPage > xDrawPage;
2299
0
    return xDrawPage;
2300
0
}
2301
2302
// XDrawPagesSupplier
2303
uno::Reference< drawing::XDrawPages > SAL_CALL SdXImpressDocument::getDrawPages()
2304
27.4k
{
2305
27.4k
    ::SolarMutexGuard aGuard;
2306
2307
27.4k
    return getSdDrawPages();
2308
27.4k
}
2309
2310
rtl::Reference< SdDrawPagesAccess > SdXImpressDocument::getSdDrawPages()
2311
27.4k
{
2312
27.4k
    if( nullptr == mpDoc )
2313
0
        throw lang::DisposedException();
2314
2315
27.4k
    rtl::Reference< SdDrawPagesAccess > xDrawPages( mxDrawPagesAccess );
2316
2317
27.4k
    if( !xDrawPages.is() )
2318
27.4k
    {
2319
27.4k
        initializeDocument();
2320
27.4k
        xDrawPages = new SdDrawPagesAccess(*this);
2321
27.4k
        mxDrawPagesAccess = xDrawPages.get();
2322
27.4k
    }
2323
2324
27.4k
    return xDrawPages;
2325
27.4k
}
2326
2327
// XMasterPagesSupplier
2328
uno::Reference< drawing::XDrawPages > SAL_CALL SdXImpressDocument::getMasterPages()
2329
18.3k
{
2330
18.3k
    ::SolarMutexGuard aGuard;
2331
2332
18.3k
    if( nullptr == mpDoc )
2333
0
        throw lang::DisposedException();
2334
2335
18.3k
    rtl::Reference< SdMasterPagesAccess > xMasterPages( mxMasterPagesAccess );
2336
2337
18.3k
    if( !xMasterPages.is() )
2338
18.3k
    {
2339
18.3k
        if ( !hasControllersLocked() )
2340
16.1k
            initializeDocument();
2341
18.3k
        xMasterPages = new SdMasterPagesAccess(*this);
2342
18.3k
        mxMasterPagesAccess = xMasterPages.get();
2343
18.3k
    }
2344
2345
18.3k
    return xMasterPages;
2346
18.3k
}
2347
2348
// XLayerManagerSupplier
2349
uno::Reference< container::XNameAccess > SAL_CALL SdXImpressDocument::getLayerManager(  )
2350
320
{
2351
320
    ::SolarMutexGuard aGuard;
2352
2353
320
    if( nullptr == mpDoc )
2354
0
        throw lang::DisposedException();
2355
2356
320
    rtl::Reference< SdLayerManager >  xLayerManager( mxLayerManager );
2357
2358
320
    if( !xLayerManager.is() )
2359
320
    {
2360
320
        xLayerManager = new SdLayerManager(*this);
2361
320
        mxLayerManager = xLayerManager.get();
2362
320
    }
2363
2364
320
    return xLayerManager;
2365
320
}
2366
2367
// XCustomPresentationSupplier
2368
uno::Reference< container::XNameContainer > SAL_CALL SdXImpressDocument::getCustomPresentations()
2369
2
{
2370
2
    ::SolarMutexGuard aGuard;
2371
2372
2
    if( nullptr == mpDoc )
2373
0
        throw lang::DisposedException();
2374
2375
2
    rtl::Reference< SdXCustomPresentationAccess >  xCustomPres( mxCustomPresentationAccess );
2376
2377
2
    if( !xCustomPres.is() )
2378
2
    {
2379
2
        xCustomPres = new SdXCustomPresentationAccess(*this);
2380
2
        mxCustomPresentationAccess = xCustomPres.get();
2381
2
    }
2382
2383
2
    return xCustomPres;
2384
2
}
2385
2386
// XPresentationSupplier
2387
uno::Reference< presentation::XPresentation > SAL_CALL SdXImpressDocument::getPresentation()
2388
718
{
2389
718
    ::SolarMutexGuard aGuard;
2390
2391
718
    if( nullptr == mpDoc )
2392
0
        throw lang::DisposedException();
2393
2394
718
    return mpDoc->getPresentation();
2395
718
}
2396
2397
// XHandoutMasterSupplier
2398
uno::Reference< drawing::XDrawPage > SAL_CALL SdXImpressDocument::getHandoutMasterPage()
2399
289
{
2400
289
    ::SolarMutexGuard aGuard;
2401
2402
289
    if( nullptr == mpDoc )
2403
0
        throw lang::DisposedException();
2404
2405
289
    uno::Reference< drawing::XDrawPage > xPage;
2406
2407
289
    initializeDocument();
2408
289
    SdPage* pPage = mpDoc->GetMasterSdPage(0, PageKind::Handout);
2409
289
    if (pPage)
2410
289
        xPage.set(pPage->getUnoPage(), uno::UNO_QUERY);
2411
289
    return xPage;
2412
289
}
2413
2414
// XMultiServiceFactory ( SvxFmMSFactory )
2415
2416
css::uno::Reference<css::uno::XInterface> SdXImpressDocument::create(
2417
    OUString const & aServiceSpecifier, OUString const & referer)
2418
113k
{
2419
113k
    ::SolarMutexGuard aGuard;
2420
2421
113k
    if( nullptr == mpDoc )
2422
0
        throw lang::DisposedException();
2423
2424
113k
    if( aServiceSpecifier == "com.sun.star.drawing.DashTable" )
2425
17
    {
2426
17
        if( !mxDashTable.is() )
2427
17
            mxDashTable = SvxUnoDashTable_createInstance( mpDoc );
2428
2429
17
        return mxDashTable;
2430
17
    }
2431
113k
    if( aServiceSpecifier == "com.sun.star.drawing.GradientTable" )
2432
114
    {
2433
114
        if( !mxGradientTable.is() )
2434
114
            mxGradientTable = SvxUnoGradientTable_createInstance( mpDoc );
2435
2436
114
        return mxGradientTable;
2437
114
    }
2438
113k
    if( aServiceSpecifier == "com.sun.star.drawing.HatchTable" )
2439
17
    {
2440
17
        if( !mxHatchTable.is() )
2441
17
            mxHatchTable = SvxUnoHatchTable_createInstance( mpDoc );
2442
2443
17
        return mxHatchTable;
2444
17
    }
2445
113k
    if( aServiceSpecifier == "com.sun.star.drawing.BitmapTable" )
2446
29
    {
2447
29
        if( !mxBitmapTable.is() )
2448
29
            mxBitmapTable = SvxUnoBitmapTable_createInstance( mpDoc );
2449
2450
29
        return mxBitmapTable;
2451
29
    }
2452
113k
    if( aServiceSpecifier == "com.sun.star.drawing.TransparencyGradientTable" )
2453
25
    {
2454
25
        if( !mxTransGradientTable.is() )
2455
25
            mxTransGradientTable = SvxUnoTransGradientTable_createInstance( mpDoc );
2456
2457
25
        return mxTransGradientTable;
2458
25
    }
2459
113k
    if( aServiceSpecifier == "com.sun.star.drawing.MarkerTable" )
2460
910
    {
2461
910
        if( !mxMarkerTable.is() )
2462
910
            mxMarkerTable = SvxUnoMarkerTable_createInstance( mpDoc );
2463
2464
910
        return mxMarkerTable;
2465
910
    }
2466
112k
    if( aServiceSpecifier == "com.sun.star.text.NumberingRules" )
2467
746
    {
2468
746
        return uno::Reference< uno::XInterface >( SvxCreateNumRule( mpDoc ), uno::UNO_QUERY );
2469
746
    }
2470
111k
    if( aServiceSpecifier == "com.sun.star.drawing.Background" )
2471
3.76k
    {
2472
3.76k
        return uno::Reference<uno::XInterface>(cppu::getXWeak(new SdUnoPageBackground(mpDoc)));
2473
3.76k
    }
2474
2475
107k
    if( aServiceSpecifier == "com.sun.star.drawing.Defaults" )
2476
303
    {
2477
303
        if( !mxDrawingPool.is() )
2478
300
            mxDrawingPool = SdUnoCreatePool( mpDoc );
2479
2480
303
        return mxDrawingPool;
2481
2482
303
    }
2483
2484
107k
    if ( aServiceSpecifier == sUNO_Service_ImageMapRectangleObject )
2485
0
    {
2486
0
        return SvUnoImageMapRectangleObject_createInstance( ImplGetSupportedMacroItems() );
2487
0
    }
2488
2489
107k
    if ( aServiceSpecifier == sUNO_Service_ImageMapCircleObject )
2490
0
    {
2491
0
        return SvUnoImageMapCircleObject_createInstance( ImplGetSupportedMacroItems() );
2492
0
    }
2493
2494
107k
    if ( aServiceSpecifier == sUNO_Service_ImageMapPolygonObject )
2495
0
    {
2496
0
        return SvUnoImageMapPolygonObject_createInstance( ImplGetSupportedMacroItems() );
2497
0
    }
2498
2499
107k
    if( aServiceSpecifier == "com.sun.star.document.Settings" ||
2500
106k
        ( !mbImpressDoc && ( aServiceSpecifier == "com.sun.star.drawing.DocumentSettings" ) ) ||
2501
106k
        (  mbImpressDoc && ( aServiceSpecifier == "com.sun.star.presentation.DocumentSettings" ) ) )
2502
1.35k
    {
2503
1.35k
        return sd::DocumentSettings_createInstance( this );
2504
1.35k
    }
2505
2506
106k
    if( aServiceSpecifier == "com.sun.star.text.TextField.DateTime" ||
2507
104k
        aServiceSpecifier == "com.sun.star.text.textfield.DateTime" )
2508
1.83k
    {
2509
1.83k
        return cppu::getXWeak(new SvxUnoTextField(text::textfield::Type::DATE));
2510
1.83k
    }
2511
2512
104k
    if( aServiceSpecifier == "com.sun.star.presentation.TextField.Header" ||
2513
103k
        aServiceSpecifier == "com.sun.star.presentation.textfield.Header" )
2514
270
    {
2515
270
        return cppu::getXWeak(new SvxUnoTextField(text::textfield::Type::PRESENTATION_HEADER));
2516
270
    }
2517
2518
103k
    if( aServiceSpecifier == "com.sun.star.presentation.TextField.Footer" ||
2519
99.5k
        aServiceSpecifier == "com.sun.star.presentation.textfield.Footer" )
2520
4.42k
    {
2521
4.42k
        return cppu::getXWeak(new SvxUnoTextField(text::textfield::Type::PRESENTATION_FOOTER));
2522
4.42k
    }
2523
2524
99.5k
    if( aServiceSpecifier == "com.sun.star.presentation.TextField.DateTime" ||
2525
95.0k
        aServiceSpecifier == "com.sun.star.presentation.textfield.DateTime" )
2526
4.44k
    {
2527
4.44k
        return cppu::getXWeak(new SvxUnoTextField(text::textfield::Type::PRESENTATION_DATE_TIME));
2528
4.44k
    }
2529
2530
95.0k
    if( aServiceSpecifier == "com.sun.star.text.TextField.PageName" ||
2531
95.0k
        aServiceSpecifier == "com.sun.star.text.textfield.PageName" )
2532
0
    {
2533
0
        return cppu::getXWeak(new SvxUnoTextField(text::textfield::Type::PAGE_NAME));
2534
0
    }
2535
2536
95.0k
    if (aServiceSpecifier == "com.sun.star.text.TextField.DocInfo.Custom" ||
2537
95.0k
        aServiceSpecifier == "com.sun.star.text.textfield.DocInfo.Custom")
2538
0
    {
2539
0
        return cppu::getXWeak(new SvxUnoTextField(text::textfield::Type::DOCINFO_CUSTOM));
2540
0
    }
2541
2542
95.0k
    if( aServiceSpecifier == "com.sun.star.xml.NamespaceMap" )
2543
24
    {
2544
24
        static const sal_uInt16 aWhichIds[] = { SDRATTR_XMLATTRIBUTES, EE_CHAR_XMLATTRIBS, EE_PARA_XMLATTRIBS, 0 };
2545
2546
24
        return svx::NamespaceMap_createInstance( aWhichIds, &mpDoc->GetItemPool() );
2547
24
    }
2548
2549
    // Support creation of GraphicStorageHandler and EmbeddedObjectResolver
2550
95.0k
    if (aServiceSpecifier == "com.sun.star.document.ExportGraphicStorageHandler")
2551
0
    {
2552
0
        return cppu::getXWeak(new SvXMLGraphicHelper(SvXMLGraphicHelperMode::Write));
2553
0
    }
2554
2555
95.0k
    if (aServiceSpecifier == "com.sun.star.document.ImportGraphicStorageHandler")
2556
0
    {
2557
0
        return cppu::getXWeak(new SvXMLGraphicHelper(SvXMLGraphicHelperMode::Read));
2558
0
    }
2559
2560
95.0k
    if( aServiceSpecifier == "com.sun.star.document.ExportEmbeddedObjectResolver" )
2561
24
    {
2562
24
        comphelper::IEmbeddedHelper* pPersist = mpDoc->GetPersist();
2563
24
        if( nullptr == pPersist )
2564
0
            throw lang::DisposedException();
2565
2566
24
        return cppu::getXWeak(new SvXMLEmbeddedObjectHelper( *pPersist, SvXMLEmbeddedObjectHelperMode::Write ));
2567
24
    }
2568
2569
95.0k
    if( aServiceSpecifier == "com.sun.star.document.ImportEmbeddedObjectResolver" )
2570
16.1k
    {
2571
16.1k
        comphelper::IEmbeddedHelper* pPersist = mpDoc->GetPersist();
2572
16.1k
        if( nullptr == pPersist )
2573
0
            throw lang::DisposedException();
2574
2575
16.1k
        return cppu::getXWeak(new SvXMLEmbeddedObjectHelper( *pPersist, SvXMLEmbeddedObjectHelperMode::Read ));
2576
16.1k
    }
2577
2578
78.8k
    uno::Reference< uno::XInterface > xRet;
2579
2580
78.8k
    if (std::u16string_view aType; aServiceSpecifier.startsWith("com.sun.star.presentation.", &aType))
2581
39.0k
    {
2582
39.0k
        SdrObjKind nType;
2583
        // create a shape wrapper
2584
39.0k
        if( o3tl::starts_with(aType, u"TitleTextShape" ) )
2585
8.27k
        {
2586
8.27k
            nType = SdrObjKind::Text;
2587
8.27k
        }
2588
30.7k
        else if( o3tl::starts_with(aType, u"OutlinerShape" ) )
2589
14.1k
        {
2590
14.1k
            nType = SdrObjKind::Text;
2591
14.1k
        }
2592
16.5k
        else if( o3tl::starts_with(aType, u"SubtitleShape" ) )
2593
1.29k
        {
2594
1.29k
            nType = SdrObjKind::Text;
2595
1.29k
        }
2596
15.2k
        else if( o3tl::starts_with(aType, u"GraphicObjectShape" ) )
2597
0
        {
2598
0
            nType = SdrObjKind::Graphic;
2599
0
        }
2600
15.2k
        else if( o3tl::starts_with(aType, u"PageShape" ) )
2601
167
        {
2602
167
            nType = SdrObjKind::Page;
2603
167
        }
2604
15.1k
        else if( o3tl::starts_with(aType, u"OLE2Shape" ) )
2605
0
        {
2606
0
            nType = SdrObjKind::OLE2;
2607
0
        }
2608
15.1k
        else if( o3tl::starts_with(aType, u"ChartShape" ) )
2609
0
        {
2610
0
            nType = SdrObjKind::OLE2;
2611
0
        }
2612
15.1k
        else if( o3tl::starts_with(aType, u"CalcShape" ) )
2613
0
        {
2614
0
            nType = SdrObjKind::OLE2;
2615
0
        }
2616
15.1k
        else if( o3tl::starts_with(aType, u"TableShape" ) )
2617
0
        {
2618
0
            nType = SdrObjKind::Table;
2619
0
        }
2620
15.1k
        else if( o3tl::starts_with(aType, u"OrgChartShape" ) )
2621
0
        {
2622
0
            nType = SdrObjKind::OLE2;
2623
0
        }
2624
15.1k
        else if( o3tl::starts_with(aType, u"NotesShape" ) )
2625
212
        {
2626
212
            nType = SdrObjKind::Text;
2627
212
        }
2628
14.9k
        else if( o3tl::starts_with(aType, u"HandoutShape" ) )
2629
1.28k
        {
2630
1.28k
            nType = SdrObjKind::Page;
2631
1.28k
        }
2632
13.6k
        else if( o3tl::starts_with(aType, u"FooterShape" ) )
2633
4.45k
        {
2634
4.45k
            nType = SdrObjKind::Text;
2635
4.45k
        }
2636
9.18k
        else if( o3tl::starts_with(aType, u"HeaderShape" ) )
2637
252
        {
2638
252
            nType = SdrObjKind::Text;
2639
252
        }
2640
8.92k
        else if( o3tl::starts_with(aType, u"SlideNumberShape" ) )
2641
4.45k
        {
2642
4.45k
            nType = SdrObjKind::Text;
2643
4.45k
        }
2644
4.47k
        else if( o3tl::starts_with(aType, u"DateTimeShape" ) )
2645
4.47k
        {
2646
4.47k
            nType = SdrObjKind::Text;
2647
4.47k
        }
2648
0
        else if( o3tl::starts_with(aType, u"MediaShape" ) )
2649
0
        {
2650
0
            nType = SdrObjKind::Media;
2651
0
        }
2652
0
        else
2653
0
        {
2654
0
            throw lang::ServiceNotRegisteredException();
2655
0
        }
2656
2657
        // create the API wrapper
2658
39.0k
        rtl::Reference<SvxShape> pShape = CreateSvxShapeByTypeAndInventor(nType, SdrInventor::Default, referer);
2659
2660
        // set shape type
2661
39.0k
        if( pShape && !mbClipBoard )
2662
39.0k
            pShape->SetShapeType(aServiceSpecifier);
2663
2664
39.0k
        xRet = cppu::getXWeak(pShape.get());
2665
39.0k
    }
2666
39.8k
    else if ( aServiceSpecifier == "com.sun.star.drawing.TableShape" )
2667
784
    {
2668
784
        rtl::Reference<SvxShape> pShape = CreateSvxShapeByTypeAndInventor( SdrObjKind::Table, SdrInventor::Default, referer );
2669
784
        if( pShape && !mbClipBoard )
2670
784
            pShape->SetShapeType(aServiceSpecifier);
2671
2672
784
        xRet = cppu::getXWeak(pShape.get());
2673
784
    }
2674
39.0k
    else
2675
39.0k
    {
2676
39.0k
        xRet = SvxFmMSFactory::createInstance( aServiceSpecifier );
2677
39.0k
    }
2678
2679
78.8k
    uno::Reference< drawing::XShape > xShape( xRet, uno::UNO_QUERY );
2680
78.8k
    SvxShape* pShape = xShape.is() ? comphelper::getFromUnoTunnel<SvxShape>(xShape) : nullptr;
2681
78.8k
    if (pShape)
2682
58.2k
    {
2683
58.2k
        xRet.clear();
2684
58.2k
        new SdXShape( pShape, this );
2685
58.2k
        xRet = xShape;
2686
58.2k
        xShape.clear();
2687
58.2k
    }
2688
2689
78.8k
    return xRet;
2690
78.8k
}
2691
2692
uno::Reference< uno::XInterface > SAL_CALL SdXImpressDocument::createInstance( const OUString& aServiceSpecifier )
2693
113k
{
2694
113k
    return create(aServiceSpecifier, u""_ustr);
2695
113k
}
2696
2697
css::uno::Reference<css::uno::XInterface>
2698
SdXImpressDocument::createInstanceWithArguments(
2699
    OUString const & ServiceSpecifier,
2700
    css::uno::Sequence<css::uno::Any> const & Arguments)
2701
7
{
2702
7
    OUString arg;
2703
7
    if ((ServiceSpecifier == "com.sun.star.drawing.GraphicObjectShape"
2704
7
         || ServiceSpecifier == "com.sun.star.drawing.AppletShape"
2705
7
         || ServiceSpecifier == "com.sun.star.drawing.FrameShape"
2706
7
         || ServiceSpecifier == "com.sun.star.drawing.OLE2Shape"
2707
0
         || ServiceSpecifier == "com.sun.star.drawing.MediaShape"
2708
0
         || ServiceSpecifier == "com.sun.star.drawing.PluginShape"
2709
0
         || ServiceSpecifier == "com.sun.star.presentation.MediaShape")
2710
7
        && Arguments.getLength() == 1 && (Arguments[0] >>= arg))
2711
7
    {
2712
7
        return create(ServiceSpecifier, arg);
2713
7
    }
2714
0
    return SvxFmMSFactory::createInstanceWithArguments(
2715
0
        ServiceSpecifier, Arguments);
2716
7
}
2717
2718
uno::Sequence< OUString > SAL_CALL SdXImpressDocument::getAvailableServiceNames()
2719
18.4k
{
2720
18.4k
    ::SolarMutexGuard aGuard;
2721
2722
18.4k
    if( nullptr == mpDoc )
2723
0
        throw lang::DisposedException();
2724
2725
18.4k
    const uno::Sequence< OUString > aSNS_ORG( SvxFmMSFactory::getAvailableServiceNames() );
2726
2727
18.4k
    uno::Sequence< OUString > aSNS_Common{ u"com.sun.star.drawing.DashTable"_ustr,
2728
18.4k
                                           u"com.sun.star.drawing.GradientTable"_ustr,
2729
18.4k
                                           u"com.sun.star.drawing.HatchTable"_ustr,
2730
18.4k
                                           u"com.sun.star.drawing.BitmapTable"_ustr,
2731
18.4k
                                           u"com.sun.star.drawing.TransparencyGradientTable"_ustr,
2732
18.4k
                                           u"com.sun.star.drawing.MarkerTable"_ustr,
2733
18.4k
                                           u"com.sun.star.text.NumberingRules"_ustr,
2734
18.4k
                                           u"com.sun.star.drawing.Background"_ustr,
2735
18.4k
                                           u"com.sun.star.document.Settings"_ustr,
2736
18.4k
                                           sUNO_Service_ImageMapRectangleObject,
2737
18.4k
                                           sUNO_Service_ImageMapCircleObject,
2738
18.4k
                                           sUNO_Service_ImageMapPolygonObject,
2739
18.4k
                                           u"com.sun.star.xml.NamespaceMap"_ustr,
2740
2741
                                           // Support creation of GraphicStorageHandler and EmbeddedObjectResolver
2742
18.4k
                                           u"com.sun.star.document.ExportGraphicStorageHandler"_ustr,
2743
18.4k
                                           u"com.sun.star.document.ImportGraphicStorageHandler"_ustr,
2744
18.4k
                                           u"com.sun.star.document.ExportEmbeddedObjectResolver"_ustr,
2745
18.4k
                                           u"com.sun.star.document.ImportEmbeddedObjectResolver"_ustr,
2746
18.4k
                                           u"com.sun.star.drawing.TableShape"_ustr };
2747
2748
18.4k
    uno::Sequence< OUString > aSNS_Specific;
2749
2750
18.4k
    if(mbImpressDoc)
2751
18.4k
        aSNS_Specific = { u"com.sun.star.presentation.TitleTextShape"_ustr,
2752
18.4k
                          u"com.sun.star.presentation.OutlinerShape"_ustr,
2753
18.4k
                          u"com.sun.star.presentation.SubtitleShape"_ustr,
2754
18.4k
                          u"com.sun.star.presentation.GraphicObjectShape"_ustr,
2755
18.4k
                          u"com.sun.star.presentation.ChartShape"_ustr,
2756
18.4k
                          u"com.sun.star.presentation.PageShape"_ustr,
2757
18.4k
                          u"com.sun.star.presentation.OLE2Shape"_ustr,
2758
18.4k
                          u"com.sun.star.presentation.TableShape"_ustr,
2759
18.4k
                          u"com.sun.star.presentation.OrgChartShape"_ustr,
2760
18.4k
                          u"com.sun.star.presentation.NotesShape"_ustr,
2761
18.4k
                          u"com.sun.star.presentation.HandoutShape"_ustr,
2762
18.4k
                          u"com.sun.star.presentation.DocumentSettings"_ustr,
2763
18.4k
                          u"com.sun.star.presentation.FooterShape"_ustr,
2764
18.4k
                          u"com.sun.star.presentation.HeaderShape"_ustr,
2765
18.4k
                          u"com.sun.star.presentation.SlideNumberShape"_ustr,
2766
18.4k
                          u"com.sun.star.presentation.DateTimeShape"_ustr,
2767
18.4k
                          u"com.sun.star.presentation.CalcShape"_ustr,
2768
18.4k
                          u"com.sun.star.presentation.MediaShape"_ustr };
2769
24
    else
2770
24
        aSNS_Specific = { u"com.sun.star.drawing.DocumentSettings"_ustr };
2771
2772
18.4k
    return comphelper::concatSequences( aSNS_ORG, aSNS_Common, aSNS_Specific );
2773
18.4k
}
2774
2775
// lang::XServiceInfo
2776
OUString SAL_CALL SdXImpressDocument::getImplementationName()
2777
0
{
2778
0
    return u"SdXImpressDocument"_ustr;
2779
    /* // Matching the .component information:
2780
       return mbImpressDoc
2781
           ? OUString("com.sun.star.comp.Draw.PresentationDocument")
2782
           : OUString("com.sun.star.comp.Draw.DrawingDocument");
2783
    */
2784
0
}
2785
2786
sal_Bool SAL_CALL SdXImpressDocument::supportsService( const OUString& ServiceName )
2787
32.3k
{
2788
32.3k
    return cppu::supportsService(this, ServiceName);
2789
32.3k
}
2790
2791
uno::Sequence< OUString > SAL_CALL SdXImpressDocument::getSupportedServiceNames()
2792
32.3k
{
2793
32.3k
    ::SolarMutexGuard aGuard;
2794
2795
32.3k
    return { u"com.sun.star.document.OfficeDocument"_ustr,
2796
32.3k
             u"com.sun.star.drawing.GenericDrawingDocument"_ustr,
2797
32.3k
             u"com.sun.star.drawing.DrawingDocumentFactory"_ustr,
2798
32.3k
             mbImpressDoc?u"com.sun.star.presentation.PresentationDocument"_ustr:u"com.sun.star.drawing.DrawingDocument"_ustr };
2799
32.3k
}
2800
2801
// XPropertySet
2802
uno::Reference< beans::XPropertySetInfo > SAL_CALL SdXImpressDocument::getPropertySetInfo(  )
2803
11.4k
{
2804
11.4k
    ::SolarMutexGuard aGuard;
2805
11.4k
    return mpPropSet->getPropertySetInfo();
2806
11.4k
}
2807
2808
void SAL_CALL SdXImpressDocument::setPropertyValue( const OUString& aPropertyName, const uno::Any& aValue )
2809
13.1k
{
2810
13.1k
    ::SolarMutexGuard aGuard;
2811
2812
13.1k
    if( nullptr == mpDoc )
2813
0
        throw lang::DisposedException();
2814
2815
13.1k
    const SfxItemPropertyMapEntry* pEntry = mpPropSet->getPropertyMapEntry(aPropertyName);
2816
2817
13.1k
    switch( pEntry ? pEntry->nWID : -1 )
2818
13.1k
    {
2819
0
        case WID_MODEL_LANGUAGE:
2820
0
        {
2821
0
            lang::Locale aLocale;
2822
0
            if(!(aValue >>= aLocale))
2823
0
                throw lang::IllegalArgumentException();
2824
2825
0
            mpDoc->SetLanguage( LanguageTag::convertToLanguageType(aLocale), EE_CHAR_LANGUAGE );
2826
0
            break;
2827
0
        }
2828
0
        case WID_MODEL_TABSTOP:
2829
0
        {
2830
0
            sal_Int32 nValue = 0;
2831
0
            if(!(aValue >>= nValue) || nValue < 0 )
2832
0
                throw lang::IllegalArgumentException();
2833
2834
0
            mpDoc->SetDefaultTabulator(static_cast<sal_uInt16>(nValue));
2835
0
            break;
2836
0
        }
2837
1.65k
        case WID_MODEL_VISAREA:
2838
1.65k
            {
2839
1.65k
                SfxObjectShell* pEmbeddedObj = mpDoc->GetDocSh();
2840
1.65k
                if( !pEmbeddedObj )
2841
0
                    break;
2842
2843
1.65k
                awt::Rectangle aVisArea;
2844
1.65k
                if( !(aValue >>= aVisArea) || (aVisArea.Width < 0) || (aVisArea.Height < 0) )
2845
156
                    throw lang::IllegalArgumentException();
2846
2847
1.50k
                sal_Int32 nRight, nTop;
2848
1.50k
                if (o3tl::checked_add(aVisArea.X, aVisArea.Width, nRight) || o3tl::checked_add(aVisArea.Y, aVisArea.Height, nTop))
2849
1
                    throw lang::IllegalArgumentException();
2850
2851
1.50k
                pEmbeddedObj->SetVisArea(::tools::Rectangle(aVisArea.X, aVisArea.Y, nRight, nTop));
2852
1.50k
            }
2853
0
            break;
2854
0
        case WID_MODEL_CONTFOCUS:
2855
0
            {
2856
0
                bool bFocus = false;
2857
0
                if( !(aValue >>= bFocus ) )
2858
0
                    throw lang::IllegalArgumentException();
2859
0
                mpDoc->SetAutoControlFocus( bFocus );
2860
0
            }
2861
0
            break;
2862
0
        case WID_MODEL_DSGNMODE:
2863
0
            {
2864
0
                bool bMode = false;
2865
0
                if( !(aValue >>= bMode ) )
2866
0
                    throw lang::IllegalArgumentException();
2867
0
                mpDoc->SetOpenInDesignMode( bMode );
2868
0
            }
2869
0
            break;
2870
0
        case WID_MODEL_BUILDID:
2871
0
            aValue >>= maBuildId;
2872
0
            return;
2873
0
        case WID_MODEL_MAPUNIT:
2874
0
        case WID_MODEL_BASICLIBS:
2875
0
        case WID_MODEL_RUNTIMEUID: // is read-only
2876
0
        case WID_MODEL_DIALOGLIBS:
2877
0
        case WID_MODEL_FONTS:
2878
0
            throw beans::PropertyVetoException();
2879
11.4k
        case WID_MODEL_INTEROPGRABBAG:
2880
11.4k
            setGrabBagItem(aValue);
2881
11.4k
            break;
2882
0
        case WID_MODEL_THEME:
2883
0
            getSdrModelFromUnoModel().setTheme(model::Theme::FromAny(aValue));
2884
0
            break;
2885
0
        default:
2886
0
            throw beans::UnknownPropertyException( aPropertyName, static_cast<cppu::OWeakObject*>(this));
2887
13.1k
    }
2888
2889
12.9k
    SetModified();
2890
12.9k
}
2891
2892
uno::Any SAL_CALL SdXImpressDocument::getPropertyValue( const OUString& PropertyName )
2893
11.9k
{
2894
11.9k
    ::SolarMutexGuard aGuard;
2895
2896
11.9k
    uno::Any aAny;
2897
11.9k
    if( nullptr == mpDoc )
2898
0
        throw lang::DisposedException();
2899
2900
11.9k
    const SfxItemPropertyMapEntry* pEntry = mpPropSet->getPropertyMapEntry(PropertyName);
2901
2902
11.9k
    switch( pEntry ? pEntry->nWID : -1 )
2903
11.9k
    {
2904
0
        case WID_MODEL_LANGUAGE:
2905
0
        {
2906
0
            LanguageType eLang = mpDoc->GetLanguage( EE_CHAR_LANGUAGE );
2907
0
            aAny <<= LanguageTag::convertToLocale( eLang);
2908
0
            break;
2909
0
        }
2910
0
        case WID_MODEL_TABSTOP:
2911
0
            aAny <<= static_cast<sal_Int32>(mpDoc->GetDefaultTabulator());
2912
0
            break;
2913
24
        case WID_MODEL_VISAREA:
2914
24
            {
2915
24
                SfxObjectShell* pEmbeddedObj = mpDoc->GetDocSh();
2916
24
                if( !pEmbeddedObj )
2917
0
                    break;
2918
2919
24
                const ::tools::Rectangle& aRect = pEmbeddedObj->GetVisArea();
2920
24
                awt::Rectangle aVisArea( aRect.Left(), aRect.Top(), aRect.getOpenWidth(), aRect.getOpenHeight() );
2921
24
                aAny <<= aVisArea;
2922
24
            }
2923
0
            break;
2924
0
        case WID_MODEL_MAPUNIT:
2925
0
            {
2926
0
                SfxObjectShell* pEmbeddedObj = mpDoc->GetDocSh();
2927
0
                if( !pEmbeddedObj )
2928
0
                    break;
2929
2930
0
                sal_Int16 nMeasureUnit = 0;
2931
0
                SvxMapUnitToMeasureUnit( pEmbeddedObj->GetMapUnit(), nMeasureUnit );
2932
0
                aAny <<= nMeasureUnit;
2933
0
        }
2934
0
        break;
2935
0
        case WID_MODEL_FORBCHARS:
2936
0
        {
2937
0
            aAny <<= getForbiddenCharsTable();
2938
0
        }
2939
0
        break;
2940
0
        case WID_MODEL_CONTFOCUS:
2941
0
            aAny <<= mpDoc->GetAutoControlFocus();
2942
0
            break;
2943
0
        case WID_MODEL_DSGNMODE:
2944
0
            aAny <<= mpDoc->GetOpenInDesignMode();
2945
0
            break;
2946
398
        case WID_MODEL_BASICLIBS:
2947
398
            aAny <<= mpDocShell->GetBasicContainer();
2948
398
            break;
2949
0
        case WID_MODEL_DIALOGLIBS:
2950
0
            aAny <<= mpDocShell->GetDialogContainer();
2951
0
            break;
2952
0
        case WID_MODEL_RUNTIMEUID:
2953
0
            aAny <<= getRuntimeUID();
2954
0
            break;
2955
0
        case WID_MODEL_BUILDID:
2956
0
            return uno::Any( maBuildId );
2957
0
        case WID_MODEL_HASVALIDSIGNATURES:
2958
0
            aAny <<= hasValidSignatures();
2959
0
            break;
2960
0
        case WID_MODEL_ALLOWLINKUPDATE:
2961
0
        {
2962
0
            comphelper::EmbeddedObjectContainer& rEmbeddedObjectContainer = mpDocShell->getEmbeddedObjectContainer();
2963
0
            aAny <<= rEmbeddedObjectContainer.getUserAllowsLinkUpdate();
2964
0
            break;
2965
0
        }
2966
51
        case WID_MODEL_FONTS:
2967
51
            {
2968
51
                uno::Sequence<uno::Any> aSeq;
2969
51
                int nSeqIndex = 0;
2970
2971
51
                sal_uInt16 const aWhichIds[] { EE_CHAR_FONTINFO, EE_CHAR_FONTINFO_CJK,
2972
51
                                               EE_CHAR_FONTINFO_CTL };
2973
2974
51
                const SfxItemPool& rPool = mpDoc->GetPool();
2975
2976
51
                for(sal_uInt16 nWhichId : aWhichIds)
2977
153
                {
2978
153
                    ItemSurrogates aSurrogates = rPool.GetItemSurrogates(nWhichId);
2979
153
                    const sal_uInt32 nItems(aSurrogates.size());
2980
2981
153
                    aSeq.realloc( aSeq.getLength() + nItems*5 + 5 );
2982
153
                    auto pSeq = aSeq.getArray();
2983
2984
153
                    for (const SfxPoolItem* pItem : aSurrogates)
2985
333
                    {
2986
333
                        const SvxFontItem *pFont = static_cast<const SvxFontItem *>(pItem);
2987
2988
333
                        pSeq[nSeqIndex++] <<= pFont->GetFamilyName();
2989
333
                        pSeq[nSeqIndex++] <<= pFont->GetStyleName();
2990
333
                        pSeq[nSeqIndex++] <<= sal_Int16(pFont->GetFamily());
2991
333
                        pSeq[nSeqIndex++] <<= sal_Int16(pFont->GetPitch());
2992
333
                        pSeq[nSeqIndex++] <<= sal_Int16(pFont->GetCharSet());
2993
333
                    }
2994
2995
153
                    const SvxFontItem& rFont = static_cast<const SvxFontItem&>(rPool.GetUserOrPoolDefaultItem( nWhichId ));
2996
2997
153
                    pSeq[nSeqIndex++] <<= rFont.GetFamilyName();
2998
153
                    pSeq[nSeqIndex++] <<= rFont.GetStyleName();
2999
153
                    pSeq[nSeqIndex++] <<= sal_Int16(rFont.GetFamily());
3000
153
                    pSeq[nSeqIndex++] <<= sal_Int16(rFont.GetPitch());
3001
153
                    pSeq[nSeqIndex++] <<= sal_Int16(rFont.GetCharSet());
3002
3003
153
                }
3004
3005
51
                aAny <<= aSeq;
3006
51
                break;
3007
0
            }
3008
11.4k
        case WID_MODEL_INTEROPGRABBAG:
3009
11.4k
            getGrabBagItem(aAny);
3010
11.4k
            break;
3011
0
        case WID_MODEL_THEME:
3012
0
            if (auto const& pTheme = getSdrModelFromUnoModel().getTheme())
3013
0
                pTheme->ToAny(aAny);
3014
0
            break;
3015
17
        default:
3016
17
            throw beans::UnknownPropertyException( PropertyName, static_cast<cppu::OWeakObject*>(this));
3017
11.9k
    }
3018
3019
11.9k
    return aAny;
3020
11.9k
}
3021
3022
0
void SAL_CALL SdXImpressDocument::addPropertyChangeListener( const OUString& , const uno::Reference< beans::XPropertyChangeListener >&  ) {}
3023
0
void SAL_CALL SdXImpressDocument::removePropertyChangeListener( const OUString& , const uno::Reference< beans::XPropertyChangeListener >&  ) {}
3024
0
void SAL_CALL SdXImpressDocument::addVetoableChangeListener( const OUString& , const uno::Reference< beans::XVetoableChangeListener >&  ) {}
3025
0
void SAL_CALL SdXImpressDocument::removeVetoableChangeListener( const OUString& , const uno::Reference< beans::XVetoableChangeListener >&  ) {}
3026
3027
// XLinkTargetSupplier
3028
uno::Reference< container::XNameAccess > SAL_CALL SdXImpressDocument::getLinks()
3029
0
{
3030
0
    ::SolarMutexGuard aGuard;
3031
3032
0
    if( nullptr == mpDoc )
3033
0
        throw lang::DisposedException();
3034
3035
0
    rtl::Reference< SdDocLinkTargets > xLinks( mxLinks );
3036
0
    if( !xLinks.is() )
3037
0
    {
3038
0
        xLinks = new SdDocLinkTargets( *this );
3039
0
        mxLinks = xLinks.get();
3040
0
    }
3041
0
    return xLinks;
3042
0
}
3043
3044
// XStyleFamiliesSupplier
3045
uno::Reference< container::XNameAccess > SAL_CALL SdXImpressDocument::getStyleFamilies(  )
3046
93.8k
{
3047
93.8k
    ::SolarMutexGuard aGuard;
3048
3049
93.8k
    if( nullptr == mpDoc )
3050
0
        throw lang::DisposedException();
3051
3052
93.8k
    uno::Reference< container::XNameAccess > xStyles( static_cast< OWeakObject* >( mpDoc->GetStyleSheetPool() ), css::uno::UNO_QUERY );
3053
93.8k
    return xStyles;
3054
93.8k
}
3055
3056
// XAnyCompareFactory
3057
uno::Reference< css::ucb::XAnyCompare > SAL_CALL SdXImpressDocument::createAnyCompareByName( const OUString& )
3058
18.5k
{
3059
18.5k
    return SvxCreateNumRuleCompare();
3060
18.5k
}
3061
3062
// XRenderable
3063
sal_Int32 SAL_CALL SdXImpressDocument::getRendererCount( const uno::Any& rSelection,
3064
                                                         const uno::Sequence< beans::PropertyValue >&  )
3065
0
{
3066
0
    ::SolarMutexGuard aGuard;
3067
0
    sal_Int32   nRet = 0;
3068
3069
0
    if( nullptr == mpDoc )
3070
0
        throw lang::DisposedException();
3071
3072
0
    if (mpDocShell)
3073
0
    {
3074
0
        uno::Reference< frame::XModel > xModel;
3075
3076
0
        rSelection >>= xModel;
3077
3078
0
        if( xModel == mpDocShell->GetModel() )
3079
0
            nRet = mpDoc->GetSdPageCount( PageKind::Standard );
3080
0
        else
3081
0
        {
3082
0
            uno::Reference< drawing::XShapes > xShapes;
3083
3084
0
            rSelection >>= xShapes;
3085
3086
0
            if( xShapes.is() && xShapes->getCount() )
3087
0
                nRet = 1;
3088
0
        }
3089
0
    }
3090
0
    return nRet;
3091
0
}
3092
3093
uno::Sequence< beans::PropertyValue > SAL_CALL SdXImpressDocument::getRenderer( sal_Int32 , const uno::Any& ,
3094
                                                                                const uno::Sequence< beans::PropertyValue >& rxOptions )
3095
0
{
3096
0
    ::SolarMutexGuard aGuard;
3097
3098
0
    if( nullptr == mpDoc )
3099
0
        throw lang::DisposedException();
3100
3101
0
    bool bExportNotesPages = false;
3102
0
    for( const auto& rOption : rxOptions )
3103
0
    {
3104
0
        if ( rOption.Name == "ExportNotesPages" )
3105
0
            rOption.Value >>= bExportNotesPages;
3106
0
    }
3107
0
    uno::Sequence< beans::PropertyValue > aRenderer;
3108
0
    if (mpDocShell)
3109
0
    {
3110
0
        awt::Size aPageSize;
3111
0
        if ( bExportNotesPages )
3112
0
        {
3113
0
            Size aNotesPageSize = mpDoc->GetSdPage( 0, PageKind::Notes )->GetSize();
3114
0
            aPageSize = awt::Size( aNotesPageSize.Width(), aNotesPageSize.Height() );
3115
0
        }
3116
0
        else
3117
0
        {
3118
0
            const ::tools::Rectangle aVisArea( mpDocShell->GetVisArea( embed::Aspects::MSOLE_DOCPRINT ) );
3119
0
            aPageSize = awt::Size( aVisArea.GetWidth(), aVisArea.GetHeight() );
3120
0
        }
3121
0
        aRenderer = { comphelper::makePropertyValue(u"PageSize"_ustr, aPageSize) };
3122
0
    }
3123
0
    return aRenderer;
3124
0
}
3125
3126
namespace {
3127
3128
class ImplRenderPaintProc : public sdr::contact::ViewObjectContactRedirector
3129
{
3130
    const SdrLayerAdmin&    rLayerAdmin;
3131
    SdrPageView*            pSdrPageView;
3132
3133
public:
3134
    bool IsVisible  ( const SdrObject* pObj ) const;
3135
    bool IsPrintable( const SdrObject* pObj ) const;
3136
3137
    ImplRenderPaintProc(const SdrLayerAdmin& rLA, SdrPageView* pView);
3138
3139
    // all default implementations just call the same methods at the original. To do something
3140
    // different, override the method and at least do what the method does.
3141
    virtual void createRedirectedPrimitive2DSequence(
3142
        const sdr::contact::ViewObjectContact& rOriginal,
3143
        const sdr::contact::DisplayInfo& rDisplayInfo,
3144
        drawinglayer::primitive2d::Primitive2DDecompositionVisitor& rVisitor) override;
3145
};
3146
3147
}
3148
3149
ImplRenderPaintProc::ImplRenderPaintProc(const SdrLayerAdmin& rLA, SdrPageView *const pView)
3150
0
    : rLayerAdmin(rLA)
3151
0
    , pSdrPageView(pView)
3152
0
{
3153
0
}
3154
3155
static sal_Int32 ImplPDFGetBookmarkPage( const OUString& rBookmark, SdDrawDocument const & rDoc )
3156
0
{
3157
0
    sal_Int32 nPage = -1;
3158
3159
0
    OUString aBookmark( rBookmark );
3160
3161
0
    if( rBookmark.startsWith("#") )
3162
0
        aBookmark = rBookmark.copy( 1 );
3163
3164
    // is the bookmark a page ?
3165
0
    bool        bIsMasterPage;
3166
0
    sal_uInt16  nPgNum = rDoc.GetPageByName( aBookmark, bIsMasterPage );
3167
3168
0
    if ( nPgNum == SDRPAGE_NOTFOUND )
3169
0
    {
3170
        // is the bookmark an object ?
3171
0
        SdrObject* pObj = rDoc.GetObj( aBookmark );
3172
0
        if (pObj)
3173
0
            nPgNum = pObj->getSdrPageFromSdrObject()->GetPageNum();
3174
0
    }
3175
0
    if ( nPgNum != SDRPAGE_NOTFOUND )
3176
0
        nPage = ( nPgNum - 1 ) / 2;
3177
0
    return nPage;
3178
0
}
3179
3180
static void ImplPDFExportComments( const uno::Reference< drawing::XDrawPage >& xPage, vcl::PDFExtOutDevData& rPDFExtOutDevData )
3181
0
{
3182
0
    try
3183
0
    {
3184
0
        uno::Reference< office::XAnnotationAccess > xAnnotationAccess( xPage, uno::UNO_QUERY_THROW );
3185
0
        uno::Reference< office::XAnnotationEnumeration > xAnnotationEnumeration( xAnnotationAccess->createAnnotationEnumeration() );
3186
3187
0
        while( xAnnotationEnumeration->hasMoreElements() )
3188
0
        {
3189
0
            uno::Reference<office::XAnnotation> xAnnotation(xAnnotationEnumeration->nextElement());
3190
3191
0
            geometry::RealPoint2D aRealPoint2D(xAnnotation->getPosition());
3192
0
            geometry::RealSize2D aRealSize2D(xAnnotation->getSize());
3193
3194
0
            Point aPoint(aRealPoint2D.X * 100.0, aRealPoint2D.Y * 100.0);
3195
0
            Size aSize(aRealSize2D.Width * 100.0, aRealSize2D.Height * 100.0);
3196
3197
0
            Point aPopupPoint(aPoint.X(), aPoint.Y());
3198
0
            Size aPopupSize(aSize.Width() * 10.0, aSize.Height() * 10.0);
3199
3200
0
            uno::Reference<text::XText> xText(xAnnotation->getTextRange());
3201
3202
0
            vcl::pdf::PDFNote aNote;
3203
0
            aNote.maTitle = xAnnotation->getAuthor();
3204
0
            aNote.maContents = xText->getString();
3205
0
            aNote.maModificationDate = xAnnotation->getDateTime();
3206
0
            auto* pAnnotation = dynamic_cast<sd::Annotation*>(xAnnotation.get());
3207
3208
0
            if (pAnnotation && pAnnotation->getCreationInfo().meType != sdr::annotation::AnnotationType::None)
3209
0
            {
3210
0
                sdr::annotation::CreationInfo const& rCreation = pAnnotation->getCreationInfo();
3211
0
                aNote.maPolygons = rCreation.maPolygons;
3212
0
                aNote.maAnnotationColor = rCreation.maColor;
3213
0
                aNote.maInteriorColor = rCreation.maFillColor;
3214
0
                aNote.mfWidth = rCreation.mnWidth;
3215
0
                switch (rCreation.meType)
3216
0
                {
3217
0
                    case sdr::annotation::AnnotationType::Square:
3218
0
                        aNote.meType = vcl::pdf::PDFAnnotationSubType::Square; break;
3219
0
                    case sdr::annotation::AnnotationType::Circle:
3220
0
                        aNote.meType = vcl::pdf::PDFAnnotationSubType::Circle; break;
3221
0
                    case sdr::annotation::AnnotationType::Polygon:
3222
0
                        aNote.meType = vcl::pdf::PDFAnnotationSubType::Polygon; break;
3223
0
                    case sdr::annotation::AnnotationType::Ink:
3224
0
                        aNote.meType = vcl::pdf::PDFAnnotationSubType::Ink; break;
3225
0
                    case sdr::annotation::AnnotationType::Highlight:
3226
0
                        aNote.meType = vcl::pdf::PDFAnnotationSubType::Highlight; break;
3227
0
                    case sdr::annotation::AnnotationType::Line:
3228
0
                        aNote.meType = vcl::pdf::PDFAnnotationSubType::Line; break;
3229
0
                    case sdr::annotation::AnnotationType::FreeText:
3230
0
                        aNote.meType = vcl::pdf::PDFAnnotationSubType::FreeText; break;
3231
0
                    default:
3232
0
                        aNote.meType = vcl::pdf::PDFAnnotationSubType::Text;
3233
0
                        break;
3234
0
                }
3235
0
            }
3236
3237
0
            rPDFExtOutDevData.CreateNote(::tools::Rectangle(aPoint, aSize), aNote,
3238
0
                                         ::tools::Rectangle(aPopupPoint, aPopupSize));
3239
0
        }
3240
0
    }
3241
0
    catch (const uno::Exception&)
3242
0
    {
3243
0
    }
3244
0
}
3245
3246
static void ImplPDFExportShapeInteraction( const uno::Reference< drawing::XShape >& xShape, SdDrawDocument& rDoc, vcl::PDFExtOutDevData& rPDFExtOutDevData )
3247
0
{
3248
0
    if ( xShape->getShapeType() == "com.sun.star.drawing.GroupShape" )
3249
0
    {
3250
0
        uno::Reference< container::XIndexAccess > xIndexAccess( xShape, uno::UNO_QUERY );
3251
0
        if ( xIndexAccess.is() )
3252
0
        {
3253
0
            sal_Int32 i, nCount = xIndexAccess->getCount();
3254
0
            for ( i = 0; i < nCount; i++ )
3255
0
            {
3256
0
                uno::Reference< drawing::XShape > xSubShape( xIndexAccess->getByIndex( i ), uno::UNO_QUERY );
3257
0
                if ( xSubShape.is() )
3258
0
                    ImplPDFExportShapeInteraction( xSubShape, rDoc, rPDFExtOutDevData );
3259
0
            }
3260
0
        }
3261
0
    }
3262
0
    else
3263
0
    {
3264
0
        uno::Reference< beans::XPropertySet > xShapePropSet( xShape, uno::UNO_QUERY );
3265
0
        if( xShapePropSet.is() )
3266
0
        {
3267
0
            Size        aPageSize( rDoc.GetSdPage( 0, PageKind::Standard )->GetSize() );
3268
0
            Point aPoint( 0, 0 );
3269
0
            ::tools::Rectangle   aPageRect( aPoint, aPageSize );
3270
3271
0
            awt::Point  aShapePos( xShape->getPosition() );
3272
0
            awt::Size   aShapeSize( xShape->getSize() );
3273
0
            ::tools::Rectangle   aLinkRect( Point( aShapePos.X, aShapePos.Y ), Size( aShapeSize.Width, aShapeSize.Height ) );
3274
3275
            // Handle linked videos.
3276
0
            if (xShape->getShapeType() == "com.sun.star.drawing.MediaShape" || xShape->getShapeType() == "com.sun.star.presentation.MediaShape")
3277
0
            {
3278
0
                OUString title;
3279
0
                xShapePropSet->getPropertyValue(u"Title"_ustr) >>= title;
3280
0
                OUString description;
3281
0
                xShapePropSet->getPropertyValue(u"Description"_ustr) >>= description;
3282
0
                OUString const altText(title.isEmpty()
3283
0
                    ? description
3284
0
                    : description.isEmpty()
3285
0
                        ? title
3286
0
                        : OUString::Concat(title) + OUString::Concat("\n") + OUString::Concat(description));
3287
3288
0
                OUString aMediaURL;
3289
0
                xShapePropSet->getPropertyValue(u"MediaURL"_ustr) >>= aMediaURL;
3290
0
                if (!aMediaURL.isEmpty())
3291
0
                {
3292
0
                    SdrObject const*const pSdrObj(SdrObject::getSdrObjectFromXShape(xShape));
3293
0
                    OUString const mimeType(xShapePropSet->getPropertyValue(u"MediaMimeType"_ustr).get<OUString>());
3294
0
                    sal_Int32 nScreenId = rPDFExtOutDevData.CreateScreen(aLinkRect, altText, mimeType, rPDFExtOutDevData.GetCurrentPageNumber(), pSdrObj);
3295
0
                    if (aMediaURL.startsWith("vnd.sun.star.Package:"))
3296
0
                    {
3297
0
                        OUString aTempFileURL;
3298
0
                        xShapePropSet->getPropertyValue(u"PrivateTempFileURL"_ustr) >>= aTempFileURL;
3299
0
                        rPDFExtOutDevData.SetScreenStream(nScreenId, aTempFileURL);
3300
0
                    }
3301
0
                    else
3302
0
                        rPDFExtOutDevData.SetScreenURL(nScreenId, aMediaURL);
3303
0
                }
3304
0
            }
3305
3306
0
            presentation::ClickAction eCa;
3307
0
            uno::Any aAny( xShapePropSet->getPropertyValue( u"OnClick"_ustr ) );
3308
0
            if ( aAny >>= eCa )
3309
0
            {
3310
0
                OUString const actionName(SdResId(SdTPAction::GetClickActionSdResId(eCa)));
3311
0
                switch ( eCa )
3312
0
                {
3313
0
                    case presentation::ClickAction_LASTPAGE :
3314
0
                    {
3315
0
                        sal_Int32 nCount = rDoc.GetSdPageCount( PageKind::Standard );
3316
0
                        sal_Int32 nDestId = rPDFExtOutDevData.CreateDest( aPageRect, nCount - 1, vcl::pdf::PDFWriter::DestAreaType::FitRectangle );
3317
0
                        sal_Int32 nLinkId = rPDFExtOutDevData.CreateLink(aLinkRect, actionName);
3318
0
                        rPDFExtOutDevData.SetLinkDest( nLinkId, nDestId );
3319
0
                    }
3320
0
                    break;
3321
0
                    case presentation::ClickAction_FIRSTPAGE :
3322
0
                    {
3323
0
                        sal_Int32 nDestId = rPDFExtOutDevData.CreateDest( aPageRect, 0, vcl::pdf::PDFWriter::DestAreaType::FitRectangle );
3324
0
                        sal_Int32 nLinkId = rPDFExtOutDevData.CreateLink(aLinkRect, actionName);
3325
0
                        rPDFExtOutDevData.SetLinkDest( nLinkId, nDestId );
3326
0
                    }
3327
0
                    break;
3328
0
                    case presentation::ClickAction_PREVPAGE :
3329
0
                    {
3330
0
                        sal_Int32 nDestPage = rPDFExtOutDevData.GetCurrentPageNumber();
3331
0
                        if ( nDestPage )
3332
0
                            nDestPage--;
3333
0
                        sal_Int32 nDestId = rPDFExtOutDevData.CreateDest( aPageRect, nDestPage, vcl::pdf::PDFWriter::DestAreaType::FitRectangle );
3334
0
                        sal_Int32 nLinkId = rPDFExtOutDevData.CreateLink(aLinkRect, actionName);
3335
0
                        rPDFExtOutDevData.SetLinkDest( nLinkId, nDestId );
3336
0
                    }
3337
0
                    break;
3338
0
                    case presentation::ClickAction_NEXTPAGE :
3339
0
                    {
3340
0
                        sal_Int32 nDestPage = rPDFExtOutDevData.GetCurrentPageNumber() + 1;
3341
0
                        sal_Int32 nLastPage = rDoc.GetSdPageCount( PageKind::Standard ) - 1;
3342
0
                        if ( nDestPage > nLastPage )
3343
0
                            nDestPage = nLastPage;
3344
0
                        sal_Int32 nDestId = rPDFExtOutDevData.CreateDest( aPageRect, nDestPage, vcl::pdf::PDFWriter::DestAreaType::FitRectangle );
3345
0
                        sal_Int32 nLinkId = rPDFExtOutDevData.CreateLink(aLinkRect, actionName);
3346
0
                        rPDFExtOutDevData.SetLinkDest( nLinkId, nDestId );
3347
0
                    }
3348
0
                    break;
3349
3350
0
                    case presentation::ClickAction_PROGRAM :
3351
0
                    case presentation::ClickAction_BOOKMARK :
3352
0
                    case presentation::ClickAction_DOCUMENT :
3353
0
                    {
3354
0
                        OUString aBookmark;
3355
0
                        xShapePropSet->getPropertyValue( u"Bookmark"_ustr ) >>= aBookmark;
3356
0
                        if( !aBookmark.isEmpty() )
3357
0
                        {
3358
0
                            switch( eCa )
3359
0
                            {
3360
0
                                case presentation::ClickAction_DOCUMENT :
3361
0
                                case presentation::ClickAction_PROGRAM :
3362
0
                                {
3363
0
                                    sal_Int32 nLinkId = rPDFExtOutDevData.CreateLink(aLinkRect, actionName);
3364
0
                                    rPDFExtOutDevData.SetLinkURL( nLinkId, aBookmark );
3365
0
                                }
3366
0
                                break;
3367
0
                                case presentation::ClickAction_BOOKMARK :
3368
0
                                {
3369
0
                                    sal_Int32 nPage = ImplPDFGetBookmarkPage( aBookmark, rDoc );
3370
0
                                    if ( nPage != -1 )
3371
0
                                    {
3372
0
                                        sal_Int32 nDestId = rPDFExtOutDevData.CreateDest( aPageRect, nPage, vcl::pdf::PDFWriter::DestAreaType::FitRectangle );
3373
0
                                        sal_Int32 nLinkId = rPDFExtOutDevData.CreateLink(aLinkRect, actionName);
3374
0
                                        rPDFExtOutDevData.SetLinkDest( nLinkId, nDestId );
3375
0
                                    }
3376
0
                                }
3377
0
                                break;
3378
0
                                default:
3379
0
                                    break;
3380
0
                            }
3381
0
                        }
3382
0
                    }
3383
0
                    break;
3384
3385
0
                    case presentation::ClickAction_STOPPRESENTATION :
3386
0
                    case presentation::ClickAction_SOUND :
3387
0
                    case presentation::ClickAction_INVISIBLE :
3388
0
                    case presentation::ClickAction_VERB :
3389
0
                    case presentation::ClickAction_VANISH :
3390
0
                    case presentation::ClickAction_MACRO :
3391
0
                    default :
3392
0
                    break;
3393
0
                }
3394
0
            }
3395
0
        }
3396
0
    }
3397
0
}
3398
3399
void ImplRenderPaintProc::createRedirectedPrimitive2DSequence(
3400
    const sdr::contact::ViewObjectContact& rOriginal,
3401
    const sdr::contact::DisplayInfo& rDisplayInfo,
3402
    drawinglayer::primitive2d::Primitive2DDecompositionVisitor& rVisitor)
3403
0
{
3404
0
    SdrObject* pObject = rOriginal.GetViewContact().TryToGetSdrObject();
3405
0
    if(!pObject)
3406
0
    {
3407
        // not an object, maybe a page
3408
0
        sdr::contact::ViewObjectContactRedirector::createRedirectedPrimitive2DSequence(rOriginal, rDisplayInfo, rVisitor);
3409
0
        return;
3410
0
    }
3411
0
    SdrPage* pSdrPage(pObject->getSdrPageFromSdrObject());
3412
0
    if(!pSdrPage)
3413
0
        return;
3414
0
    if(!pSdrPage->checkVisibility(rOriginal, rDisplayInfo, false))
3415
0
        return;
3416
0
    if(!IsVisible(pObject) || !IsPrintable(pObject))
3417
0
        return;
3418
3419
0
    sdr::contact::ViewObjectContactRedirector::createRedirectedPrimitive2DSequence(rOriginal, rDisplayInfo, rVisitor);
3420
0
}
3421
3422
bool ImplRenderPaintProc::IsVisible( const SdrObject* pObj ) const
3423
0
{
3424
0
    bool bVisible = true;
3425
0
    SdrLayerID nLayerId = pObj->GetLayer();
3426
0
    if( pSdrPageView )
3427
0
    {
3428
0
        const SdrLayer* pSdrLayer = rLayerAdmin.GetLayerPerID( nLayerId );
3429
0
        if ( pSdrLayer )
3430
0
        {
3431
0
            const OUString& aLayerName = pSdrLayer->GetName();
3432
0
            bVisible = pSdrPageView->IsLayerVisible( aLayerName );
3433
0
        }
3434
0
    }
3435
0
    return bVisible;
3436
0
}
3437
bool ImplRenderPaintProc::IsPrintable( const SdrObject* pObj ) const
3438
0
{
3439
0
    bool bPrintable = true;
3440
0
    SdrLayerID nLayerId = pObj->GetLayer();
3441
0
    if( pSdrPageView )
3442
0
    {
3443
0
        const SdrLayer* pSdrLayer = rLayerAdmin.GetLayerPerID( nLayerId );
3444
0
        if ( pSdrLayer )
3445
0
        {
3446
0
            const OUString& aLayerName = pSdrLayer->GetName();
3447
0
            bPrintable = pSdrPageView->IsLayerPrintable( aLayerName );
3448
0
        }
3449
0
    }
3450
0
    return bPrintable;
3451
3452
0
}
3453
3454
namespace
3455
{
3456
    sal_Int16 CalcOutputPageNum(vcl::PDFExtOutDevData const * pPDFExtOutDevData, SdDrawDocument const *pDoc, sal_Int16 nPageNumber)
3457
0
    {
3458
        //export all pages, simple one to one case
3459
0
        if (pPDFExtOutDevData && pPDFExtOutDevData->GetIsExportHiddenSlides())
3460
0
            return nPageNumber-1;
3461
        //check all preceding pages, and only count non-hidden ones
3462
0
        sal_Int16 nRet = 0;
3463
0
        for (sal_Int16 i = 0; i < nPageNumber-1; ++i)
3464
0
        {
3465
0
           if (!pDoc->GetSdPage(i, PageKind::Standard)->IsExcluded())
3466
0
                ++nRet;
3467
0
        }
3468
0
        return nRet;
3469
0
    }
3470
}
3471
3472
void SAL_CALL SdXImpressDocument::render( sal_Int32 nRenderer, const uno::Any& rSelection,
3473
                                          const uno::Sequence< beans::PropertyValue >& rxOptions )
3474
0
{
3475
0
    ::SolarMutexGuard aGuard;
3476
3477
0
    if( nullptr == mpDoc )
3478
0
        throw lang::DisposedException();
3479
3480
0
    if (!mpDocShell)
3481
0
        return;
3482
3483
0
    uno::Reference< awt::XDevice >  xRenderDevice;
3484
0
    const sal_Int32                 nPageNumber = nRenderer + 1;
3485
0
    PageKind                        ePageKind = PageKind::Standard;
3486
0
    bool                        bExportNotesPages = false;
3487
3488
0
    for( const auto& rOption : rxOptions )
3489
0
    {
3490
0
        if ( rOption.Name == "RenderDevice" )
3491
0
            rOption.Value >>= xRenderDevice;
3492
0
        else if ( rOption.Name == "ExportNotesPages" )
3493
0
        {
3494
0
            rOption.Value >>= bExportNotesPages;
3495
0
            if ( bExportNotesPages )
3496
0
                ePageKind = PageKind::Notes;
3497
0
        }
3498
0
    }
3499
3500
0
    if( !(xRenderDevice.is() && nPageNumber && ( nPageNumber <= mpDoc->GetSdPageCount( ePageKind ) )) )
3501
0
        return;
3502
3503
0
    VCLXDevice* pDevice = dynamic_cast<VCLXDevice*>( xRenderDevice.get() );
3504
0
    VclPtr< OutputDevice> pOut = pDevice ? pDevice->GetOutputDevice() : VclPtr< OutputDevice >();
3505
3506
0
    if( !pOut )
3507
0
        return;
3508
3509
0
    vcl::PDFExtOutDevData* pPDFExtOutDevData = dynamic_cast<vcl::PDFExtOutDevData* >( pOut->GetExtOutDevData() );
3510
3511
0
    if ( mpDoc->GetSdPage(static_cast<sal_Int16>(nPageNumber)-1, PageKind::Standard)->IsExcluded() &&
3512
0
        !(pPDFExtOutDevData && pPDFExtOutDevData->GetIsExportHiddenSlides()) )
3513
0
        return;
3514
3515
0
    if (pPDFExtOutDevData)
3516
0
    {
3517
0
        css::lang::Locale const docLocale(Application::GetSettings().GetLanguageTag().getLocale());
3518
0
        pPDFExtOutDevData->SetDocumentLocale(docLocale);
3519
0
    }
3520
3521
0
    ::sd::ClientView aView( mpDocShell, pOut );
3522
0
    ::tools::Rectangle aVisArea( Point(), mpDoc->GetSdPage( static_cast<sal_uInt16>(nPageNumber) - 1, ePageKind )->GetSize() );
3523
0
    vcl::Region                       aRegion( aVisArea );
3524
3525
0
    ::sd::ViewShell* pOldViewSh = mpDocShell->GetViewShell();
3526
0
    ::sd::View* pOldSdView = pOldViewSh ? pOldViewSh->GetView() : nullptr;
3527
3528
0
    if  ( pOldSdView )
3529
0
        pOldSdView->SdrEndTextEdit();
3530
3531
0
    aView.SetHlplVisible( false );
3532
0
    aView.SetGridVisible( false );
3533
0
    aView.SetBordVisible( false );
3534
0
    aView.SetPageVisible( false );
3535
0
    aView.SetGlueVisible( false );
3536
3537
0
    pOut->SetMapMode(MapMode(MapUnit::Map100thMM));
3538
0
    pOut->IntersectClipRegion( aVisArea );
3539
3540
0
    uno::Reference< frame::XModel > xModel;
3541
0
    rSelection >>= xModel;
3542
3543
0
    if( xModel == mpDocShell->GetModel() )
3544
0
    {
3545
0
        aView.ShowSdrPage( mpDoc->GetSdPage( static_cast<sal_uInt16>(nPageNumber) - 1, ePageKind ));
3546
0
        SdrPageView* pPV = aView.GetSdrPageView();
3547
3548
0
        if( pOldSdView )
3549
0
        {
3550
0
            SdrPageView* pOldPV = pOldSdView->GetSdrPageView();
3551
0
            if( pPV && pOldPV )
3552
0
            {
3553
0
                pPV->SetVisibleLayers( pOldPV->GetVisibleLayers() );
3554
0
                pPV->SetPrintableLayers( pOldPV->GetPrintableLayers() );
3555
0
            }
3556
0
        }
3557
3558
0
        ImplRenderPaintProc aImplRenderPaintProc( mpDoc->GetLayerAdmin(),
3559
0
            pPV);
3560
3561
        // background color for outliner :o
3562
0
        SdPage* pPage = pPV ? static_cast<SdPage*>(pPV->GetPage()) : nullptr;
3563
0
        if( pPage )
3564
0
        {
3565
0
            SdrOutliner& rOutl = mpDoc->GetDrawOutliner();
3566
0
            bool bScreenDisplay(true);
3567
3568
            // #i75566# printing; suppress AutoColor BackgroundColor generation
3569
            // for visibility reasons by giving GetPageBackgroundColor()
3570
            // the needed hint
3571
            // #i75566# PDF export; suppress AutoColor BackgroundColor generation (see printing)
3572
0
            if (pOut && ((OUTDEV_PRINTER == pOut->GetOutDevType())
3573
0
                    || (OUTDEV_PDF == pOut->GetOutDevType())))
3574
0
                bScreenDisplay = false;
3575
3576
            // #i75566# Name change GetBackgroundColor -> GetPageBackgroundColor and
3577
            // hint value if screen display. Only then the AutoColor mechanisms shall be applied
3578
0
            rOutl.SetBackgroundColor( pPage->GetPageBackgroundColor( pPV, bScreenDisplay ) );
3579
0
        }
3580
3581
        // produce link annots for media shapes before painting them
3582
0
        if ( pPDFExtOutDevData && pPage )
3583
0
        {
3584
0
            try
3585
0
            {
3586
0
                uno::Any aAny;
3587
0
                uno::Reference< drawing::XDrawPage > xPage( uno::Reference< drawing::XDrawPage >::query( pPage->getUnoPage() ) );
3588
0
                if ( xPage.is() )
3589
0
                {
3590
0
                    if ( pPDFExtOutDevData->GetIsExportNotes() )
3591
0
                        ImplPDFExportComments( xPage, *pPDFExtOutDevData );
3592
0
                    uno::Reference< beans::XPropertySet > xPagePropSet( xPage, uno::UNO_QUERY );
3593
0
                    if( xPagePropSet.is() )
3594
0
                    {
3595
                        // exporting object interactions to pdf
3596
3597
                        // if necessary, the master page interactions will be exported first
3598
0
                        bool bIsBackgroundObjectsVisible = false;   // #i39428# IsBackgroundObjectsVisible not available for Draw
3599
0
                        if ( mbImpressDoc && xPagePropSet->getPropertySetInfo()->hasPropertyByName( u"IsBackgroundObjectsVisible"_ustr ) )
3600
0
                            xPagePropSet->getPropertyValue( u"IsBackgroundObjectsVisible"_ustr ) >>= bIsBackgroundObjectsVisible;
3601
0
                        if ( bIsBackgroundObjectsVisible && !pPDFExtOutDevData->GetIsExportNotesPages() )
3602
0
                        {
3603
0
                            uno::Reference< drawing::XMasterPageTarget > xMasterPageTarget( xPage, uno::UNO_QUERY );
3604
0
                            if ( xMasterPageTarget.is() )
3605
0
                            {
3606
0
                                uno::Reference< drawing::XDrawPage > xMasterPage = xMasterPageTarget->getMasterPage();
3607
0
                                if ( xMasterPage.is() )
3608
0
                                {
3609
0
                                    sal_Int32 i, nCount = xMasterPage->getCount();
3610
0
                                    for ( i = 0; i < nCount; i++ )
3611
0
                                    {
3612
0
                                        aAny = xMasterPage->getByIndex( i );
3613
0
                                        uno::Reference< drawing::XShape > xShape;
3614
0
                                        if ( aAny >>= xShape )
3615
0
                                            ImplPDFExportShapeInteraction( xShape, *mpDoc, *pPDFExtOutDevData );
3616
0
                                    }
3617
0
                                }
3618
0
                            }
3619
0
                        }
3620
3621
                        // exporting slide page object interactions
3622
0
                        sal_Int32 i, nCount = xPage->getCount();
3623
0
                        for ( i = 0; i < nCount; i++ )
3624
0
                        {
3625
0
                            aAny = xPage->getByIndex( i );
3626
0
                            uno::Reference< drawing::XShape > xShape;
3627
0
                            if ( aAny >>= xShape )
3628
0
                                ImplPDFExportShapeInteraction( xShape, *mpDoc, *pPDFExtOutDevData );
3629
0
                        }
3630
3631
                        // exporting transition effects to pdf
3632
0
                        if ( mbImpressDoc && !pPDFExtOutDevData->GetIsExportNotesPages() && pPDFExtOutDevData->GetIsExportTransitionEffects() )
3633
0
                        {
3634
0
                            static constexpr OUString sEffect( u"Effect"_ustr );
3635
0
                            static constexpr OUString sSpeed ( u"Speed"_ustr );
3636
0
                            sal_Int32 nTime = 800;
3637
0
                            presentation::AnimationSpeed aAs;
3638
0
                            if ( xPagePropSet->getPropertySetInfo( )->hasPropertyByName( sSpeed ) )
3639
0
                            {
3640
0
                                aAny = xPagePropSet->getPropertyValue( sSpeed );
3641
0
                                if ( aAny >>= aAs )
3642
0
                                {
3643
0
                                    switch( aAs )
3644
0
                                    {
3645
0
                                        case presentation::AnimationSpeed_SLOW : nTime = 1500; break;
3646
0
                                        case presentation::AnimationSpeed_FAST : nTime = 300; break;
3647
0
                                        default:
3648
0
                                        case presentation::AnimationSpeed_MEDIUM : nTime = 800;
3649
0
                                    }
3650
0
                                }
3651
0
                            }
3652
0
                            presentation::FadeEffect eFe;
3653
0
                            vcl::pdf::PDFWriter::PageTransition eType = vcl::pdf::PDFWriter::PageTransition::Regular;
3654
0
                            if ( xPagePropSet->getPropertySetInfo( )->hasPropertyByName( sEffect ) )
3655
0
                            {
3656
0
                                aAny = xPagePropSet->getPropertyValue( sEffect );
3657
0
                                if ( aAny >>= eFe )
3658
0
                                {
3659
0
                                    switch( eFe )
3660
0
                                    {
3661
0
                                        case presentation::FadeEffect_HORIZONTAL_LINES :
3662
0
                                        case presentation::FadeEffect_HORIZONTAL_CHECKERBOARD :
3663
0
                                        case presentation::FadeEffect_HORIZONTAL_STRIPES : eType = vcl::pdf::PDFWriter::PageTransition::BlindsHorizontal; break;
3664
3665
0
                                        case presentation::FadeEffect_VERTICAL_LINES :
3666
0
                                        case presentation::FadeEffect_VERTICAL_CHECKERBOARD :
3667
0
                                        case presentation::FadeEffect_VERTICAL_STRIPES : eType = vcl::pdf::PDFWriter::PageTransition::BlindsVertical; break;
3668
3669
0
                                        case presentation::FadeEffect_UNCOVER_TO_RIGHT :
3670
0
                                        case presentation::FadeEffect_UNCOVER_TO_UPPERRIGHT :
3671
0
                                        case presentation::FadeEffect_ROLL_FROM_LEFT :
3672
0
                                        case presentation::FadeEffect_FADE_FROM_UPPERLEFT :
3673
0
                                        case presentation::FadeEffect_MOVE_FROM_UPPERLEFT :
3674
0
                                        case presentation::FadeEffect_FADE_FROM_LEFT :
3675
0
                                        case presentation::FadeEffect_MOVE_FROM_LEFT : eType = vcl::pdf::PDFWriter::PageTransition::WipeLeftToRight; break;
3676
3677
0
                                        case presentation::FadeEffect_UNCOVER_TO_BOTTOM :
3678
0
                                        case presentation::FadeEffect_UNCOVER_TO_LOWERRIGHT :
3679
0
                                        case presentation::FadeEffect_ROLL_FROM_TOP :
3680
0
                                        case presentation::FadeEffect_FADE_FROM_UPPERRIGHT :
3681
0
                                        case presentation::FadeEffect_MOVE_FROM_UPPERRIGHT :
3682
0
                                        case presentation::FadeEffect_FADE_FROM_TOP :
3683
0
                                        case presentation::FadeEffect_MOVE_FROM_TOP : eType = vcl::pdf::PDFWriter::PageTransition::WipeTopToBottom; break;
3684
3685
0
                                        case presentation::FadeEffect_UNCOVER_TO_LEFT :
3686
0
                                        case presentation::FadeEffect_UNCOVER_TO_LOWERLEFT :
3687
0
                                        case presentation::FadeEffect_ROLL_FROM_RIGHT :
3688
3689
0
                                        case presentation::FadeEffect_FADE_FROM_LOWERRIGHT :
3690
0
                                        case presentation::FadeEffect_MOVE_FROM_LOWERRIGHT :
3691
0
                                        case presentation::FadeEffect_FADE_FROM_RIGHT :
3692
0
                                        case presentation::FadeEffect_MOVE_FROM_RIGHT : eType = vcl::pdf::PDFWriter::PageTransition::WipeRightToLeft; break;
3693
3694
0
                                        case presentation::FadeEffect_UNCOVER_TO_TOP :
3695
0
                                        case presentation::FadeEffect_UNCOVER_TO_UPPERLEFT :
3696
0
                                        case presentation::FadeEffect_ROLL_FROM_BOTTOM :
3697
0
                                        case presentation::FadeEffect_FADE_FROM_LOWERLEFT :
3698
0
                                        case presentation::FadeEffect_MOVE_FROM_LOWERLEFT :
3699
0
                                        case presentation::FadeEffect_FADE_FROM_BOTTOM :
3700
0
                                        case presentation::FadeEffect_MOVE_FROM_BOTTOM : eType = vcl::pdf::PDFWriter::PageTransition::WipeBottomToTop; break;
3701
3702
0
                                        case presentation::FadeEffect_OPEN_VERTICAL : eType = vcl::pdf::PDFWriter::PageTransition::SplitHorizontalInward; break;
3703
0
                                        case presentation::FadeEffect_CLOSE_HORIZONTAL : eType = vcl::pdf::PDFWriter::PageTransition::SplitHorizontalOutward; break;
3704
3705
0
                                        case presentation::FadeEffect_OPEN_HORIZONTAL : eType = vcl::pdf::PDFWriter::PageTransition::SplitVerticalInward; break;
3706
0
                                        case presentation::FadeEffect_CLOSE_VERTICAL : eType = vcl::pdf::PDFWriter::PageTransition::SplitVerticalOutward; break;
3707
3708
0
                                        case presentation::FadeEffect_FADE_TO_CENTER : eType = vcl::pdf::PDFWriter::PageTransition::BoxInward; break;
3709
0
                                        case presentation::FadeEffect_FADE_FROM_CENTER : eType = vcl::pdf::PDFWriter::PageTransition::BoxOutward; break;
3710
3711
0
                                        case presentation::FadeEffect_NONE : eType = vcl::pdf::PDFWriter::PageTransition::Regular; break;
3712
3713
0
                                        case presentation::FadeEffect_RANDOM :
3714
0
                                        case presentation::FadeEffect_DISSOLVE :
3715
0
                                        default: eType = vcl::pdf::PDFWriter::PageTransition::Dissolve; break;
3716
0
                                    }
3717
0
                                }
3718
0
                            }
3719
3720
0
                            if ( xPagePropSet->getPropertySetInfo( )->hasPropertyByName( sEffect ) ||
3721
0
                                xPagePropSet->getPropertySetInfo( )->hasPropertyByName( sSpeed ) )
3722
0
                            {
3723
0
                                pPDFExtOutDevData->SetPageTransition( eType, nTime );
3724
0
                            }
3725
0
                        }
3726
0
                    }
3727
0
                }
3728
0
            }
3729
0
            catch (const uno::Exception&)
3730
0
            {
3731
0
            }
3732
0
        }
3733
3734
0
        aView.SdrPaintView::CompleteRedraw(pOut, aRegion, &aImplRenderPaintProc);
3735
3736
0
        if (pPDFExtOutDevData && pPage)
3737
0
        {
3738
0
            try
3739
0
            {
3740
0
                Size        aPageSize( mpDoc->GetSdPage( 0, PageKind::Standard )->GetSize() );
3741
0
                Point aPoint( 0, 0 );
3742
0
                ::tools::Rectangle   aPageRect( aPoint, aPageSize );
3743
3744
                // resolving links found in this page by the method ImpEditEngine::Paint
3745
0
                std::vector< vcl::PDFExtOutDevBookmarkEntry >& rBookmarks = pPDFExtOutDevData->GetBookmarks();
3746
0
                for ( const auto& rBookmark : rBookmarks )
3747
0
                {
3748
0
                    sal_Int32 nPage = ImplPDFGetBookmarkPage( rBookmark.aBookmark, *mpDoc );
3749
0
                    if ( nPage != -1 )
3750
0
                    {
3751
0
                        if ( rBookmark.nLinkId != -1 )
3752
0
                            pPDFExtOutDevData->SetLinkDest( rBookmark.nLinkId, pPDFExtOutDevData->CreateDest( aPageRect, nPage, vcl::pdf::PDFWriter::DestAreaType::FitRectangle ) );
3753
0
                        else
3754
0
                            pPDFExtOutDevData->DescribeRegisteredDest( rBookmark.nDestId, aPageRect, nPage, vcl::pdf::PDFWriter::DestAreaType::FitRectangle );
3755
0
                    }
3756
0
                    else
3757
0
                        pPDFExtOutDevData->SetLinkURL( rBookmark.nLinkId, rBookmark.aBookmark );
3758
0
                }
3759
0
                rBookmarks.clear();
3760
                //---> #i56629, #i40318
3761
                //get the page name, will be used as outline element in PDF bookmark pane
3762
0
                OUString aPageName = mpDoc->GetSdPage( static_cast<sal_uInt16>(nPageNumber) - 1 , PageKind::Standard )->GetName();
3763
0
                if( !aPageName.isEmpty() )
3764
0
                {
3765
                    // Destination PageNum
3766
0
                    const sal_Int32 nDestPageNum = CalcOutputPageNum(pPDFExtOutDevData, mpDoc, nPageNumber);
3767
3768
                    // insert the bookmark to this page into the NamedDestinations
3769
0
                    if( pPDFExtOutDevData->GetIsExportNamedDestinations() )
3770
0
                        pPDFExtOutDevData->CreateNamedDest(aPageName, aPageRect, nDestPageNum);
3771
3772
                    // add the name to the outline, (almost) same code as in sc/source/ui/unoobj/docuno.cxx
3773
                    // issue #i40318.
3774
3775
0
                    if( pPDFExtOutDevData->GetIsExportBookmarks() )
3776
0
                    {
3777
                        // Destination Export
3778
0
                        const sal_Int32 nDestId =
3779
0
                            pPDFExtOutDevData->CreateDest(aPageRect , nDestPageNum);
3780
3781
                        // Create a new outline item:
3782
0
                        pPDFExtOutDevData->CreateOutlineItem( -1 , aPageName, nDestId );
3783
0
                    }
3784
0
                }
3785
                //<--- #i56629, #i40318
3786
0
            }
3787
0
            catch (const uno::Exception&)
3788
0
            {
3789
0
            }
3790
3791
0
        }
3792
0
    }
3793
0
    else
3794
0
    {
3795
0
        uno::Reference< drawing::XShapes > xShapes;
3796
0
        rSelection >>= xShapes;
3797
3798
0
        if( xShapes.is() && xShapes->getCount() )
3799
0
        {
3800
0
            SdrPageView* pPV = nullptr;
3801
3802
0
            ImplRenderPaintProc  aImplRenderPaintProc( mpDoc->GetLayerAdmin(),
3803
0
                            pOldSdView ? pOldSdView->GetSdrPageView() : nullptr);
3804
3805
0
            for( sal_uInt32 i = 0, nCount = xShapes->getCount(); i < nCount; i++ )
3806
0
            {
3807
0
                uno::Reference< drawing::XShape > xShape;
3808
0
                xShapes->getByIndex( i ) >>= xShape;
3809
3810
0
                if( xShape.is() )
3811
0
                {
3812
0
                    SdrObject* pObj = SdrObject::getSdrObjectFromXShape( xShape );
3813
0
                    if( pObj && pObj->getSdrPageFromSdrObject()
3814
0
                        && aImplRenderPaintProc.IsVisible( pObj )
3815
0
                            && aImplRenderPaintProc.IsPrintable( pObj ) )
3816
0
                    {
3817
0
                        if( !pPV )
3818
0
                            pPV = aView.ShowSdrPage( pObj->getSdrPageFromSdrObject() );
3819
3820
0
                        if( pPV )
3821
0
                            aView.MarkObj( pObj, pPV );
3822
0
                    }
3823
0
                }
3824
0
            }
3825
0
            aView.DrawMarkedObj(*pOut);
3826
0
        }
3827
0
    }
3828
0
}
3829
3830
DrawViewShell* SdXImpressDocument::GetViewShell()
3831
0
{
3832
0
    if (!mpDocShell)
3833
0
    {
3834
0
        return nullptr;
3835
0
    }
3836
3837
0
    DrawViewShell* pViewSh = dynamic_cast<DrawViewShell*>(mpDocShell->GetViewShell());
3838
0
    if (!pViewSh)
3839
0
    {
3840
0
        SAL_WARN("sd", "DrawViewShell not available!");
3841
0
        return nullptr;
3842
0
    }
3843
0
    return pViewSh;
3844
0
}
3845
3846
void SdXImpressDocument::paintTile( VirtualDevice& rDevice,
3847
                            int nOutputWidth, int nOutputHeight,
3848
                            int nTilePosX, int nTilePosY,
3849
                            ::tools::Long nTileWidth, ::tools::Long nTileHeight )
3850
0
{
3851
0
    DrawViewShell* pViewSh = GetViewShell();
3852
0
    if (!pViewSh)
3853
0
        return;
3854
3855
    // we need to skip tile invalidation for controls on rendering
3856
0
    comphelper::LibreOfficeKit::setTiledPainting(true);
3857
3858
    // Setup drawing layer to work properly. Since we use a custom VirtualDevice
3859
    // for the drawing, SdrPaintView::BeginCompleteRedraw() will call FindPaintWindow()
3860
    // unsuccessfully and use a temporary window that doesn't keep state. So patch
3861
    // the existing SdrPageWindow to use a temporary, and this way the state will be kept.
3862
    // Well, at least that's how I understand it based on Writer's RenderContextGuard,
3863
    // as the drawing layer classes lack documentation.
3864
0
    SdrPageWindow* patchedPageWindow = nullptr;
3865
0
    SdrPaintWindow* previousPaintWindow = nullptr;
3866
0
    std::unique_ptr<SdrPaintWindow> temporaryPaintWindow;
3867
0
    if(SdrView* pDrawView = pViewSh->GetDrawView())
3868
0
    {
3869
0
        if(SdrPageView* pSdrPageView = pDrawView->GetSdrPageView())
3870
0
        {
3871
0
            pSdrPageView->SetApplicationDocumentColor(pViewSh->GetViewOptions().mnDocBackgroundColor);
3872
0
            patchedPageWindow = pSdrPageView->FindPageWindow(*getDocWindow()->GetOutDev());
3873
0
            temporaryPaintWindow.reset(new SdrPaintWindow(*pDrawView, rDevice));
3874
0
            if (patchedPageWindow)
3875
0
                previousPaintWindow = patchedPageWindow->patchPaintWindow(*temporaryPaintWindow);
3876
0
        }
3877
0
    }
3878
3879
    // Scaling. Must convert from pixels to twips. We know
3880
    // that VirtualDevices use a DPI of 96.
3881
    // We specifically calculate these scales first as we're still
3882
    // in TWIPs, and might as well minimize the number of conversions.
3883
0
    const Fraction scale = conversionFract(o3tl::Length::px, o3tl::Length::twip);
3884
0
    Fraction scaleX = Fraction(nOutputWidth, nTileWidth) * scale;
3885
0
    Fraction scaleY = Fraction(nOutputHeight, nTileHeight) * scale;
3886
3887
    // svx seems to be the only component that works natively in
3888
    // 100th mm rather than TWIP. It makes most sense just to
3889
    // convert here and in getDocumentSize, and leave the tiled
3890
    // rendering API working in TWIPs.
3891
0
    ::tools::Long nTileWidthHMM = convertTwipToMm100( nTileWidth );
3892
0
    ::tools::Long nTileHeightHMM = convertTwipToMm100( nTileHeight );
3893
0
    int nTilePosXHMM = convertTwipToMm100( nTilePosX );
3894
0
    int nTilePosYHMM = convertTwipToMm100( nTilePosY );
3895
3896
0
    MapMode aMapMode = rDevice.GetMapMode();
3897
0
    aMapMode.SetMapUnit( MapUnit::Map100thMM );
3898
0
    aMapMode.SetOrigin( Point( -nTilePosXHMM,
3899
0
                               -nTilePosYHMM) );
3900
0
    aMapMode.SetScaleX( scaleX );
3901
0
    aMapMode.SetScaleY( scaleY );
3902
3903
0
    rDevice.SetMapMode( aMapMode );
3904
3905
0
    rDevice.SetOutputSizePixel( Size(nOutputWidth, nOutputHeight), /*bErase*/false );
3906
3907
0
    Point aPoint(nTilePosXHMM, nTilePosYHMM);
3908
0
    Size aSize(nTileWidthHMM, nTileHeightHMM);
3909
0
    ::tools::Rectangle aRect(aPoint, aSize);
3910
3911
0
    SdrView* pView = pViewSh->GetDrawView();
3912
0
    if (comphelper::LibreOfficeKit::isActive())
3913
0
        pView->SetPaintTextEdit(mbPaintTextEdit);
3914
3915
0
    pViewSh->GetView()->CompleteRedraw(&rDevice, vcl::Region(aRect));
3916
3917
0
    if (comphelper::LibreOfficeKit::isActive())
3918
0
        pView->SetPaintTextEdit(true);
3919
3920
0
    LokChartHelper::PaintAllChartsOnTile(rDevice, nOutputWidth, nOutputHeight,
3921
0
                                         nTilePosX, nTilePosY, nTileWidth, nTileHeight);
3922
0
    LokStarMathHelper::PaintAllInPlaceOnTile(rDevice, nOutputWidth, nOutputHeight, nTilePosX,
3923
0
                                             nTilePosY, nTileWidth, nTileHeight);
3924
3925
0
    if(patchedPageWindow != nullptr)
3926
0
        patchedPageWindow->unpatchPaintWindow(previousPaintWindow);
3927
3928
    // Draw Form controls
3929
0
    SdrView* pDrawView = pViewSh->GetDrawView();
3930
0
    SdrPageView* pPageView = pDrawView->GetSdrPageView();
3931
0
    if (pPageView != nullptr)
3932
0
    {
3933
0
        SdrPage* pPage = pPageView->GetPage();
3934
0
        ::sd::Window* pActiveWin = pViewSh->GetActiveWindow();
3935
0
        ::tools::Rectangle aTileRect(Point(nTilePosX, nTilePosY), Size(nTileWidth, nTileHeight));
3936
0
        Size aOutputSize(nOutputWidth, nOutputHeight);
3937
0
        LokControlHandler::paintControlTile(pPage, pDrawView, *pActiveWin, rDevice, aOutputSize, aTileRect);
3938
0
    }
3939
3940
0
    comphelper::LibreOfficeKit::setTiledPainting(false);
3941
0
}
3942
3943
OString SdXImpressDocument::getViewRenderState(SfxViewShell* pViewShell)
3944
0
{
3945
0
    OStringBuffer aState;
3946
0
    DrawViewShell* pView = nullptr;
3947
3948
0
    if (ViewShellBase* pShellBase = dynamic_cast<ViewShellBase*>(pViewShell))
3949
0
        pView = dynamic_cast<DrawViewShell*>(pShellBase->GetMainViewShell().get());
3950
0
    else
3951
0
        pView = GetViewShell();
3952
3953
0
    if (pView)
3954
0
    {
3955
0
        const SdViewOptions& pVOpt = pView->GetViewOptions();
3956
0
        if (mpDoc && mpDoc->GetOnlineSpell())
3957
0
            aState.append('S');
3958
0
        if (!ThemeColors::UseOnlyWhiteDocBackground())
3959
0
        {
3960
0
            if (pVOpt.mnDocBackgroundColor
3961
0
                == svtools::ColorConfig::GetDefaultColor(svtools::DOCCOLOR))
3962
0
                aState.append('D');
3963
0
        }
3964
0
        aState.append(';');
3965
3966
0
        OString aThemeName = OUStringToOString(pVOpt.msColorSchemeName, RTL_TEXTENCODING_UTF8);
3967
0
        aState.append(aThemeName);
3968
0
    }
3969
0
    return aState.makeStringAndClear();
3970
0
}
3971
3972
void SdXImpressDocument::selectPart(int nPart, int nSelect)
3973
0
{
3974
0
    DrawViewShell* pViewSh = GetViewShell();
3975
0
    if (!pViewSh)
3976
0
        return;
3977
3978
0
    pViewSh->SelectPage(nPart, nSelect);
3979
0
}
3980
3981
void SdXImpressDocument::moveSelectedParts(int nPosition, bool bDuplicate)
3982
0
{
3983
    // Duplicating is currently unsupported.
3984
0
    if (bDuplicate)
3985
0
        return;
3986
3987
0
    DrawViewShell* pViewSh = GetViewShell();
3988
0
    if (!pViewSh)
3989
0
        return;
3990
3991
0
    auto pSlideSorter
3992
0
        = sd::slidesorter::SlideSorterViewShell::GetSlideSorter(pViewSh->GetViewShellBase());
3993
0
    sd::slidesorter::SharedPageSelection pSelectedPage
3994
0
        = pSlideSorter ? pSlideSorter->GetPageSelection() : nullptr;
3995
0
    if (!pSelectedPage)
3996
0
        return;
3997
0
    mpDoc->MovePages(nPosition, *pSelectedPage);
3998
0
}
3999
4000
OUString SdXImpressDocument::getPartInfo(int nPart)
4001
0
{
4002
0
    DrawViewShell* pViewSh = GetViewShell();
4003
0
    if (!pViewSh)
4004
0
        return OUString();
4005
4006
0
    SdPage* pSdPage = mpDoc->GetSdPage(nPart, pViewSh->GetPageKind());
4007
0
    const sal_Int16 nMasterPageCount= pViewSh->GetDoc()->GetMasterSdPageCount(pViewSh->GetPageKind());
4008
4009
0
    ::tools::JsonWriter jsonWriter;
4010
4011
0
    jsonWriter.put("masterPageCount", nMasterPageCount);
4012
0
    jsonWriter.put("mode", getEditMode());
4013
0
    jsonWriter.put("gridSnapEnabled", pViewSh->GetDrawView()->IsGridSnap());
4014
0
    jsonWriter.put("gridVisible", pViewSh->GetDrawView()->IsGridVisible());
4015
4016
    // Below information is useful when grid snapping is enabled. It let's to calculate the points we can snap to.
4017
0
    const Size gridCoarse = pViewSh->GetDrawView()->GetGridCoarse();
4018
0
    const Size innerDots = pViewSh->GetDrawView()->GetGridFine();
4019
0
    jsonWriter.put("gridCoarseWidth", gridCoarse.getWidth());
4020
0
    jsonWriter.put("gridCoarseHeight", gridCoarse.getHeight());
4021
0
    jsonWriter.put("innerSpacesX", innerDots.getWidth() ? gridCoarse.getWidth() / innerDots.getWidth() : 0);
4022
0
    jsonWriter.put("innerSpacesY", innerDots.getHeight() ? gridCoarse.getHeight() / innerDots.getHeight() : 0);
4023
4024
0
    if (pSdPage)
4025
0
        pSdPage->GetPageInfo(jsonWriter);
4026
0
    else
4027
0
        SAL_WARN("sd", "getPartInfo request for SdPage " << nPart << " that does not exist!");
4028
4029
0
    return OStringToOUString(jsonWriter.finishAndGetAsOString(), RTL_TEXTENCODING_UTF8);
4030
0
}
4031
4032
void SdXImpressDocument::setPart( int nPart, bool bAllowChangeFocus )
4033
0
{
4034
0
    DrawViewShell* pViewSh = GetViewShell();
4035
0
    if (!pViewSh)
4036
0
        return;
4037
4038
0
    pViewSh->SwitchPage( nPart, bAllowChangeFocus );
4039
0
}
4040
4041
int SdXImpressDocument::getParts()
4042
0
{
4043
0
    if (!mpDoc)
4044
0
        return 0;
4045
4046
0
    if (isMasterViewMode())
4047
0
        return mpDoc->GetMasterSdPageCount(PageKind::Standard);
4048
4049
0
    return mpDoc->GetSdPageCount(PageKind::Standard);
4050
0
}
4051
4052
int SdXImpressDocument::getPart()
4053
0
{
4054
0
    DrawViewShell* pViewSh = GetViewShell();
4055
0
    if (!pViewSh)
4056
0
        return 0;
4057
4058
0
    return pViewSh->GetViewShellBase().getPart();
4059
0
}
4060
4061
OUString SdXImpressDocument::getPartName(int nPart)
4062
0
{
4063
0
    SdPage* pPage;
4064
0
    if (isMasterViewMode())
4065
0
        pPage = mpDoc->GetMasterSdPage(nPart, PageKind::Standard);
4066
0
    else
4067
0
        pPage = mpDoc->GetSdPage(nPart, PageKind::Standard);
4068
4069
0
    if (!pPage)
4070
0
    {
4071
0
        SAL_WARN("sd", "DrawViewShell not available!");
4072
0
        return OUString();
4073
0
    }
4074
4075
0
    return pPage->GetName();
4076
0
}
4077
4078
OUString SdXImpressDocument::getPartHash(int nPart)
4079
0
{
4080
0
    SdPage* pPage;
4081
0
    if (isMasterViewMode())
4082
0
        pPage = mpDoc->GetMasterSdPage(nPart, PageKind::Standard);
4083
0
    else
4084
0
        pPage = mpDoc->GetSdPage(nPart, PageKind::Standard);
4085
4086
0
    if (!pPage)
4087
0
    {
4088
0
        SAL_WARN("sd", "DrawViewShell not available!");
4089
0
        return OUString();
4090
0
    }
4091
4092
0
    uno::Reference<drawing::XDrawPage> xDrawPage(pPage->getUnoPage(), uno::UNO_QUERY);
4093
0
    return OUString::fromUtf8(GetInterfaceHash(xDrawPage));
4094
0
}
4095
4096
bool SdXImpressDocument::isMasterViewMode()
4097
0
{
4098
0
    DrawViewShell* pViewSh = GetViewShell();
4099
0
    if (!pViewSh)
4100
0
        return false;
4101
4102
0
    if (pViewSh->GetDispatcher())
4103
0
    {
4104
0
        SfxPoolItemHolder aResult;
4105
0
        pViewSh->GetDispatcher()->QueryState(SID_SLIDE_MASTER_MODE, aResult);
4106
0
        const SfxBoolItem* isMasterViewMode(static_cast<const SfxBoolItem*>(aResult.getItem()));
4107
0
        if (isMasterViewMode && isMasterViewMode->GetValue())
4108
0
            return true;
4109
0
    }
4110
0
    return false;
4111
0
}
4112
4113
VclPtr<vcl::Window> SdXImpressDocument::getDocWindow()
4114
0
{
4115
0
    SolarMutexGuard aGuard;
4116
0
    DrawViewShell* pViewShell = GetViewShell();
4117
0
    if (!pViewShell)
4118
0
        return {};
4119
4120
0
    if (VclPtr<vcl::Window> pWindow = SfxLokHelper::getInPlaceDocWindow(pViewShell->GetViewShell()))
4121
0
        return pWindow;
4122
4123
0
    return pViewShell->GetActiveWindow();
4124
0
}
4125
4126
void SdXImpressDocument::setPartMode( int nPartMode )
4127
0
{
4128
0
    DrawViewShell* pViewSh = GetViewShell();
4129
0
    if (!pViewSh)
4130
0
        return;
4131
4132
0
    PageKind aPageKind( PageKind::Standard );
4133
0
    switch ( nPartMode )
4134
0
    {
4135
0
    case LOK_PARTMODE_SLIDES:
4136
0
        break;
4137
0
    case LOK_PARTMODE_NOTES:
4138
0
        aPageKind = PageKind::Notes;
4139
0
        break;
4140
0
    }
4141
0
    pViewSh->SetPageKind( aPageKind );
4142
    //TODO do the same as setEditMode and then can probably remove the TODOs
4143
    //from doc_setPartMode
4144
0
}
4145
4146
int SdXImpressDocument::getEditMode()
4147
0
{
4148
0
    DrawViewShell* pViewSh = GetViewShell();
4149
0
    if (!pViewSh)
4150
0
        return 0;
4151
4152
0
    return pViewSh->GetViewShellBase().getEditMode();
4153
0
}
4154
4155
void SdXImpressDocument::setEditMode(int nMode)
4156
0
{
4157
0
    SolarMutexGuard aGuard;
4158
4159
0
    DrawViewShell* pViewSh = GetViewShell();
4160
0
    if (!pViewSh)
4161
0
        return;
4162
4163
0
    pViewSh->GetViewShellBase().setEditMode(nMode);
4164
0
}
4165
4166
Size SdXImpressDocument::getDocumentSize()
4167
0
{
4168
0
    DrawViewShell* pViewSh = GetViewShell();
4169
0
    if (!pViewSh)
4170
0
        return Size();
4171
4172
0
    SdrView *pSdrView = pViewSh->GetView();
4173
0
    if (!pSdrView)
4174
0
        return Size();
4175
4176
0
    SdrPageView* pCurPageView = pSdrView->GetSdrPageView();
4177
0
    if (!pCurPageView)
4178
0
        return Size();
4179
4180
0
    Size aSize = pCurPageView->GetPageRect().GetSize();
4181
    // Convert the size in 100th mm to TWIP
4182
    // See paintTile above for further info.
4183
0
    return o3tl::convert(aSize, o3tl::Length::mm100, o3tl::Length::twip);
4184
0
}
4185
4186
Size SdXImpressDocument::getPartSize(int part)
4187
0
{
4188
0
    if (part < 0 || part > 0xFFFF)
4189
0
        return Size(0,0);
4190
4191
0
    const sal_uInt16 nSlideIndex = static_cast<sal_uInt16>(part);
4192
0
    SdPage* pPage = mpDoc ? mpDoc->GetSdPage(nSlideIndex, PageKind::Standard) : nullptr;
4193
4194
0
    if (pPage == nullptr)
4195
0
        return Size(0,0);
4196
4197
0
    Size aRectSize(pPage->GetWidth() + 1, pPage->GetHeight() + 1);
4198
0
    return o3tl::convert(aRectSize, o3tl::Length::mm100, o3tl::Length::twip);
4199
0
}
4200
4201
void SdXImpressDocument::getAllPartSize(::tools::JsonWriter& rJsonWriter)
4202
0
{
4203
0
    auto aArray = rJsonWriter.startArray("parts");
4204
0
    const int nParts = getParts();
4205
0
    for (int i = 0; i < nParts; ++i)
4206
0
    {
4207
0
        const Size aSize = getPartSize(i);
4208
0
        auto aItem = rJsonWriter.startStruct();
4209
0
        rJsonWriter.put("width", aSize.getWidth());
4210
0
        rJsonWriter.put("height", aSize.getHeight());
4211
0
    }
4212
0
}
4213
4214
void SdXImpressDocument::getPostIts(::tools::JsonWriter& rJsonWriter)
4215
0
{
4216
0
    auto commentsNode = rJsonWriter.startNode("comments");
4217
0
    if (!mpDoc)
4218
0
        return;
4219
    // Return annotations on master pages too ?
4220
0
    const sal_uInt16 nMaxPages = mpDoc->GetPageCount();
4221
0
    for (sal_uInt16 nPage = 0; nPage < nMaxPages; ++nPage)
4222
0
    {
4223
0
        SdrPage* pPage = mpDoc->GetPage(nPage);
4224
4225
0
        for (auto const& xAnnotation : pPage->getAnnotations())
4226
0
        {
4227
0
            sal_uInt32 nID = xAnnotation->GetId();
4228
0
            OString nodeName = "comment" + OString::number(nID);
4229
0
            auto commentNode = rJsonWriter.startNode(nodeName);
4230
0
            rJsonWriter.put("id", nID);
4231
0
            rJsonWriter.put("author", xAnnotation->getAuthor());
4232
0
            rJsonWriter.put("dateTime", utl::toISO8601(xAnnotation->getDateTime()));
4233
0
            uno::Reference<text::XText> xText(xAnnotation->getTextRange());
4234
0
            rJsonWriter.put("text", xText->getString());
4235
0
            rJsonWriter.put("parthash", pPage->GetUniqueID());
4236
0
            geometry::RealPoint2D const aPoint = xAnnotation->getPosition();
4237
0
            geometry::RealSize2D const aSize = xAnnotation->getSize();
4238
0
            ::tools::Rectangle aRectangle(Point(aPoint.X * 100.0, aPoint.Y * 100.0), Size(aSize.Width * 100.0, aSize.Height * 100.0));
4239
0
            aRectangle = o3tl::toTwips(aRectangle, o3tl::Length::mm100);
4240
0
            OString sRectangle = aRectangle.toString();
4241
0
            rJsonWriter.put("rectangle", sRectangle.getStr());
4242
0
        }
4243
0
    }
4244
0
}
4245
4246
void SdXImpressDocument::initializeForTiledRendering(const css::uno::Sequence<css::beans::PropertyValue>& rArguments)
4247
0
{
4248
0
    SolarMutexGuard aGuard;
4249
4250
0
    OUString sThemeName;
4251
0
    OUString sBackgroundThemeName;
4252
4253
0
    if (DrawViewShell* pViewShell = GetViewShell())
4254
0
    {
4255
0
        DrawView* pDrawView = pViewShell->GetDrawView();
4256
0
        for (const beans::PropertyValue& rValue : rArguments)
4257
0
        {
4258
0
            if (rValue.Name == ".uno:ShowBorderShadow" && rValue.Value.has<bool>())
4259
0
                pDrawView->SetPageShadowVisible(rValue.Value.get<bool>());
4260
0
            else if (rValue.Name == ".uno:Author" && rValue.Value.has<OUString>())
4261
0
                pDrawView->SetAuthor(rValue.Value.get<OUString>());
4262
0
            else if (rValue.Name == ".uno:SpellOnline" && rValue.Value.has<bool>())
4263
0
                mpDoc->SetOnlineSpell(rValue.Value.get<bool>());
4264
0
            else if (rValue.Name == ".uno:ChangeTheme" && rValue.Value.has<OUString>())
4265
0
                sThemeName = rValue.Value.get<OUString>();
4266
0
            else if (rValue.Name == ".uno:InvertBackground" && rValue.Value.has<OUString>())
4267
0
                sBackgroundThemeName = rValue.Value.get<OUString>();
4268
0
        }
4269
4270
        // Disable comments if requested
4271
0
        SdOptions* pOptions = SdModule::get()->GetSdOptions(mpDoc->GetDocumentType());
4272
0
        pOptions->SetShowComments(comphelper::LibreOfficeKit::isTiledAnnotations());
4273
4274
0
        pViewShell->SetRuler(false);
4275
0
        pViewShell->SetScrollBarsVisible(false);
4276
4277
0
        if (sd::Window* pWindow = pViewShell->GetActiveWindow())
4278
0
        {
4279
            // get the full page size in pixels
4280
0
            pWindow->EnableMapMode();
4281
0
            Size aSize(pWindow->LogicToPixel(pDrawView->GetSdrPageView()->GetPage()->GetSize()));
4282
            // Disable map mode, so that it's possible to send mouse event
4283
            // coordinates in logic units
4284
0
            pWindow->EnableMapMode(false);
4285
4286
            // arrange UI elements again with new view size
4287
0
            pViewShell->GetParentWindow()->SetSizePixel(aSize);
4288
0
            pViewShell->Resize();
4289
0
        }
4290
4291
        // Forces all images to be swapped in synchronously, this
4292
        // ensures that images are available when paintTile is called
4293
        // (whereas with async loading images start being loaded after
4294
        //  we have painted the tile, resulting in an invalidate, followed
4295
        //  by the tile being rerendered - which is wasteful and ugly).
4296
0
        pDrawView->SetSwapAsynchron(false);
4297
0
    }
4298
4299
    // when the "This document may contain formatting or content that cannot
4300
    // be saved..." dialog appears, it is auto-cancelled with tiled rendering,
4301
    // causing 'Save' being disabled; so let's always save to the original
4302
    // format
4303
0
    auto xChanges = comphelper::ConfigurationChanges::create();
4304
0
    officecfg::Office::Common::Save::Document::WarnAlienFormat::set(false, xChanges);
4305
4306
0
    if (!o3tl::IsRunningUnitTest() || !comphelper::LibreOfficeKit::isActive())
4307
0
        officecfg::Office::Impress::MultiPaneGUI::SlideSorterBar::Visible::ImpressView::set(true,xChanges);
4308
0
    xChanges->commit();
4309
4310
    // if we know what theme the user wants, then we can dispatch that now early
4311
0
    if (!sThemeName.isEmpty())
4312
0
    {
4313
0
        css::uno::Sequence<css::beans::PropertyValue> aPropertyValues(comphelper::InitPropertySequence(
4314
0
        {
4315
0
            { "NewTheme", uno::Any(sThemeName) }
4316
0
        }));
4317
0
        comphelper::dispatchCommand(u".uno:ChangeTheme"_ustr, aPropertyValues);
4318
0
    }
4319
0
    if (!sBackgroundThemeName.isEmpty())
4320
0
    {
4321
0
        css::uno::Sequence<css::beans::PropertyValue> aPropertyValues(comphelper::InitPropertySequence(
4322
0
        {
4323
0
            { "NewTheme", uno::Any(sBackgroundThemeName) }
4324
0
        }));
4325
0
        comphelper::dispatchCommand(".uno:InvertBackground", aPropertyValues);
4326
0
    }
4327
0
}
4328
4329
void SdXImpressDocument::postKeyEvent(int nType, int nCharCode, int nKeyCode)
4330
0
{
4331
0
    SolarMutexGuard aGuard;
4332
0
    SfxLokHelper::postKeyEventAsync(getDocWindow(), nType, nCharCode, nKeyCode);
4333
0
}
4334
4335
void SdXImpressDocument::postMouseEvent(int nType, int nX, int nY, int nCount, int nButtons, int nModifier)
4336
0
{
4337
0
    SolarMutexGuard aGuard;
4338
4339
0
    DrawViewShell* pViewShell = GetViewShell();
4340
0
    if (!pViewShell)
4341
0
        return;
4342
4343
0
    constexpr double fScale = o3tl::convert(1.0, o3tl::Length::twip, o3tl::Length::px);
4344
4345
0
    if (SfxLokHelper::testInPlaceComponentMouseEventHit(
4346
0
            pViewShell->GetViewShell(), nType, nX, nY, nCount, nButtons, nModifier, fScale, fScale))
4347
0
        return;
4348
4349
    // try to forward mouse event to control
4350
0
    const Point aPointTwip(nX, nY);
4351
0
    const Point aPointHMM = o3tl::convert(aPointTwip, o3tl::Length::twip, o3tl::Length::mm100);
4352
0
    SdrView* pDrawView = pViewShell->GetDrawView();
4353
0
    SdrPageView* pPageView = pDrawView->GetSdrPageView();
4354
0
    if (!pPageView)
4355
0
    {
4356
0
        return;
4357
0
    }
4358
4359
0
    SdrPage* pPage = pPageView->GetPage();
4360
0
    ::sd::Window* pActiveWin = pViewShell->GetActiveWindow();
4361
0
    if (!pActiveWin)
4362
0
    {
4363
0
        return;
4364
0
    }
4365
4366
0
    if (LokControlHandler::postMouseEvent(pPage, pDrawView, *pActiveWin, nType, aPointHMM, nCount, nButtons, nModifier))
4367
0
            return;
4368
4369
0
    LokMouseEventData aMouseEventData(nType, aPointHMM, nCount, MouseEventModifiers::SIMPLECLICK,
4370
0
                                      nButtons, nModifier);
4371
0
    SfxLokHelper::postMouseEventAsync(pViewShell->GetActiveWindow(), aMouseEventData);
4372
0
}
4373
4374
void SdXImpressDocument::setTextSelection(int nType, int nX, int nY)
4375
0
{
4376
0
    SolarMutexGuard aGuard;
4377
4378
0
    DrawViewShell* pViewShell = GetViewShell();
4379
0
    if (!pViewShell)
4380
0
        return;
4381
4382
0
    LokChartHelper aChartHelper(pViewShell->GetViewShell());
4383
0
    if (aChartHelper.setTextSelection(nType, nX, nY))
4384
0
        return;
4385
4386
0
    Point aPoint(convertTwipToMm100(nX), convertTwipToMm100(nY));
4387
0
    switch (nType)
4388
0
    {
4389
0
    case LOK_SETTEXTSELECTION_START:
4390
0
        pViewShell->SetCursorMm100Position(aPoint, /*bPoint=*/false, /*bClearMark=*/false);
4391
0
        break;
4392
0
    case LOK_SETTEXTSELECTION_END:
4393
0
        pViewShell->SetCursorMm100Position(aPoint, /*bPoint=*/true, /*bClearMark=*/false);
4394
0
        break;
4395
0
    case LOK_SETTEXTSELECTION_RESET:
4396
0
        pViewShell->SetCursorMm100Position(aPoint, /*bPoint=*/true, /*bClearMark=*/true);
4397
0
        break;
4398
0
    default:
4399
0
        assert(false);
4400
0
        break;
4401
0
    }
4402
0
}
4403
4404
uno::Reference<datatransfer::XTransferable> SdXImpressDocument::getSelection()
4405
0
{
4406
0
    SolarMutexGuard aGuard;
4407
4408
0
    DrawViewShell* pViewShell = GetViewShell();
4409
0
    if (!pViewShell)
4410
0
        return uno::Reference<datatransfer::XTransferable>();
4411
4412
0
    return pViewShell->GetSelectionTransferable();
4413
0
}
4414
4415
void SdXImpressDocument::setGraphicSelection(int nType, int nX, int nY)
4416
0
{
4417
0
    SolarMutexGuard aGuard;
4418
4419
0
    DrawViewShell* pViewShell = GetViewShell();
4420
0
    if (!pViewShell)
4421
0
        return;
4422
4423
0
    constexpr double fScale = o3tl::convert(1.0, o3tl::Length::twip, o3tl::Length::px);
4424
4425
0
    LokChartHelper aChartHelper(pViewShell->GetViewShell());
4426
0
    if (aChartHelper.setGraphicSelection(nType, nX, nY, fScale, fScale))
4427
0
        return;
4428
4429
0
    Point aPoint(convertTwipToMm100(nX), convertTwipToMm100(nY));
4430
0
    switch (nType)
4431
0
    {
4432
0
    case LOK_SETGRAPHICSELECTION_START:
4433
0
        pViewShell->SetGraphicMm100Position(/*bStart=*/true, aPoint);
4434
0
        break;
4435
0
    case LOK_SETGRAPHICSELECTION_END:
4436
0
        pViewShell->SetGraphicMm100Position(/*bStart=*/false, aPoint);
4437
0
        break;
4438
0
    default:
4439
0
        assert(false);
4440
0
        break;
4441
0
    }
4442
0
}
4443
4444
void SdXImpressDocument::resetSelection()
4445
0
{
4446
0
    SolarMutexGuard aGuard;
4447
4448
0
    DrawViewShell* pViewShell = GetViewShell();
4449
0
    if (!pViewShell)
4450
0
        return;
4451
4452
0
    SdrView* pSdrView = pViewShell->GetView();
4453
0
    if (!pSdrView)
4454
0
        return;
4455
4456
0
    if (pSdrView->IsTextEdit())
4457
0
    {
4458
        // Reset the editeng selection.
4459
0
        pSdrView->UnmarkAll();
4460
        // Finish editing.
4461
0
        pSdrView->SdrEndTextEdit();
4462
0
    }
4463
    // Reset graphic selection.
4464
0
    pSdrView->UnmarkAll();
4465
0
}
4466
4467
void SdXImpressDocument::setPageZoom(int nPageZoom)
4468
0
{
4469
0
    SolarMutexGuard aGuard;
4470
0
    DrawViewShell* pViewShell = GetViewShell();
4471
0
    if (!pViewShell)
4472
0
        return;
4473
0
    pViewShell->RememberPageZoom(nPageZoom);
4474
0
}
4475
4476
void SdXImpressDocument::setClientVisibleArea(const ::tools::Rectangle& rRectangle)
4477
0
{
4478
0
    SolarMutexGuard aGuard;
4479
4480
0
    DrawViewShell* pViewShell = GetViewShell();
4481
0
    if (!pViewShell)
4482
0
        return;
4483
4484
0
    pViewShell->GetViewShellBase().setLOKVisibleArea(rRectangle);
4485
4486
0
    if (pViewShell->getCurrentPage()->IsCanvasPage())
4487
0
        pViewShell->RememberCanvasPageVisArea(rRectangle);
4488
0
}
4489
4490
void SdXImpressDocument::setClipboard(const uno::Reference<datatransfer::clipboard::XClipboard>& xClipboard)
4491
0
{
4492
0
    SolarMutexGuard aGuard;
4493
4494
0
    DrawViewShell* pViewShell = GetViewShell();
4495
0
    if (!pViewShell)
4496
0
        return;
4497
4498
0
    pViewShell->GetActiveWindow()->SetClipboard(xClipboard);
4499
0
}
4500
4501
bool SdXImpressDocument::isMimeTypeSupported()
4502
0
{
4503
0
    SolarMutexGuard aGuard;
4504
0
    DrawViewShell* pViewShell = GetViewShell();
4505
0
    if (!pViewShell)
4506
0
        return false;
4507
4508
0
    TransferableDataHelper aDataHelper(TransferableDataHelper::CreateFromSystemClipboard(pViewShell->GetActiveWindow()));
4509
0
    return EditEngine::HasValidData(aDataHelper.GetTransferable());
4510
0
}
4511
4512
PointerStyle SdXImpressDocument::getPointer()
4513
0
{
4514
0
    SolarMutexGuard aGuard;
4515
0
    DrawViewShell* pViewShell = GetViewShell();
4516
0
    if (!pViewShell)
4517
0
        return PointerStyle::Arrow;
4518
4519
0
    Window* pWindow = pViewShell->GetActiveWindow();
4520
0
    if (!pWindow)
4521
0
        return PointerStyle::Arrow;
4522
4523
0
    return pWindow->GetPointer();
4524
0
}
4525
4526
uno::Reference< i18n::XForbiddenCharacters > SdXImpressDocument::getForbiddenCharsTable()
4527
638
{
4528
638
    rtl::Reference<SdUnoForbiddenCharsTable> xRef = mxForbiddenCharacters.get();
4529
638
    if( !xRef )
4530
638
    {
4531
638
        xRef = new SdUnoForbiddenCharsTable( mpDoc );
4532
638
        mxForbiddenCharacters = xRef.get();
4533
638
    }
4534
638
    return xRef;
4535
638
}
4536
4537
void SdXImpressDocument::initializeDocument()
4538
43.9k
{
4539
43.9k
    if( mbClipBoard )
4540
0
        return;
4541
4542
43.9k
    switch( mpDoc->GetPageCount() )
4543
43.9k
    {
4544
0
    case 1:
4545
0
    {
4546
        // nasty hack to detect clipboard document
4547
0
        mbClipBoard = true;
4548
0
        break;
4549
0
    }
4550
25.1k
    case 0:
4551
25.1k
    {
4552
25.1k
        mpDoc->CreateFirstPages();
4553
25.1k
        mpDoc->StopWorkStartupDelay();
4554
25.1k
        break;
4555
0
    }
4556
43.9k
    }
4557
43.9k
}
4558
4559
static
4560
void getShapeClickAction(const uno::Reference<drawing::XShape> &xShape, ::tools::JsonWriter& rJsonWriter)
4561
0
{
4562
0
    bool bIsShapeVisible = true;
4563
0
    uno::Reference<beans::XPropertySet> xShapeProps(xShape, uno::UNO_QUERY);
4564
0
    if (!xShapeProps)
4565
0
        return;
4566
4567
0
    if (!xShapeProps->getPropertySetInfo()->hasPropertyByName( u"Visible"_ustr ))
4568
0
        return;
4569
0
    xShapeProps->getPropertyValue("Visible") >>= bIsShapeVisible;
4570
4571
0
    if (!bIsShapeVisible)
4572
0
        return;
4573
4574
0
    if (!xShapeProps->getPropertySetInfo()->hasPropertyByName( u"OnClick"_ustr ))
4575
0
        return;
4576
4577
0
    presentation::ClickAction eClickAction = presentation::ClickAction_NONE;
4578
0
    xShapeProps->getPropertyValue(u"OnClick"_ustr) >>= eClickAction;
4579
4580
0
    if (eClickAction != presentation::ClickAction_NONE)
4581
0
    {
4582
0
        auto aShape = rJsonWriter.startStruct();
4583
4584
0
        sal_Int32 nVerb = 0;
4585
0
        OUString sBookmark;
4586
4587
0
        if (xShapeProps->getPropertySetInfo()->hasPropertyByName( u"Bookmark"_ustr ))
4588
0
            xShapeProps->getPropertyValue(u"Bookmark"_ustr) >>= sBookmark;
4589
4590
0
        {
4591
0
            auto* pObject = SdrObject::getSdrObjectFromXShape(xShape);
4592
0
            auto const& rRectangle = pObject->GetLogicRect();
4593
0
            auto aRectangle = o3tl::convert(rRectangle, o3tl::Length::mm100, o3tl::Length::twip);
4594
0
            auto aRect = rJsonWriter.startNode("bounds");
4595
0
            rJsonWriter.put("x", aRectangle.Left());
4596
0
            rJsonWriter.put("y", aRectangle.Top());
4597
0
            rJsonWriter.put("width", aRectangle.GetWidth());
4598
0
            rJsonWriter.put("height", aRectangle.GetHeight());
4599
0
        }
4600
4601
0
        {
4602
0
            auto aInteraction = rJsonWriter.startNode("clickAction");
4603
0
            switch (eClickAction)
4604
0
            {
4605
0
            case presentation::ClickAction_BOOKMARK:
4606
0
                rJsonWriter.put("action", "bookmark");
4607
0
                rJsonWriter.put("bookmark", sBookmark);
4608
0
                break;
4609
0
            case presentation::ClickAction_DOCUMENT:
4610
0
                rJsonWriter.put("action", "document");
4611
0
                rJsonWriter.put("document", sBookmark);
4612
0
                break;
4613
4614
0
            case presentation::ClickAction_PREVPAGE:
4615
0
                rJsonWriter.put("action", "prevpage");
4616
0
                break;
4617
0
            case presentation::ClickAction_NEXTPAGE:
4618
0
                rJsonWriter.put("action", "nextpage");
4619
0
                break;
4620
4621
0
            case presentation::ClickAction_FIRSTPAGE:
4622
0
                rJsonWriter.put("action", "firstpage");
4623
0
                break;
4624
0
            case presentation::ClickAction_LASTPAGE:
4625
0
                rJsonWriter.put("action", "lastpage");
4626
0
                break;
4627
4628
0
            case presentation::ClickAction_SOUND:
4629
0
                rJsonWriter.put("action", "sound");
4630
0
                rJsonWriter.put("sound", sBookmark);
4631
0
                break;
4632
4633
0
            case presentation::ClickAction_VERB:
4634
0
                rJsonWriter.put("action", "verb");
4635
0
                xShapeProps->getPropertyValue(u"Verb"_ustr) >>= nVerb;
4636
0
                rJsonWriter.put("verb", nVerb);
4637
0
                break;
4638
4639
0
            case presentation::ClickAction_PROGRAM:
4640
0
                rJsonWriter.put("action", "program");
4641
0
                rJsonWriter.put("program", sBookmark);
4642
0
                break;
4643
4644
0
            case presentation::ClickAction_MACRO:
4645
0
                rJsonWriter.put("action", "macro");
4646
0
                rJsonWriter.put("macro", sBookmark);
4647
0
                break;
4648
4649
0
            case presentation::ClickAction_STOPPRESENTATION:
4650
0
                rJsonWriter.put("action", "stoppresentation");
4651
0
                break;
4652
4653
0
            default:
4654
0
                break;
4655
0
            }
4656
0
        }
4657
0
    }
4658
0
}
4659
4660
OString SdXImpressDocument::getPresentationInfo(bool bAllyState) const
4661
0
{
4662
0
    ::tools::JsonWriter aJsonWriter;
4663
4664
0
    try
4665
0
    {
4666
0
        rtl::Reference<SdDrawPagesAccess> xDrawPages = const_cast<SdXImpressDocument*>(this)->getSdDrawPages();
4667
        // size in twips
4668
0
        Size aDocSize = const_cast<SdXImpressDocument*>(this)->getDocumentSize();
4669
0
        aJsonWriter.put("docWidth", aDocSize.getWidth());
4670
0
        aJsonWriter.put("docHeight", aDocSize.getHeight());
4671
4672
0
        sd::PresentationSettings const& rSettings = mpDoc->getPresentationSettings();
4673
4674
0
        const bool bIsEndless = rSettings.mbEndless;
4675
0
        aJsonWriter.put("isEndless", bIsEndless);
4676
4677
0
        if (bIsEndless) {
4678
0
            const sal_Int32 nPauseTimeout = rSettings.mnPauseTimeout;
4679
0
            aJsonWriter.put("loopAndRepeatDuration", nPauseTimeout);
4680
0
        }
4681
4682
0
        auto aSlideList = aJsonWriter.startArray("slides");
4683
0
        sal_Int32 nSlideCount = xDrawPages->getCount();
4684
0
        for (sal_Int32 i = 0; i < nSlideCount; ++i)
4685
0
        {
4686
0
            SdGenericDrawPage* pSlide(xDrawPages->getDrawPageByIndex(i));
4687
0
            SdPage* pPage = SdPage::getImplementation(pSlide);
4688
0
            if (!pPage)
4689
0
            {
4690
0
                SAL_WARN("sd", "slide: " << i << " is disposed, skipping");
4691
0
                continue;
4692
0
            }
4693
4694
0
            bool bIsVisible = true; // default visible
4695
0
            pSlide->getPropertyValue("Visible") >>= bIsVisible;
4696
4697
0
            if (!bIsVisible)
4698
0
            {
4699
0
                auto aSlideNode = aJsonWriter.startStruct();
4700
0
                std::string sSlideHash = GetInterfaceHash(cppu::getXWeak(pSlide));
4701
0
                aJsonWriter.put("hash", sSlideHash);
4702
0
                aJsonWriter.put("index", i);
4703
0
                aJsonWriter.put("hidden", true);
4704
0
                aJsonWriter.put("uniqueID", pPage->GetUniqueID());
4705
0
            }
4706
0
            else
4707
0
            {
4708
0
                auto aSlideNode = aJsonWriter.startStruct();
4709
0
                std::string sSlideHash = GetInterfaceHash(cppu::getXWeak(pSlide));
4710
0
                aJsonWriter.put("hash", sSlideHash);
4711
0
                aJsonWriter.put("index", i);
4712
0
                aJsonWriter.put("uniqueID", pPage->GetUniqueID());
4713
4714
0
                auto aName = SdDrawPage::getPageApiNameFromUiName(pPage->GetName());
4715
0
                aJsonWriter.put("name", aName);
4716
4717
0
                if (bAllyState)
4718
0
                {
4719
0
                    OUStringBuffer aHtml;
4720
0
                    SdrOutliner* pOutliner = mpDoc->GetInternalOutliner();
4721
0
                    if (pOutliner)
4722
0
                    {
4723
0
                        SdHTMLFilter::ExportPage(pOutliner, pPage, aHtml);
4724
0
                        aJsonWriter.put("a11y", aHtml.makeStringAndClear());
4725
0
                        pOutliner->Clear();
4726
0
                    }
4727
0
                }
4728
4729
0
                bool bIsDrawPageEmpty = pSlide->getCount() == 0;
4730
0
                aJsonWriter.put("empty", bIsDrawPageEmpty);
4731
4732
                // Notes
4733
0
                SdPage* pNotesPage = mpDoc->GetSdPage((pPage->GetPageNum() - 1) >> 1, PageKind::Notes);
4734
0
                if (pNotesPage)
4735
0
                {
4736
0
                    SdrObject* pItObj = nullptr;
4737
0
                    SdrObject* pNotes = pNotesPage->GetPresObj(PresObjKind::Notes);
4738
4739
0
                    if (!pNotes)
4740
0
                    {
4741
0
                        for (size_t nNote = 0; nNote < pNotesPage->GetObjCount(); nNote++)
4742
0
                        {
4743
0
                            pItObj = pNotesPage->GetObj(nNote);
4744
4745
0
                            if (pItObj && pItObj->HasText() &&
4746
0
                                (pItObj->GetObjIdentifier() == SdrObjKind::Text
4747
0
                                 || pItObj->GetObjIdentifier() == SdrObjKind::TitleText
4748
0
                                 || pItObj->GetObjIdentifier() == SdrObjKind::OutlineText))
4749
0
                            {
4750
0
                                pNotes = pItObj;
4751
0
                                break;
4752
0
                            }
4753
0
                        }
4754
0
                    }
4755
4756
0
                    if (pNotes)
4757
0
                    {
4758
0
                        OUStringBuffer strNotes;
4759
0
                        OutlinerParaObject* pPara = pNotes->GetOutlinerParaObject();
4760
0
                        if (pPara)
4761
0
                        {
4762
0
                            const EditTextObject& rText = pPara->GetTextObject();
4763
0
                            for (sal_Int32 nNote = 0; nNote < rText.GetParagraphCount(); nNote++)
4764
0
                            {
4765
0
                                strNotes.append(rText.GetText(nNote));
4766
0
                            }
4767
0
                            aJsonWriter.put("notes", strNotes.makeStringAndClear());
4768
0
                        }
4769
0
                    }
4770
0
                }
4771
4772
0
                SdMasterPage* pMasterPage = nullptr;
4773
0
                SdDrawPage* pMasterPageTarget(dynamic_cast<SdDrawPage*>(pSlide));
4774
0
                if (pMasterPageTarget)
4775
0
                {
4776
0
                    pMasterPage = pMasterPageTarget->getSdMasterPage();
4777
0
                    if (pMasterPage)
4778
0
                    {
4779
0
                        std::string sMPHash = GetInterfaceHash(cppu::getXWeak(pMasterPage));
4780
0
                        aJsonWriter.put("masterPage", sMPHash);
4781
4782
0
                        bool bBackgroundObjectsVisibility = true; // default visible
4783
0
                        pSlide->getPropertyValue("IsBackgroundObjectsVisible") >>= bBackgroundObjectsVisibility;
4784
0
                        aJsonWriter.put("masterPageObjectsVisibility", bBackgroundObjectsVisibility);
4785
0
                    }
4786
0
                }
4787
4788
0
                bool bBackgroundVisibility = true; // default visible
4789
0
                pSlide->getPropertyValue("IsBackgroundVisible")  >>= bBackgroundVisibility;
4790
0
                if (bBackgroundVisibility)
4791
0
                {
4792
0
                    SlideBackgroundInfo aSlideBackgroundInfo(pSlide, static_cast<SvxDrawPage*>(pMasterPage));
4793
0
                    if (aSlideBackgroundInfo.hasBackground())
4794
0
                    {
4795
0
                        auto aBackgroundNode = aJsonWriter.startNode("background");
4796
0
                        aJsonWriter.put("isCustom", aSlideBackgroundInfo.slideHasOwnBackground());
4797
0
                        if (aSlideBackgroundInfo.isSolidColor())
4798
0
                        {
4799
0
                            aJsonWriter.put("fillColor", aSlideBackgroundInfo.getFillColorAsRGBA());
4800
0
                        }
4801
0
                    }
4802
0
                }
4803
4804
0
                {
4805
0
                    auto aVideoList = aJsonWriter.startArray("videos");
4806
0
                    SdrObjListIter aIterator(pPage, SdrIterMode::DeepWithGroups);
4807
0
                    while (aIterator.IsMore())
4808
0
                    {
4809
0
                        auto* pObject = aIterator.Next();
4810
0
                        if (pObject->GetObjIdentifier() == SdrObjKind::Media)
4811
0
                        {
4812
0
                            auto aVideosNode = aJsonWriter.startStruct();
4813
0
                            auto* pMediaObject = static_cast<SdrMediaObj*>(pObject);
4814
0
                            auto const& rRectangle = pMediaObject->GetLogicRect();
4815
0
                            auto aRectangle = o3tl::convert(rRectangle, o3tl::Length::mm100, o3tl::Length::twip);
4816
0
                            aJsonWriter.put("id", reinterpret_cast<sal_uInt64>(pMediaObject));
4817
0
                            aJsonWriter.put("url", pMediaObject->getTempURL());
4818
0
                            aJsonWriter.put("x", aRectangle.Left());
4819
0
                            aJsonWriter.put("y", aRectangle.Top());
4820
0
                            aJsonWriter.put("width", aRectangle.GetWidth());
4821
0
                            aJsonWriter.put("height", aRectangle.GetHeight());
4822
0
                        }
4823
0
                    }
4824
0
                }
4825
4826
0
                uno::Reference<drawing::XShapes> const xShapes(cppu::getXWeak(pSlide), uno::UNO_QUERY_THROW);
4827
0
                if (xShapes.is())
4828
0
                {
4829
0
                    auto aInteractions = aJsonWriter.startArray("interactions");
4830
0
                    auto count = xShapes->getCount();
4831
0
                    for (auto j = 0; j < count; j++)
4832
0
                    {
4833
0
                        auto xObject = xShapes->getByIndex(j);
4834
0
                        uno::Reference<drawing::XShape> xShape(xObject, uno::UNO_QUERY);
4835
0
                        if (!xShape.is())
4836
0
                        {
4837
0
                            continue;
4838
0
                        }
4839
4840
0
                        getShapeClickAction(xShape, aJsonWriter);
4841
0
                    }
4842
0
                }
4843
4844
0
                sal_Int32 nTransitionType = 0;
4845
0
                pSlide->getPropertyValue("TransitionType") >>= nTransitionType;
4846
4847
0
                if (nTransitionType != 0)
4848
0
                {
4849
0
                    auto iterator = constTransitionTypeToString.find(nTransitionType);
4850
4851
0
                    if (iterator != constTransitionTypeToString.end())
4852
0
                    {
4853
0
                        aJsonWriter.put("transitionType", iterator->second);
4854
4855
0
                        sal_Int32 nTransitionSubtype = 0;
4856
0
                        pSlide->getPropertyValue("TransitionSubtype") >>= nTransitionSubtype;
4857
4858
0
                        auto iteratorSubType = constTransitionSubTypeToString.find(nTransitionSubtype);
4859
0
                        if (iteratorSubType != constTransitionSubTypeToString.end())
4860
0
                        {
4861
0
                            aJsonWriter.put("transitionSubtype", iteratorSubType->second);
4862
0
                        }
4863
0
                        else
4864
0
                        {
4865
0
                            SAL_WARN("sd", "Transition sub-type unknown: " << nTransitionSubtype);
4866
0
                        }
4867
4868
0
                        if (bAllyState)
4869
0
                        {
4870
0
                            const TransitionPresetList& rList = TransitionPreset::getTransitionPresetList();
4871
0
                            auto aTransition = std::find_if(rList.begin(), rList.end(),
4872
0
                                                            [nTransitionType,
4873
0
                                                             nTransitionSubtype](const TransitionPresetPtr& rxPreset) {
4874
0
                                                                return (rxPreset->getTransition() == nTransitionType)
4875
0
                                                                    && (rxPreset->getSubtype() == nTransitionSubtype);
4876
0
                                                            });
4877
4878
0
                            if (aTransition != rList.end())
4879
0
                            {
4880
0
                                aJsonWriter.put("transitionLabel", (*aTransition)->getSetLabel());
4881
0
                            }
4882
0
                        }
4883
4884
0
                        bool nTransitionDirection = false;
4885
0
                        pSlide->getPropertyValue("TransitionDirection") >>= nTransitionDirection;
4886
0
                        aJsonWriter.put("transitionDirection", nTransitionDirection);
4887
4888
                        // fade color
4889
0
                        if ((nTransitionType == TransitionType::FADE)
4890
0
                                && ((nTransitionSubtype == TransitionSubType::FADETOCOLOR)
4891
0
                                    || (nTransitionSubtype == TransitionSubType::FADEFROMCOLOR)
4892
0
                                    || (nTransitionSubtype == TransitionSubType::FADEOVERCOLOR)))
4893
0
                        {
4894
0
                            sal_Int32 nFadeColor = 0;
4895
0
                            pSlide->getPropertyValue("TransitionFadeColor") >>= nFadeColor;
4896
0
                            OUStringBuffer sTmpBuf;
4897
0
                            ::sax::Converter::convertColor(sTmpBuf, nFadeColor);
4898
0
                            aJsonWriter.put("transitionFadeColor", sTmpBuf.makeStringAndClear());
4899
0
                        }
4900
0
                    }
4901
4902
0
                    double nTransitionDuration(0.0);
4903
0
                    if( pSlide->getPropertySetInfo()->hasPropertyByName( "TransitionDuration" ) &&
4904
0
                        (pSlide->getPropertyValue( "TransitionDuration" ) >>= nTransitionDuration ) && nTransitionDuration != 0.0 )
4905
0
                    {
4906
                        // convert transitionDuration time to ms
4907
0
                        aJsonWriter.put("transitionDuration", nTransitionDuration * 1000);
4908
0
                    }
4909
0
                }
4910
4911
0
                sal_Int32 nChange(0);
4912
0
                if( pSlide->getPropertySetInfo()->hasPropertyByName( "Change" ) &&
4913
0
                        (pSlide->getPropertyValue( "Change" ) >>= nChange ) && nChange == 1 )
4914
0
                {
4915
0
                    double fSlideDuration(0);
4916
0
                    if( pSlide->getPropertySetInfo()->hasPropertyByName( "HighResDuration" ) &&
4917
0
                            (pSlide->getPropertyValue( "HighResDuration" ) >>= fSlideDuration) )
4918
0
                    {
4919
                        // convert slide duration time to ms
4920
0
                        aJsonWriter.put("nextSlideDuration", fSlideDuration * 1000);
4921
0
                    }
4922
0
                }
4923
4924
4925
0
                AnimationsExporter aAnimationExporter(aJsonWriter, pSlide);
4926
0
                if (aAnimationExporter.hasEffects())
4927
0
                {
4928
0
                    {
4929
0
                        auto aAnimationsNode = aJsonWriter.startNode("animations");
4930
0
                        aAnimationExporter.exportAnimations();
4931
0
                    }
4932
0
                    aAnimationExporter.exportTriggers();
4933
0
                }
4934
0
            }
4935
0
        }
4936
0
    }
4937
0
    catch (uno::Exception& )
4938
0
    {
4939
0
        TOOLS_WARN_EXCEPTION("sd", "SdXImpressDocument::getSlideShowInfo ... maybe some property can't be retrieved");
4940
0
    }
4941
0
    return aJsonWriter.finishAndGetAsOString();
4942
0
}
4943
4944
namespace
4945
{
4946
bool isRequestedSlideValid(SdDrawDocument* mpDoc, sal_Int32 nSlideNumber, const std::string& slideHash)
4947
0
{
4948
0
    try
4949
0
    {
4950
0
        SdXImpressDocument* pDoc = mpDoc->getUnoModel();
4951
0
        rtl::Reference<SdDrawPagesAccess> xDrawPages = pDoc->getSdDrawPages();
4952
0
        SdGenericDrawPage* pSlide(xDrawPages->getDrawPageByIndex(nSlideNumber));
4953
0
        if (pSlide)
4954
0
        {
4955
0
            return slideHash == GetInterfaceHash(cppu::getXWeak(pSlide));
4956
0
        }
4957
0
    }
4958
0
    catch (uno::Exception&)
4959
0
    {
4960
0
        TOOLS_WARN_EXCEPTION( "sd", "SdXImpressDocument::createLOKSlideRenderer: failed" );
4961
0
    }
4962
0
    return false;
4963
0
}
4964
}
4965
4966
bool SdXImpressDocument::createSlideRenderer(
4967
    const OString& rSlideHash,
4968
    sal_Int32 nSlideNumber, sal_Int32& nViewWidth, sal_Int32& nViewHeight,
4969
    bool bRenderBackground, bool bRenderMasterPage)
4970
0
{
4971
0
    std::string sSlideHash(rSlideHash);
4972
0
    if (!isRequestedSlideValid(mpDoc, nSlideNumber, sSlideHash))
4973
0
        return false;
4974
4975
0
    SdPage* pPage = mpDoc->GetSdPage(sal_uInt16(nSlideNumber), PageKind::Standard);
4976
0
    if (!pPage)
4977
0
        return false;
4978
4979
0
    mpSlideshowLayerRenderer.reset(new SlideshowLayerRenderer(*pPage, rSlideHash, bRenderBackground, bRenderMasterPage));
4980
0
    Size aDesiredSize(nViewWidth, nViewHeight);
4981
0
    Size aCalculatedSize = mpSlideshowLayerRenderer->calculateAndSetSizePixel(aDesiredSize);
4982
0
    nViewWidth = aCalculatedSize.Width();
4983
0
    nViewHeight = aCalculatedSize.Height();
4984
0
    return true;
4985
0
}
4986
4987
void SdXImpressDocument::postSlideshowCleanup()
4988
0
{
4989
0
    DrawViewShell* pViewSh = GetViewShell();
4990
0
    if (!pViewSh)
4991
0
        return;
4992
4993
0
    pViewSh->destroyXSlideShowInstance();
4994
0
}
4995
4996
bool SdXImpressDocument::renderNextSlideLayer(unsigned char* pBuffer, bool& bIsBitmapLayer, double& rScale, OUString& rJsonMsg)
4997
0
{
4998
0
    bool bDone = true;
4999
5000
0
    if (!mpSlideshowLayerRenderer)
5001
0
        return bDone;
5002
5003
0
    OString sMsg;
5004
0
    bool bOK = mpSlideshowLayerRenderer->render(pBuffer, bIsBitmapLayer, rScale, sMsg);
5005
5006
0
    if (bOK)
5007
0
    {
5008
0
        rJsonMsg = OUString::fromUtf8(sMsg);
5009
0
        bDone = false;
5010
0
    }
5011
5012
0
    return bDone;
5013
0
}
5014
5015
SdrModel& SdXImpressDocument::getSdrModelFromUnoModel() const
5016
0
{
5017
0
    OSL_ENSURE(GetDoc(), "No SdrModel in draw/Impress, should not happen");
5018
0
    return *GetDoc(); // TTTT should be reference
5019
0
}
5020
5021
void SAL_CALL SdXImpressDocument::dispose()
5022
36.3k
{
5023
36.3k
    if( mbDisposed )
5024
0
        return;
5025
5026
36.3k
    ::SolarMutexGuard aGuard;
5027
5028
36.3k
    if( mpDoc )
5029
36.3k
    {
5030
36.3k
        EndListening( *mpDoc );
5031
36.3k
        mpDoc = nullptr;
5032
36.3k
    }
5033
5034
    // Call the base class dispose() before setting the mbDisposed flag
5035
    // to true.  The reason for this is that if close() has not yet been
5036
    // called this is done in SfxBaseModel::dispose().  At the end of
5037
    // that dispose() is called again.  It is important to forward this
5038
    // second dispose() to the base class, too.
5039
    // As a consequence the following code has to be able to be run twice.
5040
36.3k
    SfxBaseModel::dispose();
5041
36.3k
    mbDisposed = true;
5042
5043
36.3k
    rtl::Reference< SdDocLinkTargets > xLinks( mxLinks );
5044
36.3k
    if( xLinks.is() )
5045
0
    {
5046
0
        xLinks->dispose();
5047
0
        xLinks = nullptr;
5048
0
    }
5049
5050
36.3k
    rtl::Reference< SdDrawPagesAccess > xDrawPagesAccess( mxDrawPagesAccess );
5051
36.3k
    if( xDrawPagesAccess.is() )
5052
0
    {
5053
0
        xDrawPagesAccess->dispose();
5054
0
        xDrawPagesAccess = nullptr;
5055
0
    }
5056
5057
36.3k
    rtl::Reference< SdMasterPagesAccess > xMasterPagesAccess( mxMasterPagesAccess );
5058
36.3k
    if( xDrawPagesAccess.is() )
5059
0
    {
5060
0
        xMasterPagesAccess->dispose();
5061
0
        xMasterPagesAccess = nullptr;
5062
0
    }
5063
5064
36.3k
    rtl::Reference< SdLayerManager > xLayerManager( mxLayerManager );
5065
36.3k
    if( xLayerManager.is() )
5066
0
    {
5067
0
        xLayerManager->dispose();
5068
0
        xLayerManager = nullptr;
5069
0
    }
5070
5071
36.3k
    mxDashTable = nullptr;
5072
36.3k
    mxGradientTable = nullptr;
5073
36.3k
    mxHatchTable = nullptr;
5074
36.3k
    mxBitmapTable = nullptr;
5075
36.3k
    mxTransGradientTable = nullptr;
5076
36.3k
    mxMarkerTable = nullptr;
5077
36.3k
    mxDrawingPool = nullptr;
5078
36.3k
    mpDocShell = nullptr;
5079
36.3k
}
5080
5081
SdDrawPagesAccess::SdDrawPagesAccess( SdXImpressDocument& rMyModel )  noexcept
5082
27.4k
:   mpModel( &rMyModel)
5083
27.4k
{
5084
27.4k
}
5085
5086
SdDrawPagesAccess::~SdDrawPagesAccess() noexcept
5087
27.4k
{
5088
27.4k
}
5089
5090
// XIndexAccess
5091
sal_Int32 SAL_CALL SdDrawPagesAccess::getCount()
5092
21.1k
{
5093
21.1k
    ::SolarMutexGuard aGuard;
5094
5095
21.1k
    if( nullptr == mpModel )
5096
0
        throw lang::DisposedException();
5097
5098
21.1k
    return mpModel->mpDoc->GetSdPageCount( PageKind::Standard );
5099
21.1k
}
5100
5101
uno::Any SAL_CALL SdDrawPagesAccess::getByIndex( sal_Int32 Index )
5102
27.9k
{
5103
27.9k
    uno::Reference< drawing::XDrawPage > xDrawPage( getDrawPageByIndex(Index) );
5104
27.9k
    return uno::Any(xDrawPage);
5105
27.9k
}
5106
5107
SdGenericDrawPage* SdDrawPagesAccess::getDrawPageByIndex( sal_Int32 Index )
5108
27.9k
{
5109
27.9k
    ::SolarMutexGuard aGuard;
5110
5111
27.9k
    if( nullptr == mpModel )
5112
0
        throw lang::DisposedException();
5113
5114
27.9k
    if( (Index < 0) || (Index >= mpModel->mpDoc->GetSdPageCount( PageKind::Standard ) ) )
5115
0
        throw lang::IndexOutOfBoundsException();
5116
5117
27.9k
    SdPage* pPage = mpModel->mpDoc->GetSdPage( static_cast<sal_uInt16>(Index), PageKind::Standard );
5118
27.9k
    if( pPage )
5119
27.9k
        return dynamic_cast<SdGenericDrawPage*>( pPage->getUnoPage().get() );
5120
5121
0
    return nullptr;
5122
27.9k
}
5123
5124
// XNameAccess
5125
uno::Any SAL_CALL SdDrawPagesAccess::getByName( const OUString& aName )
5126
0
{
5127
0
    ::SolarMutexGuard aGuard;
5128
5129
0
    if( nullptr == mpModel )
5130
0
        throw lang::DisposedException();
5131
5132
0
    if( !aName.isEmpty() )
5133
0
    {
5134
0
        const sal_uInt16 nCount = mpModel->mpDoc->GetSdPageCount( PageKind::Standard );
5135
0
        sal_uInt16 nPage;
5136
0
        for( nPage = 0; nPage < nCount; nPage++ )
5137
0
        {
5138
0
            SdPage* pPage = mpModel->mpDoc->GetSdPage( nPage, PageKind::Standard );
5139
0
            if(nullptr == pPage)
5140
0
                continue;
5141
5142
0
            if( aName == SdDrawPage::getPageApiName( pPage ) )
5143
0
            {
5144
0
                uno::Any aAny;
5145
0
                uno::Reference< drawing::XDrawPage >  xDrawPage( pPage->getUnoPage(), uno::UNO_QUERY );
5146
0
                aAny <<= xDrawPage;
5147
0
                return aAny;
5148
0
            }
5149
0
        }
5150
0
    }
5151
5152
0
    throw container::NoSuchElementException();
5153
0
}
5154
5155
uno::Sequence< OUString > SAL_CALL SdDrawPagesAccess::getElementNames()
5156
0
{
5157
0
    ::SolarMutexGuard aGuard;
5158
5159
0
    if( nullptr == mpModel )
5160
0
        throw lang::DisposedException();
5161
5162
0
    const sal_uInt16 nCount = mpModel->mpDoc->GetSdPageCount( PageKind::Standard );
5163
0
    uno::Sequence< OUString > aNames( nCount );
5164
0
    OUString* pNames = aNames.getArray();
5165
5166
0
    sal_uInt16 nPage;
5167
0
    for( nPage = 0; nPage < nCount; nPage++ )
5168
0
    {
5169
0
        SdPage* pPage = mpModel->mpDoc->GetSdPage( nPage, PageKind::Standard );
5170
0
        *pNames++ = SdDrawPage::getPageApiName( pPage );
5171
0
    }
5172
5173
0
    return aNames;
5174
0
}
5175
5176
sal_Bool SAL_CALL SdDrawPagesAccess::hasByName( const OUString& aName )
5177
0
{
5178
0
    ::SolarMutexGuard aGuard;
5179
5180
0
    if( nullptr == mpModel )
5181
0
        throw lang::DisposedException();
5182
5183
0
    const sal_uInt16 nCount = mpModel->mpDoc->GetSdPageCount( PageKind::Standard );
5184
0
    sal_uInt16 nPage;
5185
0
    for( nPage = 0; nPage < nCount; nPage++ )
5186
0
    {
5187
0
        SdPage* pPage = mpModel->mpDoc->GetSdPage( nPage, PageKind::Standard );
5188
0
        if(nullptr == pPage)
5189
0
            continue;
5190
5191
0
        if( aName == SdDrawPage::getPageApiName( pPage ) )
5192
0
            return true;
5193
0
    }
5194
5195
0
    return false;
5196
0
}
5197
5198
// XElementAccess
5199
uno::Type SAL_CALL SdDrawPagesAccess::getElementType()
5200
0
{
5201
0
    return cppu::UnoType<drawing::XDrawPage>::get();
5202
0
}
5203
5204
sal_Bool SAL_CALL SdDrawPagesAccess::hasElements()
5205
0
{
5206
0
    return getCount() > 0;
5207
0
}
5208
5209
// XDrawPages
5210
5211
/**
5212
 * Creates a new page with model at the specified position.
5213
 * @returns corresponding SdDrawPage
5214
 */
5215
uno::Reference< drawing::XDrawPage > SAL_CALL SdDrawPagesAccess::insertNewByIndex( sal_Int32 nIndex )
5216
169k
{
5217
169k
    ::SolarMutexGuard aGuard;
5218
169k
    comphelper::ProfileZone aZone("insertNewByIndex");
5219
5220
169k
    if( nullptr == mpModel )
5221
0
        throw lang::DisposedException();
5222
5223
169k
    if( mpModel->mpDoc )
5224
169k
    {
5225
169k
        SdPage* pPage = mpModel->InsertSdPage( static_cast<sal_uInt16>(nIndex), false );
5226
169k
        if( pPage )
5227
169k
        {
5228
169k
            uno::Reference< drawing::XDrawPage > xDrawPage( pPage->getUnoPage(), uno::UNO_QUERY );
5229
169k
            return xDrawPage;
5230
169k
        }
5231
169k
    }
5232
0
    uno::Reference< drawing::XDrawPage > xDrawPage;
5233
0
    return xDrawPage;
5234
169k
}
5235
5236
/**
5237
 * Removes the specified SdDrawPage from the model and the internal list. It
5238
 * only works, if there is at least one *normal* page in the model after
5239
 * removing this page.
5240
 */
5241
void SAL_CALL SdDrawPagesAccess::remove( const uno::Reference< drawing::XDrawPage >& xPage )
5242
0
{
5243
0
    ::SolarMutexGuard aGuard;
5244
5245
0
    if( nullptr == mpModel || mpModel->mpDoc == nullptr )
5246
0
        throw lang::DisposedException();
5247
5248
0
    SdDrawDocument& rDoc = *mpModel->mpDoc;
5249
5250
0
    sal_uInt16 nPageCount = rDoc.GetSdPageCount( PageKind::Standard );
5251
0
    if( nPageCount > 1 )
5252
0
    {
5253
        // get pPage from xPage and determine the Id (nPos ) afterwards
5254
0
        SdDrawPage* pSvxPage = comphelper::getFromUnoTunnel<SdDrawPage>( xPage );
5255
0
        if( pSvxPage )
5256
0
        {
5257
0
            SdPage* pPage = static_cast<SdPage*>(pSvxPage->GetSdrPage());
5258
0
            if(pPage && ( pPage->GetPageKind() == PageKind::Standard ) )
5259
0
            {
5260
0
                sal_uInt16 nPage = pPage->GetPageNum();
5261
5262
0
                SdPage* pNotesPage = static_cast< SdPage* >( rDoc.GetPage( nPage+1 ) );
5263
5264
0
                bool bUndo = rDoc.IsUndoEnabled();
5265
0
                if( bUndo )
5266
0
                {
5267
                    // Add undo actions and delete the pages.  The order of adding
5268
                    // the undo actions is important.
5269
0
                    rDoc.BegUndo( SdResId( STR_UNDO_DELETEPAGES ) );
5270
0
                    if (pNotesPage)
5271
0
                    {
5272
0
                        rDoc.AddUndo(rDoc.GetSdrUndoFactory().CreateUndoDeletePage(*pNotesPage));
5273
0
                    }
5274
0
                    rDoc.AddUndo(rDoc.GetSdrUndoFactory().CreateUndoDeletePage(*pPage));
5275
0
                }
5276
5277
0
                rDoc.RemovePage( nPage ); // the page
5278
0
                if (pNotesPage)
5279
0
                {
5280
0
                    rDoc.RemovePage( nPage ); // the notes page
5281
0
                }
5282
5283
0
                if( bUndo )
5284
0
                {
5285
0
                    rDoc.EndUndo();
5286
0
                }
5287
0
            }
5288
0
        }
5289
0
    }
5290
5291
0
    mpModel->SetModified();
5292
0
}
5293
5294
// XServiceInfo
5295
5296
OUString SAL_CALL SdDrawPagesAccess::getImplementationName(  )
5297
0
{
5298
0
    return u"SdDrawPagesAccess"_ustr;
5299
0
}
5300
5301
sal_Bool SAL_CALL SdDrawPagesAccess::supportsService( const OUString& ServiceName )
5302
0
{
5303
0
    return cppu::supportsService(this, ServiceName);
5304
0
}
5305
5306
uno::Sequence< OUString > SAL_CALL SdDrawPagesAccess::getSupportedServiceNames(  )
5307
0
{
5308
0
    return { u"com.sun.star.drawing.DrawPages"_ustr };
5309
0
}
5310
5311
// XComponent
5312
void SAL_CALL SdDrawPagesAccess::dispose(  )
5313
0
{
5314
0
    mpModel = nullptr;
5315
0
}
5316
5317
void SAL_CALL SdDrawPagesAccess::addEventListener( const uno::Reference< lang::XEventListener >&  )
5318
0
{
5319
0
    OSL_FAIL( "not implemented!" );
5320
0
}
5321
5322
void SAL_CALL SdDrawPagesAccess::removeEventListener( const uno::Reference< lang::XEventListener >&  )
5323
0
{
5324
0
    OSL_FAIL( "not implemented!" );
5325
0
}
5326
5327
5328
SdMasterPagesAccess::SdMasterPagesAccess( SdXImpressDocument& rMyModel ) noexcept
5329
18.3k
:   mpModel(&rMyModel)
5330
18.3k
{
5331
18.3k
}
5332
5333
SdMasterPagesAccess::~SdMasterPagesAccess() noexcept
5334
18.3k
{
5335
18.3k
}
5336
5337
// XComponent
5338
void SAL_CALL SdMasterPagesAccess::dispose(  )
5339
0
{
5340
0
    mpModel = nullptr;
5341
0
}
5342
5343
void SAL_CALL SdMasterPagesAccess::addEventListener( const uno::Reference< lang::XEventListener >&  )
5344
0
{
5345
0
    OSL_FAIL( "not implemented!" );
5346
0
}
5347
5348
void SAL_CALL SdMasterPagesAccess::removeEventListener( const uno::Reference< lang::XEventListener >&  )
5349
0
{
5350
0
    OSL_FAIL( "not implemented!" );
5351
0
}
5352
5353
// XIndexAccess
5354
sal_Int32 SAL_CALL SdMasterPagesAccess::getCount()
5355
45.0k
{
5356
45.0k
    ::SolarMutexGuard aGuard;
5357
5358
45.0k
    if( nullptr == mpModel->mpDoc )
5359
0
        throw lang::DisposedException();
5360
5361
45.0k
    return mpModel->mpDoc->GetMasterSdPageCount(PageKind::Standard);
5362
45.0k
}
5363
5364
/**
5365
 * Provides a drawing::XDrawPage interface for accessing the Masterpage at the
5366
 * specified position in the model.
5367
 */
5368
uno::Any SAL_CALL SdMasterPagesAccess::getByIndex( sal_Int32 Index )
5369
5.27k
{
5370
5.27k
    ::SolarMutexGuard aGuard;
5371
5.27k
    comphelper::ProfileZone aZone("SdMasterPagesAccess::getByIndex");
5372
5373
5.27k
    if( nullptr == mpModel )
5374
0
        throw lang::DisposedException();
5375
5376
5.27k
    uno::Any aAny;
5377
5378
5.27k
    if( (Index < 0) || (Index >= mpModel->mpDoc->GetMasterSdPageCount( PageKind::Standard ) ) )
5379
0
        throw lang::IndexOutOfBoundsException();
5380
5381
5.27k
    SdPage* pPage = mpModel->mpDoc->GetMasterSdPage( static_cast<sal_uInt16>(Index), PageKind::Standard );
5382
5.27k
    if( pPage )
5383
5.27k
    {
5384
5.27k
        uno::Reference< drawing::XDrawPage >  xDrawPage( pPage->getUnoPage(), uno::UNO_QUERY );
5385
5.27k
        aAny <<= xDrawPage;
5386
5.27k
    }
5387
5388
5.27k
    return aAny;
5389
5.27k
}
5390
5391
// XElementAccess
5392
uno::Type SAL_CALL SdMasterPagesAccess::getElementType()
5393
0
{
5394
0
    return cppu::UnoType<drawing::XDrawPage>::get();
5395
0
}
5396
5397
sal_Bool SAL_CALL SdMasterPagesAccess::hasElements()
5398
0
{
5399
0
    return getCount() > 0;
5400
0
}
5401
5402
// XDrawPages
5403
uno::Reference< drawing::XDrawPage > SAL_CALL SdMasterPagesAccess::insertNewByIndex( sal_Int32 nInsertPos )
5404
12.7k
{
5405
12.7k
    return insertNewImpl(nInsertPos, std::nullopt);
5406
12.7k
}
5407
5408
// XDrawPages2
5409
uno::Reference< drawing::XDrawPage > SAL_CALL SdMasterPagesAccess::insertNamedNewByIndex( sal_Int32 nInsertPos, const OUString& sName )
5410
11.4k
{
5411
11.4k
    return insertNewImpl(nInsertPos, sName);
5412
11.4k
}
5413
5414
uno::Reference< drawing::XDrawPage > SdMasterPagesAccess::insertNewImpl( sal_Int32 nInsertPos, std::optional<OUString> oPageName )
5415
24.1k
{
5416
24.1k
    ::SolarMutexGuard aGuard;
5417
5418
24.1k
    if( nullptr == mpModel )
5419
0
        throw lang::DisposedException();
5420
5421
24.1k
    uno::Reference< drawing::XDrawPage > xDrawPage;
5422
5423
24.1k
    SdDrawDocument* pDoc = mpModel->mpDoc;
5424
24.1k
    if( pDoc )
5425
24.1k
    {
5426
        // calculate internal index and check for range errors
5427
24.1k
        const sal_Int32 nMPageCount = pDoc->GetMasterPageCount();
5428
24.1k
        nInsertPos = nInsertPos * 2 + 1;
5429
24.1k
        if( nInsertPos < 0 || nInsertPos > nMPageCount )
5430
0
            nInsertPos = nMPageCount;
5431
5432
        // now generate a unique name for the new masterpage
5433
24.1k
        OUString aPrefix;
5434
24.1k
        if (oPageName)
5435
11.4k
            aPrefix = *oPageName;
5436
12.7k
        else
5437
12.7k
        {
5438
12.7k
            const OUString aStdPrefix( SdResId(STR_LAYOUT_DEFAULT_NAME) );
5439
12.7k
            aPrefix = aStdPrefix;
5440
5441
12.7k
            bool bUnique = true;
5442
5443
12.7k
            std::vector<OUString> aPageNames;
5444
158k
            for (sal_Int32 nMaster = 1; nMaster < nMPageCount; ++nMaster)
5445
145k
            {
5446
145k
                const SdPage* pPage = static_cast<const SdPage*>(pDoc->GetMasterPage(static_cast<sal_uInt16>(nMaster)));
5447
145k
                if (!pPage)
5448
0
                    continue;
5449
145k
                aPageNames.push_back(pPage->GetName());
5450
145k
                if (aPageNames.back() == aPrefix)
5451
8.84k
                    bUnique = false;
5452
145k
            }
5453
5454
12.7k
            sal_Int32 i = 0;
5455
37.4k
            while (!bUnique)
5456
24.7k
            {
5457
24.7k
                aPrefix = aStdPrefix + " " + OUString::number(++i);
5458
24.7k
                bUnique = std::find(aPageNames.begin(), aPageNames.end(), aPrefix) == aPageNames.end();
5459
24.7k
            }
5460
12.7k
        }
5461
24.1k
        OUString aLayoutName = aPrefix + SD_LT_SEPARATOR + STR_LAYOUT_OUTLINE;
5462
5463
        // create styles
5464
24.1k
        static_cast<SdStyleSheetPool*>(pDoc->GetStyleSheetPool())->CreateLayoutStyleSheets( aPrefix );
5465
5466
        // get the first page for initial size and border settings
5467
24.1k
        SdPage* pPage = mpModel->mpDoc->GetSdPage( sal_uInt16(0), PageKind::Standard );
5468
24.1k
        SdPage* pRefNotesPage = mpModel->mpDoc->GetSdPage( sal_uInt16(0), PageKind::Notes);
5469
5470
        // create and insert new draw masterpage
5471
24.1k
        rtl::Reference<SdPage> pMPage = mpModel->mpDoc->AllocSdPage(true);
5472
24.1k
        pMPage->SetSize( pPage->GetSize() );
5473
24.1k
        pMPage->SetBorder( pPage->GetLeftBorder(),
5474
24.1k
                           pPage->GetUpperBorder(),
5475
24.1k
                           pPage->GetRightBorder(),
5476
24.1k
                           pPage->GetLowerBorder() );
5477
24.1k
        if (oPageName)
5478
            // no need to update the page URLs on a brand new page
5479
11.4k
            pMPage->SetName(*oPageName, /*bUpdatePageRelativeURLs*/false);
5480
24.1k
        pMPage->SetLayoutName( aLayoutName );
5481
24.1k
        pDoc->InsertMasterPage(pMPage.get(),  static_cast<sal_uInt16>(nInsertPos));
5482
5483
24.1k
        {
5484
            // ensure default MasterPage fill
5485
24.1k
            pMPage->EnsureMasterPageDefaultBackground();
5486
24.1k
        }
5487
5488
24.1k
        xDrawPage.set( pMPage->getUnoPage(), uno::UNO_QUERY );
5489
5490
        // create and insert new notes masterpage
5491
24.1k
        rtl::Reference<SdPage> pMNotesPage = mpModel->mpDoc->AllocSdPage(true);
5492
24.1k
        pMNotesPage->SetSize( pRefNotesPage->GetSize() );
5493
24.1k
        pMNotesPage->SetPageKind(PageKind::Notes);
5494
24.1k
        pMNotesPage->SetBorder( pRefNotesPage->GetLeftBorder(),
5495
24.1k
                                pRefNotesPage->GetUpperBorder(),
5496
24.1k
                                pRefNotesPage->GetRightBorder(),
5497
24.1k
                                pRefNotesPage->GetLowerBorder() );
5498
24.1k
        pMNotesPage->SetLayoutName( aLayoutName );
5499
24.1k
        pDoc->InsertMasterPage(pMNotesPage.get(),  static_cast<sal_uInt16>(nInsertPos) + 1);
5500
24.1k
        pMNotesPage->SetAutoLayout(AUTOLAYOUT_NOTES, true, true);
5501
24.1k
        mpModel->SetModified();
5502
24.1k
    }
5503
5504
24.1k
    return xDrawPage;
5505
24.1k
}
5506
5507
/**
5508
 * Removes the specified SdMasterPage from the model and the internal list. It
5509
 * only works, if there is no *normal* page using this page as MasterPage in
5510
 * the model.
5511
 */
5512
void SAL_CALL SdMasterPagesAccess::remove( const uno::Reference< drawing::XDrawPage >& xPage )
5513
0
{
5514
0
    ::SolarMutexGuard aGuard;
5515
5516
0
    if( nullptr == mpModel || mpModel->mpDoc == nullptr )
5517
0
        throw lang::DisposedException();
5518
5519
0
    SdMasterPage* pSdPage = comphelper::getFromUnoTunnel<SdMasterPage>( xPage );
5520
0
    if(pSdPage == nullptr)
5521
0
        return;
5522
5523
0
    SdPage* pPage = dynamic_cast< SdPage* > (pSdPage->GetSdrPage());
5524
5525
0
    DBG_ASSERT( pPage && pPage->IsMasterPage(), "SdMasterPage is not masterpage?");
5526
5527
0
    if( !pPage || !pPage->IsMasterPage() || (mpModel->mpDoc->GetMasterPageUserCount(pPage) > 0))
5528
0
        return; //Todo: this should be excepted
5529
5530
    // only standard pages can be removed directly
5531
0
    if( pPage->GetPageKind() != PageKind::Standard )
5532
0
        return;
5533
5534
0
    sal_uInt16 nPage = pPage->GetPageNum();
5535
5536
0
    SdDrawDocument& rDoc = *mpModel->mpDoc;
5537
5538
0
    SdPage* pNotesPage = static_cast< SdPage* >( rDoc.GetMasterPage( nPage+1 ) );
5539
5540
0
    bool bUndo = rDoc.IsUndoEnabled();
5541
0
    if( bUndo )
5542
0
    {
5543
        // Add undo actions and delete the pages.  The order of adding
5544
        // the undo actions is important.
5545
0
        rDoc.BegUndo( SdResId( STR_UNDO_DELETEPAGES ) );
5546
0
        rDoc.AddUndo(rDoc.GetSdrUndoFactory().CreateUndoDeletePage(*pNotesPage));
5547
0
        rDoc.AddUndo(rDoc.GetSdrUndoFactory().CreateUndoDeletePage(*pPage));
5548
0
    }
5549
5550
    // remove both pages
5551
0
    rDoc.RemoveMasterPage( nPage );
5552
0
    rDoc.RemoveMasterPage( nPage );
5553
5554
0
    if( bUndo )
5555
0
    {
5556
0
        rDoc.EndUndo();
5557
0
    }
5558
0
}
5559
5560
// XServiceInfo
5561
5562
OUString SAL_CALL SdMasterPagesAccess::getImplementationName(  )
5563
0
{
5564
0
    return u"SdMasterPagesAccess"_ustr;
5565
0
}
5566
5567
sal_Bool SAL_CALL SdMasterPagesAccess::supportsService( const OUString& ServiceName )
5568
0
{
5569
0
    return cppu::supportsService(this, ServiceName);
5570
0
}
5571
5572
uno::Sequence< OUString > SAL_CALL SdMasterPagesAccess::getSupportedServiceNames(  )
5573
0
{
5574
0
    return { u"com.sun.star.drawing.MasterPages"_ustr };
5575
0
}
5576
5577
SdDocLinkTargets::SdDocLinkTargets(SdXImpressDocument& rMyModel)
5578
0
    : mpModel(&rMyModel)
5579
0
{
5580
0
    for (sal_uInt16 i=0; i < SdLinkTargetType::Count; i++)
5581
0
        aNames[i] = SdResId(aTypeResIds[i]);
5582
0
}
5583
5584
SdDocLinkTargets::~SdDocLinkTargets() noexcept
5585
0
{
5586
0
}
5587
5588
// XComponent
5589
void SAL_CALL SdDocLinkTargets::dispose(  )
5590
0
{
5591
0
    mpModel = nullptr;
5592
0
}
5593
5594
void SAL_CALL SdDocLinkTargets::addEventListener( const uno::Reference< lang::XEventListener >&  )
5595
0
{
5596
0
    OSL_FAIL( "not implemented!" );
5597
0
}
5598
5599
void SAL_CALL SdDocLinkTargets::removeEventListener( const uno::Reference< lang::XEventListener >&  )
5600
0
{
5601
0
    OSL_FAIL( "not implemented!" );
5602
0
}
5603
5604
// XNameAccess
5605
uno::Any SAL_CALL SdDocLinkTargets::getByName( const OUString& aName )
5606
0
{
5607
0
    if (mpModel)
5608
0
    {
5609
0
        for (sal_uInt16 i=0; i < SdLinkTargetType::Count; i++)
5610
0
            if ( aNames[i] == aName )
5611
0
                return uno::Any(uno::Reference< beans::XPropertySet >(new SdDocLinkTargetType( mpModel, i )));
5612
0
    }
5613
5614
0
    throw container::NoSuchElementException();
5615
0
}
5616
5617
uno::Sequence< OUString > SAL_CALL SdDocLinkTargets::getElementNames()
5618
0
{
5619
0
    uno::Sequence<OUString> aRet(SdLinkTargetType::Count);
5620
0
    OUString* pArray = aRet.getArray();
5621
0
    for (sal_uInt16 i=0; i < SdLinkTargetType::Count; i++)
5622
0
        pArray[i] = aNames[i];
5623
0
    return aRet;
5624
0
}
5625
5626
sal_Bool SAL_CALL SdDocLinkTargets::hasByName( const OUString& aName )
5627
0
{
5628
0
    for (const auto & i : aNames)
5629
0
        if ( i == aName )
5630
0
            return true;
5631
0
    return false;
5632
0
}
5633
5634
// container::XElementAccess
5635
uno::Type SAL_CALL SdDocLinkTargets::getElementType()
5636
0
{
5637
0
    return cppu::UnoType<beans::XPropertySet>::get();
5638
0
}
5639
5640
sal_Bool SAL_CALL SdDocLinkTargets::hasElements()
5641
0
{
5642
0
    return true;
5643
0
}
5644
5645
SdPage* SdDocLinkTarget::FindPage( std::u16string_view rName ) const
5646
0
{
5647
0
    SdDrawDocument* pDoc = mpModel->GetDoc();
5648
0
    if( pDoc == nullptr )
5649
0
        return nullptr;
5650
5651
0
    const sal_uInt16 nMaxPages = pDoc->GetPageCount();
5652
0
    const sal_uInt16 nMaxMasterPages = pDoc->GetMasterPageCount();
5653
5654
0
    sal_uInt16 nPage;
5655
0
    SdPage* pPage;
5656
5657
0
    const bool bDraw = pDoc->GetDocumentType() == DocumentType::Draw;
5658
5659
    // standard pages
5660
0
    for( nPage = 0; nPage < nMaxPages; nPage++ )
5661
0
    {
5662
0
        pPage = static_cast<SdPage*>(pDoc->GetPage( nPage ));
5663
0
        if( (pPage->GetName() == rName) && (!bDraw || (pPage->GetPageKind() == PageKind::Standard)) )
5664
0
            return pPage;
5665
0
    }
5666
5667
    // master pages
5668
0
    for( nPage = 0; nPage < nMaxMasterPages; nPage++ )
5669
0
    {
5670
0
        pPage = static_cast<SdPage*>(pDoc->GetMasterPage( nPage ));
5671
0
        if( (pPage->GetName() == rName) && (!bDraw || (pPage->GetPageKind() == PageKind::Standard)) )
5672
0
            return pPage;
5673
0
    }
5674
5675
0
    return nullptr;
5676
0
}
5677
5678
// XServiceInfo
5679
OUString SAL_CALL SdDocLinkTargets::getImplementationName()
5680
0
{
5681
0
    return u"SdDocLinkTargets"_ustr;
5682
0
}
5683
5684
sal_Bool SAL_CALL SdDocLinkTargets::supportsService( const OUString& ServiceName )
5685
0
{
5686
0
    return cppu::supportsService( this, ServiceName );
5687
0
}
5688
5689
uno::Sequence< OUString > SAL_CALL SdDocLinkTargets::getSupportedServiceNames()
5690
0
{
5691
0
    return { u"com.sun.star.document.LinkTargets"_ustr };
5692
0
}
5693
5694
SdDocLinkTargetType::SdDocLinkTargetType(SdXImpressDocument* pModel, sal_uInt16 nT)
5695
0
    : mpModel(pModel)
5696
0
    , mnType(nT)
5697
0
{
5698
0
    maName = SdResId(aTypeResIds[nT]);
5699
0
}
5700
5701
// beans::XPropertySet
5702
5703
uno::Reference< beans::XPropertySetInfo > SAL_CALL SdDocLinkTargetType::getPropertySetInfo()
5704
0
{
5705
0
    static uno::Reference< beans::XPropertySetInfo > aRef;//(new SfxItemPropertySetInfo( lcl_GetLinkTargetMap() ));
5706
0
    return aRef;
5707
0
}
5708
5709
void SAL_CALL SdDocLinkTargetType::setPropertyValue(const OUString& /* aPropertyName */,
5710
            const uno::Any& /* aValue */)
5711
0
{
5712
    //  everything is read-only
5713
0
}
5714
5715
uno::Any SAL_CALL SdDocLinkTargetType::getPropertyValue(const OUString& PropertyName)
5716
0
{
5717
0
    uno::Any aRet;
5718
0
    if ( PropertyName == "LinkDisplayName" )
5719
0
        aRet <<= maName;
5720
5721
0
    return aRet;
5722
0
}
5723
5724
void SAL_CALL SdDocLinkTargetType::addPropertyChangeListener( const OUString&,
5725
                            const uno::Reference<beans::XPropertyChangeListener>&)
5726
0
{ OSL_FAIL("not implemented"); }
5727
5728
void SAL_CALL SdDocLinkTargetType::removePropertyChangeListener( const OUString&,
5729
                        const uno::Reference<beans::XPropertyChangeListener>&)
5730
0
{ OSL_FAIL("not implemented"); }
5731
5732
void SAL_CALL SdDocLinkTargetType::addVetoableChangeListener( const OUString&,
5733
                        const uno::Reference<beans::XVetoableChangeListener>&)
5734
0
{ OSL_FAIL("not implemented"); }
5735
5736
void SAL_CALL SdDocLinkTargetType::removeVetoableChangeListener( const OUString&,
5737
                        const uno::Reference<beans::XVetoableChangeListener>&)
5738
0
{ OSL_FAIL("not implemented"); }
5739
5740
// document::XLinkTargetSupplier
5741
5742
uno::Reference< container::XNameAccess > SAL_CALL SdDocLinkTargetType::getLinks()
5743
0
{
5744
0
    return new SdDocLinkTarget( mpModel, mnType );
5745
0
}
5746
5747
// XServiceInfo
5748
OUString SAL_CALL SdDocLinkTargetType::getImplementationName()
5749
0
{
5750
0
    return u"SdDocLinkTargetType"_ustr;
5751
0
}
5752
5753
sal_Bool SAL_CALL SdDocLinkTargetType::supportsService( const OUString& ServiceName )
5754
0
{
5755
0
    return cppu::supportsService( this, ServiceName );
5756
0
}
5757
5758
uno::Sequence< OUString > SAL_CALL SdDocLinkTargetType::getSupportedServiceNames()
5759
0
{
5760
0
    return { u"com.sun.star.document.LinkTargetSupplier"_ustr };
5761
0
}
5762
5763
SdDocLinkTarget::SdDocLinkTarget( SdXImpressDocument* pModel, sal_uInt16 nT )
5764
0
    : mpModel(pModel)
5765
0
    , mnType(nT)
5766
0
{
5767
0
}
5768
5769
// container::XNameAccess
5770
5771
uno::Any SAL_CALL SdDocLinkTarget::getByName(const OUString& aName)
5772
0
{
5773
0
    ::SolarMutexGuard aGuard;
5774
5775
0
    if( nullptr == mpModel )
5776
0
        throw lang::DisposedException();
5777
5778
0
    SdPage* pPage = FindPage( aName );
5779
5780
0
    if( pPage == nullptr )
5781
0
        throw container::NoSuchElementException();
5782
5783
0
    uno::Any aAny;
5784
5785
0
    uno::Reference< beans::XPropertySet > xProps( pPage->getUnoPage(), uno::UNO_QUERY );
5786
0
    if( xProps.is() )
5787
0
        aAny <<= xProps;
5788
5789
0
    return aAny;
5790
0
}
5791
5792
uno::Sequence<OUString> SAL_CALL SdDocLinkTarget::getElementNames()
5793
0
{
5794
0
    ::SolarMutexGuard aGuard;
5795
5796
0
    if( nullptr == mpModel )
5797
0
        throw lang::DisposedException();
5798
5799
0
    SdDrawDocument* pDoc = mpModel->GetDoc();
5800
0
    if( pDoc == nullptr )
5801
0
    {
5802
0
        return { };
5803
0
    }
5804
5805
0
    if( pDoc->GetDocumentType() == DocumentType::Draw )
5806
0
    {
5807
0
        const sal_uInt16 nMaxPages = pDoc->GetSdPageCount( PageKind::Standard );
5808
0
        const sal_uInt16 nMaxMasterPages = pDoc->GetMasterSdPageCount( PageKind::Standard );
5809
5810
0
        uno::Sequence< OUString > aSeq( mnType == SdLinkTargetType::Page ? nMaxPages : nMaxMasterPages );
5811
0
        OUString* pStr = aSeq.getArray();
5812
5813
0
        sal_uInt16 nPage;
5814
0
        if (mnType == SdLinkTargetType::Page)
5815
0
        {
5816
            // standard pages
5817
0
            for( nPage = 0; nPage < nMaxPages; nPage++ )
5818
0
                *pStr++ = pDoc->GetSdPage( nPage, PageKind::Standard )->GetName();
5819
0
        }
5820
0
        else
5821
0
        {
5822
            // master pages
5823
0
            for( nPage = 0; nPage < nMaxMasterPages; nPage++ )
5824
0
                *pStr++ = pDoc->GetMasterSdPage( nPage, PageKind::Standard )->GetName();
5825
0
        }
5826
0
        return aSeq;
5827
0
    }
5828
0
    else
5829
0
    {
5830
0
        PageKind eKind;
5831
0
        switch (mnType)
5832
0
        {
5833
0
            case SdLinkTargetType::Notes:
5834
0
                eKind = PageKind::Notes;
5835
0
                break;
5836
0
            case SdLinkTargetType::Handout:
5837
0
                eKind = PageKind::Handout;
5838
0
                break;
5839
0
            default:
5840
0
                eKind = PageKind::Standard;
5841
0
                break;
5842
0
        }
5843
0
        const sal_uInt16 nMaxPages = pDoc->GetSdPageCount( eKind );
5844
0
        const sal_uInt16 nMaxMasterPages = pDoc->GetMasterPageCount();
5845
5846
0
        uno::Sequence< OUString > aSeq( mnType == SdLinkTargetType::MasterPage ? nMaxMasterPages : nMaxPages );
5847
0
        OUString* pStr = aSeq.getArray();
5848
5849
0
        sal_uInt16 nPage;
5850
0
        switch (mnType)
5851
0
        {
5852
0
            case SdLinkTargetType::Page:
5853
0
            {
5854
0
                for( nPage = 0; nPage < nMaxPages; nPage++ )
5855
0
                    *pStr++ = pDoc->GetSdPage( nPage, PageKind::Standard )->GetName();
5856
0
                break;
5857
0
            }
5858
0
            case SdLinkTargetType::Notes:
5859
0
            {
5860
0
                for( nPage = 0; nPage < nMaxPages; nPage++ )
5861
0
                    *pStr++ = pDoc->GetSdPage( nPage, PageKind::Notes )->GetName();
5862
0
                break;
5863
0
            }
5864
0
            case SdLinkTargetType::Handout:
5865
0
            {
5866
0
                for( nPage = 0; nPage < nMaxPages; nPage++ )
5867
0
                    *pStr++ = pDoc->GetSdPage( nPage, PageKind::Handout )->GetName();
5868
0
                break;
5869
0
            }
5870
0
            case SdLinkTargetType::MasterPage:
5871
0
            {
5872
0
                for( nPage = 0; nPage < nMaxMasterPages; nPage++ )
5873
0
                    *pStr++ = static_cast<SdPage*>(pDoc->GetMasterPage( nPage ))->GetName();
5874
0
                break;
5875
0
            }
5876
0
        }
5877
0
        return aSeq;
5878
0
    }
5879
0
}
5880
5881
sal_Bool SAL_CALL SdDocLinkTarget::hasByName(const OUString& aName)
5882
0
{
5883
0
    ::SolarMutexGuard aGuard;
5884
5885
0
    if( nullptr == mpModel )
5886
0
        throw lang::DisposedException();
5887
5888
0
    return FindPage( aName ) != nullptr;
5889
0
}
5890
5891
// container::XElementAccess
5892
5893
uno::Type SAL_CALL SdDocLinkTarget::getElementType()
5894
0
{
5895
0
    return cppu::UnoType<beans::XPropertySet>::get();
5896
0
}
5897
5898
sal_Bool SAL_CALL SdDocLinkTarget::hasElements()
5899
0
{
5900
0
    ::SolarMutexGuard aGuard;
5901
5902
0
    if( nullptr == mpModel )
5903
0
        throw lang::DisposedException();
5904
5905
0
    return mpModel->GetDoc() != nullptr;
5906
0
}
5907
5908
// XServiceInfo
5909
OUString SAL_CALL SdDocLinkTarget::getImplementationName()
5910
0
{
5911
0
    return u"SdDocLinkTarget"_ustr;
5912
0
}
5913
5914
sal_Bool SAL_CALL SdDocLinkTarget::supportsService( const OUString& ServiceName )
5915
0
{
5916
0
    return cppu::supportsService( this, ServiceName );
5917
0
}
5918
5919
uno::Sequence< OUString > SAL_CALL SdDocLinkTarget::getSupportedServiceNames()
5920
0
{
5921
0
    return { u"com.sun.star.document.LinkTargets"_ustr };
5922
0
}
5923
5924
rtl::Reference< SdXImpressDocument > SdXImpressDocument::GetModel( SdDrawDocument const & rDocument )
5925
245
{
5926
245
    rtl::Reference< SdXImpressDocument > xRet;
5927
245
    ::sd::DrawDocShell* pDocShell(rDocument.GetDocSh());
5928
245
    if( pDocShell )
5929
245
    {
5930
245
        uno::Reference<frame::XModel> xModel(pDocShell->GetModel());
5931
5932
245
        xRet.set( dynamic_cast< SdXImpressDocument* >( xModel.get() ) );
5933
245
    }
5934
5935
245
    return xRet;
5936
245
}
5937
5938
void NotifyDocumentEvent(SdDrawDocument const & rDocument, const OUString& rEventName)
5939
0
{
5940
0
    rtl::Reference<SdXImpressDocument> xModel(SdXImpressDocument::GetModel(rDocument));
5941
5942
0
    if (xModel.is())
5943
0
    {
5944
0
        uno::Reference<uno::XInterface> xSource(static_cast<uno::XWeak*>(xModel.get()));
5945
0
        NotifyDocumentEvent(rDocument, rEventName, xSource);
5946
0
    }
5947
0
}
5948
5949
void NotifyDocumentEvent(SdDrawDocument const & rDocument, const OUString& rEventName, const uno::Reference<uno::XInterface>& xSource)
5950
245
{
5951
245
    rtl::Reference<SdXImpressDocument> xModel(SdXImpressDocument::GetModel(rDocument));
5952
5953
245
    if (xModel.is())
5954
245
    {
5955
245
        css::document::EventObject aEvent(xSource, rEventName);
5956
245
        xModel->notifyEvent(aEvent);
5957
245
    }
5958
245
}
5959
5960
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */