editeng/qa/unit/core-test.cxx       |   35 +++++++++++++++++++++++++++++++++--
 editeng/source/editeng/impedit2.cxx |    9 +--------
 2 files changed, 34 insertions(+), 10 deletions(-)

New commits:
commit 93b4e362f9e5c56b64ae25c27d5a3912f7586ee6
Author:     Miklos Vajna <vmik...@collabora.com>
AuthorDate: Fri Feb 2 08:08:54 2024 +0100
Commit:     Miklos Vajna <vmik...@collabora.com>
CommitDate: Fri Feb 2 09:39:19 2024 +0100

    tdf#159507 editeng: support pasting HTML fragments
    
    Commit ce53519f025158f8f64a4e8603c8c6e0dc35473a (cool#8023 editeng:
    support HTML paste, 2024-01-24) added support for pasting HTML files
    into Calc cells while editing, but this doesn't work when only a HTML
    fragment is provided, without headers and footers.
    
    The HTML code in ImpEditEngine::PasteText() was modeled after the
    HTML_SIMPLE case, which is some custom format from MSIE and that
    rejected the data in case the header didn't match, so the HTML case also
    required a HTML header in the above commit, but this doesn't work for
    HTML fragments.
    
    Fix the problem by just dropping the header check in
    ImpEditEngine::PasteText(), because that data already comes from the
    text/html slot of the clipboard, so there is already indication about
    the file format, even without the header. And without headers, it's
    almost impossible to recognize if the HTML fragment is a HTML one or
    not.
    
    Note that this is the HTML paste when a cell edit is active, the normal
    Calc HTML paste is a different codepath, in sc/.
    
    (cherry picked from commit 0503f6718f7686f3e2c93fc13af23e9fbfdace42)
    
    Change-Id: I4d37d80f947880fe22051c5fe84dc6bbc257e108

diff --git a/editeng/qa/unit/core-test.cxx b/editeng/qa/unit/core-test.cxx
index 348bb031d13c..8d2a6c11d4fc 100644
--- a/editeng/qa/unit/core-test.cxx
+++ b/editeng/qa/unit/core-test.cxx
@@ -83,6 +83,9 @@ public:
     /// Test Paste using HTML
     void testHTMLPaste();
 
+    /// Test Paste using an HTML fragment
+    void testHTMLFragmentPaste();
+
     /// Test Copy/Paste with selective selection over multiple paragraphs
     void testMultiParaSelCopyPaste();
 
@@ -130,6 +133,7 @@ public:
     CPPUNIT_TEST(testHyperlinkCopyPaste);
     CPPUNIT_TEST(testCopyPaste);
     CPPUNIT_TEST(testHTMLPaste);
+    CPPUNIT_TEST(testHTMLFragmentPaste);
     CPPUNIT_TEST(testMultiParaSelCopyPaste);
     CPPUNIT_TEST(testTabsCopyPaste);
     CPPUNIT_TEST(testHyperlinkSearch);
@@ -716,12 +720,19 @@ void Test::testCopyPaste()
 /// XTransferable implementation that provides simple HTML content.
 class TestHTMLTransferable : public 
cppu::WeakImplHelper<datatransfer::XTransferable>
 {
+    OString m_aHTML;
 public:
+    TestHTMLTransferable(const OString& rHTML);
     uno::Any SAL_CALL getTransferData(const datatransfer::DataFlavor& rFlavor) 
override;
     uno::Sequence<datatransfer::DataFlavor> SAL_CALL getTransferDataFlavors() 
override;
     sal_Bool SAL_CALL isDataFlavorSupported(const datatransfer::DataFlavor& 
rFlavor) override;
 };
 
+TestHTMLTransferable::TestHTMLTransferable(const OString& rHTML)
+    : m_aHTML(rHTML)
+{
+}
+
 uno::Any TestHTMLTransferable::getTransferData(const datatransfer::DataFlavor& 
rFlavor)
 {
     if (rFlavor.MimeType != "text/html")
@@ -731,7 +742,7 @@ uno::Any TestHTMLTransferable::getTransferData(const 
datatransfer::DataFlavor& r
 
     uno::Any aRet;
     SvMemoryStream aStream;
-    aStream.WriteOString("<!DOCTYPE html>
<html><body>test</body></html>");
+    aStream.WriteOString(m_aHTML);
     aRet <<= uno::Sequence<sal_Int8>(static_cast<const 
sal_Int8*>(aStream.GetData()), aStream.GetSize());
     return aRet;
 }
@@ -756,7 +767,8 @@ void Test::testHTMLPaste()
     // Given an empty editeng document:
     EditEngine aEditEngine(mpItemPool.get());
     EditDoc &rDoc = aEditEngine.GetEditDoc();
-    uno::Reference< datatransfer::XTransferable > xData(new 
TestHTMLTransferable);
+    OString aHTML("<!DOCTYPE html>
<html><body>test</body></html>"_ostr);
+    uno::Reference< datatransfer::XTransferable > xData(new 
TestHTMLTransferable(aHTML));
 
     // When trying to paste HTML:
     aEditEngine.InsertText(xData, OUString(), rDoc.GetEndPaM(), true);
@@ -769,6 +781,25 @@ void Test::testHTMLPaste()
     CPPUNIT_ASSERT_EQUAL(OUString("test"), 
rDoc.GetParaAsString(static_cast<sal_Int32>(0)));
 }
 
+void Test::testHTMLFragmentPaste()
+{
+    // Given an empty editeng document:
+    EditEngine aEditEngine(mpItemPool.get());
+    EditDoc &rDoc = aEditEngine.GetEditDoc();
+    OString aHTML("a<b>b</b>c"_ostr);
+    uno::Reference< datatransfer::XTransferable > xData(new 
TestHTMLTransferable(aHTML));
+
+    // When trying to paste an HTML fragment:
+    aEditEngine.InsertText(xData, OUString(), rDoc.GetEndPaM(), true);
+
+    // Then make sure the text gets pasted:
+    // Without the accompanying fix in place, this test would have failed with:
+    // - Expected: abc
+    // - Actual  :
+    // i.e. a HTML fragment without a proper header was ignored on paste.
+    CPPUNIT_ASSERT_EQUAL(OUString("abc"), 
rDoc.GetParaAsString(static_cast<sal_Int32>(0)));
+}
+
 void Test::testMultiParaSelCopyPaste()
 {
     // Create EditEngine's instance
diff --git a/editeng/source/editeng/impedit2.cxx 
b/editeng/source/editeng/impedit2.cxx
index 7a5897196715..40f111b72e73 100644
--- a/editeng/source/editeng/impedit2.cxx
+++ b/editeng/source/editeng/impedit2.cxx
@@ -3978,14 +3978,7 @@ EditSelection ImpEditEngine::PasteText( uno::Reference< 
datatransfer::XTransfera
                     uno::Sequence<sal_Int8> aSeq;
                     aData >>= aSeq;
                     SvMemoryStream aHtmlStream(aSeq.getArray(), 
aSeq.getLength(), StreamMode::READ);
-                    static constexpr OUString aExpectedPrefix = u"<!DOCTYPE 
html>"_ustr;
-                    OUString aActualPrefix;
-                    aHtmlStream.ReadByteStringLine(aActualPrefix, 
RTL_TEXTENCODING_UTF8,
-                                                   
aExpectedPrefix.getLength());
-                    if (aActualPrefix == aExpectedPrefix)
-                    {
-                        aNewSelection = Read(aHtmlStream, rBaseURL, 
EETextFormat::Html, rPaM);
-                    }
+                    aNewSelection = Read(aHtmlStream, rBaseURL, 
EETextFormat::Html, rPaM);
                     bDone = true;
                 }
                 catch (const css::uno::Exception&)

Reply via email to