Coverage Report

Created: 2025-12-08 09:28

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/libreoffice/sw/source/uibase/shells/basesh.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 <config_features.h>
21
#include <config_fuzzers.h>
22
23
#include <sal/config.h>
24
25
#include <hintids.hxx>
26
#include <comphelper/servicehelper.hxx>
27
#include <svl/languageoptions.hxx>
28
#include <sfx2/docfile.hxx>
29
#include <sfx2/linkmgr.hxx>
30
#include <sfx2/htmlmode.hxx>
31
#include <svx/imapdlg.hxx>
32
#include <sfx2/dispatch.hxx>
33
#include <sfx2/viewfrm.hxx>
34
#include <sfx2/request.hxx>
35
#include <svl/whiter.hxx>
36
#include <svl/visitem.hxx>
37
#include <editeng/langitem.hxx>
38
#include <svx/clipfmtitem.hxx>
39
#include <svx/contdlg.hxx>
40
#include <vcl/graph.hxx>
41
#include <vcl/inputctx.hxx>
42
#include <svl/slstitm.hxx>
43
#include <svl/ptitem.hxx>
44
#include <svl/stritem.hxx>
45
#include <editeng/colritem.hxx>
46
#include <editeng/fhgtitem.hxx>
47
#include <editeng/fontitem.hxx>
48
#include <editeng/shaditem.hxx>
49
#include <editeng/boxitem.hxx>
50
#include <editeng/brushitem.hxx>
51
#include <editeng/opaqitem.hxx>
52
#include <editeng/sizeitem.hxx>
53
#include <editeng/protitem.hxx>
54
#include <svx/flagsdef.hxx>
55
#include <editeng/scriptsetitem.hxx>
56
#include <sfx2/objface.hxx>
57
#include <fmturl.hxx>
58
#include <fmthdft.hxx>
59
#include <fmtclds.hxx>
60
#include <docsh.hxx>
61
#include <wrtsh.hxx>
62
#include <view.hxx>
63
#include <swmodule.hxx>
64
#include <swundo.hxx>
65
#include <fldbas.hxx>
66
#include <uitool.hxx>
67
#include <basesh.hxx>
68
#include <viewopt.hxx>
69
#include <fontcfg.hxx>
70
#include <fmtsrnd.hxx>
71
#include <fldmgr.hxx>
72
#include <frmmgr.hxx>
73
#include <tablemgr.hxx>
74
#include <mdiexp.hxx>
75
#include <swdtflvr.hxx>
76
#include <pagedesc.hxx>
77
#include <fmtcol.hxx>
78
#include <edtwin.hxx>
79
#include <tblafmt.hxx>
80
#include <swwait.hxx>
81
#include <cmdid.h>
82
#include <strings.hrc>
83
#include <unotxdoc.hxx>
84
#include <doc.hxx>
85
#include <drawdoc.hxx>
86
#include <IDocumentSettingAccess.hxx>
87
#include <IDocumentDrawModelAccess.hxx>
88
#include <IDocumentUndoRedo.hxx>
89
#include <ThemeColorChanger.hxx>
90
#include <swabstdlg.hxx>
91
#include <modcfg.hxx>
92
#include <svx/fmshell.hxx>
93
#include <SwRewriter.hxx>
94
#include <GraphicSizeCheck.hxx>
95
#include <svx/galleryitem.hxx>
96
#include <sfx2/devtools/DevelopmentToolChildWindow.hxx>
97
#include <com/sun/star/gallery/GalleryItemType.hpp>
98
#include <com/sun/star/beans/PropertyValues.hpp>
99
#include <memory>
100
101
102
#include <svx/unobrushitemhelper.hxx>
103
#include <svx/dialog/ThemeDialog.hxx>
104
#include <comphelper/scopeguard.hxx>
105
#include <comphelper/lok.hxx>
106
#include <LibreOfficeKit/LibreOfficeKitEnums.h>
107
#include <osl/diagnose.h>
108
109
#include <svx/svxdlg.hxx>
110
#include <comphelper/sequenceashashmap.hxx>
111
112
#include <shellres.hxx>
113
#include <UndoTable.hxx>
114
115
#include <ndtxt.hxx>
116
#include <UndoManager.hxx>
117
#include <fmtrfmrk.hxx>
118
#include <txtrfmrk.hxx>
119
#include <translatehelper.hxx>
120
#include <rootfrm.hxx>
121
122
FlyMode SwBaseShell::s_eFrameMode = FLY_DRAG_END;
123
124
// These variables keep the state of Gallery (slot SID_GALLERY_BG_BRUSH)
125
// detected by GetGalleryState() for the subsequent ExecuteGallery() call.
126
127
static sal_uInt8 nParagraphPos;
128
static sal_uInt8 nGraphicPos;
129
static sal_uInt8 nOlePos;
130
static sal_uInt8 nFramePos;
131
static sal_uInt8 nTablePos;
132
static sal_uInt8 nTableRowPos;
133
static sal_uInt8 nTableCellPos;
134
static sal_uInt8 nPagePos;
135
static sal_uInt8 nHeaderPos;
136
static sal_uInt8 nFooterPos;
137
138
#define ShellClass_SwBaseShell
139
#include <sfx2/msg.hxx>
140
#include <swslots.hxx>
141
142
#include <AccessibilityCheck.hxx>
143
144
namespace
145
{
146
    SvxContourDlg* GetContourDlg(SwView const &rView)
147
0
    {
148
0
        SfxChildWindow *pWnd = rView.GetViewFrame().GetChildWindow(SvxContourDlgChildWindow::GetChildWindowId());
149
0
        return pWnd ? static_cast<SvxContourDlg*>(pWnd->GetController().get()) : nullptr;
150
0
    }
151
152
    SvxIMapDlg* GetIMapDlg(SwView const &rView)
153
0
    {
154
0
        SfxChildWindow* pWnd = rView.GetViewFrame().GetChildWindow(SvxIMapDlgChildWindow::GetChildWindowId());
155
0
        return pWnd ? static_cast<SvxIMapDlg*>(pWnd->GetController().get()) : nullptr;
156
0
    }
157
}
158
159
using namespace ::com::sun::star;
160
using namespace ::com::sun::star::uno;
161
using namespace ::com::sun::star::frame;
162
163
SFX_IMPL_SUPERCLASS_INTERFACE(SwBaseShell, SfxShell)
164
165
void SwBaseShell::InitInterface_Impl()
166
9
{
167
9
    GetStaticInterface()->RegisterChildWindow(SvxIMapDlgChildWindow::GetChildWindowId());
168
9
    GetStaticInterface()->RegisterChildWindow(SvxContourDlgChildWindow::GetChildWindowId());
169
9
    GetStaticInterface()->RegisterChildWindow(DevelopmentToolChildWindow::GetChildWindowId());
170
9
}
171
172
static void lcl_UpdateIMapDlg( SwWrtShell& rSh )
173
0
{
174
0
    Graphic aGrf( rSh.GetIMapGraphic() );
175
0
    GraphicType nGrfType = aGrf.GetType();
176
0
    void* pEditObj = GraphicType::NONE != nGrfType && GraphicType::Default != nGrfType
177
0
                        ? rSh.GetIMapInventor() : nullptr;
178
0
    TargetList aList;
179
0
    SfxFrame::GetDefaultTargetList(aList);
180
181
0
    SfxItemSet aSet(SfxItemSet::makeFixedSfxItemSet<RES_URL, RES_URL>(rSh.GetAttrPool()));
182
0
    rSh.GetFlyFrameAttr( aSet );
183
0
    const SwFormatURL &rURL = aSet.Get( RES_URL );
184
0
    SvxIMapDlgChildWindow::UpdateIMapDlg(
185
0
            aGrf, rURL.GetMap(), &aList, pEditObj );
186
0
}
187
188
static bool lcl_UpdateContourDlg( SwWrtShell &rSh, SelectionType nSel )
189
0
{
190
0
    Graphic aGraf( rSh.GetIMapGraphic() );
191
0
    GraphicType nGrfType = aGraf.GetType();
192
0
    bool bRet = GraphicType::NONE != nGrfType && GraphicType::Default != nGrfType;
193
0
    if( bRet )
194
0
    {
195
0
        OUString aGrfName;
196
0
        if ( nSel & SelectionType::Graphic )
197
0
            rSh.GetGrfNms( &aGrfName, nullptr );
198
199
0
        SvxContourDlg *pDlg = GetContourDlg(rSh.GetView());
200
0
        if (pDlg)
201
0
        {
202
0
            pDlg->Update(aGraf, !aGrfName.isEmpty(),
203
0
                         rSh.GetGraphicPolygon(), rSh.GetIMapInventor());
204
0
        }
205
0
    }
206
0
    return bRet;
207
0
}
208
209
void SwBaseShell::ExecDelete(SfxRequest &rReq)
210
0
{
211
0
    SwWrtShell &rSh = GetShell();
212
0
    SwEditWin& rTmpEditWin = GetView().GetEditWin();
213
0
    switch(rReq.GetSlot())
214
0
    {
215
0
        case SID_DELETE:
216
0
            if (rSh.GetViewOptions()->IsShowOutlineContentVisibilityButton())
217
0
            {
218
                // Disallow if the cursor is at the end of a paragraph and the document model
219
                // node at this position is an outline node with folded content or the next node
220
                // is an outline node with folded content.
221
0
                if (rSh.IsEndPara())
222
0
                {
223
0
                    SwNodeIndex aIdx(rSh.GetCursor()->GetPointNode());
224
0
                    if (aIdx.GetNode().IsTextNode())
225
0
                    {
226
0
                        if (!aIdx.GetNode().GetTextNode()->GetAttrOutlineContentVisible())
227
0
                            break;
228
0
                        ++aIdx;
229
0
                        if (aIdx.GetNode().IsTextNode())
230
0
                        {
231
0
                            if (!aIdx.GetNode().GetTextNode()->GetAttrOutlineContentVisible())
232
0
                                break;
233
0
                        }
234
0
                    }
235
0
                }
236
0
            }
237
0
            rSh.DelRight();
238
0
            break;
239
240
0
        case FN_BACKSPACE:
241
0
            if (rSh.GetViewOptions()->IsShowOutlineContentVisibilityButton())
242
0
            {
243
                // Disallow if the cursor is at the start of a paragraph and the document model
244
                // node at this position is an outline node with folded content or the previous
245
                // node is a content node without a layout frame.
246
0
                if (rSh.IsSttPara())
247
0
                {
248
0
                    SwNodeIndex aIdx(rSh.GetCursor()->GetPointNode());
249
0
                    if (aIdx.GetNode().IsTextNode())
250
0
                    {
251
0
                        if (!aIdx.GetNode().GetTextNode()->GetAttrOutlineContentVisible())
252
0
                            break;
253
0
                        --aIdx;
254
0
                        if (aIdx.GetNode().IsContentNode() &&
255
0
                                !aIdx.GetNode().GetContentNode()->getLayoutFrame(rSh.GetLayout()))
256
0
                            break;
257
0
                    }
258
0
                }
259
0
            }
260
0
            if( rSh.IsNoNum() )
261
0
            {
262
0
                rSh.SttCursorMove();
263
0
                bool bLeft = rSh.Left( SwCursorSkipMode::Chars, true, 1, false  );
264
0
                if( bLeft )
265
0
                {
266
0
                    rSh.DelLeft();
267
0
                }
268
0
                else
269
                    // JP 15.07.96: If it no longer goes forward, cancel
270
                    //              the numbering. For example at the beginning
271
                    //              of a doc, frame, table or an area.
272
0
                    rSh.DelNumRules();
273
274
0
                rSh.EndCursorMove();
275
0
                break;
276
0
            }
277
278
0
            [[fallthrough]]; // otherwise call DelLeft
279
0
        case FN_SHIFT_BACKSPACE:
280
0
            rSh.DelLeft();
281
0
            break;
282
0
        default:
283
0
            OSL_FAIL("wrong Dispatcher");
284
0
            return;
285
0
    }
286
0
    rReq.Done();
287
288
    //#i42732# - notify the edit window that from now on we do not use the input language
289
0
    rTmpEditWin.SetUseInputLanguage( false );
290
291
    // Test Fieldmark when empty reset the Placeholders
292
0
    const IDocumentMarkAccess* pMarksAccess = rSh.GetDoc()->getIDocumentMarkAccess();
293
0
    for (SwPaM &rPaM : rSh.GetCursor()->GetRingContainer())
294
0
    {
295
0
        const SwPosition* sp = rPaM.Start();
296
        // Legacy text/combo/checkbox: never return read-only when inside these form fields.
297
0
        sw::mark::Fieldmark* pA = pMarksAccess->getInnerFieldmarkFor(*sp);
298
0
        if (pA != nullptr)
299
0
        {
300
0
            if ((IDocumentMarkAccess::GetType(*pA) == IDocumentMarkAccess::MarkType::TEXT_FIELDMARK) &&
301
0
                (pA->GetContent().getLength() == 0)
302
0
               )
303
0
            {
304
0
                pA->ReplaceContent(vEnSpaces);
305
0
                rSh.GotoFieldmark(pA);
306
0
            }
307
0
        }
308
0
    }
309
0
}
310
311
void SwBaseShell::ExecClpbrd(SfxRequest &rReq)
312
0
{
313
    // Attention: At risk of suicide!
314
    // After paste, paste special the shell can be destroy.
315
316
0
    SwWrtShell &rSh = GetShell();
317
0
    sal_uInt16 nId = rReq.GetSlot();
318
0
    bool bIgnore = false;
319
0
    PasteTableType ePasteTable = PasteTableType::PASTE_DEFAULT;
320
321
0
    switch( nId )
322
0
    {
323
0
        case SID_CUT:
324
0
        case SID_COPY:
325
0
            m_rView.GetEditWin().FlushInBuffer();
326
0
            if ( rSh.HasSelection() )
327
0
            {
328
0
                rtl::Reference<SwTransferable> pTransfer = new SwTransferable( rSh );
329
330
0
                if ( nId == SID_CUT && FlyProtectFlags::NONE == rSh.IsSelObjProtected(FlyProtectFlags::Content|FlyProtectFlags::Parent) )
331
0
                    pTransfer->Cut();
332
0
                else
333
0
                {
334
0
                    const bool bLockedView = rSh.IsViewLocked();
335
0
                    rSh.LockView( true );    //lock visible section
336
0
                    pTransfer->Copy();
337
0
                    rSh.LockView( bLockedView );
338
0
                }
339
0
                break;
340
0
            }
341
0
            return;
342
343
0
        case FN_PASTE_NESTED_TABLE:
344
0
        case FN_TABLE_PASTE_ROW_BEFORE:
345
0
        case FN_TABLE_PASTE_COL_BEFORE:
346
0
            switch ( nId )
347
0
            {
348
0
                case FN_PASTE_NESTED_TABLE:
349
0
                     ePasteTable = PasteTableType::PASTE_TABLE;
350
0
                     break;
351
0
                case FN_TABLE_PASTE_ROW_BEFORE:
352
0
                     ePasteTable = PasteTableType::PASTE_ROW;
353
0
                     break;
354
0
                case FN_TABLE_PASTE_COL_BEFORE:
355
0
                     ePasteTable = PasteTableType::PASTE_COLUMN;
356
0
                     break;
357
0
                default:
358
0
                    ;
359
0
            }
360
0
            [[fallthrough]];
361
0
        case SID_PASTE:
362
0
            {
363
0
                TransferableDataHelper aDataHelper(
364
0
                    TransferableDataHelper::CreateFromSystemClipboard( &rSh.GetView().GetEditWin() ) );
365
0
                if( aDataHelper.GetXTransferable().is()
366
0
                    && SwTransferable::IsPaste( rSh, aDataHelper ) )
367
0
                {
368
                    // Temporary variables, because the shell could already be
369
                    // destroyed after the paste.
370
0
                    SwView* pView = &m_rView;
371
372
0
                    RndStdIds nAnchorType = RndStdIds::FLY_AT_PARA;
373
0
                    const SfxUInt16Item* pAnchorType = rReq.GetArg<SfxUInt16Item>(FN_PARAM_1);
374
0
                    if (pAnchorType)
375
0
                        nAnchorType = static_cast<RndStdIds>(pAnchorType->GetValue());
376
0
                    bool bIgnoreComments = false;
377
0
                    const SfxBoolItem* pIgnoreComments = rReq.GetArg<SfxBoolItem>(FN_PARAM_2);
378
0
                    if (pIgnoreComments)
379
0
                        bIgnoreComments = pIgnoreComments->GetValue();
380
381
                    // See if detection should be used.
382
0
                    bool bSkipDetection = false;
383
0
                    const SfxBoolItem* pSkipDetection = rReq.GetArg<SfxBoolItem>(FN_PARAM_3);
384
0
                    if (pSkipDetection)
385
0
                        bSkipDetection = pSkipDetection->GetValue();
386
387
0
                    SwTransferable::Paste(rSh, aDataHelper, nAnchorType, bIgnoreComments, ePasteTable, !bSkipDetection);
388
389
0
                    if( rSh.IsFrameSelected() || rSh.GetSelectedObjCount() )
390
0
                        rSh.EnterSelFrameMode();
391
0
                    pView->AttrChangedNotify(nullptr);
392
393
                    // Fold pasted outlines that have outline content visible attribute false
394
0
                    MakeAllOutlineContentTemporarilyVisible a(rSh.GetDoc());
395
0
                }
396
0
                else
397
0
                    return;
398
0
            }
399
0
            break;
400
401
0
        case SID_CLIPBOARD_FORMAT_ITEMS:
402
0
            {
403
0
                const SfxItemSet* pArgs = rReq.GetArgs();
404
0
                const SfxPoolItem* pFormat;
405
0
                if( pArgs && SfxItemState::SET == pArgs->GetItemState( nId, false, &pFormat ) )
406
0
                {
407
0
                    TransferableDataHelper aDataHelper(
408
0
                        TransferableDataHelper::CreateFromSystemClipboard(
409
0
                                            &rSh.GetView().GetEditWin()) );
410
0
                    if( aDataHelper.GetXTransferable().is()
411
0
                        /*&& SwTransferable::IsPaste( rSh, aDataHelper )*/ )
412
0
                    {
413
                        // Temporary variables, because the shell could already be
414
                        // destroyed after the paste.
415
0
                        SwView* pView = &m_rView;
416
417
0
                        SwTransferable::PasteFormat( rSh, aDataHelper,
418
0
                                        static_cast<SotClipboardFormatId>(static_cast<const SfxUInt32Item*>(pFormat)->GetValue()) );
419
420
                        //Done() has to be called before the shell has been removed
421
0
                        rReq.Done();
422
0
                        bIgnore = true;
423
0
                        if( rSh.IsFrameSelected() || rSh.GetSelectedObjCount())
424
0
                            rSh.EnterSelFrameMode();
425
0
                        pView->AttrChangedNotify(nullptr);
426
427
                        // Fold pasted outlines that have outline content visible attribute false
428
0
                        MakeAllOutlineContentTemporarilyVisible a(rSh.GetDoc());
429
0
                    }
430
0
                }
431
0
            }
432
0
            break;
433
434
0
        case SID_PASTE_UNFORMATTED:
435
0
            {
436
0
                TransferableDataHelper aDataHelper(
437
0
                    TransferableDataHelper::CreateFromSystemClipboard( &rSh.GetView().GetEditWin()) );
438
0
                if( aDataHelper.GetXTransferable().is()
439
0
                    && SwTransferable::IsPaste( rSh, aDataHelper ) )
440
0
                {
441
                    // Temporary variables, because the shell could already be
442
                    // destroyed after the paste.
443
0
                    SwView* pView = &m_rView;
444
0
                    rReq.Ignore();
445
0
                    bIgnore = true;
446
0
                    if(SwTransferable::PasteUnformatted( rSh, aDataHelper ))
447
0
                    {
448
0
                        SfxViewFrame& rViewFrame = pView->GetViewFrame();
449
0
                        uno::Reference< frame::XDispatchRecorder > xRecorder =
450
0
                            rViewFrame.GetBindings().GetRecorder();
451
0
                        if(xRecorder.is()) {
452
0
                            SfxRequest aReq(rViewFrame, SID_CLIPBOARD_FORMAT_ITEMS);
453
0
                            aReq.AppendItem( SfxUInt32Item( SID_CLIPBOARD_FORMAT_ITEMS, static_cast<sal_uInt32>(SotClipboardFormatId::STRING) ) );
454
0
                            aReq.Done();
455
0
                        }
456
0
                    }
457
458
0
                    if (rSh.IsFrameSelected() || rSh.GetSelectedObjCount())
459
0
                        rSh.EnterSelFrameMode();
460
0
                    pView->AttrChangedNotify(nullptr);
461
462
                    // Fold pasted outlines that have outline content visible attribute false
463
0
                    MakeAllOutlineContentTemporarilyVisible a(rSh.GetDoc());
464
0
                }
465
0
                else
466
0
                    return;
467
0
            }
468
0
            break;
469
470
0
        case SID_PASTE_SPECIAL:
471
0
            {
472
0
                std::shared_ptr<const TransferableDataHelper> aDataHelper =
473
0
                    std::make_shared<TransferableDataHelper>(TransferableDataHelper::CreateFromSystemClipboard( &rSh.GetView().GetEditWin()));
474
475
0
                if( aDataHelper->GetXTransferable().is()
476
0
                    && SwTransferable::IsPaste( rSh, *aDataHelper )
477
0
                    && !rSh.CursorInsideInputField() )
478
0
                {
479
0
                    rReq.Ignore();
480
0
                    bIgnore = true;
481
482
0
                    SvxAbstractDialogFactory* pFact = SvxAbstractDialogFactory::Create();
483
0
                    VclPtr<SfxAbstractPasteDialog> pDlg(pFact->CreatePasteDialog( rReq.GetFrameWeld() ));
484
485
                    // Prepare the dialog
486
0
                    SwTransferable::PrePasteSpecial(rSh, *aDataHelper, pDlg);
487
0
                    pDlg->PreGetFormat(*aDataHelper);
488
489
490
0
                    pDlg->StartExecuteAsync(
491
0
                        [aDataHelper=std::move(aDataHelper), pDlg, &rSh, this](sal_Int32 nResult)
492
0
                        {
493
0
                            if (nResult == RET_OK)
494
0
                            {
495
                                // Temporary variables, because the shell could already be
496
                                // destroyed after the paste.
497
0
                                SwView* pView = &m_rView;
498
0
                                bool bRet = false;
499
0
                                SotClipboardFormatId nFormatId = pDlg->GetFormatOnly();
500
501
0
                                if( nFormatId != SotClipboardFormatId::NONE )
502
0
                                    bRet = SwTransferable::PasteFormat( rSh, *aDataHelper, nFormatId );
503
504
0
                                if (bRet)
505
0
                                {
506
0
                                    SfxViewFrame& rViewFrame = pView->GetViewFrame();
507
0
                                    uno::Reference< frame::XDispatchRecorder > xRecorder =
508
0
                                            rViewFrame.GetBindings().GetRecorder();
509
0
                                    if(xRecorder.is()) {
510
0
                                        SfxRequest aReq(rViewFrame, SID_CLIPBOARD_FORMAT_ITEMS);
511
0
                                        aReq.AppendItem( SfxUInt32Item( SID_CLIPBOARD_FORMAT_ITEMS, static_cast<sal_uInt32>(nFormatId) ) );
512
0
                                        aReq.Done();
513
0
                                    }
514
0
                                }
515
516
0
                                if (rSh.IsFrameSelected() || rSh.GetSelectedObjCount())
517
0
                                    rSh.EnterSelFrameMode();
518
0
                                pView->AttrChangedNotify(nullptr);
519
520
                                // Fold pasted outlines that have outline content visible attribute false
521
0
                                MakeAllOutlineContentTemporarilyVisible a(rSh.GetDoc());
522
0
                            }
523
524
0
                            pDlg->disposeOnce();
525
0
                        }
526
0
                    );
527
0
                }
528
0
                else
529
0
                    return;
530
0
            }
531
0
            break;
532
533
0
        default:
534
0
            OSL_FAIL("wrong Dispatcher");
535
0
            return;
536
0
    }
537
0
    if(!bIgnore)
538
0
        rReq.Done();
539
0
}
540
541
// ClipBoard state
542
543
void SwBaseShell::StateClpbrd(SfxItemSet &rSet)
544
0
{
545
0
    SwWrtShell &rSh = GetShell();
546
0
    SfxWhichIter aIter(rSet);
547
548
0
    const bool bCopy = rSh.HasSelection();
549
550
0
    sal_uInt16 nWhich = aIter.FirstWhich();
551
552
0
    while(nWhich)
553
0
    {
554
0
        switch(nWhich)
555
0
        {
556
0
        case SID_CUT:
557
0
            if( FlyProtectFlags::NONE != rSh.IsSelObjProtected(FlyProtectFlags::Content|FlyProtectFlags::Parent ) )
558
0
            {
559
0
                rSet.DisableItem( nWhich );
560
0
                break;
561
0
            }
562
0
            [[fallthrough]];
563
0
        case SID_COPY:
564
0
            if( !bCopy || GetObjectShell()->isContentExtractionLocked())
565
0
                rSet.DisableItem( nWhich );
566
0
            break;
567
568
0
        case FN_PASTE_NESTED_TABLE:
569
0
        case FN_TABLE_PASTE_ROW_BEFORE:
570
0
        case FN_TABLE_PASTE_COL_BEFORE:
571
0
            if( !rSh.IsCursorInTable()
572
0
                || !GetView().IsPasteSpecialAllowed()
573
0
                || rSh.CursorInsideInputField()
574
                // disable if not a native Writer table and not a spreadsheet format
575
0
                || !GetView().IsPasteSpreadsheet(rSh.GetTableCopied()) )
576
0
            {
577
0
                rSet.DisableItem( nWhich );
578
0
            }
579
0
            break;
580
581
0
        case SID_PASTE:
582
0
            if( !GetView().IsPasteAllowed() )
583
0
            {
584
0
                rSet.DisableItem( nWhich );
585
0
            }
586
0
            break;
587
588
0
        case SID_PASTE_SPECIAL:
589
0
            if( !GetView().IsPasteSpecialAllowed()
590
0
                || rSh.CursorInsideInputField() )
591
0
            {
592
0
                rSet.DisableItem( nWhich );
593
0
            }
594
0
            break;
595
596
0
        case SID_PASTE_UNFORMATTED:
597
0
            if( !GetView().IsPasteSpecialAllowed() )
598
0
            {
599
0
                rSet.DisableItem( nWhich );
600
0
            }
601
0
            break;
602
603
0
        case SID_CLIPBOARD_FORMAT_ITEMS:
604
0
            {
605
0
                TransferableDataHelper aDataHelper(
606
0
                    TransferableDataHelper::CreateFromSystemClipboard(
607
0
                                            &rSh.GetView().GetEditWin()) );
608
609
0
                SvxClipboardFormatItem aFormatItem( SID_CLIPBOARD_FORMAT_ITEMS );
610
0
                SwTransferable::FillClipFormatItem( rSh, aDataHelper, aFormatItem );
611
0
                rSet.Put( aFormatItem );
612
0
            }
613
0
            break;
614
0
        }
615
0
        nWhich = aIter.NextWhich();
616
0
    }
617
0
}
618
619
// Perform undo
620
621
void SwBaseShell::ExecUndo(SfxRequest &rReq)
622
0
{
623
0
    MakeAllOutlineContentTemporarilyVisible a(GetShell().GetDoc(), true);
624
625
0
    SwWrtShell &rWrtShell = GetShell();
626
627
0
    SwUndoId nUndoId(SwUndoId::EMPTY);
628
0
    sal_uInt16 nId = rReq.GetSlot(), nCnt = 1;
629
0
    const SfxItemSet* pArgs = rReq.GetArgs();
630
0
    const SfxPoolItem* pItem;
631
0
    if( pArgs && SfxItemState::SET == pArgs->GetItemState( nId, false, &pItem ))
632
0
        nCnt = static_cast<const SfxUInt16Item*>(pItem)->GetValue();
633
634
    // Repair mode: allow undo/redo of all undo actions, even if access would
635
    // be limited based on the view shell ID.
636
0
    bool bRepair = false;
637
0
    const SfxBoolItem* pRepairItem;
638
0
    if (pArgs && (pRepairItem = pArgs->GetItemIfSet(SID_REPAIRPACKAGE, false)))
639
0
        bRepair = pRepairItem->GetValue();
640
641
    // #i106349#: save pointer: undo/redo may delete the shell, i.e., this!
642
0
    SfxViewFrame& rViewFrame( GetView().GetViewFrame() );
643
644
0
    IDocumentUndoRedo& rUndoRedo = rWrtShell.GetIDocumentUndoRedo();
645
0
    bool bWasRepair = rUndoRedo.DoesRepair();
646
0
    rUndoRedo.DoRepair(bRepair);
647
0
    comphelper::ScopeGuard aGuard([&rUndoRedo, bWasRepair]()
648
0
    {
649
0
        rUndoRedo.DoRepair(bWasRepair);
650
0
    });
651
652
0
    switch( nId )
653
0
    {
654
0
        case SID_UNDO:
655
0
            if (rUndoRedo.GetLastUndoInfo(nullptr, &nUndoId, &rWrtShell.GetView()))
656
0
            {
657
0
                for (SwViewShell& rShell : rWrtShell.GetRingContainer())
658
0
                    rShell.LockPaint(LockPaintReason::Undo);
659
660
0
                sal_uInt16 nUndoOffset = 0;
661
0
                if (comphelper::LibreOfficeKit::isActive() && !bRepair && nCnt == 1)
662
0
                {
663
0
                    sw::UndoManager& rManager = rWrtShell.GetDoc()->GetUndoManager();
664
0
                    const SfxUndoAction* pAction = rManager.GetUndoAction();
665
0
                    SwView& rView = rWrtShell.GetView();
666
0
                    ViewShellId nViewShellId = rView.GetViewShellId();
667
0
                    sal_uInt16 nOffset = 0;
668
0
                    if (pAction->GetViewShellId() != nViewShellId
669
0
                        && rManager.IsViewUndoActionIndependent(&rView, nOffset))
670
0
                    {
671
                        // Execute the undo with an offset: don't undo the top action, but an
672
                        // earlier one, since it's independent and that belongs to our view.
673
0
                        nUndoOffset += nOffset;
674
0
                    }
675
0
                }
676
677
0
                rWrtShell.Do(SwWrtShell::UNDO, nCnt, nUndoOffset);
678
679
0
                for (SwViewShell& rShell : rWrtShell.GetRingContainer())
680
0
                    rShell.UnlockPaint();
681
0
            }
682
0
            break;
683
684
0
        case SID_REDO:
685
0
            if (rUndoRedo.GetFirstRedoInfo(nullptr, &nUndoId, &rWrtShell.GetView()))
686
0
            {
687
0
                for (SwViewShell& rShell : rWrtShell.GetRingContainer())
688
0
                    rShell.LockPaint(LockPaintReason::Redo);
689
0
                rWrtShell.Do( SwWrtShell::REDO, nCnt );
690
0
                for (SwViewShell& rShell : rWrtShell.GetRingContainer())
691
0
                    rShell.UnlockPaint();
692
0
            }
693
0
            break;
694
695
0
        case SID_REPEAT:
696
0
            rWrtShell.Do( SwWrtShell::REPEAT );
697
0
            break;
698
0
        default:
699
0
            OSL_FAIL("wrong Dispatcher");
700
0
    }
701
702
0
    if (nUndoId == SwUndoId::CONFLICT)
703
0
    {
704
0
        rReq.SetReturnValue( SfxUInt32Item(nId, static_cast<sal_uInt32>(SID_REPAIRPACKAGE)) );
705
0
    }
706
707
0
    rViewFrame.GetBindings().InvalidateAll(false);
708
0
}
709
710
// State of undo
711
712
void SwBaseShell::StateUndo(SfxItemSet &rSet)
713
0
{
714
0
    SwUndoId nUndoId(SwUndoId::EMPTY);
715
0
    SwWrtShell &rSh = GetShell();
716
0
    SfxWhichIter aIter(rSet);
717
0
    sal_uInt16 nWhich = aIter.FirstWhich();
718
0
    while(nWhich)
719
0
    {
720
0
        switch(nWhich)
721
0
        {
722
0
            case SID_UNDO:
723
0
            {
724
0
                if (rSh.GetLastUndoInfo(nullptr, &nUndoId, &rSh.GetView()))
725
0
                {
726
0
                    rSet.Put( SfxStringItem(nWhich,
727
0
                        rSh.GetDoString(SwWrtShell::UNDO)));
728
0
                }
729
0
                else if (nUndoId == SwUndoId::CONFLICT)
730
0
                {
731
0
                    rSet.Put( SfxUInt32Item(nWhich, static_cast<sal_uInt32>(SID_REPAIRPACKAGE)) );
732
0
                }
733
0
                else
734
0
                    rSet.DisableItem(nWhich);
735
736
0
                break;
737
0
            }
738
0
            case SID_REDO:
739
0
            {
740
0
                if (rSh.GetFirstRedoInfo(nullptr, &nUndoId, &rSh.GetView()))
741
0
                {
742
0
                    rSet.Put(SfxStringItem(nWhich,
743
0
                        rSh.GetDoString(SwWrtShell::REDO)));
744
0
                }
745
0
                else if (nUndoId == SwUndoId::CONFLICT)
746
0
                {
747
0
                     rSet.Put( SfxInt32Item(nWhich, static_cast<sal_uInt32>(SID_REPAIRPACKAGE)) );
748
0
                }
749
0
                else
750
0
                    rSet.DisableItem(nWhich);
751
0
                break;
752
0
            }
753
0
            case SID_REPEAT:
754
0
            {   // Repeat is only possible if no REDO is possible - UI-Restriction
755
0
                if ((!rSh.GetFirstRedoInfo(nullptr, nullptr)) &&
756
0
                    !rSh.IsSelFrameMode() &&
757
0
                    (SwUndoId::EMPTY != rSh.GetRepeatInfo(nullptr)))
758
0
                {
759
0
                    rSet.Put(SfxStringItem(nWhich, rSh.GetRepeatString()));
760
0
                }
761
0
                else
762
0
                    rSet.DisableItem(nWhich);
763
0
                break;
764
0
            }
765
766
0
            case SID_GETUNDOSTRINGS:
767
0
                if (rSh.GetLastUndoInfo(nullptr, nullptr))
768
0
                {
769
0
                    SfxStringListItem aStrLst( nWhich );
770
0
                    rSh.GetDoStrings( SwWrtShell::UNDO, aStrLst );
771
0
                    rSet.Put( aStrLst );
772
0
                }
773
0
                else
774
0
                    rSet.DisableItem( nWhich );
775
0
                break;
776
777
0
            case SID_GETREDOSTRINGS:
778
0
                if (rSh.GetFirstRedoInfo(nullptr, nullptr))
779
0
                {
780
0
                    SfxStringListItem aStrLst( nWhich );
781
0
                    rSh.GetDoStrings( SwWrtShell::REDO, aStrLst );
782
0
                    rSet.Put( aStrLst );
783
0
                }
784
0
                else
785
0
                    rSet.DisableItem( nWhich );
786
0
                break;
787
0
        }
788
0
        nWhich = aIter.NextWhich();
789
0
    }
790
0
}
791
792
namespace
793
{
794
/// Searches for the specified field type and field name prefix and update the matching fields to
795
/// have the provided new name and content.
796
bool UpdateFieldContents(const SfxRequest& rReq, SwWrtShell& rWrtSh)
797
0
{
798
0
    const SfxStringItem* pTypeName = rReq.GetArg<SfxStringItem>(FN_PARAM_1);
799
0
    if (!pTypeName || pTypeName->GetValue() != "SetRef")
800
0
    {
801
        // This is implemented so far only for reference marks.
802
0
        return false;
803
0
    }
804
805
0
    const SfxStringItem* pNamePrefix = rReq.GetArg<SfxStringItem>(FN_PARAM_2);
806
0
    if (!pNamePrefix)
807
0
    {
808
0
        return false;
809
0
    }
810
0
    const OUString& rNamePrefix = pNamePrefix->GetValue();
811
812
0
    const SfxUnoAnyItem* pFields = rReq.GetArg<SfxUnoAnyItem>(FN_PARAM_3);
813
0
    if (!pFields)
814
0
    {
815
0
        return false;
816
0
    }
817
818
0
    bool bNeverExpand = false;
819
0
    const SfxBoolItem* pNeverExpand = rReq.GetArg<SfxBoolItem>(FN_PARAM_6);
820
0
    if (pNeverExpand)
821
0
    {
822
0
        bNeverExpand = pNeverExpand->GetValue();
823
0
    }
824
0
    uno::Sequence<beans::PropertyValues> aFields;
825
0
    pFields->GetValue() >>= aFields;
826
827
0
    SwDoc* pDoc = rWrtSh.GetDoc();
828
0
    pDoc->GetIDocumentUndoRedo().StartUndo(SwUndoId::UPDATE_FIELDS, nullptr);
829
0
    rWrtSh.StartAction();
830
831
0
    std::vector<const SwFormatRefMark*> aRefMarks;
832
0
    pDoc->GetRefMarks(aRefMarks);
833
834
0
    std::sort(aRefMarks.begin(), aRefMarks.end(),
835
0
              [](const SwFormatRefMark* pMark1, const SwFormatRefMark* pMark2) -> bool {
836
0
                  const SwTextRefMark* pTextRefMark1 = pMark1->GetTextRefMark();
837
0
                  const SwTextRefMark* pTextRefMark2 = pMark2->GetTextRefMark();
838
0
                  SwPosition aPos1(pTextRefMark1->GetTextNode(), pTextRefMark1->GetStart());
839
0
                  SwPosition aPos2(pTextRefMark2->GetTextNode(), pTextRefMark2->GetStart());
840
0
                  return aPos1 < aPos2;
841
0
              });
842
843
0
    sal_uInt16 nFieldIndex = 0;
844
0
    for (auto& pIntermediateRefMark : aRefMarks)
845
0
    {
846
0
        auto pRefMark = const_cast<SwFormatRefMark*>(pIntermediateRefMark);
847
0
        if (!pRefMark->GetRefName().toString().startsWith(rNamePrefix))
848
0
        {
849
0
            continue;
850
0
        }
851
852
0
        auto pTextRefMark = const_cast<SwTextRefMark*>(pRefMark->GetTextRefMark());
853
0
        if (bNeverExpand)
854
0
        {
855
0
            pTextRefMark->SetDontExpand(true);
856
0
            pTextRefMark->SetLockExpandFlag(true);
857
0
            pTextRefMark->SetDontExpandStartAttr(true);
858
0
        }
859
860
0
        if (nFieldIndex >= aFields.getLength())
861
0
        {
862
            // earlier we used to break here
863
            // but now we need to set expand flags for each refmark
864
0
            continue;
865
0
        }
866
0
        comphelper::SequenceAsHashMap aMap(aFields[nFieldIndex++]);
867
0
        pRefMark->GetRefName() = SwMarkName(aMap[u"Name"_ustr].get<OUString>());
868
869
0
        pTextRefMark->UpdateFieldContent(pDoc, rWrtSh, aMap[u"Content"_ustr].get<OUString>());
870
0
    }
871
872
0
    rWrtSh.EndAction();
873
0
    pDoc->GetIDocumentUndoRedo().EndUndo(SwUndoId::UPDATE_FIELDS, nullptr);
874
0
    return true;
875
0
}
876
877
/// Searches for the specified field type and field name prefix under cursor and update the matching
878
/// field to have the provided new name and content.
879
void UpdateFieldContent(const SfxRequest& rReq, SwWrtShell& rWrtSh)
880
0
{
881
0
    const SfxStringItem* pTypeName = rReq.GetArg<SfxStringItem>(FN_PARAM_1);
882
0
    if (!pTypeName || pTypeName->GetValue() != "SetRef")
883
0
    {
884
        // This is implemented so far only for reference marks.
885
0
        return;
886
0
    }
887
888
0
    const SfxStringItem* pNamePrefix = rReq.GetArg<SfxStringItem>(FN_PARAM_2);
889
0
    if (!pNamePrefix)
890
0
    {
891
0
        return;
892
0
    }
893
0
    const OUString& rNamePrefix = pNamePrefix->GetValue();
894
895
0
    const SfxUnoAnyItem* pField = rReq.GetArg<SfxUnoAnyItem>(FN_PARAM_3);
896
0
    if (!pField)
897
0
    {
898
0
        return;
899
0
    }
900
0
    uno::Sequence<beans::PropertyValue> aField;
901
0
    pField->GetValue() >>= aField;
902
903
0
    SwPosition& rCursor = *rWrtSh.GetCursor()->GetPoint();
904
0
    SwTextNode* pTextNode = rCursor.GetNode().GetTextNode();
905
0
    std::vector<SwTextAttr*> aAttrs
906
0
        = pTextNode->GetTextAttrsAt(rCursor.GetContentIndex(), RES_TXTATR_REFMARK);
907
0
    if (aAttrs.empty())
908
0
    {
909
0
        return;
910
0
    }
911
912
0
    auto& rRefmark = const_cast<SwFormatRefMark&>(aAttrs[0]->GetRefMark());
913
0
    if (!rRefmark.GetRefName().toString().startsWith(rNamePrefix))
914
0
    {
915
0
        return;
916
0
    }
917
918
0
    SwDoc* pDoc = rWrtSh.GetDoc();
919
0
    SwRewriter aRewriter;
920
0
    aRewriter.AddRule(UndoArg1, rRefmark.GetRefName());
921
0
    pDoc->GetIDocumentUndoRedo().StartUndo(SwUndoId::UPDATE_FIELD, &aRewriter);
922
0
    rWrtSh.StartAction();
923
0
    comphelper::ScopeGuard g(
924
0
        [&rWrtSh, &aRewriter]
925
0
        {
926
0
            rWrtSh.EndAction();
927
0
            rWrtSh.GetDoc()->GetIDocumentUndoRedo().EndUndo(SwUndoId::UPDATE_FIELD, &aRewriter);
928
0
        });
929
930
0
    comphelper::SequenceAsHashMap aMap(aField);
931
0
    rRefmark.GetRefName() = SwMarkName(aMap[u"Name"_ustr].get<OUString>());
932
933
0
    OUString aContent = aMap[u"Content"_ustr].get<OUString>();
934
0
    auto pTextRefMark = const_cast<SwTextRefMark*>(rRefmark.GetTextRefMark());
935
0
    pTextRefMark->UpdateFieldContent(pDoc, rWrtSh, aContent);
936
0
}
937
}
938
939
// Evaluate respectively dispatching the slot Id
940
941
void SwBaseShell::Execute(SfxRequest &rReq)
942
0
{
943
0
    const SfxPoolItem *pItem;
944
0
    SwWrtShell &rSh = GetShell();
945
0
    const SfxItemSet* pArgs = rReq.GetArgs();
946
0
    bool bMore = false;
947
948
0
    sal_uInt16 nSlot = rReq.GetSlot();
949
0
    switch(nSlot)
950
0
    {
951
0
        case FN_REPAGINATE:
952
0
            {
953
0
                Reference < XModel > xModel = GetView().GetDocShell()->GetModel();
954
0
                auto pDoc = comphelper::getFromUnoTunnel<SwXTextDocument>(xModel);
955
0
                pDoc->NotifyRefreshListeners();
956
0
                rSh.CalcLayout();
957
0
            }
958
0
            break;
959
0
        case FN_UPDATE_FIELDS:
960
0
            {
961
0
                if (UpdateFieldContents(rReq, rSh))
962
0
                {
963
                    // Parameters indicated that the name / content of fields has to be updated to
964
                    // the provided values, don't do an actual fields update.
965
0
                    break;
966
0
                }
967
968
0
                rSh.UpdateDocStat();
969
0
                rSh.EndAllTableBoxEdit();
970
0
                rSh.SwViewShell::UpdateFields(true);
971
972
0
                if( rSh.IsCursorInTable() )
973
0
                {
974
0
                    if( !rSh.IsTableComplexForChart() )
975
0
                        SwTableFUNC( &rSh ).UpdateChart();
976
0
                    rSh.ClearTableBoxContent();
977
0
                    rSh.SaveTableBoxContent();
978
0
                }
979
0
            }
980
0
            break;
981
0
        case FN_UPDATE_FIELD:
982
0
            {
983
0
                UpdateFieldContent(rReq, rSh);
984
0
            }
985
0
            break;
986
0
        case FN_UPDATE_CHARTS:
987
0
            {
988
0
                SwWait aWait( *m_rView.GetDocShell(), true );
989
0
                rSh.UpdateAllCharts();
990
0
            }
991
0
            break;
992
993
0
        case FN_UPDATE_ALL:
994
0
            {
995
0
                comphelper::EmbeddedObjectContainer& rEmbeddedObjectContainer
996
0
                    = GetObjectShell()->getEmbeddedObjectContainer();
997
0
                rEmbeddedObjectContainer.setUserAllowsLinkUpdate(true);
998
999
0
                SwView&  rTempView = GetView();
1000
0
                rSh.EnterStdMode();
1001
0
                if( !rSh.GetLinkManager().GetLinks().empty() )
1002
0
                {
1003
0
                    rSh.StartAllAction();
1004
0
                    SfxMedium * medium = nullptr;
1005
0
                    if (auto const sh = rSh.GetDoc()->GetDocShell()) {
1006
0
                        medium = sh->GetMedium();
1007
0
                    }
1008
0
                    rSh.GetLinkManager().UpdateAllLinks(
1009
0
                        false, true, nullptr, medium == nullptr ? OUString() : medium->GetName() );
1010
0
                    rSh.EndAllAction();
1011
0
                }
1012
0
                SfxDispatcher &rDis = *rTempView.GetViewFrame().GetDispatcher();
1013
0
                rDis.Execute( FN_UPDATE_FIELDS );
1014
0
                rDis.Execute( FN_UPDATE_TOX );
1015
0
                rDis.Execute( FN_UPDATE_CHARTS );
1016
0
                rSh.Reformat();
1017
0
                rSh.UpdateOleObjectPreviews();
1018
0
            }
1019
0
            break;
1020
1021
0
        case FN_UPDATE_INPUTFIELDS:
1022
0
            rSh.UpdateInputFields();
1023
0
            break;
1024
1025
0
        case FN_PREV_BOOKMARK:
1026
0
            rReq.SetReturnValue(SfxBoolItem( nSlot, rSh.GoPrevBookmark()));
1027
0
            break;
1028
0
        case FN_NEXT_BOOKMARK:
1029
0
            rReq.SetReturnValue(SfxBoolItem( nSlot, rSh.GoNextBookmark()));
1030
0
            break;
1031
1032
0
        case FN_GOTO_NEXT_MARK:
1033
0
        case FN_GOTO_PREV_MARK:
1034
0
        {
1035
0
            SwFieldMgr aFieldMgr;
1036
0
            SwFieldType* pFieldType = aFieldMgr.GetFieldType(SwFieldIds::JumpEdit);
1037
1038
0
            if (pFieldType)
1039
0
            {
1040
0
                if (rSh.IsSelFrameMode())
1041
0
                {
1042
0
                    rSh.UnSelectFrame();
1043
0
                    rSh.LeaveSelFrameMode();
1044
0
                }
1045
1046
0
                if (rSh.HasMark())
1047
0
                {
1048
0
                    SwMvContext aMvContext(&rSh);
1049
0
                    if (rSh.IsCursorPtAtEnd())
1050
0
                        rSh.SwapPam();
1051
0
                    rSh.ClearMark();
1052
0
                    rSh.EndSelect();
1053
0
                }
1054
0
                bool bRet = rSh.MoveFieldType( pFieldType, nSlot == FN_GOTO_NEXT_MARK );
1055
0
                SwField* pCurField = bRet ? rSh.GetCurField() : nullptr;
1056
0
                if (pCurField)
1057
0
                    rSh.ClickToField(*pCurField, /*bExecHyperlinks=*/false);
1058
0
                rReq.SetReturnValue(SfxBoolItem( nSlot, bRet));
1059
0
            }
1060
0
        }
1061
0
        break;
1062
1063
0
        case FN_START_DOC_DIRECT:
1064
0
        case FN_END_DOC_DIRECT:
1065
0
        {
1066
0
            if (rSh.IsSelFrameMode())
1067
0
            {
1068
0
                rSh.UnSelectFrame();
1069
0
                rSh.LeaveSelFrameMode();
1070
0
            }
1071
0
            rSh.EnterStdMode();
1072
0
            nSlot == FN_START_DOC_DIRECT ?
1073
0
                rSh.SttEndDoc(true) :
1074
0
                    rSh.SttEndDoc(false);
1075
0
        }
1076
0
        break;
1077
0
        case FN_GOTO_PREV_OBJ:
1078
0
        case FN_GOTO_NEXT_OBJ:
1079
0
        {
1080
0
                bool bSuccess = rSh.GotoObj( nSlot == FN_GOTO_NEXT_OBJ );
1081
0
                rReq.SetReturnValue(SfxBoolItem(nSlot, bSuccess));
1082
0
                if (bSuccess && !rSh.IsSelFrameMode())
1083
0
                {
1084
0
                    rSh.HideCursor();
1085
0
                    rSh.EnterSelFrameMode();
1086
0
                    GetView().AttrChangedNotify(nullptr);
1087
0
                }
1088
0
        }
1089
0
        break;
1090
0
        case SID_GALLERY_FORMATS:
1091
0
        {
1092
0
            const SvxGalleryItem* pGalleryItem = SfxItemSet::GetItem<SvxGalleryItem>(pArgs, SID_GALLERY_FORMATS, false);
1093
0
            if ( !pGalleryItem )
1094
0
                break;
1095
1096
0
            const SelectionType nSelType = rSh.GetSelectionType();
1097
0
            sal_Int8 nGalleryItemType( pGalleryItem->GetType() );
1098
1099
0
            if ( (!rSh.IsSelFrameMode() || nSelType & SelectionType::Graphic) &&
1100
0
                nGalleryItemType == css::gallery::GalleryItemType::GRAPHIC )
1101
0
            {
1102
0
                SwWait aWait( *m_rView.GetDocShell(), true );
1103
1104
0
                OUString aGrfName, aFltName;
1105
0
                const Graphic aGrf( pGalleryItem->GetGraphic() );
1106
1107
0
                if ( nSelType & SelectionType::Graphic )
1108
0
                    rSh.ReRead( aGrfName, aFltName, &aGrf );
1109
0
                else
1110
0
                    rSh.InsertGraphic( aGrfName, aFltName, aGrf );
1111
1112
0
                GetView().GetEditWin().GrabFocus();
1113
0
            }
1114
0
            else if(!rSh.IsSelFrameMode() &&
1115
0
                nGalleryItemType == css::gallery::GalleryItemType::MEDIA  )
1116
0
            {
1117
0
                const SfxStringItem aMediaURLItem( SID_INSERT_AVMEDIA, pGalleryItem->GetURL() );
1118
0
                GetView().GetViewFrame().GetDispatcher()->ExecuteList(
1119
0
                        SID_INSERT_AVMEDIA, SfxCallMode::SYNCHRON,
1120
0
                        { &aMediaURLItem });
1121
0
            }
1122
0
        }
1123
0
        break;
1124
0
        case FN_PAGE_STYLE_SET_COLS:
1125
0
        {
1126
0
            if (pArgs)
1127
0
            {
1128
                // Determine the current PageDescriptor and fill the set with that.
1129
0
                const size_t nCurIdx = rSh.GetCurPageDesc();
1130
0
                SwPageDesc aPageDesc(rSh.GetPageDesc(nCurIdx));
1131
1132
0
                SwFrameFormat &rFormat = aPageDesc.GetMaster();
1133
1134
0
                SwFormatCol aFormatCol = rFormat.GetCol();
1135
1136
0
                sal_uInt16 nCount;
1137
0
                if(SfxItemState::SET == pArgs->GetItemState(nSlot))
1138
0
                    nCount = static_cast<const SfxUInt16Item &>(pArgs->Get(nSlot)).GetValue();
1139
0
                else
1140
0
                    nCount = pArgs->Get(SID_ATTR_COLUMNS).GetValue();
1141
0
                sal_uInt16 nGutterWidth = DEF_GUTTER_WIDTH;
1142
1143
0
                aFormatCol.Init(nCount ? nCount : 1, nGutterWidth, USHRT_MAX);
1144
0
                aFormatCol.SetWishWidth(USHRT_MAX);
1145
0
                aFormatCol.SetGutterWidth(nGutterWidth, USHRT_MAX);
1146
1147
0
                rFormat.SetFormatAttr(aFormatCol);
1148
1149
0
                rSh.ChgPageDesc(nCurIdx, aPageDesc);
1150
0
            }
1151
0
            else
1152
0
                GetView().GetViewFrame().GetDispatcher()->Execute(FN_FORMAT_PAGE_COLUMN_DLG);
1153
0
        }
1154
0
        break;
1155
0
        case FN_CONVERT_TABLE_TO_TEXT:
1156
0
        case FN_CONVERT_TEXT_TO_TABLE:
1157
0
        case FN_CONVERT_TEXT_TABLE:
1158
0
        {
1159
0
            sal_Unicode cDelim = 0;
1160
0
            bool bToTable = false;
1161
0
            if( nSlot == FN_CONVERT_TEXT_TO_TABLE ||
1162
0
                ( nSlot == FN_CONVERT_TEXT_TABLE && nullptr == rSh.GetTableFormat() ))
1163
0
                bToTable = true;
1164
0
            SwInsertTableOptions aInsTableOpts( SwInsertTableFlags::All, 1 );
1165
0
            SwTableAutoFormat const* pTAFormat = nullptr;
1166
0
            std::unique_ptr<SwTableAutoFormatTable> pAutoFormatTable;
1167
0
            bool bDeleteFormat = true;
1168
0
            if(pArgs && SfxItemState::SET == pArgs->GetItemState( FN_PARAM_1, true, &pItem))
1169
0
            {
1170
0
                aInsTableOpts.mnInsMode = SwInsertTableFlags::NONE;
1171
                // Delimiter
1172
0
                OUString sDelim = static_cast< const SfxStringItem* >(pItem)->GetValue();
1173
0
                if(!sDelim.isEmpty())
1174
0
                    cDelim = sDelim[0];
1175
                // AutoFormat
1176
0
                if(SfxItemState::SET == pArgs->GetItemState( FN_PARAM_2, true, &pItem))
1177
0
                {
1178
0
                    OUString sAutoFormat = static_cast< const SfxStringItem* >(pItem)->GetValue();
1179
1180
0
                    pAutoFormatTable.reset(new SwTableAutoFormatTable(SwModule::get()->GetAutoFormatTable()));
1181
1182
0
                    for( sal_uInt16 i = 0, nCount = pAutoFormatTable->size(); i < nCount; i++ )
1183
0
                    {
1184
0
                        SwTableAutoFormat const*const pFormat = &(*pAutoFormatTable)[ i ];
1185
0
                        if( pFormat->GetName() == sAutoFormat )
1186
0
                        {
1187
0
                            pTAFormat = pFormat;
1188
0
                            bDeleteFormat = false;
1189
0
                            break;
1190
0
                        }
1191
0
                    }
1192
0
                }
1193
                //WithHeader
1194
0
                if(SfxItemState::SET == pArgs->GetItemState( FN_PARAM_3, true, &pItem) &&
1195
0
                            static_cast< const SfxBoolItem* >(pItem)->GetValue())
1196
0
                    aInsTableOpts.mnInsMode |= SwInsertTableFlags::Headline;
1197
                // RepeatHeaderLines
1198
0
                if(SfxItemState::SET == pArgs->GetItemState( FN_PARAM_4, true, &pItem))
1199
0
                   aInsTableOpts.mnRowsToRepeat =
1200
0
                            o3tl::narrowing<sal_uInt16>(static_cast< const SfxInt16Item* >(pItem)->GetValue());
1201
                //WithBorder
1202
0
                if(SfxItemState::SET == pArgs->GetItemState( FN_PARAM_5, true, &pItem) &&
1203
0
                    static_cast< const SfxBoolItem* >(pItem)->GetValue())
1204
0
                    aInsTableOpts.mnInsMode |= SwInsertTableFlags::DefaultBorder;
1205
                //DontSplitTable
1206
0
                if(SfxItemState::SET == pArgs->GetItemState( FN_PARAM_6, true, &pItem) &&
1207
0
                    !static_cast< const SfxBoolItem* >(pItem)->GetValue() )
1208
0
                    aInsTableOpts.mnInsMode |= SwInsertTableFlags::SplitLayout;
1209
0
            }
1210
0
            else
1211
0
            {
1212
0
                SwAbstractDialogFactory* pFact = SwAbstractDialogFactory::Create();
1213
0
                ScopedVclPtr<AbstractSwConvertTableDlg> pDlg(pFact->CreateSwConvertTableDlg(GetView(), bToTable));
1214
0
                if( RET_OK == pDlg->Execute() )
1215
0
                {
1216
0
                    pDlg->GetValues( cDelim, aInsTableOpts, pTAFormat );
1217
1218
0
                }
1219
0
            }
1220
1221
0
            if( cDelim )
1222
0
            {
1223
                //Shell change!
1224
0
                SwView& rSaveView = m_rView;
1225
0
                bool bInserted = false;
1226
                //recording:
1227
0
                SfxViewFrame& rViewFrame = GetView().GetViewFrame();
1228
0
                if (SfxRequest::HasMacroRecorder(rViewFrame))
1229
0
                {
1230
0
                    SfxRequest aReq(rViewFrame, nSlot);
1231
0
                    aReq.AppendItem( SfxStringItem( FN_PARAM_1, OUString(cDelim) ));
1232
0
                    if(bToTable)
1233
0
                    {
1234
0
                        if(pTAFormat)
1235
0
                            aReq.AppendItem( SfxStringItem( FN_PARAM_2, pTAFormat->GetName().toString()));
1236
0
                        aReq.AppendItem( SfxBoolItem ( FN_PARAM_3, bool(aInsTableOpts.mnInsMode & SwInsertTableFlags::Headline)));
1237
0
                        aReq.AppendItem( SfxInt16Item( FN_PARAM_4, static_cast<short>(aInsTableOpts.mnRowsToRepeat) ));
1238
0
                        aReq.AppendItem( SfxBoolItem ( FN_PARAM_5, bool(aInsTableOpts.mnInsMode & SwInsertTableFlags::DefaultBorder) ));
1239
0
                        aReq.AppendItem( SfxBoolItem ( FN_PARAM_6, !(aInsTableOpts.mnInsMode & SwInsertTableFlags::SplitLayout)));
1240
0
                    }
1241
0
                    aReq.Done();
1242
0
                }
1243
1244
0
                if( !bToTable )
1245
0
                    rSh.TableToText( cDelim );
1246
0
                else
1247
0
                {
1248
0
                    bInserted = rSh.TextToTable( aInsTableOpts, cDelim, pTAFormat );
1249
0
                }
1250
0
                rSh.EnterStdMode();
1251
1252
0
                if( bInserted )
1253
0
                    rSaveView.AutoCaption( TABLE_CAP );
1254
0
            }
1255
0
            if(bDeleteFormat)
1256
0
                delete pTAFormat;
1257
0
        }
1258
0
        break;
1259
0
        case SID_STYLE_WATERCAN:
1260
0
        case SID_STYLE_UPDATE_BY_EXAMPLE:
1261
0
        case SID_STYLE_NEW_BY_EXAMPLE:
1262
0
        case SID_STYLE_APPLY:
1263
0
        {
1264
0
            ShellMode eMode = GetView().GetShellMode();
1265
0
            if ( ShellMode::Draw != eMode &&
1266
0
                 ShellMode::DrawForm != eMode &&
1267
0
                 ShellMode::DrawText != eMode &&
1268
0
                 ShellMode::Bezier != eMode )
1269
0
            {
1270
                // oj #107754#
1271
0
                if ( SID_STYLE_WATERCAN == nSlot )
1272
0
                {
1273
0
                    const bool bLockedView = rSh.IsViewLocked();
1274
0
                    rSh.LockView( true );    //lock visible section
1275
1276
0
                    GetView().GetDocShell()->ExecStyleSheet(rReq);
1277
1278
0
                    rSh.LockView( bLockedView );
1279
0
                }
1280
0
                else
1281
                // Will be recorded from the DocShell
1282
0
                    GetView().GetDocShell()->ExecStyleSheet(rReq);
1283
0
            }
1284
0
        }
1285
0
        break;
1286
0
        case SID_CLASSIFICATION_APPLY:
1287
0
        {
1288
0
            GetView().GetDocShell()->Execute(rReq);
1289
0
        }
1290
0
        break;
1291
0
        case SID_CLASSIFICATION_DIALOG:
1292
0
        {
1293
0
            GetView().GetDocShell()->Execute(rReq);
1294
0
        }
1295
0
        break;
1296
0
        case SID_PARAGRAPH_SIGN_CLASSIFY_DLG:
1297
0
        {
1298
0
            GetView().GetDocShell()->Execute(rReq);
1299
0
        }
1300
0
        break;
1301
0
        case SID_WATERMARK:
1302
0
        {
1303
0
            GetView().GetDocShell()->Execute(rReq);
1304
0
        }
1305
0
        break;
1306
0
        case FN_ESCAPE:
1307
0
            GetView().ExecuteSlot(rReq);
1308
0
        break;
1309
0
        case SID_IMAP:
1310
0
        {
1311
0
            sal_uInt16      nId = SvxIMapDlgChildWindow::GetChildWindowId();
1312
1313
0
            SfxViewFrame& rVFrame = GetView().GetViewFrame();
1314
0
            rVFrame.ToggleChildWindow( nId );
1315
0
            rVFrame.GetBindings().Invalidate( SID_IMAP );
1316
1317
0
            if ( rVFrame.HasChildWindow( nId ) && rSh.IsFrameSelected() )
1318
0
                lcl_UpdateIMapDlg( rSh );
1319
0
        }
1320
0
        break;
1321
0
        case SID_IMAP_EXEC:
1322
0
        {
1323
0
            SvxIMapDlg* pDlg = GetIMapDlg(GetView());
1324
1325
            // Check, if the allocation is useful or allowed at all.
1326
0
            if ( rSh.IsFrameSelected() &&
1327
0
                 pDlg->GetEditingObject() == rSh.GetIMapInventor() )
1328
0
            {
1329
0
                    SfxItemSet aSet(SfxItemSet::makeFixedSfxItemSet<RES_URL, RES_URL>(rSh.GetAttrPool()));
1330
0
                    rSh.GetFlyFrameAttr( aSet );
1331
0
                    SwFormatURL aURL( aSet.Get( RES_URL ) );
1332
0
                    aURL.SetMap( &pDlg->GetImageMap() );
1333
0
                    aSet.Put( aURL );
1334
0
                    rSh.SetFlyFrameAttr( aSet );
1335
0
            }
1336
0
        }
1337
0
        break;
1338
0
        case FN_SET_TRACKED_CHANGES_IN_TEXT:
1339
0
        case FN_SET_TRACKED_DELETIONS_IN_MARGIN:
1340
0
        case FN_SET_TRACKED_INSERTIONS_IN_MARGIN:
1341
0
        {
1342
0
            SwViewOption aViewOption = *rSh.GetViewOptions();
1343
0
            bool bAllInText = FN_SET_TRACKED_CHANGES_IN_TEXT == nSlot;
1344
0
            aViewOption.SetShowChangesInMargin( !bAllInText );
1345
0
            if ( !bAllInText )
1346
0
                aViewOption.SetShowChangesInMargin2( FN_SET_TRACKED_INSERTIONS_IN_MARGIN == nSlot );
1347
0
            rSh.ApplyViewOptions( aViewOption );
1348
1349
            // tdf#140982 restore annotation ranges stored in temporary bookmarks
1350
            // (only remove temporary bookmarks during file saving to avoid possible
1351
            // conflict with lazy deletion of the bookmarks of the moved tracked deletions)
1352
0
            if ( bAllInText || FN_SET_TRACKED_INSERTIONS_IN_MARGIN == nSlot )
1353
0
                rSh.GetDoc()->getIDocumentMarkAccess()->restoreAnnotationMarks(false);
1354
0
        }
1355
0
        break;
1356
0
        case SID_CONTOUR_DLG:
1357
0
        {
1358
0
            sal_uInt16 nId = SvxContourDlgChildWindow::GetChildWindowId();
1359
1360
0
            SfxViewFrame& rVFrame = GetView().GetViewFrame();
1361
0
            rVFrame.ToggleChildWindow( nId );
1362
0
            rVFrame.GetBindings().Invalidate( SID_CONTOUR_DLG );
1363
1364
0
            SelectionType nSel = rSh.GetSelectionType();
1365
0
            if ( rVFrame.HasChildWindow( nId ) &&
1366
0
                 (nSel & (SelectionType::Graphic|SelectionType::Ole)) )
1367
0
            {
1368
0
                lcl_UpdateContourDlg( rSh, nSel );
1369
0
            }
1370
0
        }
1371
0
        break;
1372
0
        case SID_CONTOUR_EXEC:
1373
0
        {
1374
0
            SvxContourDlg *pDlg = GetContourDlg(GetView());
1375
            // Check, if the allocation is useful or allowed at all.
1376
0
            SelectionType nSel = rSh.GetSelectionType();
1377
0
            if ( nSel & (SelectionType::Graphic|SelectionType::Ole) )
1378
0
            {
1379
0
                if (pDlg && pDlg->GetEditingObject() == rSh.GetIMapInventor())
1380
0
                {
1381
0
                    rSh.StartAction();
1382
0
                    SfxItemSet aSet(SfxItemSet::makeFixedSfxItemSet<RES_SURROUND, RES_SURROUND>(rSh.GetAttrPool()));
1383
0
                    rSh.GetFlyFrameAttr( aSet );
1384
0
                    SwFormatSurround aSur( aSet.Get( RES_SURROUND ) );
1385
0
                    if ( !aSur.IsContour() )
1386
0
                    {
1387
0
                        aSur.SetContour( true );
1388
0
                        if ( aSur.GetSurround() == css::text::WrapTextMode_NONE )
1389
0
                            aSur.SetSurround( css::text::WrapTextMode_PARALLEL );
1390
0
                        aSet.Put( aSur );
1391
0
                        rSh.SetFlyFrameAttr( aSet );
1392
0
                    }
1393
0
                    const tools::PolyPolygon aPoly( pDlg->GetPolyPolygon() );
1394
0
                    rSh.SetGraphicPolygon( &aPoly );
1395
0
                    if ( pDlg->IsGraphicChanged() )
1396
0
                        rSh.ReRead( OUString(), OUString(), &pDlg->GetGraphic());
1397
0
                    rSh.EndAction();
1398
0
                }
1399
0
            }
1400
0
        }
1401
0
        break;
1402
0
        case FN_FRAME_TO_ANCHOR:
1403
0
        {
1404
0
            rSh.GotoFlyAnchor();
1405
0
            rSh.EnterStdMode();
1406
0
            rSh.CallChgLnk();
1407
0
        }
1408
0
        break;
1409
0
        case FN_TOOL_ANCHOR_PAGE:
1410
0
        case FN_TOOL_ANCHOR_PARAGRAPH:
1411
0
        case FN_TOOL_ANCHOR_CHAR:
1412
0
        case FN_TOOL_ANCHOR_AT_CHAR:
1413
0
        case FN_TOOL_ANCHOR_FRAME:
1414
0
        {
1415
0
            RndStdIds eSet = nSlot == FN_TOOL_ANCHOR_PAGE
1416
0
                                ? RndStdIds::FLY_AT_PAGE
1417
0
                                : nSlot == FN_TOOL_ANCHOR_PARAGRAPH
1418
0
                                    ? RndStdIds::FLY_AT_PARA
1419
0
                                    : nSlot == FN_TOOL_ANCHOR_FRAME
1420
0
                                        ? RndStdIds::FLY_AT_FLY
1421
0
                                        : nSlot == FN_TOOL_ANCHOR_CHAR
1422
0
                                            ? RndStdIds::FLY_AS_CHAR
1423
0
                                            : RndStdIds::FLY_AT_CHAR;
1424
0
            rSh.StartUndo();
1425
0
            if (rSh.GetSelectedObjCount())
1426
0
                rSh.ChgAnchor(eSet);
1427
0
            else if (rSh.IsFrameSelected())
1428
0
            {
1429
0
                SwFormatAnchor aAnc(eSet, eSet == RndStdIds::FLY_AT_PAGE ? rSh.GetPhyPageNum() : 0);
1430
0
                SfxItemSet aSet(SwFEShell::makeItemSetFromFormatAnchor(GetPool(), aAnc));
1431
0
                rSh.SetFlyFrameAttr(aSet);
1432
0
            }
1433
            // if new anchor is 'as char' and it is a Math object and the usual
1434
            // pre-conditions are met then align the formula to the baseline of the text
1435
0
            const uno::Reference < embed::XEmbeddedObject > xObj( rSh.GetOleRef() );
1436
0
            const bool bDoMathBaselineAlignment = xObj.is() && SotExchange::IsMath( xObj->getClassID() )
1437
0
                    && RndStdIds::FLY_AS_CHAR == eSet && rSh.GetDoc()->getIDocumentSettingAccess().get( DocumentSettingId::MATH_BASELINE_ALIGNMENT );
1438
0
            if (bDoMathBaselineAlignment)
1439
0
                rSh.AlignFormulaToBaseline( xObj );
1440
1441
0
            sal_uInt16 nHtmlMode = ::GetHtmlMode(GetView().GetDocShell());
1442
0
            if( nHtmlMode )
1443
0
            {
1444
0
                SfxItemSet aSet(SfxItemSet::makeFixedSfxItemSet<RES_SURROUND, RES_HORI_ORIENT>(GetPool()));
1445
0
                rSh.GetFlyFrameAttr(aSet);
1446
1447
0
                const SwFormatSurround& rSurround = aSet.Get(RES_SURROUND);
1448
0
                const SwFormatVertOrient& rVert = aSet.Get(RES_VERT_ORIENT);
1449
0
                const SwFormatHoriOrient& rHori = aSet.Get(RES_HORI_ORIENT);
1450
0
                sal_Int16 eVOrient = rVert.GetVertOrient();
1451
0
                sal_Int16 eHOrient = rHori.GetHoriOrient();
1452
0
                css::text::WrapTextMode eSurround = rSurround.GetSurround();
1453
1454
0
                switch( eSet )
1455
0
                {
1456
0
                case RndStdIds::FLY_AT_FLY:
1457
0
                case RndStdIds::FLY_AT_PAGE:
1458
                    //Wrap through, left or from left, top, from top
1459
0
                    if(eSurround != css::text::WrapTextMode_THROUGH)
1460
0
                        aSet.Put(SwFormatSurround(css::text::WrapTextMode_THROUGH));
1461
1462
0
                    if( eVOrient != text::VertOrientation::TOP && eVOrient != text::VertOrientation::NONE)
1463
0
                        aSet.Put(SwFormatVertOrient(0, text::VertOrientation::TOP));
1464
1465
0
                    if (eHOrient != text::HoriOrientation::NONE && eHOrient != text::HoriOrientation::LEFT)
1466
0
                        aSet.Put(SwFormatHoriOrient(0, text::HoriOrientation::LEFT));
1467
0
                    break;
1468
1469
0
                case RndStdIds::FLY_AT_PARA:
1470
                    // left, from left, right, top, no wrap, wrap left and right
1471
0
                    if (eSurround != css::text::WrapTextMode_LEFT && eSurround != css::text::WrapTextMode_RIGHT)
1472
0
                        aSet.Put(SwFormatSurround(css::text::WrapTextMode_LEFT));
1473
1474
0
                    if( eVOrient != text::VertOrientation::TOP)
1475
0
                        aSet.Put(SwFormatVertOrient(0, text::VertOrientation::TOP));
1476
1477
0
                    if (eHOrient != text::HoriOrientation::NONE && eHOrient != text::HoriOrientation::LEFT && eHOrient != text::HoriOrientation::RIGHT)
1478
0
                        aSet.Put(SwFormatHoriOrient(0, text::HoriOrientation::LEFT));
1479
0
                    break;
1480
1481
0
                case RndStdIds::FLY_AT_CHAR:
1482
                    // left, from left, right, top, wrap through
1483
0
                    if(eSurround != css::text::WrapTextMode_THROUGH)
1484
0
                        aSet.Put(SwFormatSurround(css::text::WrapTextMode_THROUGH));
1485
1486
0
                    if( eVOrient != text::VertOrientation::TOP)
1487
0
                        aSet.Put(SwFormatVertOrient(0, text::VertOrientation::TOP));
1488
1489
0
                    if (eHOrient != text::HoriOrientation::NONE && eHOrient != text::HoriOrientation::LEFT && eHOrient != text::HoriOrientation::RIGHT)
1490
0
                        aSet.Put(SwFormatHoriOrient(0, text::HoriOrientation::LEFT));
1491
0
                    break;
1492
1493
0
                default:
1494
0
                    ;
1495
0
                }
1496
1497
0
                if( aSet.Count() )
1498
0
                    rSh.SetFlyFrameAttr( aSet );
1499
0
            }
1500
0
            rSh.EndUndo();
1501
1502
0
            GetView().GetViewFrame().GetBindings().Invalidate( SID_ANCHOR_MENU );
1503
0
        }
1504
0
        break;
1505
1506
0
        case FN_FRAME_NOWRAP:
1507
0
        case FN_FRAME_WRAP:
1508
0
        case FN_FRAME_WRAP_IDEAL:
1509
0
        case FN_FRAME_WRAPTHRU:
1510
0
        case FN_FRAME_WRAPTHRU_TRANSP:
1511
0
        case FN_FRAME_WRAPTHRU_TOGGLE:
1512
0
        case FN_FRAME_WRAP_CONTOUR:
1513
0
        case FN_WRAP_ANCHOR_ONLY:
1514
0
        case FN_FRAME_WRAP_LEFT:
1515
0
        case FN_FRAME_WRAP_RIGHT:
1516
0
            SetWrapMode( nSlot );
1517
0
            break;
1518
1519
0
        case FN_UPDATE_ALL_LINKS:
1520
0
            {
1521
0
                if( !rSh.GetLinkManager().GetLinks().empty() )
1522
0
                {
1523
0
                    rSh.EnterStdMode();
1524
0
                    rSh.StartAllAction();
1525
0
                    SfxMedium * medium = nullptr;
1526
0
                    if (auto const sh = rSh.GetDoc()->GetDocShell()) {
1527
0
                        medium = sh->GetMedium();
1528
0
                    }
1529
0
                    rSh.GetLinkManager().UpdateAllLinks(
1530
0
                        false, false, nullptr, medium == nullptr ? OUString() : medium->GetName() );
1531
0
                    rSh.EndAllAction();
1532
0
                }
1533
0
            }
1534
0
            break;
1535
1536
0
        case SID_PROTECTSIZE:
1537
0
        case SID_PROTECTPOS:
1538
0
            {
1539
0
                const bool bIsProtected
1540
0
                    = rSh.IsSelObjProtected(nSlot == SID_PROTECTSIZE ? FlyProtectFlags::Size
1541
0
                                                                     : FlyProtectFlags::Pos)
1542
0
                      != FlyProtectFlags::NONE;
1543
1544
0
                SfxItemSet aSet( GetPool(), aFrameFormatSetRange );
1545
0
                rSh.GetFlyFrameAttr( aSet );
1546
1547
0
                SvxProtectItem rProt = aSet.Get( RES_PROTECT );
1548
0
                if (nSlot == SID_PROTECTSIZE)
1549
0
                    rProt.SetSizeProtect(!bIsProtected);
1550
0
                else
1551
0
                    rProt.SetPosProtect(!bIsProtected);
1552
0
                aSet.Put( rProt );
1553
1554
0
                rSh.SetFlyFrameAttr( aSet );
1555
0
            }
1556
0
            break;
1557
1558
0
        default:
1559
0
            bMore = true;
1560
0
    }
1561
1562
1563
0
    if(!bMore || !pArgs)
1564
0
        return;
1565
1566
0
    pItem = nullptr;
1567
0
    pArgs->GetItemState(GetPool().GetWhichIDFromSlotID(nSlot), false, &pItem);
1568
0
    if(!pItem)
1569
0
        return;
1570
1571
0
    switch(nSlot)
1572
0
    {
1573
0
    case SID_ATTR_BRUSH:
1574
0
    case SID_ATTR_BORDER_SHADOW:
1575
0
    case RES_SHADOW:
1576
0
    {
1577
0
        rSh.StartAllAction();
1578
        // Table cell(s) selected?
1579
0
        if ( rSh.IsTableMode() )
1580
0
        {
1581
0
            SwFrameFormat *pFormat = rSh.GetTableFormat();
1582
0
            pFormat->SetFormatAttr( *pItem );
1583
0
        }
1584
0
        else if ( rSh.IsFrameSelected() )
1585
0
        {
1586
            // Set border attributes via Frame-Manager.
1587
0
            SwFlyFrameAttrMgr aMgr( false, &rSh, Frmmgr_Type::NONE, nullptr );
1588
0
            aMgr.SetAttrSet( *pArgs );
1589
0
            aMgr.UpdateFlyFrame();
1590
0
        }
1591
0
        else
1592
0
        {
1593
0
            rSh.SetAttrSet( *pArgs );
1594
0
        }
1595
0
        rSh.EndAllAction();
1596
0
    }
1597
0
    break;
1598
0
    case FN_PAGE_STYLE_SET_LR_MARGIN:
1599
0
    case FN_PAGE_STYLE_SET_UL_MARGIN:
1600
0
    case FN_PAGE_STYLE_SET_NUMBER_FORMAT:
1601
0
    case FN_PAGE_STYLE_SET_PAPER_SIZE:
1602
0
    case FN_PAGE_STYLE_SET_PAPER_BIN:
1603
0
    {
1604
0
        OSL_FAIL("not implemented");
1605
0
    }
1606
0
    break;
1607
1608
0
    case SID_ATTR_BORDER_OUTER:
1609
0
    {
1610
        // Table cell(s) selected?
1611
0
        if ( rSh.IsTableMode() )
1612
0
        {
1613
            // Set border attributes Get/SetTabBorders()
1614
0
            rSh.SetTabBorders(*pArgs);
1615
0
        }
1616
0
        else if ( rSh.IsFrameSelected() )
1617
0
        {
1618
            // Set border attributes via Frame-Manager.
1619
0
            SwFlyFrameAttrMgr aMgr( false, &rSh, Frmmgr_Type::NONE, nullptr );
1620
0
            aMgr.SetAttrSet(*pArgs);
1621
0
            aMgr.UpdateFlyFrame();
1622
0
        }
1623
0
        else
1624
0
        {
1625
            // Set border attributes via shell quite normally.
1626
0
            rSh.SetAttrItem( *pItem );
1627
0
        }
1628
0
    }
1629
0
    break;
1630
0
    default:
1631
0
            OSL_FAIL("wrong Dispatcher");
1632
0
    }
1633
0
}
1634
1635
// Here the state for SID_IMAP / SID_CONTOUR will be handled
1636
// until the swapping of the graphic is finished.
1637
1638
IMPL_LINK_NOARG(SwBaseShell, GraphicArrivedHdl, SwCursorShell&, void)
1639
0
{
1640
0
    SwWrtShell &rSh = GetShell();
1641
0
    if (CNT_GRF != rSh.SwEditShell::GetCntType())
1642
0
        return;
1643
0
    GraphicType const nGrfType(rSh.GetGraphicType());
1644
0
    if (GraphicType::NONE == nGrfType || m_aGrfUpdateSlots.empty())
1645
0
        return;
1646
1647
0
    bool bProtect = FlyProtectFlags::NONE != rSh.IsSelObjProtected(FlyProtectFlags::Content|FlyProtectFlags::Parent);
1648
0
    SfxViewFrame& rVFrame = GetView().GetViewFrame();
1649
0
    for( const auto nSlot : m_aGrfUpdateSlots )
1650
0
    {
1651
0
        bool bSetState = false;
1652
0
        bool bState = false;
1653
0
        switch( nSlot )
1654
0
        {
1655
0
        case SID_IMAP:
1656
0
        case SID_IMAP_EXEC:
1657
0
            {
1658
0
                sal_uInt16 nId = SvxIMapDlgChildWindow::GetChildWindowId();
1659
0
                SfxChildWindow *pChildWindow = rVFrame.HasChildWindow(nId) ?
1660
0
                    rVFrame.GetChildWindow(nId) : nullptr;
1661
0
                SvxIMapDlg *pDlg = pChildWindow ?
1662
0
                    static_cast<SvxIMapDlg*>(pChildWindow->GetController().get()) : nullptr;
1663
1664
0
                if( pDlg && ( SID_IMAP_EXEC == nSlot ||
1665
0
                            ( SID_IMAP == nSlot && !bProtect)) &&
1666
0
                    pDlg->GetEditingObject() != rSh.GetIMapInventor())
1667
0
                        lcl_UpdateIMapDlg( rSh );
1668
1669
0
                if( !bProtect && SID_IMAP == nSlot )
1670
0
                {
1671
0
                    bSetState = true;
1672
0
                    bState = nullptr != pDlg;
1673
0
                }
1674
0
            }
1675
0
            break;
1676
1677
0
        case SID_CONTOUR_DLG:
1678
0
            if( !bProtect )
1679
0
            {
1680
0
                sal_uInt16 nId = SvxContourDlgChildWindow::GetChildWindowId();
1681
0
                SfxChildWindow *pChildWindow = rVFrame.HasChildWindow(nId) ?
1682
0
                    rVFrame.GetChildWindow(nId) : nullptr;
1683
0
                SvxIMapDlg *pDlg = pChildWindow ?
1684
0
                    static_cast<SvxIMapDlg*>(pChildWindow->GetController().get()) : nullptr;
1685
0
                if( pDlg && pDlg->GetEditingObject() !=
1686
0
                            rSh.GetIMapInventor() )
1687
0
                    lcl_UpdateContourDlg( rSh, SelectionType::Graphic );
1688
1689
0
                bSetState = true;
1690
0
                bState = nullptr != pDlg;
1691
0
            }
1692
0
            break;
1693
1694
0
        case FN_FRAME_WRAP_CONTOUR:
1695
0
            if( !bProtect )
1696
0
            {
1697
0
                SfxItemSet aSet(SfxItemSet::makeFixedSfxItemSet<RES_SURROUND, RES_SURROUND>(GetPool()));
1698
0
                rSh.GetFlyFrameAttr(aSet);
1699
0
                const SwFormatSurround& rWrap = aSet.Get(RES_SURROUND);
1700
0
                bSetState = true;
1701
0
                bState = rWrap.IsContour();
1702
0
            }
1703
0
            break;
1704
1705
0
        case SID_GRFFILTER:
1706
0
        case SID_GRFFILTER_INVERT:
1707
0
        case SID_GRFFILTER_SMOOTH:
1708
0
        case SID_GRFFILTER_SHARPEN:
1709
0
        case SID_GRFFILTER_REMOVENOISE:
1710
0
        case SID_GRFFILTER_SOBEL:
1711
0
        case SID_GRFFILTER_MOSAIC:
1712
0
        case SID_GRFFILTER_EMBOSS:
1713
0
        case SID_GRFFILTER_POSTER:
1714
0
        case SID_GRFFILTER_POPART:
1715
0
        case SID_GRFFILTER_SEPIA:
1716
0
        case SID_GRFFILTER_SOLARIZE:
1717
0
            bSetState = bState = GraphicType::Bitmap == nGrfType;
1718
0
            break;
1719
0
        }
1720
1721
0
        if( bSetState )
1722
0
        {
1723
0
            SfxBoolItem aBool( nSlot, bState );
1724
0
            if( m_pGetStateSet )
1725
0
                m_pGetStateSet->Put( aBool );
1726
0
            else
1727
0
                rVFrame.GetBindings().SetState( aBool );
1728
0
        }
1729
0
    }
1730
0
    m_aGrfUpdateSlots.clear();
1731
0
}
1732
1733
void SwBaseShell::GetState( SfxItemSet &rSet )
1734
0
{
1735
0
    SwWrtShell &rSh = GetShell();
1736
0
    SfxViewFrame& rVFrame = GetView().GetViewFrame();
1737
0
    SfxWhichIter aIter( rSet );
1738
0
    sal_uInt16 nWhich = aIter.FirstWhich();
1739
0
    m_pGetStateSet = &rSet;
1740
0
    while ( nWhich )
1741
0
    {
1742
0
        switch ( nWhich )
1743
0
        {
1744
0
            case SID_GALLERY_FORMATS:
1745
0
                if ( rSh.GetSelectedObjCount() ||
1746
0
                     (rSh.IsSelFrameMode() &&
1747
0
                      !(rSh.GetSelectionType() & SelectionType::Graphic)) )
1748
0
                    rSet.DisableItem( nWhich );
1749
0
                break;
1750
0
            case SID_GALLERY_ENABLE_ADDCOPY:
1751
                // #108230# allow copy from gallery in Writer AND Writer/Web!
1752
0
                rSet.Put( SfxBoolItem( SID_GALLERY_ENABLE_ADDCOPY, true ) );
1753
0
                break;
1754
0
            case FN_EDIT_REGION:
1755
0
                if( !rSh.IsAnySectionInDoc() )
1756
0
                    rSet.DisableItem(nWhich);
1757
0
                break;
1758
1759
0
            case FN_EDIT_CURRENT_REGION:
1760
                //tdf#112808 if cursor is in an index, don't show the edit section.
1761
0
                if( !rSh.GetCurrSection() ||
1762
0
                    (rSh.GetCurrSection()->GetType() != SectionType::Content &&
1763
0
                    rSh.GetCurrSection()->GetType() != SectionType::FileLink ))
1764
0
                {
1765
0
                    rSet.DisableItem(nWhich);
1766
0
                }
1767
0
                break;
1768
1769
0
            case FN_INSERT_REGION:
1770
0
                if( rSh.CursorInsideInputField()
1771
0
                    || rSh.IsSelFrameMode()
1772
0
                    || !rSh.IsInsRegionAvailable() )
1773
0
                {
1774
0
                    rSet.DisableItem( nWhich );
1775
0
                }
1776
0
                break;
1777
1778
0
            case FN_CONVERT_TABLE_TO_TEXT:
1779
0
            {
1780
0
                FrameTypeFlags eFrameType = rSh.GetFrameType(nullptr,true);
1781
0
                if( (eFrameType & FrameTypeFlags::FOOTNOTE) ||
1782
0
                    !rSh.GetTableFormat() )
1783
0
                    rSet.DisableItem( nWhich );
1784
0
            }
1785
0
            break;
1786
0
            case FN_CONVERT_TEXT_TO_TABLE:
1787
0
            {
1788
0
                FrameTypeFlags eFrameType = rSh.GetFrameType(nullptr,true);
1789
0
                if( (eFrameType & FrameTypeFlags::FOOTNOTE) ||
1790
0
                    !rSh.IsTextToTableAvailable()  )
1791
0
                    rSet.DisableItem( nWhich );
1792
0
            }
1793
0
            break;
1794
0
            case FN_CONVERT_TEXT_TABLE:
1795
0
            {
1796
0
                FrameTypeFlags eFrameType = rSh.GetFrameType(nullptr,true);
1797
0
                if( (eFrameType & FrameTypeFlags::FOOTNOTE) ||
1798
0
                    (!rSh.GetTableFormat() && !rSh.IsTextToTableAvailable() ) )
1799
0
                    rSet.DisableItem( nWhich );
1800
0
            }
1801
0
            break;
1802
0
            case RES_SHADOW:
1803
0
            {
1804
0
                SfxItemSet aSet(SfxItemSet::makeFixedSfxItemSet<RES_SHADOW, RES_SHADOW>(rSh.GetAttrPool()));
1805
1806
                // Table cell(s) selected?
1807
0
                if ( rSh.IsTableMode() )
1808
0
                {
1809
0
                    SwFrameFormat *pFormat = rSh.GetTableFormat();
1810
0
                    aSet.Put(pFormat->GetFormatAttr( nWhich ));
1811
0
                }
1812
0
                else if( rSh.IsFrameSelected() )
1813
0
                {
1814
0
                    SwFlyFrameAttrMgr aMgr( false, &rSh, Frmmgr_Type::NONE, nullptr );
1815
0
                    aSet.Put( aMgr.GetAttrSet() );
1816
0
                }
1817
0
                else
1818
0
                    rSh.GetCurAttr( aSet );
1819
1820
0
                const SvxShadowItem& rShItem = static_cast<const SvxShadowItem&>(aSet.Get(nWhich));
1821
0
                rSet.Put(rShItem);
1822
0
            }
1823
0
            break;
1824
0
            case SID_IMAP:
1825
0
            {
1826
                // #i59688#
1827
                // Improve efficiency:
1828
                // If selected object is protected, item has to disabled.
1829
0
                const bool bProtect = FlyProtectFlags::NONE != rSh.IsSelObjProtected(FlyProtectFlags::Content|FlyProtectFlags::Parent);
1830
0
                if ( bProtect )
1831
0
                {
1832
0
                    rSet.DisableItem( nWhich );
1833
0
                }
1834
0
                else
1835
0
                {
1836
0
                    const sal_uInt16 nId = SvxIMapDlgChildWindow::GetChildWindowId();
1837
0
                    const bool bHas = rVFrame.HasChildWindow( nId );
1838
0
                    const bool bFrameSel = rSh.IsFrameSelected();
1839
0
                    const bool bIsGraphicSelection =
1840
0
                                rSh.GetSelectionType() == SelectionType::Graphic;
1841
1842
                    // #i59688#
1843
                    // Avoid unnecessary loading of selected graphic.
1844
                    // The graphic is only needed, if the dialog is open.
1845
                    // If the swapping of the graphic is finished, the status
1846
                    // must be determined asynchronously, until this the slot
1847
                    // will be disabled.
1848
0
                    if ( bHas && bIsGraphicSelection && rSh.IsLinkedGrfSwapOut() )
1849
0
                    {
1850
0
                        if( AddGrfUpdateSlot( nWhich ))
1851
0
                            rSh.GetGraphic(false);  // start the loading
1852
0
                    }
1853
0
                    else
1854
0
                    {
1855
0
                        if ( !bHas &&
1856
0
                             ( !bFrameSel ||
1857
0
                               ( bIsGraphicSelection &&
1858
0
                                 rSh.GetGraphicType() == GraphicType::NONE ) ) )
1859
0
                        {
1860
0
                            rSet.DisableItem( nWhich );
1861
0
                        }
1862
0
                        else
1863
0
                        {
1864
0
                            SfxBoolItem aBool(nWhich, bHas);
1865
0
                            if ( bHas && bFrameSel )
1866
0
                                lcl_UpdateIMapDlg( rSh );
1867
0
                            rSet.Put(aBool);
1868
0
                        }
1869
0
                    }
1870
0
                }
1871
0
            }
1872
0
            break;
1873
0
            case SID_IMAP_EXEC:
1874
0
            {
1875
0
                bool bDisable = false;
1876
0
                if( !rSh.IsFrameSelected())
1877
0
                    bDisable = true;
1878
0
                sal_uInt16 nId = SvxIMapDlgChildWindow::GetChildWindowId();
1879
0
                if(!bDisable && rVFrame.HasChildWindow( nId ))
1880
0
                {
1881
0
                    if(rSh.GetSelectionType() == SelectionType::Graphic
1882
0
                                    && rSh.IsLinkedGrfSwapOut())
1883
0
                    {
1884
0
                        if( AddGrfUpdateSlot( nWhich ))
1885
0
                            rSh.GetGraphic(false);  // start the loading
1886
0
                    }
1887
0
                    else
1888
0
                    {
1889
0
                        SvxIMapDlg *pDlg = GetIMapDlg(GetView());
1890
0
                        if (pDlg && pDlg->GetEditingObject() != rSh.GetIMapInventor())
1891
0
                            lcl_UpdateIMapDlg( rSh );
1892
0
                    }
1893
0
                }
1894
0
                rSet.Put(SfxBoolItem(nWhich, bDisable));
1895
0
            }
1896
0
            break;
1897
1898
0
            case FN_BACKSPACE:
1899
0
            case SID_DELETE:
1900
0
                if ( ( rSh.HasReadonlySel() && !rSh.CursorInsideInputField() )
1901
0
                     || rSh.IsSelObjProtected( FlyProtectFlags::Content|FlyProtectFlags::Parent ) != FlyProtectFlags::NONE )
1902
0
                {
1903
0
                    rSet.DisableItem( nWhich );
1904
0
                }
1905
0
                break;
1906
1907
0
            case SID_CONTOUR_DLG:
1908
0
            {
1909
0
                bool bParentCntProt = FlyProtectFlags::NONE != rSh.IsSelObjProtected(FlyProtectFlags::Content|FlyProtectFlags::Parent );
1910
1911
0
                if( bParentCntProt || 0 != (HTMLMODE_ON & ::GetHtmlMode(
1912
0
                                            GetView().GetDocShell() )) )
1913
0
                    rSet.DisableItem( nWhich );
1914
0
                else
1915
0
                {
1916
0
                    sal_uInt16 nId = SvxContourDlgChildWindow::GetChildWindowId();
1917
0
                    bool bHas = GetView().GetViewFrame().HasChildWindow( nId );
1918
0
                    SelectionType nSel = rSh.GetSelectionType();
1919
0
                    bool bOk(nSel & (SelectionType::Graphic|SelectionType::Ole));
1920
1921
0
                    bool bDisable = false;
1922
0
                    if( !bHas && !bOk )
1923
0
                        bDisable = true;
1924
                    // #i59688#
1925
                    // Avoid unnecessary loading of selected graphic.
1926
                    // The graphic is only needed, if the dialog is open.
1927
                    // If the swapping of the graphic is finished, the status
1928
                    // must be determined asynchronously, until this the slot
1929
                    // will be disabled.
1930
0
                    else if ( bHas && (nSel & SelectionType::Graphic) &&
1931
0
                              rSh.IsLinkedGrfSwapOut() )
1932
0
                    {
1933
0
                        if( AddGrfUpdateSlot( nWhich ))
1934
0
                            rSh.GetGraphic(false);  // start the loading
1935
                        // #i75481#
1936
0
                        bDisable = true;
1937
0
                    }
1938
0
                    else if( bHas && bOk )
1939
0
                        bDisable = !lcl_UpdateContourDlg( rSh, nSel );
1940
0
                    else if( bOk )
1941
0
                    {
1942
                        // #i75481#
1943
                        // apply fix #i59688# only for selected graphics
1944
0
                        if ( nSel & SelectionType::Graphic )
1945
0
                            bDisable = GraphicType::NONE == rSh.GetGraphicType();
1946
0
                        else
1947
0
                            bDisable = GraphicType::NONE == rSh.GetIMapGraphic().GetType();
1948
0
                    }
1949
1950
0
                    if( bDisable )
1951
0
                        rSet.DisableItem( nWhich );
1952
0
                    else
1953
0
                        rSet.Put( SfxBoolItem(nWhich, bHas) );
1954
0
                }
1955
0
            }
1956
0
            break;
1957
0
            case SID_CONTOUR_EXEC:
1958
0
            {
1959
0
                bool bDisable = false;
1960
0
                SelectionType nSel = rSh.GetSelectionType();
1961
0
                if( !(nSel & (SelectionType::Graphic|SelectionType::Ole)) )
1962
0
                    bDisable = true;
1963
0
                sal_uInt16 nId = SvxContourDlgChildWindow::GetChildWindowId();
1964
0
                if( !bDisable && GetView().GetViewFrame().HasChildWindow( nId ))
1965
0
                {
1966
0
                    SvxContourDlg *pDlg = GetContourDlg(GetView());
1967
0
                    if (pDlg && pDlg->GetEditingObject() != rSh.GetIMapInventor())
1968
0
                        bDisable = true;
1969
0
                }
1970
0
                rSet.Put(SfxBoolItem(nWhich, bDisable));
1971
0
            }
1972
0
            break;
1973
1974
0
            case SID_ANCHOR_MENU:
1975
0
            case FN_TOOL_ANCHOR_PAGE:
1976
0
            case FN_TOOL_ANCHOR_PARAGRAPH:
1977
0
            case FN_TOOL_ANCHOR_CHAR:
1978
0
            case FN_TOOL_ANCHOR_AT_CHAR:
1979
0
            case FN_TOOL_ANCHOR_FRAME:
1980
0
            {
1981
0
                bool bObj = 0 != rSh.GetSelectedObjCount();
1982
0
                bool bParentCntProt = rSh.IsSelObjProtected( FlyProtectFlags::Content|FlyProtectFlags::Parent ) != FlyProtectFlags::NONE;
1983
1984
0
                if( !bParentCntProt && (bObj || rSh.IsFrameSelected()))
1985
0
                {
1986
0
                    SfxItemSet aSet(SfxItemSet::makeFixedSfxItemSet<RES_ANCHOR, RES_ANCHOR>(GetPool()));
1987
0
                    if(bObj)
1988
0
                        rSh.GetObjAttr(aSet);
1989
0
                    else
1990
0
                        rSh.GetFlyFrameAttr(aSet);
1991
0
                    RndStdIds eSet = aSet.Get(RES_ANCHOR).GetAnchorId();
1992
0
                    const bool bSet =
1993
0
                           ((nWhich == FN_TOOL_ANCHOR_PAGE) &&
1994
0
                            (eSet == RndStdIds::FLY_AT_PAGE))
1995
0
                        || ((nWhich == FN_TOOL_ANCHOR_PARAGRAPH) &&
1996
0
                            (eSet == RndStdIds::FLY_AT_PARA))
1997
0
                        || ((nWhich == FN_TOOL_ANCHOR_FRAME) &&
1998
0
                            (eSet == RndStdIds::FLY_AT_FLY))
1999
0
                        || ((nWhich == FN_TOOL_ANCHOR_AT_CHAR) &&
2000
0
                            (eSet == RndStdIds::FLY_AT_CHAR))
2001
0
                        || ((nWhich == FN_TOOL_ANCHOR_CHAR) &&
2002
0
                            (eSet == RndStdIds::FLY_AS_CHAR));
2003
2004
0
                    if( nWhich == FN_TOOL_ANCHOR_FRAME && !rSh.IsFlyInFly() )
2005
0
                        rSet.DisableItem(nWhich);
2006
0
                    else if(nWhich != SID_ANCHOR_MENU)
2007
0
                        rSet.Put(SfxBoolItem(nWhich, bSet));
2008
2009
0
                    if (comphelper::LibreOfficeKit::isActive())
2010
0
                    {
2011
0
                        if (nWhich == FN_TOOL_ANCHOR_PAGE || nWhich == FN_TOOL_ANCHOR_FRAME)
2012
0
                        {
2013
0
                            rSet.DisableItem(nWhich);
2014
0
                        }
2015
0
                    }
2016
0
                }
2017
0
                else
2018
0
                    rSet.DisableItem( nWhich );
2019
0
            }
2020
0
            break;
2021
0
            case FN_FRAME_NOWRAP:
2022
0
            case FN_FRAME_WRAP:
2023
0
            case FN_FRAME_WRAP_IDEAL:
2024
0
            case FN_FRAME_WRAPTHRU:
2025
0
            case FN_FRAME_WRAPTHRU_TRANSP:
2026
0
            case FN_FRAME_WRAPTHRU_TOGGLE:
2027
0
            case FN_FRAME_WRAP_CONTOUR:
2028
0
            case FN_WRAP_ANCHOR_ONLY:
2029
0
            case FN_FRAME_WRAP_LEFT:
2030
0
            case FN_FRAME_WRAP_RIGHT:
2031
0
            {
2032
0
                bool bObj = 0 != rSh.GetSelectedObjCount();
2033
0
                bool bParentCntProt = rSh.IsSelObjProtected( FlyProtectFlags::Content|FlyProtectFlags::Parent ) != FlyProtectFlags::NONE;
2034
2035
0
                if( !bParentCntProt && (bObj || rSh.IsFrameSelected()))
2036
0
                {
2037
0
                    SfxItemSet aSet(SfxItemSet::makeFixedSfxItemSet<RES_OPAQUE, RES_ANCHOR>(GetPool()));
2038
0
                    RndStdIds nAnchorType;
2039
0
                    if(bObj)
2040
0
                    {
2041
0
                        rSh.GetObjAttr(aSet);
2042
0
                        nAnchorType = rSh.GetAnchorId();
2043
0
                    }
2044
0
                    else
2045
0
                    {
2046
0
                        rSh.GetFlyFrameAttr(aSet);
2047
0
                        nAnchorType = aSet.Get(RES_ANCHOR).GetAnchorId();
2048
0
                    }
2049
0
                    const SwFormatSurround& rWrap = aSet.Get(RES_SURROUND);
2050
2051
0
                    const SvxOpaqueItem& rOpaque = aSet.Get(RES_OPAQUE);
2052
0
                    bool bOpaque = rOpaque.GetValue();
2053
0
                    css::text::WrapTextMode nSurround = rWrap.GetSurround();
2054
0
                    bool bSet = false;
2055
2056
0
                    bool bDisable =
2057
0
                        (nAnchorType == RndStdIds::UNKNOWN) || (nAnchorType == RndStdIds::FLY_AS_CHAR);
2058
0
                    const bool bHtmlMode =
2059
0
                        0 != ::GetHtmlMode(GetView().GetDocShell());
2060
2061
0
                    switch( nWhich )
2062
0
                    {
2063
0
                        case FN_FRAME_NOWRAP:
2064
0
                            bDisable |=
2065
0
                                (   (nAnchorType != RndStdIds::FLY_AT_PARA)
2066
0
                                 && (nAnchorType != RndStdIds::FLY_AT_CHAR)
2067
0
                                 && (nAnchorType != RndStdIds::FLY_AT_PAGE));
2068
0
                            bSet = nSurround == css::text::WrapTextMode_NONE;
2069
0
                        break;
2070
0
                        case FN_FRAME_WRAP:
2071
0
                            bDisable |= bHtmlMode;
2072
0
                            bSet = nSurround == css::text::WrapTextMode_PARALLEL;
2073
0
                        break;
2074
0
                        case FN_FRAME_WRAP_IDEAL:
2075
0
                            bDisable |= bHtmlMode;
2076
0
                            bSet = nSurround == css::text::WrapTextMode_DYNAMIC;
2077
0
                        break;
2078
0
                        case FN_FRAME_WRAPTHRU:
2079
0
                            bDisable |= (bHtmlMode ||
2080
0
                                (   (nAnchorType != RndStdIds::FLY_AT_PARA)
2081
0
                                 && (nAnchorType != RndStdIds::FLY_AT_CHAR)
2082
0
                                 && (nAnchorType != RndStdIds::FLY_AT_PAGE)));
2083
0
                            if(bObj)
2084
0
                                bSet = nSurround == css::text::WrapTextMode_THROUGH && rSh.GetLayerId();
2085
0
                            else
2086
0
                                bSet = nSurround == css::text::WrapTextMode_THROUGH && bOpaque;
2087
0
                        break;
2088
0
                        case FN_FRAME_WRAPTHRU_TRANSP:
2089
0
                        case FN_FRAME_WRAPTHRU_TOGGLE:
2090
0
                            bDisable |= bHtmlMode;
2091
0
                            if(bObj)
2092
0
                                bSet = nSurround == css::text::WrapTextMode_THROUGH && !rSh.GetLayerId();
2093
0
                            else
2094
0
                                bSet = nSurround == css::text::WrapTextMode_THROUGH && !bOpaque;
2095
0
                        break;
2096
0
                        case FN_FRAME_WRAP_CONTOUR:
2097
0
                            bDisable |= bHtmlMode;
2098
                            //no contour available when no wrap or wrap through is set
2099
0
                            bDisable |= (nSurround == css::text::WrapTextMode_NONE || nSurround == css::text::WrapTextMode_THROUGH);
2100
0
                            if( !bDisable )
2101
0
                            {
2102
0
                                SelectionType nSel = rSh.GetSelectionType();
2103
0
                                if( (nSel & SelectionType::Graphic) &&
2104
0
                                            rSh.IsLinkedGrfSwapOut())
2105
0
                                {
2106
0
                                    if( AddGrfUpdateSlot( nWhich ))
2107
0
                                        rSh.GetGraphic(false);  // start the loading
2108
0
                                }
2109
0
                                else if( rSh.IsFrameSelected() )
2110
0
                                {
2111
                                    // #i102253# applied patch from OD (see task)
2112
0
                                    bDisable =
2113
0
                                        nSel & SelectionType::Frame ||
2114
0
                                        GraphicType::NONE == rSh.GetIMapGraphic().GetType();
2115
0
                                }
2116
0
                            }
2117
0
                            bSet = !bDisable && rWrap.IsContour();
2118
2119
0
                        break;
2120
0
                        case FN_WRAP_ANCHOR_ONLY:
2121
0
                            bDisable |= (bHtmlMode ||
2122
0
                                (nAnchorType != RndStdIds::FLY_AT_PARA));
2123
0
                            bSet = rWrap.IsAnchorOnly();
2124
0
                        break;
2125
0
                        case FN_FRAME_WRAP_LEFT:
2126
0
                            bSet = nSurround == css::text::WrapTextMode_LEFT;
2127
0
                        break;
2128
0
                        case FN_FRAME_WRAP_RIGHT:
2129
0
                            bSet = nSurround == css::text::WrapTextMode_RIGHT;
2130
0
                        break;
2131
0
                    }
2132
2133
0
                    if(bDisable)
2134
0
                        rSet.DisableItem(nWhich);
2135
0
                    else
2136
0
                        rSet.Put(SfxBoolItem(nWhich, bSet));
2137
0
                }
2138
0
                else
2139
0
                    rSet.DisableItem(nWhich);
2140
0
            }
2141
0
            break;
2142
0
            case FN_UPDATE_CHARTS:
2143
0
                if( !rSh.HasCharts() )
2144
0
                    rSet.DisableItem( nWhich );
2145
0
                break;
2146
0
            case FN_UPDATE_ALL_LINKS:
2147
0
                if ( rSh.GetLinkManager().GetLinks().empty() )
2148
0
                    rSet.DisableItem(nWhich);
2149
0
                break;
2150
0
            case SID_GRAPHIC_SIZE_CHECK:
2151
0
            {
2152
0
                sal_Int32 nDPI = rSh.GetDoc()->getIDocumentSettingAccess().getImagePreferredDPI();
2153
0
                if (nDPI <= 0)
2154
0
                    rSet.DisableItem(nWhich);
2155
0
            }
2156
0
            break;
2157
0
            case SID_THEME_DIALOG:
2158
0
            {
2159
0
                bool bDisable = true;
2160
0
                auto* pDocument = rSh.GetDoc();
2161
0
                auto* pDocumentShell = pDocument->GetDocShell();
2162
0
                if (pDocumentShell)
2163
0
                {
2164
0
                    SdrModel* pModel = pDocument->getIDocumentDrawModelAccess().GetDrawModel();
2165
0
                    if (pModel)
2166
0
                    {
2167
0
                        auto const& pTheme = pModel->getTheme();
2168
0
                        if (pTheme)
2169
0
                            bDisable = false;
2170
0
                    }
2171
0
                }
2172
0
                if (bDisable)
2173
0
                    rSet.DisableItem(nWhich);
2174
0
            }
2175
0
            break;
2176
0
            case FN_SET_TRACKED_CHANGES_IN_TEXT:
2177
0
            {
2178
0
                bool bShowRedlines = !rSh.GetLayout()->IsHideRedlines();
2179
0
                const SwViewOption* pOptions = rSh.GetViewOptions();
2180
                // First setting is false: inline.
2181
0
                bool bAllInText = bShowRedlines && !pOptions->IsShowChangesInMargin();
2182
0
                rSet.Put(SfxBoolItem(nWhich, bAllInText));
2183
0
            }
2184
0
            break;
2185
0
            case FN_SET_TRACKED_DELETIONS_IN_MARGIN:
2186
0
            {
2187
0
                bool bShowRedlines = !rSh.GetLayout()->IsHideRedlines();
2188
0
                const SwViewOption* pOptions = rSh.GetViewOptions();
2189
                // Second setting is false: show deletions in margin.
2190
0
                bool bDelInMargin = bShowRedlines && pOptions->IsShowChangesInMargin()
2191
0
                                    && !pOptions->IsShowChangesInMargin2();
2192
0
                rSet.Put(SfxBoolItem(nWhich, bDelInMargin));
2193
0
            }
2194
0
            break;
2195
0
            case FN_SET_TRACKED_INSERTIONS_IN_MARGIN:
2196
0
            {
2197
0
                bool bShowRedlines = !rSh.GetLayout()->IsHideRedlines();
2198
0
                const SwViewOption* pOptions = rSh.GetViewOptions();
2199
                // Second setting is true: show insertions in margin.
2200
0
                bool bInsInMargin = bShowRedlines && pOptions->IsShowChangesInMargin()
2201
0
                                    && pOptions->IsShowChangesInMargin2();
2202
0
                rSet.Put(SfxBoolItem(nWhich, bInsInMargin));
2203
0
            }
2204
0
            break;
2205
0
            case SID_PROTECTSIZE:
2206
0
            case SID_PROTECTPOS:
2207
0
            {
2208
0
                if( rSh.GetGraphicType() == GraphicType::NONE )
2209
0
                    rSet.DisableItem(nWhich);
2210
0
                else
2211
0
                {
2212
0
                    const bool bIsProtected
2213
0
                        = rSh.IsSelObjProtected(nWhich == SID_PROTECTSIZE ? FlyProtectFlags::Size
2214
0
                                                                          : FlyProtectFlags::Pos)
2215
0
                          != FlyProtectFlags::NONE;
2216
0
                    rSet.Put(SfxBoolItem(nWhich, bIsProtected));
2217
0
                }
2218
0
            }
2219
0
            break;
2220
2221
0
        }
2222
0
        nWhich = aIter.NextWhich();
2223
0
    }
2224
0
    m_pGetStateSet = nullptr;
2225
0
}
2226
2227
// Disable the slots with this status method
2228
2229
void SwBaseShell::StateDisableItems( SfxItemSet &rSet )
2230
0
{
2231
0
    SfxWhichIter aIter(rSet);
2232
0
    sal_uInt16 nWhich = aIter.FirstWhich();
2233
2234
0
    while (nWhich)
2235
0
    {
2236
0
        rSet.DisableItem( nWhich );
2237
0
        nWhich = aIter.NextWhich();
2238
0
    }
2239
0
}
2240
2241
// Disable the slots with this status method
2242
2243
void SwBaseShell::StateStyle( SfxItemSet &rSet )
2244
0
{
2245
0
    bool bParentCntProt = GetShell().IsSelObjProtected( FlyProtectFlags::Content|FlyProtectFlags::Parent ) != FlyProtectFlags::NONE;
2246
0
    ShellMode eMode = GetView().GetShellMode();
2247
2248
0
    if ( bParentCntProt ||
2249
0
         ShellMode::Draw == eMode ||
2250
0
         ShellMode::DrawForm == eMode ||
2251
0
         ShellMode::DrawText == eMode ||
2252
0
         ShellMode::Bezier == eMode )
2253
0
    {
2254
0
        SfxWhichIter aIter( rSet );
2255
0
        sal_uInt16 nWhich = aIter.FirstWhich();
2256
0
        while ( nWhich )
2257
0
        {
2258
0
            rSet.DisableItem( nWhich );
2259
0
            nWhich = aIter.NextWhich();
2260
0
        }
2261
0
    }
2262
0
    else
2263
0
        GetView().GetDocShell()->StateStyleSheet(rSet, &GetShell());
2264
0
}
2265
2266
void SwBaseShell::SetWrapMode( sal_uInt16 nSlot )
2267
0
{
2268
0
    SwWrtShell &rSh = GetShell();
2269
0
    bool bObj = 0 != rSh.GetSelectedObjCount();
2270
0
    if( !bObj && !rSh.IsFrameSelected())
2271
0
        return;
2272
2273
0
    SfxItemSet aSet(SfxItemSet::makeFixedSfxItemSet<RES_OPAQUE, RES_SURROUND>(GetPool()));
2274
0
    if(bObj)
2275
0
        rSh.GetObjAttr(aSet);
2276
0
    else
2277
0
        rSh.GetFlyFrameAttr(aSet);
2278
0
    SwFormatSurround aWrap( aSet.Get(RES_SURROUND) );
2279
0
    css::text::WrapTextMode nOldSurround(aWrap.GetSurround());
2280
0
    css::text::WrapTextMode nSurround = css::text::WrapTextMode_PARALLEL;
2281
2282
0
    switch (nSlot)
2283
0
    {
2284
0
        case FN_FRAME_NOWRAP:
2285
0
            nSurround = css::text::WrapTextMode_NONE;
2286
0
            if (aWrap.IsContour())
2287
0
                aWrap.SetContour(false);
2288
0
            break;
2289
0
        case FN_FRAME_WRAP_IDEAL:
2290
0
            nSurround = css::text::WrapTextMode_DYNAMIC;
2291
0
            break;
2292
0
        case FN_WRAP_ANCHOR_ONLY:
2293
0
            aWrap.SetAnchorOnly(!aWrap.IsAnchorOnly());
2294
2295
            // keep previous wrapping
2296
2297
            // switch to wrap css::text::WrapTextMode_PARALLEL, if previous wrap is css::text::WrapTextMode_NONE
2298
0
            if ( nOldSurround != css::text::WrapTextMode_NONE )
2299
0
            {
2300
0
                nSurround = nOldSurround;
2301
0
            }
2302
0
            break;
2303
0
        case FN_FRAME_WRAP_CONTOUR:
2304
0
            aWrap.SetContour(!aWrap.IsContour());
2305
            // Contour is meaningless in no-wrap or wrap-through context. Otherwise keep existing wrap.
2306
0
            if ( !aWrap.IsContour() ||
2307
0
                 ( nOldSurround != css::text::WrapTextMode_NONE &&
2308
0
                   nOldSurround != css::text::WrapTextMode_THROUGH ) )
2309
0
            {
2310
0
                nSurround = nOldSurround;
2311
0
            }
2312
0
            break;
2313
0
        case FN_FRAME_WRAPTHRU_TRANSP:
2314
0
        case FN_FRAME_WRAPTHRU_TOGGLE:
2315
0
            if (aWrap.IsContour())
2316
0
                aWrap.SetContour(false);
2317
0
            [[fallthrough]];
2318
0
        case FN_FRAME_WRAPTHRU:
2319
0
            nSurround = css::text::WrapTextMode_THROUGH;
2320
0
            break;
2321
2322
0
        case FN_FRAME_WRAP_LEFT:
2323
0
            nSurround = css::text::WrapTextMode_LEFT;
2324
0
            break;
2325
2326
0
        case FN_FRAME_WRAP_RIGHT:
2327
0
            nSurround = css::text::WrapTextMode_RIGHT;
2328
0
            break;
2329
2330
0
        default:
2331
0
            break;
2332
0
    }
2333
0
    aWrap.SetSurround(nSurround);
2334
2335
0
    if (nSlot != FN_FRAME_WRAP_CONTOUR)
2336
0
    {
2337
        // Defaulting the contour wrap on draw objects.
2338
0
        if (bObj && nOldSurround != nSurround &&
2339
0
            (nOldSurround == css::text::WrapTextMode_NONE || nOldSurround == css::text::WrapTextMode_THROUGH))
2340
0
        {
2341
0
            aWrap.SetContour(true);
2342
0
        }
2343
0
    }
2344
2345
0
    aSet.Put( aWrap );
2346
2347
0
    bool bOpaque = nSlot != FN_FRAME_WRAPTHRU_TRANSP && nSlot != FN_FRAME_WRAPTHRU_TOGGLE;
2348
0
    if( nSlot == FN_FRAME_WRAPTHRU_TOGGLE )
2349
0
    {
2350
0
        if( bObj )
2351
0
            bOpaque = !rSh.GetLayerId();
2352
0
        else
2353
0
        {
2354
0
            const SvxOpaqueItem& aOpaque( aSet.Get(RES_OPAQUE) );
2355
0
            bOpaque = !aOpaque.GetValue();
2356
0
        }
2357
0
    }
2358
0
    aSet.Put(SvxOpaqueItem(RES_OPAQUE, bOpaque ));
2359
2360
0
    if(bObj)
2361
0
    {
2362
0
        rSh.SetObjAttr(aSet);
2363
0
        if ( bOpaque )
2364
0
            rSh.SelectionToHeaven();
2365
0
        else
2366
0
            rSh.SelectionToHell();
2367
0
    }
2368
0
    else
2369
0
        rSh.SetFlyFrameAttr(aSet);
2370
2371
0
}
2372
2373
//Force update of the status line
2374
2375
void SwBaseShell::SetFrameMode(FlyMode eMode, SwWrtShell *pSh )
2376
0
{
2377
0
    s_eFrameMode = eMode;
2378
0
    SfxBindings &rBnd = pSh->GetView().GetViewFrame().GetBindings();
2379
2380
0
    if( eMode == FLY_DRAG || pSh->IsFrameSelected() || pSh->GetSelectedObjCount() )
2381
0
    {
2382
0
        const SfxPointItem aTmp1( SID_ATTR_POSITION, pSh->GetAnchorObjDiff());
2383
0
        const SvxSizeItem  aTmp2( SID_ATTR_SIZE,     pSh->GetObjSize());
2384
0
        rBnd.SetState( aTmp1 );
2385
0
        rBnd.SetState( aTmp2 );
2386
0
    }
2387
0
    else if( eMode == FLY_DRAG_END )
2388
0
    {
2389
0
        static const sal_uInt16 aInval[] =
2390
0
        {
2391
0
            SID_ATTR_POSITION, SID_ATTR_SIZE, 0
2392
0
        };
2393
0
        rBnd.Invalidate(aInval);
2394
0
    }
2395
0
}
2396
2397
SwBaseShell::SwBaseShell(SwView& rVw) :
2398
8.54k
    SfxShell( &rVw ),
2399
8.54k
    m_rView(rVw),
2400
8.54k
    m_pGetStateSet(nullptr)
2401
8.54k
{
2402
8.54k
    SwWrtShell& rWrtSh = m_rView.GetWrtShell();
2403
2404
8.54k
    SetPool(&rWrtSh.GetAttrPool());
2405
8.54k
    SetName(u"Base"_ustr);
2406
8.54k
    rWrtSh.SetGrfArrivedLnk( LINK( this, SwBaseShell, GraphicArrivedHdl));
2407
8.54k
}
2408
2409
SwBaseShell::~SwBaseShell()
2410
8.54k
{
2411
8.54k
    if( m_rView.GetCurShell() == this )
2412
0
        m_rView.ResetSubShell();
2413
2414
8.54k
    Link<SwCursorShell&,void> aTmp( LINK( this, SwBaseShell, GraphicArrivedHdl));
2415
8.54k
    if( aTmp == m_rView.GetWrtShell().GetGrfArrivedLnk() )
2416
4.26k
        m_rView.GetWrtShell().SetGrfArrivedLnk( Link<SwCursorShell&,void>() );
2417
8.54k
}
2418
2419
void SwBaseShell::ExecTextCtrl( SfxRequest& rReq )
2420
0
{
2421
0
    const SfxItemSet *pArgs = rReq.GetArgs();
2422
0
    const sal_uInt16 nSlot = rReq.GetSlot();
2423
2424
0
    if( pArgs)
2425
0
    {
2426
0
        SwWrtShell &rSh = GetShell();
2427
0
        std::unique_ptr<SvxScriptSetItem> pSSetItem;
2428
0
        SfxItemPool& rPool = rSh.GetAttrPool();
2429
0
        sal_uInt16 nWhich = rPool.GetWhichIDFromSlotID( nSlot );
2430
0
        SvtScriptType nScripts = SvtScriptType::LATIN | SvtScriptType::ASIAN | SvtScriptType::COMPLEX;
2431
0
        SfxItemSet aHeightSet(SfxItemSet::makeFixedSfxItemSet<
2432
0
                                            RES_CHRATR_FONTSIZE, RES_CHRATR_FONTSIZE,
2433
0
                                            RES_CHRATR_CJK_FONTSIZE, RES_CHRATR_CJK_FONTSIZE,
2434
0
                                            RES_CHRATR_CTL_FONTSIZE, RES_CHRATR_CTL_FONTSIZE>(GetPool()));
2435
2436
0
        switch( nSlot )
2437
0
        {
2438
0
            case SID_ATTR_CHAR_FONT:
2439
0
            {
2440
0
                nScripts = rSh.GetScriptType();
2441
                // #i42732# input language should be preferred over
2442
                // current cursor position to detect script type
2443
0
                if(!rSh.HasSelection())
2444
0
                {
2445
0
                    LanguageType nInputLang = GetView().GetEditWin().GetInputLanguage();
2446
0
                    if(nInputLang != LANGUAGE_DONTKNOW && nInputLang != LANGUAGE_SYSTEM)
2447
0
                        nScripts = SvtLanguageOptions::GetScriptTypeOfLanguage( nInputLang );
2448
0
                }
2449
0
                [[fallthrough]];
2450
0
            }
2451
0
            case SID_ATTR_CHAR_POSTURE:
2452
0
            case SID_ATTR_CHAR_WEIGHT:
2453
0
            {
2454
0
                pSSetItem.reset(new SvxScriptSetItem( nSlot, rPool ));
2455
0
                pSSetItem->PutItemForScriptType( nScripts, pArgs->Get( nWhich ));
2456
0
                pArgs = &pSSetItem->GetItemSet();
2457
0
            }
2458
0
            break;
2459
0
            case SID_ATTR_CHAR_FONTHEIGHT:
2460
0
            {
2461
0
                if(rSh.HasSelection())
2462
0
                {
2463
0
                    pSSetItem.reset(new SvxScriptSetItem( nSlot, rPool ));
2464
0
                    pSSetItem->PutItemForScriptType( nScripts, pArgs->Get( nWhich ));
2465
0
                    pArgs = &pSSetItem->GetItemSet();
2466
0
                }
2467
0
                else
2468
0
                {
2469
0
                    nScripts = rSh.GetScriptType();
2470
0
                    LanguageType nInputLang = GetView().GetEditWin().GetInputLanguage();
2471
0
                    if(nInputLang != LANGUAGE_DONTKNOW && nInputLang != LANGUAGE_SYSTEM)
2472
0
                        nScripts = SvtLanguageOptions::GetScriptTypeOfLanguage( nInputLang );
2473
0
                    sal_uInt32 nHeight = static_cast< const SvxFontHeightItem& >(pArgs->Get( nWhich )).GetHeight();
2474
0
                    SwStdFontConfig* pStdFont = SwModule::get()->GetStdFontConfig();
2475
2476
0
                    SfxItemSet aLangSet(SfxItemSet::makeFixedSfxItemSet<
2477
0
                                            RES_CHRATR_LANGUAGE, RES_CHRATR_LANGUAGE,
2478
0
                                            RES_CHRATR_CJK_LANGUAGE, RES_CHRATR_CJK_LANGUAGE,
2479
0
                                            RES_CHRATR_CTL_LANGUAGE, RES_CHRATR_CTL_LANGUAGE>(GetPool()));
2480
0
                    rSh.GetCurAttr( aLangSet );
2481
2482
0
                    sal_Int32 nWesternSize =
2483
0
                            pStdFont->GetFontHeight(FONT_STANDARD, FONT_GROUP_DEFAULT,
2484
0
                            aLangSet.Get( RES_CHRATR_LANGUAGE).GetLanguage());
2485
0
                    sal_Int32 nCJKSize =
2486
0
                            pStdFont->GetFontHeight(FONT_STANDARD, FONT_GROUP_CJK,
2487
0
                            aLangSet.Get( RES_CHRATR_CJK_LANGUAGE).GetLanguage());
2488
0
                    sal_Int32 nCTLSize =
2489
0
                            pStdFont->GetFontHeight(FONT_STANDARD, FONT_GROUP_CTL,
2490
0
                            aLangSet.Get( RES_CHRATR_CTL_LANGUAGE).GetLanguage());
2491
2492
0
                    switch(nScripts)
2493
0
                    {
2494
0
                        case SvtScriptType::LATIN:
2495
0
                            nCJKSize = nHeight * nCJKSize / nWesternSize;
2496
0
                            nCTLSize = nHeight * nCTLSize / nWesternSize;
2497
0
                            nWesternSize = static_cast<sal_Int32>(nHeight);
2498
0
                        break;
2499
0
                        case SvtScriptType::ASIAN:
2500
0
                            nCTLSize = nHeight* nCTLSize / nCJKSize;
2501
0
                            nWesternSize = nHeight * nWesternSize / nCJKSize;
2502
0
                            nCJKSize = static_cast<sal_Int32>(nHeight);
2503
0
                        break;
2504
0
                        case SvtScriptType::COMPLEX:
2505
0
                            nCJKSize = nHeight * nCJKSize / nCTLSize;
2506
0
                            nWesternSize = nHeight * nWesternSize / nCTLSize;
2507
0
                            nCTLSize = static_cast<sal_Int32>(nHeight);
2508
0
                        break;
2509
0
                        default: break;
2510
0
                    }
2511
0
                    aHeightSet.Put( SvxFontHeightItem( static_cast<sal_uInt32>(nWesternSize), 100, RES_CHRATR_FONTSIZE ));
2512
0
                    aHeightSet.Put( SvxFontHeightItem( static_cast<sal_uInt32>(nCJKSize), 100, RES_CHRATR_CJK_FONTSIZE ));
2513
0
                    aHeightSet.Put( SvxFontHeightItem( static_cast<sal_uInt32>(nCTLSize), 100, RES_CHRATR_CTL_FONTSIZE ));
2514
0
                    pArgs = &aHeightSet;
2515
0
                }
2516
0
            }
2517
0
            break;
2518
0
        }
2519
2520
0
        if( pArgs )
2521
0
        {
2522
0
            bool bAuto = false;
2523
0
            if ( !isCHRATR(nWhich) ||
2524
0
                 ( rSh.HasSelection() && rSh.IsSelFullPara() ) )
2525
0
            {
2526
0
                SwTextFormatColl * pColl = rSh.GetCurTextFormatColl();
2527
0
                if ( pColl && pColl->IsAutoUpdateOnDirectFormat() )
2528
0
                {
2529
0
                    rSh.AutoUpdatePara( pColl, *pArgs );
2530
0
                    bAuto = true;
2531
0
                }
2532
0
            }
2533
2534
0
            if (!bAuto)
2535
0
            {
2536
0
                rSh.SetAttrSet( *pArgs );
2537
0
            }
2538
0
        }
2539
0
    }
2540
0
    else
2541
0
    {
2542
0
        if (nSlot == SID_ATTR_CHAR_KERNING)
2543
0
            GetView().GetViewFrame().GetDispatcher()->Execute(SID_CHAR_DLG_POSITION);
2544
0
        else if (nSlot == SID_ATTR_CHAR_COLOR)
2545
0
            GetView().GetViewFrame().GetDispatcher()->Execute(SID_CHAR_DLG_EFFECT);
2546
0
        else
2547
0
            GetView().GetViewFrame().GetDispatcher()->Execute(SID_CHAR_DLG);
2548
0
    }
2549
0
    rReq.Done();
2550
0
}
2551
2552
void SwBaseShell::GetTextCtrlState( SfxItemSet& rSet )
2553
0
{
2554
0
    SwWrtShell &rSh = GetShell();
2555
0
    rSh.GetCurAttr( rSet );
2556
0
}
2557
2558
void SwBaseShell::GetTextFontCtrlState( SfxItemSet& rSet )
2559
0
{
2560
0
    SwWrtShell &rSh = GetShell();
2561
0
    bool bFirst = true;
2562
0
    std::optional<SfxItemSet> pFntCoreSet;
2563
0
    SvtScriptType nScriptType = SvtScriptType::LATIN;
2564
0
    SfxWhichIter aIter( rSet );
2565
0
    sal_uInt16 nWhich = aIter.FirstWhich();
2566
0
    while( nWhich )
2567
0
    {
2568
0
        switch( nWhich )
2569
0
        {
2570
0
        case RES_CHRATR_FONT:
2571
0
        case RES_CHRATR_FONTSIZE:
2572
0
        case RES_CHRATR_WEIGHT:
2573
0
        case RES_CHRATR_POSTURE:
2574
0
            {
2575
0
                if( !pFntCoreSet )
2576
0
                {
2577
0
                    pFntCoreSet.emplace( *rSet.GetPool(),
2578
0
                                    svl::Items<RES_CHRATR_BEGIN, RES_CHRATR_END-1> );
2579
0
                    rSh.GetCurAttr( *pFntCoreSet );
2580
0
                    nScriptType = rSh.GetScriptType();
2581
                    // #i42732# input language should be preferred over
2582
                    // current cursor position to detect script type
2583
0
                    SwEditWin& rEditWin = GetView().GetEditWin();
2584
0
                    if( rEditWin.IsUseInputLanguage() )
2585
0
                    {
2586
0
                        if(!rSh.HasSelection() && (
2587
0
                            nWhich == RES_CHRATR_FONT ||
2588
0
                            nWhich == RES_CHRATR_FONTSIZE ))
2589
0
                        {
2590
0
                            LanguageType nInputLang = rEditWin.GetInputLanguage();
2591
0
                            if(nInputLang != LANGUAGE_DONTKNOW && nInputLang != LANGUAGE_SYSTEM)
2592
0
                                nScriptType = SvtLanguageOptions::GetScriptTypeOfLanguage( nInputLang );
2593
0
                        }
2594
0
                    }
2595
0
                }
2596
0
                SfxItemPool& rPool = *rSet.GetPool();
2597
0
                SvxScriptSetItem aSetItem( rPool.GetSlotId( nWhich ), rPool );
2598
0
                aSetItem.GetItemSet().Put( *pFntCoreSet, false );
2599
0
                const SfxPoolItem* pI = aSetItem.GetItemOfScript( nScriptType );
2600
0
                if( pI )
2601
0
                {
2602
0
                    rSet.Put( pI->CloneSetWhich(nWhich) );
2603
0
                }
2604
0
                else
2605
0
                    rSet.InvalidateItem( nWhich );
2606
                // Set input context of the SwEditWin according to the selected font and script type
2607
0
                if(RES_CHRATR_FONT == nWhich)
2608
0
                {
2609
0
                    vcl::Font aFont;
2610
0
                    if (const SvxFontItem* pFontItem = dynamic_cast<const SvxFontItem*>(pI))
2611
0
                    {
2612
0
                        aFont.SetFamilyName(pFontItem->GetFamilyName());
2613
0
                        aFont.SetStyleName(pFontItem->GetStyleName());
2614
0
                        aFont.SetFamily(pFontItem->GetFamily());
2615
0
                        aFont.SetPitch(pFontItem->GetPitch());
2616
0
                        aFont.SetCharSet(pFontItem->GetCharSet());
2617
0
                    }
2618
2619
0
                    bool bVertical = rSh.IsInVerticalText();
2620
0
                    aFont.SetOrientation(Degree10(bVertical ? 2700 : 0));
2621
0
                    aFont.SetVertical(bVertical);
2622
0
                    GetView().GetEditWin().SetInputContext( InputContext( std::move(aFont), InputContextFlags::Text |
2623
0
                                                        InputContextFlags::ExtText ) );
2624
0
                }
2625
0
            }
2626
0
            break;
2627
2628
0
        default:
2629
0
            if( bFirst )
2630
0
            {
2631
0
                rSh.GetCurAttr( rSet );
2632
0
                bFirst = false;
2633
0
            }
2634
0
        }
2635
0
        nWhich = aIter.NextWhich();
2636
0
    }
2637
0
}
2638
2639
void SwBaseShell::GetBckColState(SfxItemSet &rSet)
2640
0
{
2641
0
    SwWrtShell &rSh = GetShell();
2642
0
    SfxWhichIter aIter(rSet);
2643
0
    sal_uInt16 nWhich(aIter.FirstWhich());
2644
0
    SelectionType nSelType(rSh.GetSelectionType());
2645
0
    std::unique_ptr<SvxBrushItem> aBrushItem(std::make_unique<SvxBrushItem>(RES_BACKGROUND));
2646
2647
0
    if( nWhich == SID_TABLE_CELL_BACKGROUND_COLOR )
2648
0
    {
2649
0
        rSh.GetBoxBackground( aBrushItem );
2650
0
    }
2651
0
    else
2652
0
    {
2653
        // Adapt to new DrawingLayer FillStyle; use a parent which has XFILL_NONE set
2654
0
        SfxItemSet aCoreSet(SfxItemSet::makeFixedSfxItemSet<XATTR_FILL_FIRST, XATTR_FILL_LAST>(GetPool()));
2655
2656
0
        aCoreSet.SetParent(&GetView().GetDocShell()->GetDoc()->GetDfltFrameFormat()->GetAttrSet());
2657
2658
0
        if(nSelType & SelectionType::Graphic || SelectionType::Frame & nSelType)
2659
0
        {
2660
0
            rSh.GetFlyFrameAttr(aCoreSet);
2661
0
        }
2662
0
        else
2663
0
        {
2664
0
            rSh.GetCurAttr(aCoreSet);
2665
0
        }
2666
2667
0
        aBrushItem = getSvxBrushItemFromSourceSet(aCoreSet, RES_BACKGROUND);
2668
0
    }
2669
2670
0
    while(nWhich)
2671
0
    {
2672
0
        switch(nWhich)
2673
0
        {
2674
0
            case SID_BACKGROUND_COLOR:
2675
0
            case SID_TABLE_CELL_BACKGROUND_COLOR:
2676
0
            {
2677
0
                SvxColorItem aColorItem(aBrushItem->GetColor(), aBrushItem->getComplexColor(), nWhich);
2678
0
                rSet.Put(aColorItem);
2679
0
                break;
2680
0
            }
2681
0
            case SID_ATTR_BRUSH:
2682
0
            case RES_BACKGROUND:
2683
0
            {
2684
                // if this was intended to have a independent copy of the Item to be set
2685
                // this is not needed due to the ItemSet/Pool cloning Items which get set anyways.
2686
                // Keeping code as reference - it may have had other reasons I do notz see (?!?)
2687
                // std::unique_ptr<SfxPoolItem> pNewItem(aBrushItem.CloneSetWhich(GetPool().GetWhich(nWhich)));
2688
0
                rSet.Put(*aBrushItem);
2689
0
                break;
2690
0
            }
2691
0
        }
2692
2693
0
        nWhich = aIter.NextWhich();
2694
0
    }
2695
0
}
2696
2697
void SwBaseShell::ExecBckCol(SfxRequest& rReq)
2698
0
{
2699
0
    SwWrtShell &rSh = GetShell();
2700
0
    SelectionType nSelType(rSh.GetSelectionType());
2701
0
    const SfxItemSet* pArgs = rReq.GetArgs();
2702
0
    sal_uInt16 nSlot(rReq.GetSlot());
2703
2704
0
    if (!pArgs && nSlot != SID_BACKGROUND_COLOR && nSlot != SID_TABLE_CELL_BACKGROUND_COLOR)
2705
0
    {
2706
0
        return;
2707
0
    }
2708
2709
0
    std::unique_ptr<SvxBrushItem> aBrushItem(std::make_unique<SvxBrushItem>(RES_BACKGROUND));
2710
2711
0
    if ( nSlot == SID_TABLE_CELL_BACKGROUND_COLOR )
2712
0
    {
2713
0
        rSh.GetBoxBackground( aBrushItem );
2714
0
    }
2715
0
    else
2716
0
    {
2717
        // Adapt to new DrawingLayer FillStyle; use a parent which has XFILL_NONE set
2718
0
        SfxItemSet aCoreSet(SfxItemSet::makeFixedSfxItemSet<XATTR_FILL_FIRST, XATTR_FILL_LAST>(GetPool()));
2719
2720
0
        aCoreSet.SetParent(&GetView().GetDocShell()->GetDoc()->GetDfltFrameFormat()->GetAttrSet());
2721
2722
0
        if((SelectionType::Frame & nSelType) || (SelectionType::Graphic & nSelType))
2723
0
        {
2724
0
            rSh.GetFlyFrameAttr(aCoreSet);
2725
0
        }
2726
0
        else
2727
0
        {
2728
0
            rSh.GetCurAttr(aCoreSet);
2729
0
        }
2730
2731
0
        aBrushItem = getSvxBrushItemFromSourceSet(aCoreSet, RES_BACKGROUND);
2732
0
    }
2733
2734
0
    switch(nSlot)
2735
0
    {
2736
0
        case SID_BACKGROUND_COLOR:
2737
0
        case SID_TABLE_CELL_BACKGROUND_COLOR:
2738
0
        {
2739
0
            bool bIsTransparent = false;
2740
2741
0
            aBrushItem->SetGraphicPos(GPOS_NONE);
2742
2743
0
            sal_uInt16 nSlotId = (nSlot == SID_BACKGROUND_COLOR) ? SID_BACKGROUND_COLOR : SID_TABLE_CELL_BACKGROUND_COLOR;
2744
0
            if (pArgs)
2745
0
            {
2746
0
                const SvxColorItem& rNewColorItem = static_cast<const SvxColorItem&>(pArgs->Get(nSlotId));
2747
0
                aBrushItem->SetColor(rNewColorItem.GetValue());
2748
0
                aBrushItem->setComplexColor(rNewColorItem.getComplexColor());
2749
0
                GetView().GetViewFrame().GetBindings().SetState(rNewColorItem);
2750
0
            }
2751
0
            else
2752
0
            {
2753
0
                bIsTransparent = true;
2754
0
            }
2755
2756
0
            if (bIsTransparent)
2757
0
            {
2758
0
                aBrushItem->SetColor(COL_TRANSPARENT);
2759
0
                rReq.AppendItem(SvxColorItem(COL_TRANSPARENT,nSlot));
2760
0
            }
2761
0
            break;
2762
0
        }
2763
2764
0
        case SID_ATTR_BRUSH:
2765
0
        case RES_BACKGROUND:
2766
0
        {
2767
0
            assert(pArgs && "only SID_BACKGROUND_COLOR can have !pArgs, checked at entry");
2768
0
            aBrushItem.reset(static_cast<SvxBrushItem*>(pArgs->Get(GetPool().GetWhichIDFromSlotID(nSlot)).Clone()));
2769
0
            break;
2770
0
        }
2771
0
        default:
2772
0
        {
2773
0
            rReq.Ignore();
2774
0
            OSL_FAIL("unknown message in ExecuteAttr!" );
2775
0
            return;
2776
0
        }
2777
0
    }
2778
2779
0
    if ( nSlot == SID_TABLE_CELL_BACKGROUND_COLOR )
2780
0
    {
2781
0
        rSh.SetBoxBackground( *aBrushItem );
2782
0
    }
2783
0
    else
2784
0
    {
2785
        // Adapt to new DrawingLayer FillStyle; use a parent which has XFILL_NONE set
2786
0
        SfxItemSet aCoreSet(SfxItemSet::makeFixedSfxItemSet<XATTR_FILL_FIRST, XATTR_FILL_LAST>(GetPool()));
2787
2788
0
        aCoreSet.SetParent(&GetView().GetDocShell()->GetDoc()->GetDfltFrameFormat()->GetAttrSet());
2789
0
        setSvxBrushItemAsFillAttributesToTargetSet(*aBrushItem, aCoreSet);
2790
2791
0
        if((SelectionType::Frame & nSelType) || (SelectionType::Graphic & nSelType))
2792
0
        {
2793
            // Template autoupdate
2794
0
            SwFrameFormat* pFormat = rSh.GetSelectedFrameFormat();
2795
2796
0
            if(pFormat && pFormat->IsAutoUpdateOnDirectFormat())
2797
0
            {
2798
0
                rSh.AutoUpdateFrame(pFormat, aCoreSet);
2799
0
            }
2800
0
            else
2801
0
            {
2802
0
                rSh.SetFlyFrameAttr(aCoreSet);
2803
0
            }
2804
0
        }
2805
0
        else
2806
0
        {
2807
0
            SwTextFormatColl* pColl = rSh.GetCurTextFormatColl();
2808
2809
0
            if(pColl && pColl->IsAutoUpdateOnDirectFormat())
2810
0
            {
2811
0
                rSh.AutoUpdatePara(pColl, aCoreSet);
2812
0
            }
2813
0
            else
2814
0
            {
2815
0
                rSh.SetAttrSet(aCoreSet);
2816
0
            }
2817
0
        }
2818
0
    }
2819
2820
0
    rReq.Done();
2821
0
}
2822
2823
void SwBaseShell::GetBorderState(SfxItemSet &rSet)
2824
0
{
2825
0
    SwWrtShell &rSh = GetShell();
2826
    // Table cell(s) selected?
2827
0
    bool bPrepare = true;
2828
0
    bool bTableMode = rSh.IsTableMode();
2829
0
    if ( bTableMode )
2830
0
    {
2831
0
        SfxItemSet aCoreSet(SfxItemSet::makeFixedSfxItemSet<
2832
0
                                RES_BOX, RES_BOX, SID_ATTR_BORDER_INNER,
2833
0
                                SID_ATTR_BORDER_INNER>(GetPool()));
2834
0
        SvxBoxInfoItem aBoxInfo( SID_ATTR_BORDER_INNER );
2835
0
        aCoreSet.Put( aBoxInfo );
2836
0
        rSh.GetTabBorders( aCoreSet );
2837
0
        rSet.Put( aCoreSet );
2838
0
    }
2839
0
    else if ( rSh.IsFrameSelected() )
2840
0
    {
2841
0
        SwFlyFrameAttrMgr aMgr( false, &rSh, Frmmgr_Type::NONE, nullptr );
2842
0
        rSet.Put( aMgr.GetAttrSet() );
2843
0
        bPrepare = false;
2844
0
    }
2845
0
    else
2846
        // Get border attributes via shell quite normal
2847
0
        rSh.GetCurAttr( rSet );
2848
0
    if ( bPrepare )
2849
0
        ::PrepareBoxInfo( rSet, rSh );
2850
    // Switch the border toolbox controller mode
2851
0
    rSet.Put( SfxBoolItem( SID_BORDER_REDUCED_MODE, !bTableMode ));
2852
0
}
2853
2854
void SwBaseShell::ExecDlg(SfxRequest &rReq)
2855
0
{
2856
0
    SwWrtShell &rSh = GetShell();
2857
0
    weld::Window* pMDI = GetView().GetFrameWeld();
2858
    // So that from the basic no dialogues for the background views are called:
2859
0
    bool bBackground = (&GetView() != GetActiveView());
2860
0
    const SfxPoolItem* pItem = nullptr;
2861
0
    const SfxItemSet* pArgs = rReq.GetArgs();
2862
2863
0
    sal_uInt16 nSlot = rReq.GetSlot();
2864
0
    const SfxItemSet* pOutSet = nullptr;
2865
0
    bool bDone = false;
2866
0
    if(pArgs)
2867
0
        pArgs->GetItemState( GetPool().GetWhichIDFromSlotID(nSlot), false, &pItem );
2868
2869
0
    switch ( nSlot )
2870
0
    {
2871
0
        case FN_FORMAT_TITLEPAGE_DLG:
2872
0
        {
2873
0
            SwAbstractDialogFactory* pFact = SwAbstractDialogFactory::Create();
2874
0
            ScopedVclPtr<VclAbstractDialog> pDlg(pFact->CreateTitlePageDlg(pMDI));
2875
0
            VclAbstractDialog::AsyncContext aContext;
2876
0
            aContext.maEndDialogFn = [](sal_Int32){};
2877
0
            pDlg->StartExecuteAsync(aContext);
2878
0
        }
2879
0
        break;
2880
0
        case FN_FORMAT_PAGE_DLG:
2881
0
        case FN_FORMAT_PAGE_COLUMN_DLG:
2882
0
        case FN_FORMAT_PAGE_SETTING_DLG:
2883
0
        case FN_FORMAT_PAGE_AREA_DLG:
2884
0
        {
2885
0
            if( !bBackground )
2886
0
            {
2887
0
                const size_t nCurIdx = rSh.GetCurPageDesc();
2888
0
                const SwPageDesc& rPageDesc = rSh.GetPageDesc( nCurIdx );
2889
                // Temporary view, because the shell does not need to be valid after the dialog
2890
                // for example disable header
2891
0
                SwView& rTempView = GetView();
2892
2893
0
                OUString sPageId;
2894
0
                switch (nSlot)
2895
0
                {
2896
0
                    case FN_FORMAT_PAGE_COLUMN_DLG:
2897
0
                        sPageId = "columns";
2898
0
                        break;
2899
0
                    case FN_FORMAT_PAGE_SETTING_DLG:
2900
0
                        sPageId = "page";
2901
0
                        break;
2902
0
                    case FN_FORMAT_PAGE_AREA_DLG:
2903
0
                        sPageId = "area";
2904
0
                        break;
2905
0
                    case FN_FORMAT_PAGE_DLG:
2906
0
                        if (pItem)
2907
0
                          sPageId = static_cast<const SfxStringItem*>(pItem)->GetValue();
2908
0
                        break;
2909
0
                }
2910
0
                rTempView.GetDocShell()->FormatPage(rReq.GetFrameWeld(), rPageDesc.GetName(), sPageId, rSh, &rReq);
2911
0
                rTempView.InvalidateRulerPos();
2912
2913
0
                bDone = true; // FormatPage() takes care of calling Done()
2914
0
            }
2915
0
        }
2916
0
        break;
2917
0
        case FN_FORMAT_BORDER_DLG:
2918
0
        {
2919
0
            SfxItemSet aSet(SfxItemSet::makeFixedSfxItemSet<
2920
0
                RES_BOX, RES_SHADOW, SID_ATTR_BORDER_INNER, SID_ATTR_BORDER_INNER>(rSh.GetAttrPool()));
2921
0
            ScopedVclPtr<SfxAbstractDialog> pDlg;
2922
            // Table cell(s) selected?
2923
0
            if ( rSh.IsTableMode() )
2924
0
            {
2925
                // Set border attributes Get/SetTabBorders()
2926
0
                ::PrepareBoxInfo( aSet, rSh );
2927
0
                rSh.GetTabBorders( aSet );
2928
0
                SwAbstractDialogFactory* pFact = SwAbstractDialogFactory::Create();
2929
0
                pDlg.disposeAndReset(pFact->CreateSwBorderDlg(pMDI, aSet, SwBorderModes::TABLE));
2930
0
                if ( pDlg->Execute() == RET_OK )
2931
0
                {
2932
0
                    rSh.SetTabBorders( *pDlg->GetOutputItemSet() );
2933
0
                    pOutSet = pDlg->GetOutputItemSet();
2934
0
                }
2935
0
            }
2936
0
            else if ( rSh.IsFrameSelected() )
2937
0
            {
2938
                // Set border attributes via Frame-Manager
2939
0
                SwFlyFrameAttrMgr aMgr( false, &rSh, Frmmgr_Type::NONE, nullptr );
2940
0
                aSet.Put( aMgr.GetAttrSet() );
2941
2942
0
                SwAbstractDialogFactory* pFact = SwAbstractDialogFactory::Create();
2943
0
                pDlg.disposeAndReset(pFact->CreateSwBorderDlg(pMDI, aSet, SwBorderModes::FRAME));
2944
0
                if ( pDlg->Execute() == RET_OK )
2945
0
                {
2946
0
                    aMgr.SetAttrSet( *pDlg->GetOutputItemSet() );
2947
0
                    aMgr.UpdateFlyFrame();
2948
0
                    pOutSet = pDlg->GetOutputItemSet();
2949
0
                }
2950
0
            }
2951
0
            else
2952
0
            {
2953
                // Set border attributes via Shell quite normal
2954
0
                rSh.GetCurAttr( aSet );
2955
0
                ::PrepareBoxInfo( aSet, rSh );
2956
2957
0
                SwAbstractDialogFactory* pFact = SwAbstractDialogFactory::Create();
2958
0
                pDlg.disposeAndReset(pFact->CreateSwBorderDlg(pMDI, aSet, SwBorderModes::PARA));
2959
0
                if ( pDlg->Execute() == RET_OK )
2960
0
                {
2961
0
                    rSh.SetAttrSet( *pDlg->GetOutputItemSet() );
2962
0
                    pOutSet = pDlg->GetOutputItemSet();
2963
0
                }
2964
0
            }
2965
0
            if(pOutSet)
2966
0
            {
2967
0
                rReq.Done(*pOutSet);
2968
0
                bDone = true;
2969
0
            }
2970
0
        }
2971
0
        break;
2972
0
        case FN_FORMAT_BACKGROUND_DLG:
2973
0
        {
2974
0
            SfxItemSet aSet(SfxItemSet::makeFixedSfxItemSet<
2975
0
                            RES_BACKGROUND, RES_BACKGROUND,
2976
0
                            XATTR_FILL_FIRST, XATTR_FILL_LAST>(rSh.GetAttrPool()));
2977
2978
0
            ScopedVclPtr<SfxAbstractDialog> pDlg;
2979
0
            SwAbstractDialogFactory* pFact = SwAbstractDialogFactory::Create();
2980
2981
            // Table cell(s) selected?
2982
0
            if ( rSh.IsTableMode() )
2983
0
            {
2984
                // Get background attributes of the table and put it in the set
2985
                // tdf#144843 calling GetBoxBackground *requires* an incarnation to be handed over
2986
0
                std::unique_ptr<SvxBrushItem> aBrush(std::make_unique<SvxBrushItem>(RES_BACKGROUND));
2987
0
                rSh.GetBoxBackground( aBrush );
2988
0
                pDlg.disposeAndReset(pFact->CreateSwBackgroundDialog(pMDI, aSet));
2989
0
                aSet.Put( std::move(aBrush) );
2990
0
                if ( pDlg->Execute() == RET_OK )
2991
0
                {
2992
2993
0
                    rSh.SetBoxBackground( pDlg->GetOutputItemSet()->Get( RES_BACKGROUND ) );
2994
0
                    pOutSet = pDlg->GetOutputItemSet();
2995
0
                }
2996
0
            }
2997
0
            else if ( rSh.IsFrameSelected() )
2998
0
            {
2999
3000
0
                rSh.GetFlyFrameAttr( aSet );
3001
3002
0
                pDlg.disposeAndReset(pFact->CreateSwBackgroundDialog(pMDI, aSet));
3003
0
                if ( pDlg->Execute() == RET_OK )
3004
0
                {
3005
0
                    rSh.SetFlyFrameAttr(const_cast<SfxItemSet &>(*pDlg->GetOutputItemSet()) );
3006
0
                    pOutSet = pDlg->GetOutputItemSet();
3007
0
                }
3008
0
            }
3009
0
            else
3010
0
            {
3011
                // Set border attributes Umrandungsattribute with the shell quite normal.
3012
0
                rSh.GetCurAttr( aSet );
3013
3014
0
                pDlg.disposeAndReset(pFact->CreateSwBackgroundDialog(pMDI, aSet));
3015
0
                if ( pDlg->Execute() == RET_OK )
3016
0
                {
3017
0
                    rSh.SetAttrSet( *pDlg->GetOutputItemSet() );
3018
0
                    pOutSet = pDlg->GetOutputItemSet();
3019
0
                }
3020
0
            }
3021
0
            if(pOutSet)
3022
0
            {
3023
0
                rReq.Done(*pOutSet);
3024
0
                bDone = true;
3025
0
            }
3026
0
        }
3027
0
        break;
3028
3029
0
        case SID_GRAPHIC_SIZE_CHECK:
3030
0
        {
3031
0
            sw::GraphicSizeCheckGUIResult aResult(rSh.GetDoc());
3032
0
            svx::GenericCheckDialog aDialog(pMDI, aResult);
3033
0
            aDialog.run();
3034
0
        }
3035
0
        break;
3036
3037
0
        case SID_THEME_DIALOG:
3038
0
        {
3039
0
            auto* pDocument = rSh.GetDoc();
3040
0
            auto* pDocumentShell = pDocument->GetDocShell();
3041
0
            if (pDocumentShell)
3042
0
            {
3043
0
                SdrModel* pModel = pDocument->getIDocumentDrawModelAccess().GetDrawModel();
3044
0
                auto const& pTheme = pModel->getTheme();
3045
0
                if (pTheme)
3046
0
                {
3047
0
                    std::shared_ptr<svx::IThemeColorChanger> xChanger(new sw::ThemeColorChanger(pDocumentShell));
3048
0
                    auto pDialog = std::make_shared<svx::ThemeDialog>(pMDI, pTheme.get());
3049
0
                    weld::DialogController::runAsync(pDialog, [pDialog, xChanger=std::move(xChanger)](sal_uInt32 nResult) {
3050
0
                        if (RET_OK != nResult)
3051
0
                            return;
3052
3053
0
                        auto pColorSet = pDialog->getCurrentColorSet();
3054
0
                        if (pColorSet)
3055
0
                        {
3056
0
                            xChanger->apply(pColorSet);
3057
0
                        }
3058
0
                    });
3059
0
                }
3060
0
            }
3061
0
        }
3062
0
        break;
3063
3064
0
        default:OSL_FAIL("wrong Dispatcher (basesh.cxx)");
3065
0
    }
3066
0
    if(!bDone)
3067
0
        rReq.Done();
3068
0
}
3069
3070
SwWrtShell& SwBaseShell::GetShell()
3071
0
{
3072
0
    return m_rView.GetWrtShell();
3073
0
}
3074
3075
SwWrtShell* SwBaseShell::GetShellPtr()
3076
0
{
3077
0
    return m_rView.GetWrtShellPtr();
3078
0
}
3079
3080
static void EndUndo(SwWrtShell& rSh)
3081
0
{
3082
0
    SwRewriter aRewriter;
3083
3084
0
    if (rSh.GetTableFormat())
3085
0
    {
3086
0
        aRewriter.AddRule(UndoArg1, SwResId(STR_START_QUOTE));
3087
0
        aRewriter.AddRule(UndoArg2, rSh.GetTableFormat()->GetName());
3088
0
        aRewriter.AddRule(UndoArg3, SwResId(STR_END_QUOTE));
3089
3090
0
    }
3091
0
    rSh.EndUndo(SwUndoId::INSTABLE, &aRewriter); // If possible change the Shell
3092
0
}
3093
3094
static void InsertTableImpl(SwWrtShell& rSh,
3095
                    SwView &rTempView,
3096
                    const UIName& aTableName,
3097
                    sal_uInt16 nRows,
3098
                    sal_uInt16 nCols,
3099
                    SwInsertTableOptions aInsTableOpts,
3100
                    const TableStyleName& aAutoName,
3101
                    const std::unique_ptr<SwTableAutoFormat>& pTAFormat)
3102
0
{
3103
0
    rSh.StartUndo(SwUndoId::INSTABLE);
3104
3105
0
    rSh.StartAllAction();
3106
0
    if( rSh.HasSelection() )
3107
0
        rSh.DelRight();
3108
3109
0
    rSh.InsertTable( aInsTableOpts, nRows, nCols, pTAFormat.get() );
3110
0
    rSh.MoveTable( GotoPrevTable, fnTableStart );
3111
3112
0
    if( !aTableName.isEmpty() && !rSh.GetTableStyle( aTableName ) )
3113
0
        rSh.GetTableFormat()->SetFormatName( aTableName );
3114
3115
0
    if( pTAFormat != nullptr && !aAutoName.isEmpty()
3116
0
                        && aAutoName != SwViewShell::GetShellRes()->aStrNone )
3117
0
    {
3118
0
        SwTableNode* pTableNode = const_cast<SwTableNode*>( rSh.IsCursorInTable() );
3119
0
        if ( pTableNode )
3120
0
        {
3121
0
            pTableNode->GetTable().SetTableStyleName( aAutoName );
3122
0
            SwUndoTableAutoFormat* pUndo = new SwUndoTableAutoFormat( *pTableNode, *pTAFormat );
3123
0
            rSh.GetIDocumentUndoRedo().AppendUndo( std::unique_ptr<SwUndo>(pUndo) );
3124
0
        }
3125
0
    }
3126
3127
0
    rSh.EndAllAction();
3128
0
    rTempView.AutoCaption(TABLE_CAP);
3129
0
}
3130
3131
void SwBaseShell::InsertTable( SfxRequest& _rRequest )
3132
0
{
3133
0
    const SfxItemSet* pArgs = _rRequest.GetArgs();
3134
0
    SwWrtShell& rSh = GetShell();
3135
3136
0
    if ( rSh.GetFrameType( nullptr, true ) & FrameTypeFlags::FOOTNOTE )
3137
0
        return;
3138
3139
0
    SwView &rTempView = GetView(); // Because GetView() does not work after the shell exchange
3140
0
    bool bHTMLMode = 0 != (::GetHtmlMode(rTempView.GetDocShell())&HTMLMODE_ON);
3141
0
    bool bCallEndUndo = false;
3142
3143
0
    if( !pArgs && rSh.IsSelection() && !rSh.IsInClickToEdit() &&
3144
0
        !rSh.IsTableMode() )
3145
0
    {
3146
0
        const SwModuleOptions* pModOpt = SwModule::get()->GetModuleConfig();
3147
0
        SwInsertTableOptions aInsTableOpts = pModOpt->GetInsTableFlags(bHTMLMode);
3148
3149
0
        rSh.StartUndo(SwUndoId::INSTABLE);
3150
0
        bCallEndUndo = true;
3151
3152
0
        bool bInserted = rSh.TextToTable( aInsTableOpts, '\t' );
3153
0
        rSh.EnterStdMode();
3154
0
        if (bInserted)
3155
0
            rTempView.AutoCaption(TABLE_CAP);
3156
0
        _rRequest.Done();
3157
0
    }
3158
0
    else
3159
0
    {
3160
0
        sal_uInt16 nColsIn = 0;
3161
0
        sal_uInt16 nRowsIn = 0;
3162
0
        SwInsertTableOptions aInsTableOptsIn( SwInsertTableFlags::All, 1 );
3163
0
        OUString aTableNameIn;
3164
0
        OUString aAutoNameIn;
3165
0
        std::unique_ptr<SwTableAutoFormat> pTAFormatIn;
3166
3167
0
        if( pArgs && pArgs->Count() >= 2 )
3168
0
        {
3169
0
            const SfxStringItem* pName = _rRequest.GetArg(FN_INSERT_TABLE);
3170
0
            const SfxUInt16Item* pCols = _rRequest.GetArg(SID_ATTR_TABLE_COLUMN);
3171
0
            const SfxUInt16Item* pRows = _rRequest.GetArg(SID_ATTR_TABLE_ROW);
3172
0
            const SfxInt32Item* pFlags = _rRequest.GetArg<SfxInt32Item>(FN_PARAM_1);
3173
0
            const SfxStringItem* pAuto = _rRequest.GetArg<SfxStringItem>(FN_PARAM_2);
3174
3175
0
            if ( pName )
3176
0
                aTableNameIn = pName->GetValue();
3177
0
            if ( pCols )
3178
0
                nColsIn = pCols->GetValue();
3179
0
            if ( pRows )
3180
0
                nRowsIn = pRows->GetValue();
3181
0
            if ( pAuto )
3182
0
            {
3183
0
                aAutoNameIn = pAuto->GetValue();
3184
0
                if ( !aAutoNameIn.isEmpty() )
3185
0
                {
3186
0
                    const SwTableAutoFormatTable& rTableTable = SwModule::get()->GetAutoFormatTable();
3187
0
                    for (size_t n = 0; n < rTableTable.size(); ++n)
3188
0
                    {
3189
0
                        if (rTableTable[n].GetName() == aAutoNameIn)
3190
0
                        {
3191
0
                            pTAFormatIn.reset(new SwTableAutoFormat(rTableTable[n]));
3192
0
                            break;
3193
0
                        }
3194
0
                    }
3195
0
                }
3196
0
            }
3197
3198
0
            if ( pFlags )
3199
0
                aInsTableOptsIn.mnInsMode = static_cast<SwInsertTableFlags>(pFlags->GetValue());
3200
0
            else
3201
0
            {
3202
0
                const SwModuleOptions* pModOpt = SwModule::get()->GetModuleConfig();
3203
0
                aInsTableOptsIn = pModOpt->GetInsTableFlags(bHTMLMode);
3204
0
            }
3205
0
        }
3206
3207
0
        if( !nColsIn || !nRowsIn )
3208
0
        {
3209
0
            SwAbstractDialogFactory* pFact = SwAbstractDialogFactory::Create();
3210
0
            std::shared_ptr<AbstractInsTableDlg> pAbstractDialog(pFact->CreateInsTableDlg(rTempView));
3211
0
            std::shared_ptr<weld::DialogController> pDialogController(pAbstractDialog->getDialogController());
3212
3213
0
            weld::DialogController::runAsync(pDialogController,
3214
0
                [pAbstractDialog=std::move(pAbstractDialog), &rSh, &rTempView, aTableNameIn,
3215
0
                 nRowsIn, nColsIn, aInsTableOptsIn, aAutoNameIn] (sal_Int32 nResult) {
3216
0
                    if( RET_OK == nResult )
3217
0
                    {
3218
0
                        sal_uInt16 nCols = nColsIn;
3219
0
                        sal_uInt16 nRows = nRowsIn;
3220
0
                        SwInsertTableOptions aInsTableOpts = aInsTableOptsIn;
3221
0
                        OUString aTableName = aTableNameIn;
3222
0
                        OUString aAutoName = aAutoNameIn;
3223
0
                        std::unique_ptr<SwTableAutoFormat> pTAFormat;
3224
3225
0
                        pAbstractDialog->GetValues( aTableName, nRows, nCols, aInsTableOpts, aAutoName, pTAFormat );
3226
3227
0
                        if( nCols && nRows )
3228
0
                        {
3229
0
                            InsertTableImpl( rSh, rTempView, UIName(aTableName), nRows, nCols, aInsTableOpts, TableStyleName(aAutoName), pTAFormat );
3230
0
                            EndUndo(rSh);
3231
0
                        }
3232
0
                    }
3233
0
                }
3234
0
            );
3235
0
        }
3236
0
        else
3237
0
        {
3238
            // record before shell change
3239
0
            _rRequest.AppendItem( SfxStringItem( FN_INSERT_TABLE, aTableNameIn ) );
3240
0
            if ( !aAutoNameIn.isEmpty() )
3241
0
                _rRequest.AppendItem( SfxStringItem( FN_PARAM_2, aAutoNameIn ) );
3242
0
            _rRequest.AppendItem( SfxUInt16Item( SID_ATTR_TABLE_COLUMN, nColsIn ) );
3243
0
            _rRequest.AppendItem( SfxUInt16Item( SID_ATTR_TABLE_ROW, nRowsIn ) );
3244
0
            _rRequest.AppendItem( SfxInt32Item( FN_PARAM_1, static_cast<sal_Int32>(aInsTableOptsIn.mnInsMode) ) );
3245
0
            _rRequest.Done();
3246
3247
0
            InsertTableImpl( rSh, rTempView, UIName(aTableNameIn), nRowsIn, nColsIn, aInsTableOptsIn, TableStyleName(aAutoNameIn), pTAFormatIn );
3248
3249
0
            bCallEndUndo = true;
3250
0
        }
3251
0
    }
3252
3253
0
    if( bCallEndUndo )
3254
0
        EndUndo(rSh);
3255
0
}
3256
3257
void SwBaseShell::GetGalleryState( SfxItemSet &rSet )
3258
0
{
3259
0
    SwWrtShell &rSh = GetShell();
3260
0
    SfxWhichIter aIter( rSet );
3261
0
    sal_uInt16 nWhich = aIter.FirstWhich();
3262
0
    switch ( nWhich )
3263
0
    {
3264
0
        case SID_GALLERY_BG_BRUSH:
3265
0
        {
3266
0
            SelectionType nSel = rSh.GetSelectionType();
3267
0
            SfxStringListItem aLst( nWhich );
3268
0
            std::vector<OUString> &rLst = aLst.GetList();
3269
0
            nParagraphPos = nGraphicPos = nOlePos = nFramePos = nTablePos =
3270
0
            nTableRowPos  = nTableCellPos = nPagePos =
3271
0
            nHeaderPos    = nFooterPos = 0;
3272
0
            sal_uInt8 nPos = 1;
3273
0
            rLst.push_back( SwResId( STR_SWBG_PAGE ) );
3274
0
            nPagePos = nPos++;
3275
0
            sal_uInt16 nHtmlMode = ::GetHtmlMode(GetView().GetDocShell());
3276
0
            bool bHtmlMode = 0 != (nHtmlMode & HTMLMODE_ON);
3277
3278
0
            if ( (!bHtmlMode || (nHtmlMode & HTMLMODE_FULL_STYLES)) &&
3279
0
                 (nSel & SelectionType::Text) )
3280
0
            {
3281
0
                rLst.push_back( SwResId( STR_SWBG_PARAGRAPH ) );
3282
0
                nParagraphPos = nPos++;
3283
0
            }
3284
0
            if ( (!bHtmlMode || (nHtmlMode & HTMLMODE_SOME_STYLES)) &&
3285
0
                    nSel & (SelectionType::Table|SelectionType::TableCell) )
3286
0
            {
3287
0
                rLst.push_back( SwResId( STR_SWBG_TABLE ) );
3288
0
                nTablePos = nPos++;
3289
3290
0
                if(!bHtmlMode)
3291
0
                {
3292
0
                    rLst.push_back( SwResId( STR_SWBG_TABLE_ROW ) );
3293
0
                    nTableRowPos = nPos++;
3294
0
                }
3295
3296
0
                rLst.push_back( SwResId( STR_SWBG_TABLE_CELL) );
3297
0
                nTableCellPos = nPos++;
3298
0
            }
3299
0
            if(!bHtmlMode)
3300
0
            {
3301
0
                if ( nSel & SelectionType::Frame )
3302
0
                {
3303
0
                    rLst.push_back( SwResId( STR_SWBG_FRAME ) );
3304
0
                    nFramePos = nPos++;
3305
0
                }
3306
0
                if ( nSel & SelectionType::Graphic )
3307
0
                {
3308
0
                    rLst.push_back( SwResId( STR_SWBG_GRAPHIC ) );
3309
0
                    nGraphicPos = nPos++;
3310
0
                }
3311
0
                if ( nSel & SelectionType::Ole )
3312
0
                {
3313
0
                    rLst.push_back( SwResId( STR_SWBG_OLE ) );
3314
0
                    nOlePos = nPos++;
3315
0
                }
3316
0
                const FrameTypeFlags nType = rSh.GetFrameType(nullptr,true);
3317
0
                if ( nType & FrameTypeFlags::HEADER )
3318
0
                {
3319
0
                    rLst.push_back( SwResId( STR_SWBG_HEADER ) );
3320
0
                    nHeaderPos = nPos++;
3321
0
                }
3322
0
                if ( nType & FrameTypeFlags::FOOTER )
3323
0
                {
3324
0
                    rLst.push_back( SwResId( STR_SWBG_FOOTER ) );
3325
0
                    nFooterPos = nPos;
3326
0
                }
3327
0
            }
3328
0
            if ( rLst.empty() )
3329
0
                rSet.DisableItem( nWhich );
3330
0
            else
3331
0
                rSet.Put( aLst );
3332
0
            break;
3333
0
        }
3334
0
    }
3335
0
}
3336
3337
void SwBaseShell::ExecuteGallery(SfxRequest &rReq)
3338
0
{
3339
0
    SwWrtShell &rSh = GetShell();
3340
0
    rSh.StartAction();
3341
0
    const SfxItemSet* pArgs = rReq.GetArgs();
3342
0
    sal_uInt16 nSlot = rReq.GetSlot();
3343
0
    switch(nSlot)
3344
0
    {
3345
0
        case SID_GALLERY_BG_BRUSH:
3346
0
        {
3347
0
            if ( !pArgs )
3348
0
                break;
3349
3350
0
            SelectionType nSel = rSh.GetSelectionType();
3351
0
            if ( nSel & SelectionType::DrawObjectEditMode )
3352
0
                break;
3353
3354
0
            const SfxUInt16Item* pPos = rReq.GetArg<SfxUInt16Item>(SID_GALLERY_BG_POS);
3355
0
            const SvxBrushItem* pBrush = rReq.GetArg<SvxBrushItem>(SID_GALLERY_BG_BRUSH);
3356
0
            if ( !pPos || !pBrush )
3357
0
                break;
3358
3359
0
            sal_uInt8 nPos = pPos->GetValue();
3360
0
            ++nPos;
3361
3362
0
            SvxBrushItem aBrush( *pBrush );
3363
0
            aBrush.SetWhich( RES_BACKGROUND );
3364
0
            if ( nPos == nParagraphPos )
3365
0
                rSh.SetAttrItem( aBrush );
3366
0
            else if ( nPos == nTablePos )
3367
0
                rSh.SetTabBackground( aBrush );
3368
0
            else if ( nPos == nTableRowPos )
3369
0
                rSh.SetRowBackground( aBrush );
3370
0
            else if ( nPos == nTableCellPos )
3371
0
                rSh.SetBoxBackground( aBrush );
3372
0
            else if ( nPos == nFramePos || nPos == nGraphicPos || nPos == nOlePos )
3373
0
            {
3374
0
                SfxItemSet aCoreSet(SfxItemSet::makeFixedSfxItemSet<RES_BACKGROUND, RES_BACKGROUND>(GetPool()));
3375
0
                aCoreSet.Put( aBrush );
3376
0
                rSh.SetFlyFrameAttr( aCoreSet );
3377
0
            }
3378
0
            else if ( nPos == nPagePos || nPos == nHeaderPos || nPos == nFooterPos )
3379
0
            {
3380
0
                sal_uInt16 nDesc = rSh.GetCurPageDesc();
3381
0
                SwPageDesc aDesc( rSh.GetPageDesc( nDesc ) );
3382
0
                if ( nPos == nPagePos )
3383
0
                    aDesc.GetMaster().SetFormatAttr( aBrush );
3384
0
                else if ( nPos == nHeaderPos )
3385
0
                {
3386
0
                    SwFormatHeader aHead( aDesc.GetMaster().GetHeader() );
3387
0
                    aHead.GetHeaderFormat()->SetFormatAttr( aBrush );
3388
0
                    aDesc.GetMaster().SetFormatAttr( aHead );
3389
0
                }
3390
0
                else if ( nPos == nFooterPos )
3391
0
                {
3392
0
                    SwFormatFooter aFoot( aDesc.GetMaster().GetFooter() );
3393
0
                    aFoot.GetFooterFormat()->SetFormatAttr( aBrush );
3394
0
                    aDesc.GetMaster().SetFormatAttr( aFoot );
3395
0
                }
3396
0
                rSh.ChgPageDesc( nDesc, aDesc );
3397
0
            }
3398
0
            break;
3399
0
        }
3400
0
    }
3401
0
    rSh.EndAction();
3402
0
    rReq.Done();
3403
0
}
3404
3405
void SwBaseShell::ExecField( SfxRequest const & rReq )
3406
0
{
3407
0
    sal_uInt16 nSlot = rReq.GetSlot();
3408
0
    switch( nSlot )
3409
0
    {
3410
#if HAVE_FEATURE_DBCONNECTIVITY && !ENABLE_FUZZERS
3411
        case FN_CHANGE_DBFIELD:
3412
        {
3413
            SwAbstractDialogFactory* pFact = SwAbstractDialogFactory::Create();
3414
            VclPtr<AbstractChangeDbDialog> pDlg(pFact->CreateSwChangeDBDlg(GetView()));
3415
            pDlg->StartExecuteAsync(
3416
                [pDlg] (sal_Int32 nResult)->void
3417
                {
3418
                    if (nResult == RET_OK)
3419
                        pDlg->UpdateFields();
3420
                    pDlg->disposeOnce();
3421
                }
3422
            );
3423
        }
3424
        break;
3425
#endif
3426
0
        default:
3427
0
            OSL_FAIL("wrong dispatcher");
3428
0
    }
3429
0
}
3430
3431
std::shared_ptr<std::vector<std::unique_ptr<SwPaM>>> SwBaseShell::CopyPaMRing(SwPaM& rOrig)
3432
0
{
3433
0
    auto vCursors = std::make_shared<std::vector<std::unique_ptr<SwPaM>>>();
3434
0
    vCursors->emplace_back(std::make_unique<SwPaM>(rOrig, nullptr));
3435
0
    for (auto& rCursor : rOrig.GetRingContainer())
3436
0
    {
3437
0
        if (&rCursor != &rOrig)
3438
0
            vCursors->emplace_back(std::make_unique<SwPaM>(rCursor, vCursors->front().get()));
3439
0
    }
3440
0
    return vCursors;
3441
0
}
3442
3443
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */