sc/Library_sc.mk                                        |    1 
 sc/source/ui/docshell/docfunc.cxx                       |   78 ----------
 sc/source/ui/inc/docfunc.hxx                            |    2 
 sc/source/ui/inc/operation/SetNormalStringOperation.hxx |   41 +++++
 sc/source/ui/operation/SetNormalStringOperation.cxx     |  115 ++++++++++++++++
 5 files changed, 166 insertions(+), 71 deletions(-)

New commits:
commit e116e204463346203d122e9c40f3453edcdc7e7a
Author:     Tomaž Vajngerl <[email protected]>
AuthorDate: Fri Feb 6 16:17:21 2026 +0900
Commit:     Miklos Vajna <[email protected]>
CommitDate: Mon Feb 16 09:24:04 2026 +0100

    sc: Introduce SetNormalStringOperation and use impl. from ScDocFunc
    
    No functional change, just moving and adapting the code to new
    location.
    
    Change-Id: I6cad3bbb6ae772859744b5ba8a897945d0d76430
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/198961
    Tested-by: Jenkins CollaboraOffice <[email protected]>
    Reviewed-by: Miklos Vajna <[email protected]>

diff --git a/sc/Library_sc.mk b/sc/Library_sc.mk
index 74accd38dc06..eb7c339d7c42 100644
--- a/sc/Library_sc.mk
+++ b/sc/Library_sc.mk
@@ -532,6 +532,7 @@ $(eval $(call gb_Library_add_exception_objects,sc,\
     sc/source/ui/operation/DeleteCellOperation \
     sc/source/ui/operation/DeleteContentOperation \
     sc/source/ui/operation/Operation \
+    sc/source/ui/operation/SetNormalStringOperation \
     sc/source/ui/operation/SortOperation \
     sc/source/ui/pagedlg/areasdlg \
     sc/source/ui/pagedlg/tphfedit \
diff --git a/sc/source/ui/docshell/docfunc.cxx 
b/sc/source/ui/docshell/docfunc.cxx
index 71f2039e74e1..0eb84decbca6 100644
--- a/sc/source/ui/docshell/docfunc.cxx
+++ b/sc/source/ui/docshell/docfunc.cxx
@@ -112,6 +112,7 @@
 #include <memory>
 #include <operation/DeleteContentOperation.hxx>
 #include <operation/DeleteCellOperation.hxx>
+#include <operation/SetNormalStringOperation.hxx>
 #include <basic/basmgr.hxx>
 #include <set>
 #include <vector>
@@ -683,78 +684,13 @@ bool ScDocFunc::TransliterateText( const ScMarkData& 
rMark, TransliterationFlags
     return true;
 }
 
-bool ScDocFunc::SetNormalString( bool& o_rbNumFmtSet, const ScAddress& rPos, 
const OUString& rText, bool bApi )
+bool ScDocFunc::SetNormalString(bool& o_rbNumFmtSet, const ScAddress& rPos, 
const OUString& rText, bool bApi )
 {
-    ScDocShellModificator aModificator( rDocShell );
-    ScDocument& rDoc = rDocShell.GetDocument();
-
-    bool bUndo(rDoc.IsUndoEnabled());
-
-    if (!CheckSheetViewProtection(sc::OperationType::SetNormalString))
-        return false;
-
-    ScEditableTester aTester = ScEditableTester::CreateAndTestBlock(rDoc, 
rPos.Tab(), rPos.Col(), rPos.Row(), rPos.Col(), rPos.Row());
-    if (!aTester.IsEditable())
-    {
-        if (!bApi)
-            rDocShell.ErrorMessage(aTester.GetMessageId());
-        return false;
-    }
-
-    bool bEditDeleted = (rDoc.GetCellType(rPos) == CELLTYPE_EDIT);
-    ScUndoEnterData::ValuesType aOldValues;
-
-    if (bUndo)
-    {
-        ScUndoEnterData::Value aOldValue;
-
-        aOldValue.mnTab = rPos.Tab();
-        aOldValue.maCell.assign(rDoc, rPos);
-
-        const ScPatternAttr* pPattern = rDoc.GetPattern( 
rPos.Col(),rPos.Row(),rPos.Tab() );
-        if ( const SfxUInt32Item* pItem = pPattern->GetItemSet().GetItemIfSet(
-                                ATTR_VALUE_FORMAT,false) )
-        {
-            aOldValue.mbHasFormat = true;
-            aOldValue.mnFormat = pItem->GetValue();
-        }
-        else
-            aOldValue.mbHasFormat = false;
-
-        aOldValues.push_back(aOldValue);
-    }
-
-    tools::Long nBefore(rDocShell.GetTwipWidthHint(rPos));
-    o_rbNumFmtSet = rDoc.SetString( rPos.Col(), rPos.Row(), rPos.Tab(), rText 
);
-    tools::Long nAfter(rDocShell.GetTwipWidthHint(rPos));
-
-    if (bUndo)
-    {
-        //  because of ChangeTracking, UndoAction can be created only after 
SetString was called
-        rDocShell.GetUndoManager()->AddUndoAction(
-            std::make_unique<ScUndoEnterData>(&rDocShell, rPos, aOldValues, 
rText, nullptr));
-    }
-
-    if ( bEditDeleted || rDoc.HasAttrib( ScRange(rPos), 
HasAttrFlags::NeedHeight ) )
-        AdjustRowHeight( ScRange(rPos), true, bApi );
-
-    rDocShell.PostPaintCell( rPos, std::max(nBefore, nAfter) );
-    aModificator.SetDocumentModified();
-
-    // notify input handler here the same way as in PutCell
-    if (bApi)
-        NotifyInputHandler( rPos );
-
-    const SfxUInt32Item* pItem = rDoc.GetAttr(rPos, ATTR_VALIDDATA);
-    const ScValidationData* pData = rDoc.GetValidationEntry(pItem->GetValue());
-    if (pData)
-    {
-        ScRefCellValue aCell(rDoc, rPos);
-        if (pData->IsDataValid(aCell, rPos))
-            ScDetectiveFunc(rDoc, rPos.Tab()).DeleteCirclesAt(rPos.Col(), 
rPos.Row());
-    }
-
-    return true;
+    sc::SetNormalStringOperation aOperation(*this, rDocShell, rPos, rText, 
bApi);
+    bool bResult = aOperation.run();
+    if (bResult)
+        o_rbNumFmtSet = aOperation.isNumberFormatSet();
+    return bResult;
 }
 
 bool ScDocFunc::SetValueCell( const ScAddress& rPos, double fVal, bool 
bInteraction )
diff --git a/sc/source/ui/inc/docfunc.hxx b/sc/source/ui/inc/docfunc.hxx
index e74fd3ddf16e..e8a3ef5fb514 100644
--- a/sc/source/ui/inc/docfunc.hxx
+++ b/sc/source/ui/inc/docfunc.hxx
@@ -61,6 +61,7 @@ namespace sc
     enum class OperationType;
     class DeleteContentOperation;
     class DeleteCellOperation;
+    class SetNormalStringOperation;
 }
 namespace tools
 {
@@ -71,6 +72,7 @@ class ScDocFunc
 {
     friend class sc::DeleteContentOperation;
     friend class sc::DeleteCellOperation;
+    friend class sc::SetNormalStringOperation;
 
     ScDocShell&     rDocShell;
     static bool CheckSheetViewProtection(sc::OperationType eOperation);
diff --git a/sc/source/ui/inc/operation/SetNormalStringOperation.hxx 
b/sc/source/ui/inc/operation/SetNormalStringOperation.hxx
new file mode 100644
index 000000000000..f255122c0159
--- /dev/null
+++ b/sc/source/ui/inc/operation/SetNormalStringOperation.hxx
@@ -0,0 +1,41 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+#pragma once
+
+#include "Operation.hxx"
+#include <sal/types.h>
+#include <rtl/ustring.hxx>
+
+class ScDocShell;
+class ScAddress;
+class ScDocFunc;
+
+namespace sc
+{
+/** Operation which sets string content to a cell. */
+class SetNormalStringOperation : public Operation
+{
+private:
+    ScDocFunc& mrDocFunc;
+    ScDocShell& mrDocShell;
+    ScAddress const& mrPosition;
+    OUString const& mrText;
+    bool mbIsNumberFormatSet;
+
+    bool runImplementation() override;
+
+public:
+    SetNormalStringOperation(ScDocFunc& rDocFunc, ScDocShell& rDocShell, const 
ScAddress& rPosition,
+                             const OUString& rText, bool bApi);
+    bool isNumberFormatSet() { return mbIsNumberFormatSet; }
+};
+} // end sc namespace
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/sc/source/ui/operation/SetNormalStringOperation.cxx 
b/sc/source/ui/operation/SetNormalStringOperation.cxx
new file mode 100644
index 000000000000..921bd8de7bb7
--- /dev/null
+++ b/sc/source/ui/operation/SetNormalStringOperation.cxx
@@ -0,0 +1,115 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+#include <operation/SetNormalStringOperation.hxx>
+
+#include <docfuncutil.hxx>
+#include <docfunc.hxx>
+#include <address.hxx>
+#include <editable.hxx>
+#include <undocell.hxx>
+#include <validat.hxx>
+#include <detfunc.hxx>
+
+#include <memory>
+
+namespace sc
+{
+SetNormalStringOperation::SetNormalStringOperation(ScDocFunc& rDocFunc, 
ScDocShell& rDocShell,
+                                                   const ScAddress& rPosition,
+                                                   const OUString& rText, bool 
bApi)
+    : Operation(OperationType::SetNormalString, true, bApi)
+    , mrDocFunc(rDocFunc)
+    , mrDocShell(rDocShell)
+    , mrPosition(rPosition)
+    , mrText(rText)
+{
+}
+
+bool SetNormalStringOperation::runImplementation()
+{
+    ScDocShellModificator aModificator(mrDocShell);
+    ScDocument& rDoc = mrDocShell.GetDocument();
+
+    bool bUndo(rDoc.IsUndoEnabled());
+
+    if (!checkSheetViewProtection())
+        return false;
+
+    ScEditableTester aTester = ScEditableTester::CreateAndTestBlock(
+        rDoc, mrPosition.Tab(), mrPosition.Col(), mrPosition.Row(), 
mrPosition.Col(),
+        mrPosition.Row());
+    if (!aTester.IsEditable())
+    {
+        if (!mbApi)
+            mrDocShell.ErrorMessage(aTester.GetMessageId());
+        return false;
+    }
+
+    bool bEditDeleted = (rDoc.GetCellType(mrPosition) == CELLTYPE_EDIT);
+    ScUndoEnterData::ValuesType aOldValues;
+
+    if (bUndo)
+    {
+        ScUndoEnterData::Value aOldValue;
+
+        aOldValue.mnTab = mrPosition.Tab();
+        aOldValue.maCell.assign(rDoc, mrPosition);
+
+        const ScPatternAttr* pPattern
+            = rDoc.GetPattern(mrPosition.Col(), mrPosition.Row(), 
mrPosition.Tab());
+        if (const SfxUInt32Item* pItem
+            = pPattern->GetItemSet().GetItemIfSet(ATTR_VALUE_FORMAT, false))
+        {
+            aOldValue.mbHasFormat = true;
+            aOldValue.mnFormat = pItem->GetValue();
+        }
+        else
+            aOldValue.mbHasFormat = false;
+
+        aOldValues.push_back(aOldValue);
+    }
+
+    tools::Long nBefore(mrDocShell.GetTwipWidthHint(mrPosition));
+    mbIsNumberFormatSet
+        = rDoc.SetString(mrPosition.Col(), mrPosition.Row(), mrPosition.Tab(), 
mrText);
+    tools::Long nAfter(mrDocShell.GetTwipWidthHint(mrPosition));
+
+    if (bUndo)
+    {
+        //  because of ChangeTracking, UndoAction can be created only after 
SetString was called
+        
mrDocShell.GetUndoManager()->AddUndoAction(std::make_unique<ScUndoEnterData>(
+            &mrDocShell, mrPosition, aOldValues, mrText, nullptr));
+    }
+
+    if (bEditDeleted || rDoc.HasAttrib(ScRange(mrPosition), 
HasAttrFlags::NeedHeight))
+        mrDocFunc.AdjustRowHeight(ScRange(mrPosition), true, mbApi);
+
+    mrDocShell.PostPaintCell(mrPosition, std::max(nBefore, nAfter));
+    aModificator.SetDocumentModified();
+
+    // notify input handler here the same way as in PutCell
+    if (mbApi)
+        mrDocFunc.NotifyInputHandler(mrPosition);
+
+    const SfxUInt32Item* pItem = rDoc.GetAttr(mrPosition, ATTR_VALIDDATA);
+    const ScValidationData* pData = rDoc.GetValidationEntry(pItem->GetValue());
+    if (pData)
+    {
+        ScRefCellValue aCell(rDoc, mrPosition);
+        if (pData->IsDataValid(aCell, mrPosition))
+            ScDetectiveFunc(rDoc, mrPosition.Tab())
+                .DeleteCirclesAt(mrPosition.Col(), mrPosition.Row());
+    }
+
+    return true;
+}
+} // end sc namespace
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Reply via email to