Kaydet (Commit) 087b71f4 authored tarafından Miklos Vajna's avatar Miklos Vajna

sw: allow accept/reject of redline by index

Previously .uno:AcceptTrackedChange / .uno:RejectTrackedChange always
worked by cursor position, but redlines are stored in the redline table,
so they have a unique index. Allow specifying that index when invoking
the command, and in that case ignore the cursor position.

The index is not stable after an insertion / deletion.

Change-Id: I493a22e84800ded224fb6b9c61261744dc0fb64f
Reviewed-on: https://gerrit.libreoffice.org/28192Reviewed-by: 's avatarMiklos Vajna <vmiklos@collabora.co.uk>
Tested-by: 's avatarJenkins <ci@libreoffice.org>
üst f2033c28
......@@ -466,8 +466,10 @@ static void documentRedline(GtkWidget* pButton, gpointer /*pItem*/)
GtkWidget* pDialog = gtk_dialog_new_with_buttons("Manage Changes",
GTK_WINDOW (gtk_widget_get_toplevel(GTK_WIDGET(pDocView))),
GTK_DIALOG_MODAL,
"Close",
GTK_RESPONSE_OK,
"Accept",
GTK_RESPONSE_YES,
"Reject",
GTK_RESPONSE_NO,
nullptr);
GtkWidget* pContentArea = gtk_dialog_get_content_area(GTK_DIALOG (pDialog));
......@@ -486,7 +488,7 @@ static void documentRedline(GtkWidget* pButton, gpointer /*pItem*/)
-1);
}
GtkWidget* pTreeView = gtk_tree_view_new_with_model(GTK_TREE_MODEL(pTreeStore));
std::vector<std::string> aColumns = {"Index", "Type", "Comment", "Author", "Timestamp"};
std::vector<std::string> aColumns = {"Index", "Author", "Type", "Comment", "Timestamp"};
for (size_t nColumn = 0; nColumn < aColumns.size(); ++nColumn)
{
GtkCellRenderer* pRenderer = gtk_cell_renderer_text_new();
......@@ -500,7 +502,38 @@ static void documentRedline(GtkWidget* pButton, gpointer /*pItem*/)
// Show the dialog.
gtk_widget_show_all(pDialog);
gtk_dialog_run(GTK_DIALOG(pDialog));
gint res = gtk_dialog_run(GTK_DIALOG(pDialog));
// Dispatch the matching command, if necessary.
if (res == GTK_RESPONSE_YES || res == GTK_RESPONSE_NO)
{
GtkTreeSelection* pSelection = gtk_tree_view_get_selection(GTK_TREE_VIEW(pTreeView));
GtkTreeIter aTreeIter;
GtkTreeModel* pTreeModel;
if (gtk_tree_selection_get_selected(pSelection, &pTreeModel, &aTreeIter))
{
gint nIndex = 0;
// 0: index
gtk_tree_model_get(pTreeModel, &aTreeIter, 0, &nIndex, -1);
std::string aCommand;
if (res == GTK_RESPONSE_YES)
aCommand = ".uno:AcceptTrackedChange";
else
aCommand = ".uno:RejectTrackedChange";
// Without the '.uno:' prefix.
std::string aKey = aCommand.substr(strlen(".uno:"));
// Post the command.
boost::property_tree::ptree aCommandTree;
aCommandTree.put(boost::property_tree::ptree::path_type(aKey + "/type", '/'), "unsigned short");
aCommandTree.put(boost::property_tree::ptree::path_type(aKey + "/value", '/'), nIndex);
aStream.str(std::string());
boost::property_tree::write_json(aStream, aCommandTree);
std::string aArguments = aStream.str();
lok_doc_view_post_command(pDocView, aCommand.c_str(), aArguments.c_str(), false);
}
}
gtk_widget_destroy(pDialog);
}
......
......@@ -202,6 +202,7 @@ public:
void testTdf84695();
void testTdf84695NormalChar();
void testTableStyleUndo();
void testRedlineParam();
CPPUNIT_TEST_SUITE(SwUiWriterTest);
CPPUNIT_TEST(testReplaceForward);
......@@ -305,6 +306,7 @@ public:
CPPUNIT_TEST(testTdf84695);
CPPUNIT_TEST(testTdf84695NormalChar);
CPPUNIT_TEST(testTableStyleUndo);
CPPUNIT_TEST(testRedlineParam);
CPPUNIT_TEST_SUITE_END();
private:
......@@ -3824,6 +3826,37 @@ void SwUiWriterTest::testTableStyleUndo()
CPPUNIT_ASSERT(pStyle->GetBoxFormat(0).GetBackground() == aBackground2);
}
void SwUiWriterTest::testRedlineParam()
{
// Create a document with minimal content.
SwDoc* pDoc = createDoc();
SwDocShell* pDocShell = pDoc->GetDocShell();
SwWrtShell* pWrtShell = pDocShell->GetWrtShell();
pWrtShell->Insert("middle");
// Turn on track changes, and add changes to the start and end of the document.
uno::Reference<beans::XPropertySet> xPropertySet(mxComponent, uno::UNO_QUERY);
xPropertySet->setPropertyValue("RecordChanges", uno::makeAny(true));
pWrtShell->SttDoc();
pWrtShell->Insert("aaa");
pWrtShell->EndDoc();
pWrtShell->Insert("zzz");
// Move the cursor to the start again, and reject the second change.
pWrtShell->SttDoc();
uno::Sequence<beans::PropertyValue> aPropertyValues(comphelper::InitPropertySequence(
{
{"RejectTrackedChange", uno::makeAny(static_cast<sal_uInt16>(1))}
}));
lcl_dispatchCommand(mxComponent, ".uno:RejectTrackedChange", aPropertyValues);
Scheduler::ProcessEventsToIdle();
SwShellCursor* pShellCursor = pWrtShell->getShellCursor(false);
// This was 'middlezzz', the uno command rejected the redline under the
// cursor, instead of the requested one.
CPPUNIT_ASSERT_EQUAL(OUString("aaamiddle"), pShellCursor->GetPoint()->nNode.GetNode().GetTextNode()->GetText());
}
CPPUNIT_TEST_SUITE_REGISTRATION(SwUiWriterTest);
CPPUNIT_PLUGIN_IMPLEMENT();
......
......@@ -7273,6 +7273,7 @@ SfxBoolItem SpellingAndGrammarDialog FN_SPELL_GRAMMAR_DIALOG
]
SfxVoidItem AcceptTrackedChange FN_REDLINE_ACCEPT_DIRECT
( SfxUInt16Item AcceptTrackedChange FN_REDLINE_ACCEPT_DIRECT )
[
AutoUpdate = FALSE,
FastCall = FALSE,
......@@ -7291,6 +7292,7 @@ SfxVoidItem AcceptTrackedChange FN_REDLINE_ACCEPT_DIRECT
]
SfxVoidItem RejectTrackedChange FN_REDLINE_REJECT_DIRECT
( SfxUInt16Item RejectTrackedChange FN_REDLINE_REJECT_DIRECT )
[
AutoUpdate = FALSE,
FastCall = FALSE,
......
......@@ -664,7 +664,11 @@ void SwView::Execute(SfxRequest &rReq)
{
SwDoc *pDoc = m_pWrtShell->GetDoc();
SwPaM *pCursor = m_pWrtShell->GetCursor();
if( pCursor->HasMark())
sal_uInt16 nRedline = USHRT_MAX;
if (pArgs && pArgs->GetItemState(nSlot, false, &pItem) == SfxItemState::SET)
nRedline = static_cast<const SfxUInt16Item*>(pItem)->GetValue();
if( pCursor->HasMark() && nRedline == USHRT_MAX)
{
if (FN_REDLINE_ACCEPT_DIRECT == nSlot)
m_pWrtShell->AcceptRedlinesInSelection();
......@@ -677,8 +681,18 @@ void SwView::Execute(SfxRequest &rReq)
// This ensures we work properly with FN_REDLINE_NEXT_CHANGE, which leaves the
// point at the *end* of the redline and the mark at the start (so GetRedline
// would return NULL if called on the point)
sal_uInt16 nRedline = 0;
const SwRangeRedline *pRedline = pDoc->getIDocumentRedlineAccess().GetRedline(*pCursor->Start(), &nRedline);
const SwRangeRedline* pRedline = nullptr;
if (nRedline < USHRT_MAX)
{
// A redline was explicitly requested by specifying an
// index, don't guess based on the cursor position.
const SwRedlineTable& rTable = pDoc->getIDocumentRedlineAccess().GetRedlineTable();
if (nRedline < rTable.size())
pRedline = rTable[nRedline];
}
else
pRedline = pDoc->getIDocumentRedlineAccess().GetRedline(*pCursor->Start(), &nRedline);
assert(pRedline != nullptr);
if (pRedline)
{
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment