sw: add a new .uno:DeleteFields UNO command

This is similar to 40753de837 (sw: add a
new .uno:DeleteBookmarks UNO command, 2023-01-13), but that was about
deleting bookmarks matching a given prefix with their name, and this one
is about reference marks (fields in general), matching a certain type &
prefix with their name.

Change-Id: Iec953034cd0e6875f173712b0fb10bfddf16ed3f
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/145551
Reviewed-by: Miklos Vajna <vmiklos@collabora.com>
Tested-by: Jenkins
This commit is contained in:
Miklos Vajna
2023-01-16 08:10:16 +01:00
parent 4114218584
commit 1d6593dd79
5 changed files with 112 additions and 0 deletions

View File

@@ -328,6 +328,7 @@ class SwUINumRuleItem;
#define FN_UPDATE_BOOKMARK (FN_INSERT2 + 37)
#define FN_UPDATE_FIELD (FN_INSERT2 + 38)
#define FN_DELETE_BOOKMARKS (FN_INSERT2 + 39)
#define FN_DELETE_FIELDS (FN_INSERT2 + 40)
// Region: Format
#define FN_AUTOFORMAT_APPLY (FN_FORMAT + 1 ) /* apply autoformat options */

View File

@@ -898,6 +898,43 @@ CPPUNIT_TEST_FIXTURE(SwUibaseShellsTest, testDeleteBookmarks)
CPPUNIT_ASSERT(it != pDoc->getIDocumentMarkAccess()->getAllMarksEnd());
}
CPPUNIT_TEST_FIXTURE(SwUibaseShellsTest, testDeleteFields)
{
// Given a document with a refmark:
createSwDoc();
uno::Sequence<css::beans::PropertyValue> aArgs = {
comphelper::makePropertyValue("TypeName", uno::Any(OUString("SetRef"))),
comphelper::makePropertyValue(
"Name", uno::Any(OUString("ZOTERO_ITEM CSL_CITATION {} RNDpyJknp173F"))),
comphelper::makePropertyValue("Content", uno::Any(OUString("aaa<b>bbb</b>ccc"))),
};
dispatchCommand(mxComponent, ".uno:InsertField", aArgs);
// When deleting the refmarks:
std::vector<beans::PropertyValue> aArgsVec = comphelper::JsonToPropertyValues(R"json(
{
"TypeName": {
"type": "string",
"value": "SetRef"
},
"NamePrefix": {
"type": "string",
"value": "ZOTERO_ITEM CSL_CITATION"
}
}
)json");
aArgs = comphelper::containerToSequence(aArgsVec);
dispatchCommand(mxComponent, ".uno:DeleteFields", aArgs);
// Then make sure that no refmark is kept:
SwDoc* pDoc = getSwDoc();
// Without the accompanying fix in place, this test would have failed with:
// - Expected: 0
// - Actual : 1
// i.e. the refmark was not deleted.
CPPUNIT_ASSERT_EQUAL(static_cast<sal_uInt16>(0), pDoc->GetRefMarks());
}
CPPUNIT_PLUGIN_IMPLEMENT();
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */

View File

@@ -1848,6 +1848,12 @@ interface BaseText
DisableFlags="SfxDisableFlags::SwOnProtectedCursor";
]
FN_DELETE_FIELDS
[
ExecMethod = Execute ;
DisableFlags="SfxDisableFlags::SwOnProtectedCursor";
]
SID_FM_CTL_PROPERTIES
[
ExecMethod = Execute ;

View File

@@ -2614,6 +2614,20 @@ SfxVoidItem DeleteBookmarks FN_DELETE_BOOKMARKS
GroupId = SfxGroupId::Controls;
]
SfxVoidItem DeleteFields FN_DELETE_FIELDS
(SfxStringItem TypeName FN_PARAM_1, SfxStringItem NamePrefix FN_PARAM_2)
[
AutoUpdate = TRUE,
FastCall = FALSE,
ReadOnlyDoc = FALSE,
Toggle = FALSE,
Container = FALSE,
RecordAbsolute = FALSE,
RecordPerSet;
GroupId = SfxGroupId::Controls;
]
SfxVoidItem UpdateBookmark FN_UPDATE_BOOKMARK
(SfxStringItem BookmarkNamePrefix FN_PARAM_1, SfxUnoAnyItem Bookmark FN_PARAM_2)
[

View File

@@ -116,6 +116,7 @@
#include <IDocumentContentOperations.hxx>
#include <IDocumentUndoRedo.hxx>
#include <fmtcntnt.hxx>
#include <fmtrfmrk.hxx>
using namespace ::com::sun::star;
using namespace com::sun::star::beans;
@@ -660,6 +661,53 @@ void DeleteBookmarks(SfxRequest& rReq, SwWrtShell& rWrtSh)
pMarkAccess->deleteMark(pMark);
}
}
void DeleteFields(SfxRequest& rReq, SwWrtShell& rWrtSh)
{
const SfxStringItem* pTypeName = rReq.GetArg<SfxStringItem>(FN_PARAM_1);
if (!pTypeName || pTypeName->GetValue() != "SetRef")
{
// This is implemented so far only for reference marks.
return;
}
OUString aNamePrefix;
const SfxStringItem* pNamePrefix = rReq.GetArg<SfxStringItem>(FN_PARAM_2);
if (pNamePrefix)
{
aNamePrefix = pNamePrefix->GetValue();
}
SwDoc* pDoc = rWrtSh.GetDoc();
pDoc->GetIDocumentUndoRedo().StartUndo(SwUndoId::DELBOOKMARK, nullptr);
rWrtSh.StartAction();
comphelper::ScopeGuard g(
[&rWrtSh]
{
rWrtSh.EndAction();
rWrtSh.GetDoc()->GetIDocumentUndoRedo().EndUndo(SwUndoId::DELBOOKMARK, nullptr);
});
std::vector<const SwFormatRefMark*> aRemovals;
for (sal_uInt16 i = 0; i < pDoc->GetRefMarks(); ++i)
{
const SwFormatRefMark* pRefMark = pDoc->GetRefMark(i);
if (!aNamePrefix.isEmpty())
{
if (!pRefMark->GetRefName().startsWith(aNamePrefix))
{
continue;
}
}
aRemovals.push_back(pRefMark);
}
for (const auto& pMark : aRemovals)
{
pDoc->DeleteFormatRefMark(pMark);
}
}
}
void SwTextShell::Execute(SfxRequest &rReq)
@@ -1068,6 +1116,12 @@ void SwTextShell::Execute(SfxRequest &rReq)
DeleteBookmarks(rReq, rWrtSh);
break;
}
case FN_DELETE_FIELDS:
{
// This deletes all fields in the document matching a specified type & prefix.
DeleteFields(rReq, rWrtSh);
break;
}
case FN_UPDATE_SECTIONS:
{
UpdateSections(rReq, rWrtSh);