docthemes: Save themes def. to a file when added to ColorSets
[LibreOffice.git] / sw / source / uibase / fldui / fldmgr.cxx
blob7d4d4e251b671edd6dc2285a01509661e562770c
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
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/.
9 * This file incorporates work covered by the following license notice:
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 .
20 #include <config_features.h>
21 #include <config_fuzzers.h>
23 #include <cmdid.h>
24 #include <hintids.hxx>
25 #include <svl/numformat.hxx>
26 #include <svl/stritem.hxx>
27 #include <com/sun/star/text/DefaultNumberingProvider.hpp>
28 #include <com/sun/star/text/XDefaultNumberingProvider.hpp>
29 #include <com/sun/star/text/XNumberingTypeInfo.hpp>
30 #include <com/sun/star/style/NumberingType.hpp>
31 #include <com/sun/star/beans/XPropertySet.hpp>
32 #include <com/sun/star/sdbc/XConnection.hpp>
33 #include <com/sun/star/sdbc/XDataSource.hpp>
34 #include <com/sun/star/uri/UriReferenceFactory.hpp>
35 #include <com/sun/star/uri/XVndSunStarScriptUrl.hpp>
36 #include <comphelper/processfactory.hxx>
37 #include <comphelper/string.hxx>
38 #include <o3tl/string_view.hxx>
39 #include <tools/resary.hxx>
40 #include <osl/diagnose.h>
41 #include <sfx2/dispatch.hxx>
42 #include <sfx2/linkmgr.hxx>
43 #include <sfx2/app.hxx>
44 #include <sfx2/viewfrm.hxx>
45 #include <svx/strarray.hxx>
46 #include <fmtrfmrk.hxx>
47 #include <svl/zforlist.hxx>
48 #include <svl/zformat.hxx>
49 #include <vcl/mnemonic.hxx>
50 #include <view.hxx>
51 #include <wrtsh.hxx>
52 #include <doc.hxx>
53 #include <swmodule.hxx>
54 #include <fmtinfmt.hxx>
55 #include <cellatr.hxx>
56 #include <dbmgr.hxx>
57 #include <shellres.hxx>
58 #include <fldbas.hxx>
59 #include <docufld.hxx>
60 #include <chpfld.hxx>
61 #include <ddefld.hxx>
62 #include <expfld.hxx>
63 #include <reffld.hxx>
64 #include <usrfld.hxx>
65 #include <dbfld.hxx>
66 #include <authfld.hxx>
67 #include <flddat.hxx>
68 #include <fldmgr.hxx>
69 #include <ndtxt.hxx>
70 #include <cntfrm.hxx>
71 #include <flddropdown.hxx>
72 #include <strings.hrc>
73 #include <tox.hxx>
74 #include <viewopt.hxx>
75 #include <txmsrt.hxx>
76 #include <unotools/useroptions.hxx>
77 #include <IDocumentContentOperations.hxx>
78 #include <translatehelper.hxx>
80 using namespace com::sun::star::uno;
81 using namespace com::sun::star::container;
82 using namespace com::sun::star::beans;
83 using namespace com::sun::star::text;
84 using namespace com::sun::star::style;
85 using namespace com::sun::star::sdbc;
86 using namespace ::com::sun::star;
87 using namespace nsSwDocInfoSubType;
89 // groups of fields
90 enum
92 GRP_DOC_BEGIN = 0,
93 GRP_DOC_END = GRP_DOC_BEGIN + 12,
95 GRP_FKT_BEGIN = GRP_DOC_END,
96 GRP_FKT_END = GRP_FKT_BEGIN + 8,
98 GRP_REF_BEGIN = GRP_FKT_END,
99 GRP_REF_END = GRP_REF_BEGIN + 2,
101 GRP_REG_BEGIN = GRP_REF_END,
102 GRP_REG_END = GRP_REG_BEGIN + 1,
104 GRP_DB_BEGIN = GRP_REG_END,
105 GRP_DB_END = GRP_DB_BEGIN + 5,
107 GRP_VAR_BEGIN = GRP_DB_END,
108 GRP_VAR_END = GRP_VAR_BEGIN + 9
111 enum
113 GRP_WEB_DOC_BEGIN = 0,
114 GRP_WEB_DOC_END = GRP_WEB_DOC_BEGIN + 9,
116 GRP_WEB_FKT_BEGIN = GRP_WEB_DOC_END + 2,
117 GRP_WEB_FKT_END = GRP_WEB_FKT_BEGIN + 0, // the group is empty!
119 GRP_WEB_REF_BEGIN = GRP_WEB_FKT_END + 6, // the group is empty!
120 GRP_WEB_REF_END = GRP_WEB_REF_BEGIN + 0,
122 GRP_WEB_REG_BEGIN = GRP_WEB_REF_END + 2,
123 GRP_WEB_REG_END = GRP_WEB_REG_BEGIN + 1,
125 GRP_WEB_DB_BEGIN = GRP_WEB_REG_END, // the group is empty!
126 GRP_WEB_DB_END = GRP_WEB_DB_BEGIN + 0,
128 GRP_WEB_VAR_BEGIN = GRP_WEB_DB_END + 5,
129 GRP_WEB_VAR_END = GRP_WEB_VAR_BEGIN + 1
132 const sal_uInt16 VF_COUNT = 1; // { 0 }
133 const sal_uInt16 VF_USR_COUNT = 2; // { 0, nsSwExtendedSubType::SUB_CMD }
134 const sal_uInt16 VF_DB_COUNT = 1; // { nsSwExtendedSubType::SUB_OWN_FMT }
136 const TranslateId FLD_EU_ARY[] =
138 FLD_EU_COMPANY,
139 FLD_EU_GIVENNAME,
140 FLD_EU_SURNAME,
141 FLD_EU_INITIALS,
142 FLD_EU_STREET,
143 FLD_EU_COUNTRY,
144 FLD_EU_POSTCODE,
145 FLD_EU_TOWN,
146 FLD_EU_TITLE,
147 FLD_EU_POS,
148 FLD_EU_TELPERSONAL,
149 FLD_EU_TELWORK,
150 FLD_EU_FAX,
151 FLD_EU_EMAIL,
152 FLD_EU_REGION
155 const TranslateId FMT_AUTHOR_ARY[] =
157 FMT_AUTHOR_NAME,
158 FMT_AUTHOR_SCUT
161 const TranslateId FLD_DATE_ARY[] =
163 FLD_DATE_FIX,
164 FLD_DATE_STD,
167 const TranslateId FLD_TIME_ARY[] =
169 FLD_TIME_FIX,
170 FLD_TIME_STD
173 const TranslateId FMT_NUM_ARY[] =
175 FMT_NUM_ABC,
176 FMT_NUM_SABC,
177 FMT_NUM_ABC_N,
178 FMT_NUM_SABC_N,
179 FMT_NUM_ROMAN,
180 FMT_NUM_SROMAN,
181 FMT_NUM_ARABIC,
182 FMT_NUM_PAGEDESC,
183 FMT_NUM_PAGESPECIAL
186 const TranslateId FMT_FF_ARY[] =
188 FMT_FF_NAME,
189 FMT_FF_PATHNAME,
190 FMT_FF_PATH,
191 FMT_FF_NAME_NOEXT,
192 FMT_FF_UI_NAME,
193 FMT_FF_UI_RANGE
196 const TranslateId FLD_STAT_ARY[] =
198 FLD_STAT_PAGE,
199 FLD_STAT_PARA,
200 FLD_STAT_WORD,
201 FLD_STAT_CHAR,
202 FLD_STAT_TABLE,
203 FLD_STAT_GRF,
204 FLD_STAT_OBJ
207 const TranslateId FMT_CHAPTER_ARY[] =
209 FMT_CHAPTER_NO,
210 FMT_CHAPTER_NAME,
211 FMT_CHAPTER_NAMENO,
212 FMT_CHAPTER_NO_NOSEPARATOR
215 const TranslateId FLD_INPUT_ARY[] =
217 FLD_INPUT_TEXT
220 const TranslateId FMT_MARK_ARY[] =
222 FMT_MARK_TEXT,
223 FMT_MARK_TABLE,
224 FMT_MARK_FRAME,
225 FMT_MARK_GRAFIC,
226 FMT_MARK_OLE
229 const TranslateId FMT_REF_ARY[] =
231 FMT_REF_PAGE,
232 FMT_REF_CHAPTER,
233 FMT_REF_TEXT,
234 FMT_REF_UPDOWN,
235 FMT_REF_PAGE_PGDSC,
236 FMT_REF_ONLYNUMBER,
237 FMT_REF_ONLYCAPTION,
238 FMT_REF_ONLYSEQNO,
239 FMT_REF_NUMBER,
240 FMT_REF_NUMBER_NO_CONTEXT,
241 FMT_REF_NUMBER_FULL_CONTEXT
244 const TranslateId FMT_REG_ARY[] =
246 FMT_REG_AUTHOR,
247 FMT_REG_TIME,
248 FMT_REG_DATE
251 const TranslateId FMT_DBFLD_ARY[] =
253 FMT_DBFLD_DB,
254 FMT_DBFLD_SYS
257 const TranslateId FMT_SETVAR_ARY[] =
259 FMT_SETVAR_SYS,
260 FMT_SETVAR_TEXT
263 const TranslateId FMT_GETVAR_ARY[] =
265 FMT_GETVAR_TEXT,
266 FMT_GETVAR_NAME
269 const TranslateId FMT_DDE_ARY[] =
271 FMT_DDE_NORMAL,
272 FMT_DDE_HOT
275 const TranslateId FLD_PAGEREF_ARY[] =
277 FLD_PAGEREF_OFF,
278 FLD_PAGEREF_ON
281 const TranslateId FMT_USERVAR_ARY[] =
283 FMT_USERVAR_TEXT,
284 FMT_USERVAR_CMD
287 namespace {
289 // field types and subtypes
290 struct SwFieldPack
292 SwFieldTypesEnum nTypeId;
294 const TranslateId* pSubTypeResIds;
295 size_t nSubTypeLength;
297 const TranslateId* pFormatResIds;
298 size_t nFormatLength;
303 // strings and formats
304 const SwFieldPack aSwFields[] =
306 // Document
307 { SwFieldTypesEnum::ExtendedUser, FLD_EU_ARY, std::size(FLD_EU_ARY), nullptr, 0 },
308 { SwFieldTypesEnum::Author, nullptr, 0, FMT_AUTHOR_ARY, std::size(FMT_AUTHOR_ARY) },
309 { SwFieldTypesEnum::Date, FLD_DATE_ARY, std::size(FLD_DATE_ARY), nullptr, 0 },
310 { SwFieldTypesEnum::Time, FLD_TIME_ARY, std::size(FLD_TIME_ARY), nullptr, 0 },
311 { SwFieldTypesEnum::PageNumber, nullptr, 0, FMT_NUM_ARY, std::size(FMT_NUM_ARY) -1 },
312 { SwFieldTypesEnum::NextPage, nullptr, 0, FMT_NUM_ARY, std::size(FMT_NUM_ARY) },
313 { SwFieldTypesEnum::PreviousPage, nullptr, 0, FMT_NUM_ARY, std::size(FMT_NUM_ARY) },
314 { SwFieldTypesEnum::Filename, nullptr, 0, FMT_FF_ARY, std::size(FMT_FF_ARY) },
315 { SwFieldTypesEnum::DocumentStatistics, FLD_STAT_ARY, std::size(FLD_STAT_ARY), FMT_NUM_ARY, std::size(FMT_NUM_ARY) -1 },
317 { SwFieldTypesEnum::Chapter, nullptr, 0, FMT_CHAPTER_ARY, std::size(FMT_CHAPTER_ARY) },
318 { SwFieldTypesEnum::TemplateName, nullptr, 0, FMT_FF_ARY, std::size(FMT_FF_ARY) },
319 { SwFieldTypesEnum::ParagraphSignature, nullptr, 0, nullptr, 0 },
321 // Functions
322 { SwFieldTypesEnum::ConditionalText, nullptr, 0, nullptr, 0 },
323 { SwFieldTypesEnum::Dropdown, nullptr, 0, nullptr, 0 },
324 { SwFieldTypesEnum::Input, FLD_INPUT_ARY, std::size(FLD_INPUT_ARY), nullptr, 0 },
325 { SwFieldTypesEnum::Macro, nullptr, 0, nullptr, 0 },
326 { SwFieldTypesEnum::JumpEdit, nullptr, 0, FMT_MARK_ARY, std::size(FMT_MARK_ARY) },
327 { SwFieldTypesEnum::CombinedChars, nullptr, 0, nullptr, 0 },
328 { SwFieldTypesEnum::HiddenText, nullptr, 0, nullptr, 0 },
329 { SwFieldTypesEnum::HiddenParagraph, nullptr, 0, nullptr, 0 },
331 // Cross-References
332 { SwFieldTypesEnum::SetRef, nullptr, 0, nullptr, 0 },
333 { SwFieldTypesEnum::GetRef, nullptr, 0, FMT_REF_ARY, std::size(FMT_REF_ARY) },
335 // DocInformation
336 { SwFieldTypesEnum::DocumentInfo, nullptr, 0, FMT_REG_ARY, std::size(FMT_REG_ARY) },
338 // Database
339 { SwFieldTypesEnum::Database, nullptr, 0, FMT_DBFLD_ARY, std::size(FMT_DBFLD_ARY) },
340 { SwFieldTypesEnum::DatabaseNextSet, nullptr, 0, nullptr, 0 },
341 { SwFieldTypesEnum::DatabaseNumberSet, nullptr, 0, nullptr, 0 },
342 { SwFieldTypesEnum::DatabaseSetNumber, nullptr, 0, FMT_NUM_ARY, std::size(FMT_NUM_ARY) - 2 },
343 { SwFieldTypesEnum::DatabaseName, nullptr, 0, nullptr, 0 },
345 // Variables
346 { SwFieldTypesEnum::Set, nullptr, 0, FMT_SETVAR_ARY, std::size(FMT_SETVAR_ARY) },
348 { SwFieldTypesEnum::Get, nullptr, 0, FMT_GETVAR_ARY, std::size(FMT_GETVAR_ARY) },
349 { SwFieldTypesEnum::DDE, nullptr, 0, FMT_DDE_ARY, std::size(FMT_DDE_ARY) },
350 { SwFieldTypesEnum::Formel, nullptr, 0, FMT_GETVAR_ARY, std::size(FMT_GETVAR_ARY) },
351 { SwFieldTypesEnum::Input, FLD_INPUT_ARY, std::size(FLD_INPUT_ARY), nullptr, 0 },
352 { SwFieldTypesEnum::Sequence, nullptr, 0, FMT_NUM_ARY, std::size(FMT_NUM_ARY) - 2 },
353 { SwFieldTypesEnum::SetRefPage, FLD_PAGEREF_ARY, std::size(FLD_PAGEREF_ARY),nullptr, 0 },
354 { SwFieldTypesEnum::GetRefPage, nullptr, 0, FMT_NUM_ARY, std::size(FMT_NUM_ARY) - 1 },
355 { SwFieldTypesEnum::User, nullptr, 0, FMT_USERVAR_ARY, std::size(FMT_USERVAR_ARY) }
358 // access to the shell
359 static SwWrtShell* lcl_GetShell()
361 if (SwView* pView = GetActiveView())
362 return pView->GetWrtShellPtr();
363 return nullptr;
366 static sal_uInt16 GetPackCount() { return SAL_N_ELEMENTS(aSwFields); }
368 // FieldManager controls inserting and updating of fields
369 SwFieldMgr::SwFieldMgr(SwWrtShell* pSh ) :
370 m_pWrtShell(pSh),
371 m_bEvalExp(true)
373 // determine current field if existing
374 GetCurField();
377 SwFieldMgr::~SwFieldMgr()
381 // organise RefMark by names
382 bool SwFieldMgr::CanInsertRefMark( std::u16string_view rStr )
384 bool bRet = false;
385 SwWrtShell *pSh = m_pWrtShell ? m_pWrtShell : lcl_GetShell();
386 OSL_ENSURE(pSh, "no SwWrtShell found");
387 if(pSh)
389 sal_uInt16 nCnt = pSh->GetCursorCnt();
391 // the last Cursor doesn't have to be a spanned selection
392 if( 1 < nCnt && !pSh->SwCursorShell::HasSelection() )
393 --nCnt;
395 bRet = 2 > nCnt && nullptr == pSh->GetRefMark( rStr );
397 return bRet;
400 // access over ResIds
401 void SwFieldMgr::RemoveFieldType(SwFieldIds nResId, const OUString& rName )
403 SwWrtShell * pSh = m_pWrtShell ? m_pWrtShell : lcl_GetShell();
404 OSL_ENSURE(pSh, "no SwWrtShell found");
405 if( pSh )
406 pSh->RemoveFieldType(nResId, rName);
409 size_t SwFieldMgr::GetFieldTypeCount() const
411 SwWrtShell * pSh = m_pWrtShell ? m_pWrtShell : lcl_GetShell();
412 OSL_ENSURE(pSh, "no SwWrtShell found");
413 return pSh ? pSh->GetFieldTypeCount() : 0;
416 SwFieldType* SwFieldMgr::GetFieldType(SwFieldIds nResId, size_t nField) const
418 SwWrtShell * pSh = m_pWrtShell ? m_pWrtShell : lcl_GetShell();
419 OSL_ENSURE(pSh, "no SwWrtShell found");
420 return pSh ? pSh->GetFieldType(nField, nResId) : nullptr;
423 SwFieldType* SwFieldMgr::GetFieldType(SwFieldIds nResId, const OUString& rName) const
425 SwWrtShell * pSh = m_pWrtShell ? m_pWrtShell : lcl_GetShell();
426 OSL_ENSURE(pSh, "no SwWrtShell found");
427 return pSh ? pSh->GetFieldType(nResId, rName) : nullptr;
430 // determine current field
431 SwField* SwFieldMgr::GetCurField()
433 SwWrtShell *pSh = m_pWrtShell ? m_pWrtShell : ::lcl_GetShell();
434 if ( pSh )
435 m_pCurField = pSh->GetCurField( true );
436 else
437 m_pCurField = nullptr;
439 // initialise strings and format
440 m_aCurPar1.clear();
441 m_aCurPar2.clear();
442 m_sCurFrame.clear();
444 if(!m_pCurField)
445 return nullptr;
447 // preprocess current values; determine parameter 1 and parameter 2
449 m_aCurPar1 = m_pCurField->GetPar1();
450 m_aCurPar2 = m_pCurField->GetPar2();
452 return m_pCurField;
455 // provide group range
456 const SwFieldGroupRgn& SwFieldMgr::GetGroupRange(bool bHtmlMode, sal_uInt16 nGrpId)
458 static SwFieldGroupRgn const aRanges[] =
460 { /* Document */ GRP_DOC_BEGIN, GRP_DOC_END },
461 { /* Functions */ GRP_FKT_BEGIN, GRP_FKT_END },
462 { /* Cross-Refs */ GRP_REF_BEGIN, GRP_REF_END },
463 { /* DocInfos */ GRP_REG_BEGIN, GRP_REG_END },
464 { /* Database */ GRP_DB_BEGIN, GRP_DB_END },
465 { /* User */ GRP_VAR_BEGIN, GRP_VAR_END }
467 static SwFieldGroupRgn const aWebRanges[] =
469 { /* Document */ GRP_WEB_DOC_BEGIN, GRP_WEB_DOC_END },
470 { /* Functions */ GRP_WEB_FKT_BEGIN, GRP_WEB_FKT_END },
471 { /* Cross-Refs */ GRP_WEB_REF_BEGIN, GRP_WEB_REF_END },
472 { /* DocInfos */ GRP_WEB_REG_BEGIN, GRP_WEB_REG_END },
473 { /* Database */ GRP_WEB_DB_BEGIN, GRP_WEB_DB_END },
474 { /* User */ GRP_WEB_VAR_BEGIN, GRP_WEB_VAR_END }
477 if (bHtmlMode)
478 return aWebRanges[nGrpId];
479 else
480 return aRanges[nGrpId];
483 // determine GroupId
484 sal_uInt16 SwFieldMgr::GetGroup(SwFieldTypesEnum nTypeId, sal_uInt16 nSubType)
486 if (nTypeId == SwFieldTypesEnum::SetInput)
487 nTypeId = SwFieldTypesEnum::Set;
489 if (nTypeId == SwFieldTypesEnum::Input && (nSubType & INP_USR))
490 nTypeId = SwFieldTypesEnum::User;
492 if (nTypeId == SwFieldTypesEnum::FixedDate)
493 nTypeId = SwFieldTypesEnum::Date;
495 if (nTypeId == SwFieldTypesEnum::FixedTime)
496 nTypeId = SwFieldTypesEnum::Time;
498 for (sal_uInt16 i = GRP_DOC; i <= GRP_VAR; i++)
500 const SwFieldGroupRgn& rRange = GetGroupRange(false/*bHtmlMode*/, i);
501 for (sal_uInt16 nPos = rRange.nStart; nPos < rRange.nEnd; nPos++)
503 if (aSwFields[nPos].nTypeId == nTypeId)
504 return i;
507 return USHRT_MAX;
510 // determine names to TypeId
511 // ACCESS over TYP_...
512 SwFieldTypesEnum SwFieldMgr::GetTypeId(sal_uInt16 nPos)
514 OSL_ENSURE(nPos < ::GetPackCount(), "forbidden Pos");
515 return aSwFields[ nPos ].nTypeId;
518 const OUString & SwFieldMgr::GetTypeStr(sal_uInt16 nPos)
520 OSL_ENSURE(nPos < ::GetPackCount(), "forbidden TypeId");
522 SwFieldTypesEnum nFieldWh = aSwFields[ nPos ].nTypeId;
524 // special treatment for date/time fields (without var/fix)
525 if( SwFieldTypesEnum::Date == nFieldWh )
527 static OUString g_aDate( SwResId( STR_DATEFLD ) );
528 return g_aDate;
530 if( SwFieldTypesEnum::Time == nFieldWh )
532 static OUString g_aTime( SwResId( STR_TIMEFLD ) );
533 return g_aTime;
536 return SwFieldType::GetTypeStr( nFieldWh );
539 // determine Pos in the list
540 sal_uInt16 SwFieldMgr::GetPos(SwFieldTypesEnum nTypeId)
542 switch( nTypeId )
544 case SwFieldTypesEnum::FixedDate: nTypeId = SwFieldTypesEnum::Date; break;
545 case SwFieldTypesEnum::FixedTime: nTypeId = SwFieldTypesEnum::Time; break;
546 case SwFieldTypesEnum::SetInput: nTypeId = SwFieldTypesEnum::Set; break;
547 case SwFieldTypesEnum::UserInput: nTypeId = SwFieldTypesEnum::User; break;
548 default: break;
551 for(sal_uInt16 i = 0; i < GetPackCount(); i++)
552 if(aSwFields[i].nTypeId == nTypeId)
553 return i;
555 return USHRT_MAX;
558 // localise subtypes of a field
559 void SwFieldMgr::GetSubTypes(SwFieldTypesEnum nTypeId, std::vector<OUString>& rToFill)
561 SwWrtShell *pSh = m_pWrtShell ? m_pWrtShell : lcl_GetShell();
562 OSL_ENSURE(pSh, "no SwWrtShell found");
563 if(!pSh)
564 return;
566 const sal_uInt16 nPos = GetPos(nTypeId);
568 switch(nTypeId)
570 case SwFieldTypesEnum::SetRef:
571 case SwFieldTypesEnum::GetRef:
573 // references are no fields
574 pSh->GetRefMarks( &rToFill );
575 break;
577 case SwFieldTypesEnum::Macro:
579 break;
581 case SwFieldTypesEnum::Input:
583 rToFill.push_back(SwResId(aSwFields[nPos].pSubTypeResIds[0]));
584 [[fallthrough]]; // move on at generic types
586 case SwFieldTypesEnum::DDE:
587 case SwFieldTypesEnum::Sequence:
588 case SwFieldTypesEnum::Formel:
589 case SwFieldTypesEnum::Get:
590 case SwFieldTypesEnum::Set:
591 case SwFieldTypesEnum::User:
594 const size_t nCount = pSh->GetFieldTypeCount();
595 for(size_t i = 0; i < nCount; ++i)
597 SwFieldType* pFieldType = pSh->GetFieldType( i );
598 const SwFieldIds nWhich = pFieldType->Which();
600 if((nTypeId == SwFieldTypesEnum::DDE && pFieldType->Which() == SwFieldIds::Dde) ||
602 (nTypeId == SwFieldTypesEnum::User && nWhich == SwFieldIds::User) ||
604 (nTypeId == SwFieldTypesEnum::Get && nWhich == SwFieldIds::SetExp &&
605 !(static_cast<SwSetExpFieldType*>(pFieldType)->GetType() & nsSwGetSetExpType::GSE_SEQ)) ||
607 (nTypeId == SwFieldTypesEnum::Set && nWhich == SwFieldIds::SetExp &&
608 !(static_cast<SwSetExpFieldType*>(pFieldType)->GetType() & nsSwGetSetExpType::GSE_SEQ)) ||
610 (nTypeId == SwFieldTypesEnum::Sequence && nWhich == SwFieldIds::SetExp &&
611 (static_cast<SwSetExpFieldType*>(pFieldType)->GetType() & nsSwGetSetExpType::GSE_SEQ)) ||
613 ((nTypeId == SwFieldTypesEnum::Input || nTypeId == SwFieldTypesEnum::Formel) &&
614 (nWhich == SwFieldIds::User ||
615 (nWhich == SwFieldIds::SetExp &&
616 !(static_cast<SwSetExpFieldType*>(pFieldType)->GetType() & nsSwGetSetExpType::GSE_SEQ))) ) )
618 rToFill.push_back(pFieldType->GetName());
621 break;
623 case SwFieldTypesEnum::DatabaseNextSet:
624 case SwFieldTypesEnum::DatabaseNumberSet:
625 case SwFieldTypesEnum::DatabaseName:
626 case SwFieldTypesEnum::DatabaseSetNumber:
627 break;
629 default:
631 // static SubTypes
632 if(nPos != USHRT_MAX)
634 sal_uInt16 nCount;
635 if (nTypeId == SwFieldTypesEnum::DocumentInfo)
636 nCount = DI_SUBTYPE_END - DI_SUBTYPE_BEGIN;
637 else
638 nCount = aSwFields[nPos].nSubTypeLength;
640 for(sal_uInt16 i = 0; i < nCount; ++i)
642 OUString sNew;
643 if (nTypeId == SwFieldTypesEnum::DocumentInfo)
645 if ( i == DI_CUSTOM )
646 sNew = SwResId(STR_CUSTOM_FIELD);
647 else
648 sNew = SwViewShell::GetShellRes()->aDocInfoLst[i];
650 else
651 sNew = SwResId(aSwFields[nPos].pSubTypeResIds[i]);
653 rToFill.push_back(sNew);
660 // determine format
661 // ACCESS over TYP_...
662 sal_uInt16 SwFieldMgr::GetFormatCount(SwFieldTypesEnum nTypeId, bool bHtmlMode) const
664 assert(nTypeId < SwFieldTypesEnum::LAST && "forbidden TypeId");
666 const sal_uInt16 nPos = GetPos(nTypeId);
668 if (nPos == USHRT_MAX || (bHtmlMode && nTypeId == SwFieldTypesEnum::Set))
669 return 0;
671 sal_uInt16 nCount = aSwFields[nPos].nFormatLength;
673 if (nTypeId == SwFieldTypesEnum::Filename)
674 nCount -= 2; // no range or template
676 const TranslateId* pStart = aSwFields[nPos].pFormatResIds;
677 if (!pStart)
678 return nCount;
680 if (*pStart == FMT_GETVAR_ARY[0] || *pStart == FMT_SETVAR_ARY[0])
681 return VF_COUNT;
682 else if (*pStart == FMT_USERVAR_ARY[0])
683 return VF_USR_COUNT;
684 else if (*pStart == FMT_DBFLD_ARY[0])
685 return VF_DB_COUNT;
686 else if (*pStart == FMT_NUM_ARY[0])
688 GetNumberingInfo();
689 if(m_xNumberingInfo.is())
691 const Sequence<sal_Int16> aTypes = m_xNumberingInfo->getSupportedNumberingTypes();
692 // #i28073# it's not necessarily a sorted sequence
693 //skip all values below or equal to CHARS_LOWER_LETTER_N
694 nCount += std::count_if(aTypes.begin(), aTypes.end(),
695 [](sal_Int16 nCurrent) { return nCurrent > NumberingType::CHARS_LOWER_LETTER_N; });
697 return nCount;
700 return nCount;
704 // determine FormatString to a type
705 OUString SwFieldMgr::GetFormatStr(SwFieldTypesEnum nTypeId, sal_uInt32 nFormatId) const
707 assert(nTypeId < SwFieldTypesEnum::LAST && "forbidden TypeId");
708 const sal_uInt16 nPos = GetPos(nTypeId);
710 if (nPos == USHRT_MAX)
711 return OUString();
713 const TranslateId* pStart = aSwFields[nPos].pFormatResIds;
714 if (!pStart)
715 return OUString();
717 if (SwFieldTypesEnum::Author == nTypeId || SwFieldTypesEnum::Filename == nTypeId)
718 nFormatId &= ~static_cast<sal_uInt32>(FF_FIXED); // mask out Fixed-Flag
720 if (nFormatId < aSwFields[nPos].nFormatLength)
721 return SwResId(pStart[nFormatId]);
723 OUString aRet;
724 if (*pStart == FMT_NUM_ARY[0])
726 if (m_xNumberingInfo.is())
728 const Sequence<sal_Int16> aTypes = m_xNumberingInfo->getSupportedNumberingTypes();
729 sal_Int32 nOffset = aSwFields[nPos].nFormatLength;
730 sal_uInt32 nValidEntry = 0;
731 for (const sal_Int16 nCurrent : aTypes)
733 if(nCurrent > NumberingType::CHARS_LOWER_LETTER_N &&
734 (nCurrent != (NumberingType::BITMAP | LINK_TOKEN)))
736 if (nValidEntry == nFormatId - nOffset)
738 sal_uInt32 n = SvxNumberingTypeTable::FindIndex(nCurrent);
739 if (n != RESARRAY_INDEX_NOTFOUND)
741 aRet = SvxNumberingTypeTable::GetString(n);
743 else
745 aRet = m_xNumberingInfo->getNumberingIdentifier( nCurrent );
747 break;
749 ++nValidEntry;
755 return aRet;
758 // determine FormatId from Pseudo-ID
759 sal_uInt16 SwFieldMgr::GetFormatId(SwFieldTypesEnum nTypeId, sal_uInt32 nFormatId) const
761 sal_uInt16 nId = o3tl::narrowing<sal_uInt16>(nFormatId);
762 switch( nTypeId )
764 case SwFieldTypesEnum::DocumentInfo:
766 TranslateId sId = aSwFields[GetPos(nTypeId)].pFormatResIds[nFormatId];
767 if (sId == FMT_REG_AUTHOR)
768 nId = DI_SUB_AUTHOR;
769 else if (sId == FMT_REG_TIME)
770 nId = DI_SUB_TIME;
771 else if (sId == FMT_REG_DATE)
772 nId = DI_SUB_DATE;
773 break;
775 case SwFieldTypesEnum::PageNumber:
776 case SwFieldTypesEnum::NextPage:
777 case SwFieldTypesEnum::PreviousPage:
778 case SwFieldTypesEnum::DocumentStatistics:
779 case SwFieldTypesEnum::DatabaseSetNumber:
780 case SwFieldTypesEnum::Sequence:
781 case SwFieldTypesEnum::GetRefPage:
783 sal_uInt16 nPos = GetPos(nTypeId);
784 if (nFormatId < aSwFields[nPos].nFormatLength)
786 const TranslateId sId = aSwFields[nPos].pFormatResIds[nFormatId];
787 if (sId == FMT_NUM_ABC)
788 nId = SVX_NUM_CHARS_UPPER_LETTER;
789 else if (sId == FMT_NUM_SABC)
790 nId = SVX_NUM_CHARS_LOWER_LETTER;
791 else if (sId == FMT_NUM_ROMAN)
792 nId = SVX_NUM_ROMAN_UPPER;
793 else if (sId == FMT_NUM_SROMAN)
794 nId = SVX_NUM_ROMAN_LOWER;
795 else if (sId == FMT_NUM_ARABIC)
796 nId = SVX_NUM_ARABIC;
797 else if (sId == FMT_NUM_PAGEDESC)
798 nId = SVX_NUM_PAGEDESC;
799 else if (sId == FMT_NUM_PAGESPECIAL)
800 nId = SVX_NUM_CHAR_SPECIAL;
801 else if (sId == FMT_NUM_ABC_N)
802 nId = SVX_NUM_CHARS_UPPER_LETTER_N;
803 else if (sId == FMT_NUM_SABC_N)
804 nId = SVX_NUM_CHARS_LOWER_LETTER_N;
806 else if (m_xNumberingInfo.is())
808 const Sequence<sal_Int16> aTypes = m_xNumberingInfo->getSupportedNumberingTypes();
809 sal_Int32 nOffset = aSwFields[nPos].nFormatLength;
810 sal_Int32 nValidEntry = 0;
811 for (const sal_Int16 nCurrent : aTypes)
813 if (nCurrent > NumberingType::CHARS_LOWER_LETTER_N)
815 if (nValidEntry == static_cast<sal_Int32>(nFormatId) - nOffset)
817 nId = nCurrent;
818 break;
820 ++nValidEntry;
824 break;
826 case SwFieldTypesEnum::DDE:
828 const TranslateId sId = aSwFields[GetPos(nTypeId)].pFormatResIds[nFormatId];
829 if (sId == FMT_DDE_NORMAL)
830 nId = static_cast<sal_uInt16>(SfxLinkUpdateMode::ONCALL);
831 else if (sId == FMT_DDE_HOT)
832 nId = static_cast<sal_uInt16>(SfxLinkUpdateMode::ALWAYS);
833 break;
835 default: break;
837 return nId;
840 // Traveling
841 bool SwFieldMgr::GoNextPrev( bool bNext, SwFieldType* pTyp )
843 SwWrtShell* pSh = m_pWrtShell ? m_pWrtShell : ::lcl_GetShell();
844 if(!pSh)
845 return false;
847 if( !pTyp && m_pCurField )
849 const SwFieldTypesEnum nTypeId = m_pCurField->GetTypeId();
850 if( SwFieldTypesEnum::SetInput == nTypeId || SwFieldTypesEnum::UserInput == nTypeId )
851 pTyp = pSh->GetFieldType( 0, SwFieldIds::Input );
852 else
853 pTyp = m_pCurField->GetTyp();
856 if (pTyp && pTyp->Which() == SwFieldIds::Database)
858 // for fieldcommand-edit (hop to all DB fields)
859 return pSh->MoveFieldType( nullptr, bNext, SwFieldIds::Database );
862 return pTyp && pSh->MoveFieldType(pTyp, bNext);
865 // insert field types
866 void SwFieldMgr::InsertFieldType(SwFieldType const & rType)
868 SwWrtShell* pSh = m_pWrtShell ? m_pWrtShell : ::lcl_GetShell();
869 OSL_ENSURE(pSh, "no SwWrtShell found");
870 if(pSh)
871 pSh->InsertFieldType(rType);
874 // determine current TypeId
875 SwFieldTypesEnum SwFieldMgr::GetCurTypeId() const
877 return m_pCurField ? m_pCurField->GetTypeId() : SwFieldTypesEnum::Unknown;
880 // Over string insert field or update
881 bool SwFieldMgr::InsertField(
882 SwInsertField_Data& rData)
884 std::unique_ptr<SwField> pField;
885 bool bExp = false;
886 bool bTable = false;
887 bool bPageVar = false;
888 sal_uInt32 nFormatId = rData.m_nFormatId;
889 sal_uInt16 nSubType = rData.m_nSubType;
890 sal_Unicode cSeparator = rData.m_cSeparator;
891 SwWrtShell* pCurShell = rData.m_pSh;
892 if(!pCurShell)
893 pCurShell = m_pWrtShell ? m_pWrtShell : ::lcl_GetShell();
894 OSL_ENSURE(pCurShell, "no SwWrtShell found");
895 if(!pCurShell)
896 return false;
898 switch (rData.m_nTypeId)
899 { // ATTENTION this field is inserted by a separate dialog
900 case SwFieldTypesEnum::Postit:
902 SvtUserOptions aUserOpt;
903 SwPostItFieldType* pType = static_cast<SwPostItFieldType*>(pCurShell->GetFieldType(0, SwFieldIds::Postit));
904 pField.reset(
905 new SwPostItField(
906 pType,
907 rData.m_sPar1, // author
908 rData.m_sPar2, // content
909 aUserOpt.GetID(), // author's initials
910 OUString(), // name
911 DateTime(DateTime::SYSTEM) ));
913 break;
914 case SwFieldTypesEnum::Script:
916 SwScriptFieldType* pType =
917 static_cast<SwScriptFieldType*>(pCurShell->GetFieldType(0, SwFieldIds::Script));
918 pField.reset(new SwScriptField(pType, rData.m_sPar1, rData.m_sPar2, static_cast<bool>(nFormatId)));
919 break;
922 case SwFieldTypesEnum::CombinedChars:
924 SwCombinedCharFieldType* pType = static_cast<SwCombinedCharFieldType*>(
925 pCurShell->GetFieldType( 0, SwFieldIds::CombinedChars ));
926 pField.reset(new SwCombinedCharField( pType, rData.m_sPar1 ));
928 break;
930 case SwFieldTypesEnum::Authority:
932 SwAuthorityFieldType* pType =
933 static_cast<SwAuthorityFieldType*>(pCurShell->GetFieldType(0, SwFieldIds::TableOfAuthorities));
934 if (!pType)
936 SwAuthorityFieldType const type(pCurShell->GetDoc());
937 pType = static_cast<SwAuthorityFieldType*>(
938 pCurShell->InsertFieldType(type));
940 pField.reset(new SwAuthorityField(pType, rData.m_sPar1));
942 break;
944 case SwFieldTypesEnum::Date:
945 case SwFieldTypesEnum::Time:
947 sal_uInt16 nSub = static_cast< sal_uInt16 >(rData.m_nTypeId == SwFieldTypesEnum::Date ? DATEFLD : TIMEFLD);
948 nSub |= nSubType == DATE_VAR ? 0 : FIXEDFLD;
950 SwDateTimeFieldType* pTyp =
951 static_cast<SwDateTimeFieldType*>( pCurShell->GetFieldType(0, SwFieldIds::DateTime) );
952 pField.reset(new SwDateTimeField(pTyp, nSub, nFormatId));
953 pField->SetPar2(rData.m_sPar2);
954 break;
957 case SwFieldTypesEnum::Filename:
959 SwFileNameFieldType* pTyp =
960 static_cast<SwFileNameFieldType*>( pCurShell->GetFieldType(0, SwFieldIds::Filename) );
961 pField.reset(new SwFileNameField(pTyp, nFormatId));
962 break;
965 case SwFieldTypesEnum::TemplateName:
967 SwTemplNameFieldType* pTyp =
968 static_cast<SwTemplNameFieldType*>( pCurShell->GetFieldType(0, SwFieldIds::TemplateName) );
969 pField.reset(new SwTemplNameField(pTyp, nFormatId));
970 break;
973 case SwFieldTypesEnum::Chapter:
975 sal_uInt16 nByte = o3tl::narrowing<sal_uInt16>(rData.m_sPar2.toInt32());
976 SwChapterFieldType* pTyp =
977 static_cast<SwChapterFieldType*>( pCurShell->GetFieldType(0, SwFieldIds::Chapter) );
978 pField.reset(new SwChapterField(pTyp, nFormatId));
979 nByte = std::max(sal_uInt16(1), nByte);
980 nByte = std::min(nByte, sal_uInt16(MAXLEVEL));
981 nByte -= 1;
982 static_cast<SwChapterField*>(pField.get())->SetLevel(static_cast<sal_uInt8>(nByte));
983 break;
986 case SwFieldTypesEnum::NextPage:
987 case SwFieldTypesEnum::PreviousPage:
988 case SwFieldTypesEnum::PageNumber:
990 short nOff = static_cast<short>(rData.m_sPar2.toInt32());
992 if(rData.m_nTypeId == SwFieldTypesEnum::NextPage)
994 if( SVX_NUM_CHAR_SPECIAL == nFormatId )
995 nOff = 1;
996 else
997 nOff += 1;
998 nSubType = PG_NEXT;
1000 else if(rData.m_nTypeId == SwFieldTypesEnum::PreviousPage)
1002 if( SVX_NUM_CHAR_SPECIAL == nFormatId )
1003 nOff = -1;
1004 else
1005 nOff -= 1;
1006 nSubType = PG_PREV;
1008 else
1009 nSubType = PG_RANDOM;
1011 SwPageNumberFieldType* pTyp =
1012 static_cast<SwPageNumberFieldType*>( pCurShell->GetFieldType(0, SwFieldIds::PageNumber) );
1013 pField.reset(new SwPageNumberField(pTyp, nSubType, nFormatId, nOff));
1015 if( SVX_NUM_CHAR_SPECIAL == nFormatId &&
1016 ( PG_PREV == nSubType || PG_NEXT == nSubType ) )
1017 static_cast<SwPageNumberField*>(pField.get())->SetUserString( rData.m_sPar2 );
1018 break;
1021 case SwFieldTypesEnum::DocumentStatistics:
1023 SwDocStatFieldType* pTyp =
1024 static_cast<SwDocStatFieldType*>( pCurShell->GetFieldType(0, SwFieldIds::DocStat) );
1025 pField.reset(new SwDocStatField(pTyp, nSubType, nFormatId));
1026 break;
1029 case SwFieldTypesEnum::Author:
1031 SwAuthorFieldType* pTyp =
1032 static_cast<SwAuthorFieldType*>( pCurShell->GetFieldType(0, SwFieldIds::Author) );
1033 pField.reset(new SwAuthorField(pTyp, nFormatId));
1034 break;
1037 case SwFieldTypesEnum::ConditionalText:
1038 case SwFieldTypesEnum::HiddenText:
1040 SwHiddenTextFieldType* pTyp =
1041 static_cast<SwHiddenTextFieldType*>( pCurShell->GetFieldType(0, SwFieldIds::HiddenText) );
1042 pField.reset(new SwHiddenTextField(pTyp, true, rData.m_sPar1, rData.m_sPar2, false, rData.m_nTypeId));
1043 bExp = true;
1044 break;
1047 case SwFieldTypesEnum::HiddenParagraph:
1049 SwHiddenParaFieldType* pTyp =
1050 static_cast<SwHiddenParaFieldType*>( pCurShell->GetFieldType(0, SwFieldIds::HiddenPara) );
1051 pField.reset(new SwHiddenParaField(pTyp, rData.m_sPar1));
1052 bExp = true;
1053 break;
1056 case SwFieldTypesEnum::SetRef:
1058 if( !rData.m_sPar1.isEmpty() && CanInsertRefMark( rData.m_sPar1 ) )
1060 const OUString& rRefmarkText = rData.m_sPar2;
1061 SwPaM* pCursorPos = pCurShell->GetCursor();
1062 pCurShell->StartAction();
1063 bool bHadMark = pCursorPos->HasMark();
1064 // If we have no selection and the refmark text is provided, then the text is
1065 // expected to be HTML.
1066 if (!bHadMark && !rRefmarkText.isEmpty())
1068 // Split node to remember where the start position is.
1069 bool bSuccess = pCurShell->GetDoc()->getIDocumentContentOperations().SplitNode(
1070 *pCursorPos->GetPoint(), /*bChkTableStart=*/false);
1071 if (bSuccess)
1073 SwPaM aRefmarkPam(*pCursorPos->GetPoint());
1074 aRefmarkPam.Move(fnMoveBackward, GoInContent);
1076 // Paste HTML content.
1077 SwTranslateHelper::PasteHTMLToPaM(
1078 *pCurShell, pCursorPos, rRefmarkText.toUtf8());
1080 // Undo the above SplitNode().
1081 aRefmarkPam.SetMark();
1082 aRefmarkPam.Move(fnMoveForward, GoInContent);
1083 pCurShell->GetDoc()->getIDocumentContentOperations().DeleteAndJoin(
1084 aRefmarkPam);
1085 *aRefmarkPam.GetMark() = *pCursorPos->GetPoint();
1086 *pCursorPos = aRefmarkPam;
1090 pCurShell->SetAttrItem( SwFormatRefMark( rData.m_sPar1 ) );
1092 if (!bHadMark && !rRefmarkText.isEmpty())
1094 pCursorPos->DeleteMark();
1096 pCurShell->EndAction();
1097 return true;
1099 return false;
1102 case SwFieldTypesEnum::GetRef:
1104 SwGetRefFieldType* pTyp =
1105 static_cast<SwGetRefFieldType*>( pCurShell->GetFieldType(0, SwFieldIds::GetRef) );
1107 sal_uInt16 nSeqNo = 0;
1108 sal_uInt16 nFlags = 0;
1110 if (nSubType == REF_STYLE) nFlags = o3tl::narrowing<sal_uInt16>(rData.m_sPar2.toInt32());
1111 else nSeqNo = o3tl::narrowing<sal_uInt16>(rData.m_sPar2.toInt32());
1113 OUString sReferenceLanguage;
1114 // handle language-variant formats
1115 if (nFormatId >= SAL_N_ELEMENTS(FMT_REF_ARY))
1117 LanguageType nLang = GetCurrLanguage();
1118 if (nLang == LANGUAGE_HUNGARIAN)
1120 if (nFormatId >= SAL_N_ELEMENTS(FMT_REF_ARY) * 2)
1121 sReferenceLanguage = "Hu";
1122 else
1123 sReferenceLanguage = "hu";
1125 nFormatId %= SAL_N_ELEMENTS(FMT_REF_ARY);
1128 pField.reset(new SwGetRefField(pTyp, rData.m_sPar1, sReferenceLanguage, nSubType, nSeqNo, nFlags, nFormatId));
1129 bExp = true;
1130 break;
1133 case SwFieldTypesEnum::DDE:
1135 //JP 28.08.95: DDE-Topics/-Items can have blanks in their names!
1136 // That's not yet considered here.
1137 sal_Int32 nIndex = 0;
1138 OUString sCmd = rData.m_sPar2.replaceFirst(" ", OUStringChar(sfx2::cTokenSeparator), &nIndex);
1139 if (nIndex>=0 && ++nIndex<sCmd.getLength())
1141 sCmd = sCmd.replaceFirst(" ", OUStringChar(sfx2::cTokenSeparator), &nIndex);
1144 SwDDEFieldType aType( rData.m_sPar1, sCmd, static_cast<SfxLinkUpdateMode>(nFormatId) );
1145 SwDDEFieldType* pTyp = static_cast<SwDDEFieldType*>( pCurShell->InsertFieldType( aType ) );
1146 pField.reset(new SwDDEField( pTyp ));
1147 break;
1150 case SwFieldTypesEnum::Macro:
1152 SwMacroFieldType* pTyp =
1153 static_cast<SwMacroFieldType*>(pCurShell->GetFieldType(0, SwFieldIds::Macro));
1155 pField.reset(new SwMacroField(pTyp, rData.m_sPar1, rData.m_sPar2));
1157 break;
1160 case SwFieldTypesEnum::Internet:
1162 SwFormatINetFormat aFormat( rData.m_sPar1, m_sCurFrame );
1163 return pCurShell->InsertURL( aFormat, rData.m_sPar2 );
1166 case SwFieldTypesEnum::JumpEdit:
1168 SwJumpEditFieldType* pTyp =
1169 static_cast<SwJumpEditFieldType*>(pCurShell->GetFieldType(0, SwFieldIds::JumpEdit));
1171 pField.reset(new SwJumpEditField(pTyp, nFormatId, rData.m_sPar1, rData.m_sPar2));
1172 break;
1175 case SwFieldTypesEnum::DocumentInfo:
1177 SwDocInfoFieldType* pTyp = static_cast<SwDocInfoFieldType*>( pCurShell->GetFieldType(
1178 0, SwFieldIds::DocInfo ) );
1179 pField.reset(new SwDocInfoField(pTyp, nSubType, rData.m_sPar1, nFormatId));
1180 break;
1183 case SwFieldTypesEnum::ExtendedUser:
1185 SwExtUserFieldType* pTyp = static_cast<SwExtUserFieldType*>( pCurShell->GetFieldType(
1186 0, SwFieldIds::ExtUser) );
1187 pField.reset(new SwExtUserField(pTyp, nSubType, nFormatId));
1188 break;
1191 case SwFieldTypesEnum::Database:
1193 #if HAVE_FEATURE_DBCONNECTIVITY && !ENABLE_FUZZERS
1194 SwDBData aDBData;
1195 OUString sPar1;
1197 if (rData.m_sPar1.indexOf(DB_DELIM)<0)
1199 aDBData = pCurShell->GetDBData();
1200 sPar1 = rData.m_sPar1;
1202 else
1204 sal_Int32 nIdx{ 0 };
1205 aDBData.sDataSource = rData.m_sPar1.getToken(0, DB_DELIM, nIdx);
1206 aDBData.sCommand = rData.m_sPar1.getToken(0, DB_DELIM, nIdx);
1207 aDBData.nCommandType = o3tl::toInt32(o3tl::getToken(rData.m_sPar1, 0, DB_DELIM, nIdx));
1208 sPar1 = rData.m_sPar1.getToken(0, DB_DELIM, nIdx);
1211 if(!aDBData.sDataSource.isEmpty() && pCurShell->GetDBData() != aDBData)
1212 pCurShell->ChgDBData(aDBData);
1214 SwDBFieldType* pTyp = static_cast<SwDBFieldType*>(pCurShell->InsertFieldType(
1215 SwDBFieldType(pCurShell->GetDoc(), sPar1, aDBData) ) );
1216 pField.reset(new SwDBField(pTyp));
1217 pField->SetSubType(nSubType);
1219 if( !(nSubType & nsSwExtendedSubType::SUB_OWN_FMT) ) // determine database format
1221 Reference< XDataSource> xSource;
1222 rData.m_aDBDataSource >>= xSource;
1223 Reference<XConnection> xConnection;
1224 rData.m_aDBConnection >>= xConnection;
1225 Reference<XPropertySet> xColumn;
1226 rData.m_aDBColumn >>= xColumn;
1227 if(xColumn.is())
1229 nFormatId = SwDBManager::GetColumnFormat(xSource, xConnection, xColumn,
1230 pCurShell->GetNumberFormatter(), GetCurrLanguage() );
1232 else
1233 nFormatId = pCurShell->GetDBManager()->GetColumnFormat(
1234 aDBData.sDataSource, aDBData.sCommand, sPar1,
1235 pCurShell->GetNumberFormatter(), GetCurrLanguage() );
1237 pField->ChangeFormat( nFormatId );
1239 bExp = true;
1240 #endif
1241 break;
1244 case SwFieldTypesEnum::DatabaseSetNumber:
1245 case SwFieldTypesEnum::DatabaseNumberSet:
1246 case SwFieldTypesEnum::DatabaseNextSet:
1247 case SwFieldTypesEnum::DatabaseName:
1249 #if HAVE_FEATURE_DBCONNECTIVITY && !ENABLE_FUZZERS
1250 SwDBData aDBData;
1252 // extract DBName from rData.m_sPar1. Format: DBName.TableName.CommandType.ExpStrg
1253 sal_Int32 nTablePos = rData.m_sPar1.indexOf(DB_DELIM);
1254 sal_Int32 nExpPos = -1;
1256 if (nTablePos>=0)
1258 aDBData.sDataSource = rData.m_sPar1.copy(0, nTablePos++);
1259 sal_Int32 nCmdTypePos = rData.m_sPar1.indexOf(DB_DELIM, nTablePos);
1260 if (nCmdTypePos>=0)
1262 aDBData.sCommand = rData.m_sPar1.copy(nTablePos, nCmdTypePos++ - nTablePos);
1263 nExpPos = rData.m_sPar1.indexOf(DB_DELIM, nCmdTypePos);
1264 if (nExpPos>=0)
1266 aDBData.nCommandType = o3tl::toInt32(rData.m_sPar1.subView(nCmdTypePos, nExpPos++ - nCmdTypePos));
1271 sal_Int32 nPos = 0;
1272 if (nExpPos>=0)
1273 nPos = nExpPos;
1274 else if (nTablePos>=0)
1275 nPos = nTablePos;
1277 OUString sPar1 = rData.m_sPar1.copy(nPos);
1279 if (!aDBData.sDataSource.isEmpty() && pCurShell->GetDBData() != aDBData)
1280 pCurShell->ChgDBData(aDBData);
1282 switch(rData.m_nTypeId)
1284 case SwFieldTypesEnum::DatabaseName:
1286 SwDBNameFieldType* pTyp =
1287 static_cast<SwDBNameFieldType*>(pCurShell->GetFieldType(0, SwFieldIds::DatabaseName));
1288 pField.reset(new SwDBNameField(pTyp, aDBData));
1290 break;
1292 case SwFieldTypesEnum::DatabaseNextSet:
1294 SwDBNextSetFieldType* pTyp = static_cast<SwDBNextSetFieldType*>(pCurShell->GetFieldType(
1295 0, SwFieldIds::DbNextSet) );
1296 pField.reset(new SwDBNextSetField(pTyp, sPar1, aDBData));
1297 bExp = true;
1298 break;
1300 case SwFieldTypesEnum::DatabaseNumberSet:
1302 SwDBNumSetFieldType* pTyp = static_cast<SwDBNumSetFieldType*>( pCurShell->GetFieldType(
1303 0, SwFieldIds::DbNumSet) );
1304 pField.reset(new SwDBNumSetField( pTyp, sPar1, rData.m_sPar2, aDBData));
1305 bExp = true;
1306 break;
1308 case SwFieldTypesEnum::DatabaseSetNumber:
1310 SwDBSetNumberFieldType* pTyp = static_cast<SwDBSetNumberFieldType*>(
1311 pCurShell->GetFieldType(0, SwFieldIds::DbSetNumber) );
1312 pField.reset(new SwDBSetNumberField( pTyp, aDBData, nFormatId));
1313 bExp = true;
1314 break;
1316 default: break;
1318 #endif
1319 break;
1322 case SwFieldTypesEnum::User:
1324 SwUserFieldType* pTyp =
1325 static_cast<SwUserFieldType*>( pCurShell->GetFieldType(SwFieldIds::User, rData.m_sPar1) );
1327 // only if existing
1328 if(!pTyp)
1330 pTyp = static_cast<SwUserFieldType*>( pCurShell->InsertFieldType(
1331 SwUserFieldType(pCurShell->GetDoc(), rData.m_sPar1)) );
1333 if (pTyp->GetContent(nFormatId) != rData.m_sPar2)
1334 pTyp->SetContent(rData.m_sPar2, nFormatId);
1335 pField.reset(new SwUserField(pTyp, 0, nFormatId));
1336 if (pField->GetSubType() != nSubType)
1337 pField->SetSubType(nSubType);
1338 bTable = true;
1339 break;
1342 case SwFieldTypesEnum::Input:
1344 if ((nSubType & 0x00ff) == INP_VAR)
1346 SwSetExpFieldType* pTyp = static_cast<SwSetExpFieldType*>(
1347 pCurShell->GetFieldType(SwFieldIds::SetExp, rData.m_sPar1) );
1349 // no Expression Type with this name existing -> create
1350 if(pTyp)
1352 std::unique_ptr<SwSetExpField> pExpField(
1353 new SwSetExpField(pTyp, OUString(), nFormatId));
1355 // Don't change type of SwSetExpFieldType:
1356 sal_uInt16 nOldSubType = pExpField->GetSubType();
1357 pExpField->SetSubType(nOldSubType | (nSubType & 0xff00));
1359 pExpField->SetPromptText(rData.m_sPar2);
1360 pExpField->SetInputFlag(true) ;
1361 bExp = true;
1362 pField = std::move(pExpField);
1364 else
1365 return false;
1367 else
1369 SwInputFieldType* pTyp =
1370 static_cast<SwInputFieldType*>( pCurShell->GetFieldType(0, SwFieldIds::Input) );
1372 pField.reset(
1373 new SwInputField( pTyp, rData.m_sPar1, rData.m_sPar2, nSubType|nsSwExtendedSubType::SUB_INVISIBLE, nFormatId));
1375 break;
1378 case SwFieldTypesEnum::Set:
1380 if (rData.m_sPar2.isEmpty()) // empty variables are not allowed
1381 return false;
1383 SwSetExpFieldType* pTyp = static_cast<SwSetExpFieldType*>( pCurShell->InsertFieldType(
1384 SwSetExpFieldType(pCurShell->GetDoc(), rData.m_sPar1) ) );
1386 std::unique_ptr<SwSetExpField> pExpField(new SwSetExpField( pTyp, rData.m_sPar2, nFormatId));
1387 pExpField->SetSubType(nSubType);
1388 pExpField->SetPar2(rData.m_sPar2);
1389 bExp = true;
1390 pField = std::move(pExpField);
1391 break;
1394 case SwFieldTypesEnum::Sequence:
1396 SwSetExpFieldType* pTyp = static_cast<SwSetExpFieldType*>( pCurShell->InsertFieldType(
1397 SwSetExpFieldType(pCurShell->GetDoc(), rData.m_sPar1, nsSwGetSetExpType::GSE_SEQ)));
1399 sal_uInt8 nLevel = static_cast< sal_uInt8 >(nSubType & 0xff);
1401 pTyp->SetOutlineLvl(nLevel);
1402 if (nLevel != 0x7f && cSeparator == 0)
1403 cSeparator = '.';
1405 pTyp->SetDelimiter(OUString(cSeparator));
1406 pField.reset(new SwSetExpField(pTyp, rData.m_sPar2, nFormatId));
1407 bExp = true;
1408 break;
1411 case SwFieldTypesEnum::Get:
1413 // is there a corresponding SetField
1414 SwSetExpFieldType* pSetTyp = static_cast<SwSetExpFieldType*>(
1415 pCurShell->GetFieldType(SwFieldIds::SetExp, rData.m_sPar1));
1417 if(pSetTyp)
1419 SwGetExpFieldType* pTyp = static_cast<SwGetExpFieldType*>( pCurShell->GetFieldType(
1420 0, SwFieldIds::GetExp) );
1421 pField.reset( new SwGetExpField(pTyp, rData.m_sPar1, pSetTyp->GetType(), nFormatId) );
1422 pField->SetSubType(nSubType | pSetTyp->GetType());
1423 bExp = true;
1425 else
1426 return false;
1427 break;
1430 case SwFieldTypesEnum::Formel:
1432 if(pCurShell->GetFrameType(nullptr,false) & FrameTypeFlags::TABLE)
1434 pCurShell->StartAllAction();
1436 SvNumberFormatter* pFormatter = pCurShell->GetDoc()->GetNumberFormatter();
1437 const SvNumberformat* pEntry = pFormatter->GetEntry(nFormatId);
1439 if (pEntry)
1441 SfxStringItem aFormat(FN_NUMBER_FORMAT, pEntry->GetFormatstring());
1442 pCurShell->GetView().GetViewFrame().GetDispatcher()->
1443 ExecuteList(FN_NUMBER_FORMAT, SfxCallMode::SYNCHRON,
1444 { &aFormat });
1447 SfxItemSet aBoxSet(SfxItemSet::makeFixedSfxItemSet<RES_BOXATR_FORMULA, RES_BOXATR_FORMULA>(pCurShell->GetAttrPool()));
1449 OUString sFormula(comphelper::string::stripStart(rData.m_sPar2, ' '));
1450 if ( sFormula.startsWith("=") )
1452 sFormula = sFormula.copy(1);
1455 aBoxSet.Put( SwTableBoxFormula( sFormula ));
1456 pCurShell->SetTableBoxFormulaAttrs( aBoxSet );
1457 pCurShell->UpdateTable();
1459 pCurShell->EndAllAction();
1460 return true;
1463 else
1465 SwGetExpFieldType* pTyp = static_cast<SwGetExpFieldType*>(
1466 pCurShell->GetFieldType(0, SwFieldIds::GetExp) );
1467 pField.reset( new SwGetExpField(pTyp, rData.m_sPar2, nsSwGetSetExpType::GSE_FORMULA, nFormatId) );
1468 pField->SetSubType(nSubType);
1469 bExp = true;
1471 break;
1473 case SwFieldTypesEnum::SetRefPage:
1474 pField.reset( new SwRefPageSetField( static_cast<SwRefPageSetFieldType*>(
1475 pCurShell->GetFieldType( 0, SwFieldIds::RefPageSet ) ),
1476 static_cast<short>(rData.m_sPar2.toInt32()), 0 != nSubType ) );
1477 bPageVar = true;
1478 break;
1480 case SwFieldTypesEnum::GetRefPage:
1481 pField.reset( new SwRefPageGetField( static_cast<SwRefPageGetFieldType*>(
1482 pCurShell->GetFieldType( 0, SwFieldIds::RefPageGet ) ), nFormatId ) );
1483 bPageVar = true;
1484 break;
1485 case SwFieldTypesEnum::Dropdown :
1487 pField.reset( new SwDropDownField(pCurShell->GetFieldType( 0, SwFieldIds::Dropdown )) );
1488 const sal_Int32 nTokenCount = comphelper::string::getTokenCount(rData.m_sPar2, DB_DELIM);
1489 Sequence<OUString> aEntries(nTokenCount);
1490 OUString* pArray = aEntries.getArray();
1491 for(sal_Int32 nToken = 0, nIdx = 0; nToken < nTokenCount; nToken++)
1492 pArray[nToken] = rData.m_sPar2.getToken(0, DB_DELIM, nIdx);
1493 static_cast<SwDropDownField*>(pField.get())->SetItems(aEntries);
1494 static_cast<SwDropDownField*>(pField.get())->SetName(rData.m_sPar1);
1496 break;
1498 // Insert Paragraph Signature field by signing the paragraph.
1499 // The resulting field is really a metadata field, created and added via signing.
1500 case SwFieldTypesEnum::ParagraphSignature:
1501 pCurShell->SignParagraph();
1502 return true;
1504 default:
1505 { OSL_ENSURE(false, "wrong field type");
1506 return false;
1509 OSL_ENSURE(pField, "field not available");
1511 //the auto language flag has to be set prior to the language!
1512 pField->SetAutomaticLanguage(rData.m_bIsAutomaticLanguage);
1513 LanguageType nLang = GetCurrLanguage();
1514 pField->SetLanguage(nLang);
1516 // insert
1517 pCurShell->StartAllAction();
1519 bool const isSuccess = pCurShell->InsertField2(*pField, rData.m_oAnnotationRange ? &*rData.m_oAnnotationRange : nullptr);
1521 if (isSuccess)
1523 if (SwFieldTypesEnum::Input == rData.m_nTypeId)
1525 pCurShell->Push();
1527 // start dialog, not before the field is inserted tdf#99529
1528 pCurShell->Left(SwCursorSkipMode::Chars, false,
1529 (INP_VAR == (nSubType & 0xff) || pCurShell->GetViewOptions()->IsFieldName()) ? 1 : 2,
1530 false);
1531 pCurShell->StartInputFieldDlg(pField.get(), false, true, rData.m_pParent);
1533 pCurShell->Pop(SwCursorShell::PopMode::DeleteCurrent);
1536 if (bExp && m_bEvalExp)
1538 pCurShell->UpdateExpFields(true);
1541 if (bTable)
1543 pCurShell->Left(SwCursorSkipMode::Chars, false, 1, false );
1544 pCurShell->UpdateOneField(*pField);
1545 pCurShell->Right(SwCursorSkipMode::Chars, false, 1, false );
1547 else if (bPageVar)
1549 static_cast<SwRefPageGetFieldType*>(pCurShell->GetFieldType(0, SwFieldIds::RefPageGet))->UpdateFields();
1551 else if (SwFieldTypesEnum::GetRef == rData.m_nTypeId)
1553 pField->GetTyp()->UpdateFields();
1557 // delete temporary field
1558 pField.reset();
1560 pCurShell->EndAllAction();
1561 return isSuccess;
1564 // fields update
1565 void SwFieldMgr::UpdateCurField(sal_uInt32 nFormat,
1566 const OUString& rPar1,
1567 const OUString& rPar2,
1568 std::unique_ptr<SwField> pTmpField)
1570 // change format
1571 OSL_ENSURE(m_pCurField, "no field at CursorPos");
1573 if (!pTmpField)
1574 pTmpField = m_pCurField->CopyField();
1576 SwFieldType* pType = pTmpField->GetTyp();
1577 const SwFieldTypesEnum nTypeId = pTmpField->GetTypeId();
1579 SwWrtShell* pSh = m_pWrtShell ? m_pWrtShell : ::lcl_GetShell();
1580 OSL_ENSURE(pSh, "no SwWrtShell found");
1581 if(!pSh)
1582 return;
1583 pSh->StartAllAction();
1585 bool bSetPar2 = true;
1586 bool bSetPar1 = true;
1587 OUString sPar2( rPar2 );
1589 // Order to Format
1590 switch( nTypeId )
1592 case SwFieldTypesEnum::DDE:
1594 // DDE-Topics/-Items can have blanks in their names!
1595 // That's not yet considered here!
1596 sal_Int32 nIndex = 0;
1597 sPar2 = sPar2.replaceFirst(" ", OUStringChar(sfx2::cTokenSeparator), &nIndex );
1598 if (nIndex>=0 && ++nIndex<sPar2.getLength())
1600 sPar2 = sPar2.replaceFirst(" ", OUStringChar(sfx2::cTokenSeparator), &nIndex);
1602 break;
1605 case SwFieldTypesEnum::Chapter:
1607 sal_uInt16 nByte = o3tl::narrowing<sal_uInt16>(rPar2.toInt32());
1608 nByte = std::max(sal_uInt16(1), nByte);
1609 nByte = std::min(nByte, sal_uInt16(MAXLEVEL));
1610 nByte -= 1;
1611 static_cast<SwChapterField*>(pTmpField.get())->SetLevel(static_cast<sal_uInt8>(nByte));
1612 bSetPar2 = false;
1613 break;
1616 case SwFieldTypesEnum::Script:
1617 static_cast<SwScriptField*>(pTmpField.get())->SetCodeURL(static_cast<bool>(nFormat));
1618 break;
1620 case SwFieldTypesEnum::NextPage:
1621 if( SVX_NUM_CHAR_SPECIAL == nFormat )
1623 static_cast<SwPageNumberField*>(m_pCurField)->SetUserString( sPar2 );
1624 sPar2 = "1";
1626 else
1628 if( nFormat + 2 == SVX_NUM_PAGEDESC )
1629 nFormat = SVX_NUM_PAGEDESC;
1630 short nOff = static_cast<short>(sPar2.toInt32());
1631 nOff += 1;
1632 sPar2 = OUString::number(nOff);
1634 break;
1636 case SwFieldTypesEnum::PreviousPage:
1637 if( SVX_NUM_CHAR_SPECIAL == nFormat )
1639 static_cast<SwPageNumberField*>(m_pCurField)->SetUserString( sPar2 );
1640 sPar2 = "-1";
1642 else
1644 if( nFormat + 2 == SVX_NUM_PAGEDESC )
1645 nFormat = SVX_NUM_PAGEDESC;
1646 short nOff = static_cast<short>(sPar2.toInt32());
1647 nOff -= 1;
1648 sPar2 = OUString::number(nOff);
1650 break;
1652 case SwFieldTypesEnum::PageNumber:
1653 case SwFieldTypesEnum::GetRefPage:
1654 if( nFormat + 2 == SVX_NUM_PAGEDESC )
1655 nFormat = SVX_NUM_PAGEDESC;
1656 break;
1658 case SwFieldTypesEnum::GetRef:
1660 bSetPar2 = false;
1661 sal_Int16 nSubType = o3tl::narrowing<sal_uInt16>(rPar2.toInt32());
1662 static_cast<SwGetRefField*>(pTmpField.get())->SetSubType( nSubType );
1663 const sal_Int32 nPos = rPar2.indexOf( '|' );
1664 if( nPos>=0 )
1665 switch (nSubType) {
1666 case REF_STYLE:
1667 static_cast<SwGetRefField*>(pTmpField.get())->SetFlags( o3tl::narrowing<sal_uInt16>(o3tl::toInt32(rPar2.subView( nPos + 1 ))));
1668 break;
1669 default:
1670 static_cast<SwGetRefField*>(pTmpField.get())->SetSeqNo( o3tl::narrowing<sal_uInt16>(o3tl::toInt32(rPar2.subView( nPos + 1 ))));
1673 break;
1674 case SwFieldTypesEnum::Dropdown:
1676 sal_Int32 nTokenCount = comphelper::string::getTokenCount(sPar2, DB_DELIM);
1677 Sequence<OUString> aEntries(nTokenCount);
1678 OUString* pArray = aEntries.getArray();
1679 for(sal_Int32 nToken = 0, nIdx = 0; nToken < nTokenCount; nToken++)
1680 pArray[nToken] = sPar2.getToken(0, DB_DELIM, nIdx);
1681 static_cast<SwDropDownField*>(pTmpField.get())->SetItems(aEntries);
1682 static_cast<SwDropDownField*>(pTmpField.get())->SetName(rPar1);
1683 bSetPar1 = bSetPar2 = false;
1685 break;
1686 case SwFieldTypesEnum::Authority :
1688 //#i99069# changes to a bibliography field should change the field type
1689 SwAuthorityField* pAuthorityField = static_cast<SwAuthorityField*>(pTmpField.get());
1690 SwAuthorityFieldType* pAuthorityType = static_cast<SwAuthorityFieldType*>(pType);
1691 rtl::Reference<SwAuthEntry> xTempEntry(new SwAuthEntry);
1692 for( sal_Int32 i = 0, nIdx = 0; i < AUTH_FIELD_END; ++i )
1693 xTempEntry->SetAuthorField( static_cast<ToxAuthorityField>(i),
1694 rPar1.getToken( 0, TOX_STYLE_DELIMITER, nIdx ));
1696 // If just the page number of the URL changed, then update the current field and not
1697 // others.
1698 bool bEquivalent = true;
1699 for (int i = 0; i < AUTH_FIELD_END; ++i)
1701 auto eField = static_cast<ToxAuthorityField>(i);
1702 if (eField == AUTH_FIELD_URL)
1704 if (SwTOXAuthority::GetSourceURL(xTempEntry->GetAuthorField(AUTH_FIELD_URL))
1705 != SwTOXAuthority::GetSourceURL(
1706 pAuthorityField->GetFieldText(AUTH_FIELD_URL)))
1708 bEquivalent = false;
1709 break;
1712 else
1714 if (xTempEntry->GetAuthorField(eField) != pAuthorityField->GetFieldText(eField))
1716 bEquivalent = false;
1717 break;
1722 if (bEquivalent)
1724 break;
1727 if( pAuthorityType->ChangeEntryContent( xTempEntry.get() ) )
1729 pType->UpdateFields();
1730 pSh->SetModified();
1733 if( xTempEntry->GetAuthorField( AUTH_FIELD_IDENTIFIER ) ==
1734 pAuthorityField->GetFieldText( AUTH_FIELD_IDENTIFIER ) )
1735 bSetPar1 = false; //otherwise it's a new or changed entry, the field needs to be updated
1736 bSetPar2 = false;
1738 break;
1739 default: break;
1742 // set format
1743 // setup format before SetPar2 because of NumberFormatter!
1744 pTmpField->ChangeFormat(nFormat);
1746 if( bSetPar1 )
1747 pTmpField->SetPar1( rPar1 );
1748 if( bSetPar2 )
1749 pTmpField->SetPar2( sPar2 );
1751 // kick off update
1752 if(nTypeId == SwFieldTypesEnum::DDE ||
1753 nTypeId == SwFieldTypesEnum::User ||
1754 nTypeId == SwFieldTypesEnum::UserInput)
1756 pType->UpdateFields();
1757 pSh->SetModified();
1759 else {
1760 // mb: #32157
1761 pSh->SwEditShell::UpdateOneField(*pTmpField);
1762 GetCurField();
1765 pTmpField.reset();
1767 pSh->EndAllAction();
1770 // explicitly evaluate ExpressionFields
1771 void SwFieldMgr::EvalExpFields(SwWrtShell* pSh)
1773 if (pSh == nullptr)
1774 pSh = m_pWrtShell ? m_pWrtShell : ::lcl_GetShell();
1776 if(pSh)
1778 pSh->StartAllAction();
1779 pSh->UpdateExpFields(true);
1780 pSh->EndAllAction();
1783 LanguageType SwFieldMgr::GetCurrLanguage() const
1785 SwWrtShell* pSh = m_pWrtShell ? m_pWrtShell : ::lcl_GetShell();
1786 if( pSh )
1787 return pSh->GetCurLang();
1788 return SvtSysLocale().GetLanguageTag().getLanguageType();
1791 void SwFieldType::GetFieldName_()
1793 static const TranslateId coFieldNms[] =
1795 FLD_DATE_STD,
1796 FLD_TIME_STD,
1797 STR_FILENAMEFLD,
1798 STR_DBNAMEFLD,
1799 STR_CHAPTERFLD,
1800 STR_PAGENUMBERFLD,
1801 STR_DOCSTATFLD,
1802 STR_AUTHORFLD,
1803 STR_SETFLD,
1804 STR_GETFLD,
1805 STR_FORMELFLD,
1806 STR_HIDDENTXTFLD,
1807 STR_SETREFFLD,
1808 STR_GETREFFLD,
1809 STR_DDEFLD,
1810 STR_MACROFLD,
1811 STR_INPUTFLD,
1812 STR_HIDDENPARAFLD,
1813 STR_DOCINFOFLD,
1814 STR_DBFLD,
1815 STR_USERFLD,
1816 STR_POSTITFLD,
1817 STR_TEMPLNAMEFLD,
1818 STR_SEQFLD,
1819 STR_DBNEXTSETFLD,
1820 STR_DBNUMSETFLD,
1821 STR_DBSETNUMBERFLD,
1822 STR_CONDTXTFLD,
1823 STR_NEXTPAGEFLD,
1824 STR_PREVPAGEFLD,
1825 STR_EXTUSERFLD,
1826 FLD_DATE_FIX,
1827 FLD_TIME_FIX,
1828 STR_SETINPUTFLD,
1829 STR_USRINPUTFLD,
1830 STR_SETREFPAGEFLD,
1831 STR_GETREFPAGEFLD,
1832 STR_INTERNETFLD,
1833 STR_JUMPEDITFLD,
1834 STR_SCRIPTFLD,
1835 STR_AUTHORITY,
1836 STR_COMBINED_CHARS,
1837 STR_DROPDOWN,
1838 STR_CUSTOM_FIELD,
1839 STR_PARAGRAPH_SIGNATURE
1842 // insert infos for fields
1843 SwFieldType::s_pFieldNames = new std::vector<OUString>;
1844 SwFieldType::s_pFieldNames->reserve(SAL_N_ELEMENTS(coFieldNms));
1845 for (const TranslateId & id : coFieldNms)
1847 const OUString aTmp(SwResId(id));
1848 SwFieldType::s_pFieldNames->push_back(MnemonicGenerator::EraseAllMnemonicChars( aTmp ));
1852 bool SwFieldMgr::ChooseMacro(weld::Window* pDialogParent)
1854 bool bRet = false;
1856 // choose script dialog
1857 OUString aScriptURL = SfxApplication::ChooseScript(pDialogParent);
1859 // the script selector dialog returns a valid script URL
1860 if ( !aScriptURL.isEmpty() )
1862 SetMacroPath( aScriptURL );
1863 bRet = true;
1866 return bRet;
1869 void SwFieldMgr::SetMacroPath(const OUString& rPath)
1871 m_sMacroPath = rPath;
1872 m_sMacroName = rPath;
1874 // try to set sMacroName member variable by parsing the macro path
1875 // using the new URI parsing services
1877 const Reference< XComponentContext >& xContext =
1878 ::comphelper::getProcessComponentContext();
1880 Reference< uri::XUriReferenceFactory >
1881 xFactory = uri::UriReferenceFactory::create( xContext );
1883 Reference< uri::XVndSunStarScriptUrl >
1884 xUrl( xFactory->parse( m_sMacroPath ), UNO_QUERY );
1886 if ( xUrl.is() )
1888 m_sMacroName = xUrl->getName();
1892 sal_uInt32 SwFieldMgr::GetDefaultFormat(SwFieldTypesEnum nTypeId, bool bIsText, SvNumberFormatter* pFormatter)
1894 SvNumFormatType nDefFormat;
1896 switch (nTypeId)
1898 case SwFieldTypesEnum::Time:
1899 case SwFieldTypesEnum::Date:
1901 nDefFormat = (nTypeId == SwFieldTypesEnum::Date) ? SvNumFormatType::DATE : SvNumFormatType::TIME;
1903 break;
1905 default:
1906 if (bIsText)
1908 nDefFormat = SvNumFormatType::TEXT;
1910 else
1912 nDefFormat = SvNumFormatType::ALL;
1914 break;
1917 return pFormatter->GetStandardFormat(nDefFormat, GetCurrLanguage());
1920 Reference<XNumberingTypeInfo> const & SwFieldMgr::GetNumberingInfo() const
1922 if(!m_xNumberingInfo.is())
1924 const Reference<XComponentContext>& xContext( ::comphelper::getProcessComponentContext() );
1925 Reference<XDefaultNumberingProvider> xDefNum = text::DefaultNumberingProvider::create(xContext);
1926 const_cast<SwFieldMgr*>(this)->m_xNumberingInfo.set(xDefNum, UNO_QUERY);
1928 return m_xNumberingInfo;
1931 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */