chart2/source/controller/inc/ChartController.hxx           |    7 
 chart2/source/controller/inc/SelectionHelper.hxx           |    6 
 chart2/source/controller/main/ChartController.cxx          |   22 +
 chart2/source/controller/main/ChartController_Position.cxx |   96 +++--
 chart2/source/controller/main/ChartController_Tools.cxx    |   37 ++
 chart2/source/controller/main/ChartController_Window.cxx   |   11 
 chart2/source/controller/main/SelectionHelper.cxx          |    6 
 chart2/source/inc/ObjectIdentifier.hxx                     |    4 
 chart2/source/tools/ObjectIdentifier.cxx                   |    6 
 desktop/source/lib/init.cxx                                |   47 ++
 filter/source/svg/svgexport.cxx                            |    2 
 include/LibreOfficeKit/LibreOfficeKitEnums.h               |   37 +-
 offapi/com/sun/star/text/TextGraphicObject.idl             |    3 
 sd/qa/unit/tiledrendering/tiledrendering.cxx               |   36 +-
 svx/source/svdraw/svdmrkv.cxx                              |  220 ++++++++++++-
 sw/inc/cmdid.h                                             |    2 
 sw/inc/unoprnms.hxx                                        |    1 
 sw/source/core/draw/dflyobj.cxx                            |   13 
 sw/source/core/inc/dflyobj.hxx                             |    1 
 sw/source/core/unocore/unoframe.cxx                        |   31 +
 sw/source/core/unocore/unomap1.cxx                         |    1 
 21 files changed, 511 insertions(+), 78 deletions(-)

New commits:
commit 7e2089e4fd30b70cd341dd02b0c8673434831386
Author:     Marco Cecchetti <mrcek...@gmail.com>
AuthorDate: Tue Mar 26 15:11:33 2019 +0100
Commit:     Jan Holesovsky <ke...@collabora.com>
CommitDate: Tue Apr 30 12:06:31 2019 +0200

    lok: update graphic selection callback description
    
    Change-Id: I1ae073cc8e307b5c42aed9b17d405ef36ce4dc43

diff --git a/include/LibreOfficeKit/LibreOfficeKitEnums.h 
b/include/LibreOfficeKit/LibreOfficeKitEnums.h
index 9639aaf9348e..fe252ca9bdbc 100644
--- a/include/LibreOfficeKit/LibreOfficeKitEnums.h
+++ b/include/LibreOfficeKit/LibreOfficeKitEnums.h
@@ -161,11 +161,40 @@ typedef enum
      */
     LOK_CALLBACK_CURSOR_VISIBLE = 5,
     /**
-     * The size and/or the position of the graphic selection changed and
-     * the rotation angle of the embedded graphic object
+     * The size and/or the position of the graphic selection changed,
+     * the rotation angle of the embedded graphic object, and a property list
+     * which can be used for informing the client about severl properties.
      *
-     * Format is "x, y, width, height, angle", where angle is in 100th
-     * of degree.
+     * Format is "x, y, width, height, angle, { list of properties }",
+     * where angle is in 100th of degree, and the property list is optional.
+     *
+     * The "{ list of properties }" part is in JSON format.
+     * Follow some examples of the property list part:
+     *
+     * 1) when the selected object is an image inserted in Writer:
+     *
+     *      { "isWriterGraphic": true }
+     *
+     * 2) when the selected object is a chart legend:
+     *
+     *      { "isDraggable": true, "isResizable": true, "isRotatable": false }
+     *
+     * 3) when the selected object is a pie segment in a chart:
+     *
+     *      {
+     *          "isDraggable": true,
+     *          "isResizable": false,
+     *          "isRotatable": false,
+     *          "dragInfo": {
+     *              "dragMethod": "PieSegmentDragging",
+     *              "initialOffset": 50,
+     *              "dragDirection": [x, y],
+     *              "svg": "<svg ..."
+     *          }
+     *      }
+     *
+     *      where the "svg" property is a string containing an svg document
+     *      which is a rapresentation of the pie segment.
      */
     LOK_CALLBACK_GRAPHIC_SELECTION = 6,
 
commit 6d63cb8749811ff407c3b3f523a329bcaab05542
Author:     Marco Cecchetti <mrcek...@gmail.com>
AuthorDate: Tue Mar 26 13:17:08 2019 +0100
Commit:     Jan Holesovsky <ke...@collabora.com>
CommitDate: Tue Apr 30 12:06:15 2019 +0200

    lok: chart: constrained dragging of pie segments
    
    The extra information for the graphic selection is now formatted
    according to JSON syntax so that is easier to parse.
    
    Information for allowing the client to performa constrained dragging
    of a pie segment is appended when needed to the graphic selection
    message.
    
    A polygon approximation of the pie segment in svg format is attached
    too to the graphic selection message.
    
    Core now is able to handle a specific msg from the client with data
    about the new pie segment offset computed by the client on drag end.
    This information is dispatched by the chart controller to a specific
    method: executeDispatch_LOKPieSegmentDragging.
    
    Change-Id: I42e7742508fa3a453383bf7b95e47df169f24834

diff --git a/chart2/source/controller/inc/ChartController.hxx 
b/chart2/source/controller/inc/ChartController.hxx
index c2b3756601a6..3fdb357dc4d9 100644
--- a/chart2/source/controller/inc/ChartController.hxx
+++ b/chart2/source/controller/inc/ChartController.hxx
@@ -493,6 +493,7 @@ private:
     void executeDispatch_ToggleGridVertical();
 
     void executeDispatch_LOKSetTextSelection(int nType, int nX, int nY);
+    void executeDispatch_LOKPieSegmentDragging(int nOffset);
 
     void sendPopupRequest(OUString const & rCID, tools::Rectangle aRectangle);
 
diff --git a/chart2/source/controller/main/ChartController.cxx 
b/chart2/source/controller/main/ChartController.cxx
index eb0d5fbfed78..96118e66406b 100644
--- a/chart2/source/controller/main/ChartController.cxx
+++ b/chart2/source/controller/main/ChartController.cxx
@@ -1108,7 +1108,25 @@ void SAL_CALL ChartController::dispatch(
     }
     else if (aCommand == "LOKTransform")
     {
-        this->executeDispatch_PositionAndSize(&rArgs);
+        if (rArgs[0].Name == "Action")
+        {
+           OUString sAction;
+            if ((rArgs[0].Value >>= sAction) && sAction == 
"PieSegmentDragging")
+            {
+                if (rArgs[1].Name == "Offset")
+                {
+                    sal_Int32 nOffset;
+                    if (rArgs[1].Value >>= nOffset)
+                    {
+                        this->executeDispatch_LOKPieSegmentDragging(nOffset);
+                    }
+                }
+            }
+        }
+        else
+        {
+            this->executeDispatch_PositionAndSize(&rArgs);
+        }
     }
     else if(aCommand == "Paste")
         this->executeDispatch_Paste();
diff --git a/chart2/source/controller/main/ChartController_Tools.cxx 
b/chart2/source/controller/main/ChartController_Tools.cxx
index d80e09f78ab8..e112d7a105d4 100644
--- a/chart2/source/controller/main/ChartController_Tools.cxx
+++ b/chart2/source/controller/main/ChartController_Tools.cxx
@@ -974,6 +974,26 @@ void 
ChartController::executeDispatch_LOKSetTextSelection(int nType, int nX, int
     }
 }
 
+void ChartController::executeDispatch_LOKPieSegmentDragging( int nOffset )
+{
+    try
+    {
+        OUString aCID( m_aSelection.getSelectedCID() );
+        const uno::Reference< frame::XModel >& xChartModel = getModel();
+        if( xChartModel.is() )
+        {
+            Reference< beans::XPropertySet > xPointProperties(
+                ObjectIdentifier::getObjectPropertySet( aCID, xChartModel ) );
+            if( xPointProperties.is() )
+                xPointProperties->setPropertyValue( "Offset", uno::Any( 
nOffset / 100.0 ) );
+        }
+    }
+    catch( const uno::Exception & ex )
+    {
+        SAL_WARN( "chart2", "Exception caught. " << ex );
+    }
+}
+
 void ChartController::impl_ShapeControllerDispatch( const util::URL& rURL, 
const Sequence< beans::PropertyValue >& rArgs )
 {
     Reference< frame::XDispatch > xDispatch( 
m_aDispatchContainer.getShapeController() );
diff --git a/chart2/source/tools/ObjectIdentifier.cxx 
b/chart2/source/tools/ObjectIdentifier.cxx
index 34321e003159..667952f4bf68 100644
--- a/chart2/source/tools/ObjectIdentifier.cxx
+++ b/chart2/source/tools/ObjectIdentifier.cxx
@@ -51,7 +51,7 @@ static const char m_aMultiClick[] = "MultiClick";
 static const char m_aDragMethodEquals[] = "DragMethod=";
 static const char m_aDragParameterEquals[] = "DragParameter=";
 static const char m_aProtocol[] = "CID/";
-static const OUString m_aPieSegmentDragMethodServiceName("PieSegmentDraging");
+static const OUString m_aPieSegmentDragMethodServiceName("PieSegmentDragging");
 
 namespace
 {
diff --git a/desktop/source/lib/init.cxx b/desktop/source/lib/init.cxx
index 3443fe4d4b9c..853b0a7882dd 100644
--- a/desktop/source/lib/init.cxx
+++ b/desktop/source/lib/init.cxx
@@ -3101,25 +3101,27 @@ static void doc_postUnoCommand(LibreOfficeKitDocument* 
pThis, const char* pComma
 
         if (aChartHelper.GetWindow())
         {
-            tools::Rectangle aChartBB = aChartHelper.GetChartBoundingBox();
-            int nLeft = OutputDevice::LogicToLogic(aChartBB.Left(), 
MapUnit::MapTwip, MapUnit::Map100thMM);
-            int nTop = OutputDevice::LogicToLogic(aChartBB.Top(), 
MapUnit::MapTwip, MapUnit::Map100thMM);
-
-            sal_Int32 value;
-            for (beans::PropertyValue& rPropValue: aPropertyValuesVector)
+            if (aPropertyValuesVector[0].Name != "Action")
             {
-                if (rPropValue.Name == "TransformPosX" || rPropValue.Name == 
"TransformRotationX")
-                {
-                    rPropValue.Value >>= value;
-                    rPropValue.Value <<= value - nLeft;
-                }
-                else if (rPropValue.Name == "TransformPosY" || rPropValue.Name 
== "TransformRotationY")
+                tools::Rectangle aChartBB = aChartHelper.GetChartBoundingBox();
+                int nLeft = OutputDevice::LogicToLogic(aChartBB.Left(), 
MapUnit::MapTwip, MapUnit::Map100thMM);
+                int nTop = OutputDevice::LogicToLogic(aChartBB.Top(), 
MapUnit::MapTwip, MapUnit::Map100thMM);
+
+                sal_Int32 value;
+                for (beans::PropertyValue& rPropValue: aPropertyValuesVector)
                 {
-                    rPropValue.Value >>= value;
-                    rPropValue.Value <<= value - nTop;
+                    if (rPropValue.Name == "TransformPosX" || rPropValue.Name 
== "TransformRotationX")
+                    {
+                        rPropValue.Value >>= value;
+                        rPropValue.Value <<= value - nLeft;
+                    }
+                    else if (rPropValue.Name == "TransformPosY" || 
rPropValue.Name == "TransformRotationY")
+                    {
+                        rPropValue.Value >>= value;
+                        rPropValue.Value <<= value - nTop;
+                    }
                 }
             }
-
             util::URL aCommandURL;
             aCommandURL.Path = "LOKTransform";
             css::uno::Reference<css::frame::XDispatch>& aChartDispatcher = 
aChartHelper.GetXDispatcher();
diff --git a/svx/source/svdraw/svdmrkv.cxx b/svx/source/svdraw/svdmrkv.cxx
index 69366b3d4a63..90865f7d5d02 100644
--- a/svx/source/svdraw/svdmrkv.cxx
+++ b/svx/source/svdraw/svdmrkv.cxx
@@ -625,6 +625,59 @@ bool SdrMarkView::ImpIsFrameHandles() const
     return bFrmHdl;
 }
 
+namespace
+{
+OUString lcl_getDragMethodServiceName( const OUString& rCID )
+{
+    OUString aRet;
+
+    sal_Int32 nIndexStart = rCID.indexOf( "DragMethod=" );
+    if( nIndexStart != -1 )
+    {
+        nIndexStart = rCID.indexOf( '=', nIndexStart );
+        if( nIndexStart != -1 )
+        {
+            nIndexStart++;
+            sal_Int32 nNextSlash = rCID.indexOf( '/', nIndexStart );
+            if( nNextSlash != -1 )
+            {
+                sal_Int32 nIndexEnd = nNextSlash;
+                sal_Int32 nNextColon = rCID.indexOf( ':', nIndexStart );
+                if( nNextColon < nNextSlash )
+                    nIndexEnd = nNextColon;
+                aRet = rCID.copy(nIndexStart,nIndexEnd-nIndexStart);
+            }
+        }
+    }
+    return aRet;
+}
+
+OUString lcl_getDragParameterString( const OUString& rCID )
+{
+    OUString aRet;
+
+    sal_Int32 nIndexStart = rCID.indexOf( "DragParameter=" );
+    if( nIndexStart != -1 )
+    {
+        nIndexStart = rCID.indexOf( '=', nIndexStart );
+        if( nIndexStart != -1 )
+        {
+            nIndexStart++;
+            sal_Int32 nNextSlash = rCID.indexOf( '/', nIndexStart );
+            if( nNextSlash != -1 )
+            {
+                sal_Int32 nIndexEnd = nNextSlash;
+                sal_Int32 nNextColon = rCID.indexOf( ':', nIndexStart );
+                if( nNextColon < nNextSlash )
+                    nIndexEnd = nNextColon;
+                aRet = rCID.copy(nIndexStart,nIndexEnd-nIndexStart);
+            }
+        }
+    }
+    return aRet;
+}
+} // anonymous namespace
+
 void SdrMarkView::SetMarkHandles(SfxViewShell* pOtherShell)
 {
     // remember old focus handle values to search for it again
@@ -821,11 +874,10 @@ void SdrMarkView::SetMarkHandles(SfxViewShell* 
pOtherShell)
 
                 sSelection += OString(", ") + OString::number(nRotAngle);
 
-                OString sProperties;
-
+                OStringBuffer aExtraInfo;
                 if (bWriterGraphic)
                 {
-                    sProperties = "{ WriterGraphic=true }";
+                    aExtraInfo.append("{ \"isWriterGraphic\": true }");
                 }
                 else if (bIsChart)
                 {
@@ -839,27 +891,127 @@ void SdrMarkView::SetMarkHandles(SfxViewShell* 
pOtherShell)
                         if (aSel >>= aValue)
                         {
                             OString aObjectCID(aValue.getStr(), 
aValue.getLength(), osl_getThreadTextEncoding());
-                            sProperties += "{ ";
-                            const std::vector<OString> aProps{"Draggable=", 
"Resizable=", "Rotatable="};
+                            aExtraInfo.append("{ ");
+                            const std::vector<OString> aProps{"Draggable", 
"Resizable", "Rotatable"};
                             for (const auto& rProp: aProps)
                             {
                                 sal_Int32 nPos = aObjectCID.indexOf(rProp);
                                 if (nPos == -1) continue;
-                                nPos += rProp.getLength();
-                                if (sProperties.getLength() > 2)
-                                    sProperties += ", ";
-                                sProperties += rProp;
-                                sProperties += 
OString::boolean(aObjectCID[nPos] == '1');
+                                nPos += rProp.getLength() + 1; // '='
+                                if (aExtraInfo.getLength() > 2) // != "{ "
+                                    aExtraInfo.append(", ");
+                                aExtraInfo.append("\"is");
+                                aExtraInfo.append(rProp);
+                                aExtraInfo.append("\": ");
+                                
aExtraInfo.append(OString::boolean(aObjectCID[nPos] == '1'));
+                            }
+
+                            OUString sDragMethod = 
lcl_getDragMethodServiceName(aValue);
+                            if (sDragMethod == "PieSegmentDragging")
+                            {
+                                // old initial offset inside the CID returned 
by xSelectionSupplier->getSelection()
+                                // after a pie segment dragging; using 
SdrObject::GetName for getting a CID with the updated offset
+                                aValue = pO->GetName();
+                                OUString sDragParameters = 
lcl_getDragParameterString(aValue);
+                                if (!sDragParameters.isEmpty())
+                                {
+                                    aExtraInfo.append(", \"dragInfo\": { ");
+                                    aExtraInfo.append("\"dragMethod\": \"");
+                                    aExtraInfo.append(sDragMethod.toUtf8());
+                                    aExtraInfo.append("\"");
+
+                                    OUString sParam;
+                                    sal_Int32 nStartIndex = 0;
+                                    std::array<int, 5> aDragParameters;
+                                    for (auto& rParam : aDragParameters)
+                                    {
+                                        sParam = sDragParameters.getToken(0, 
',', nStartIndex);
+                                        if (sParam.isEmpty())
+                                            break;
+                                        rParam = sParam.toInt32();
+                                    }
+
+                                    // initial offset in %
+                                    if (aDragParameters[0] < 0)
+                                        aDragParameters[0] = 0;
+                                    else if (aDragParameters[0] > 100)
+                                        aDragParameters[0] = 100;
+
+                                    aExtraInfo.append(", \"initialOffset\": ");
+                                    
aExtraInfo.append(OString::number(aDragParameters[0]));
+
+                                    // drag direction constraint
+                                    Point aMinPos(aDragParameters[1], 
aDragParameters[2]);
+                                    Point aMaxPos(aDragParameters[3], 
aDragParameters[4]);
+                                    Point aDragDirection = aMaxPos - aMinPos;
+                                    aDragDirection = 
OutputDevice::LogicToLogic(aDragDirection, MapMode(MapUnit::Map100thMM), 
MapMode(MapUnit::MapTwip));
+
+                                    aExtraInfo.append(", \"dragDirection\": 
[");
+                                    
aExtraInfo.append(aDragDirection.toString());
+                                    aExtraInfo.append("]");
+
+                                    // polygon approximating the pie segment 
or donut segment
+                                    if (pO->GetObjIdentifier() == OBJ_PATHFILL)
+                                    {
+                                        const basegfx::B2DPolyPolygon 
aPolyPolygon(pO->TakeXorPoly());
+                                        if (aPolyPolygon.count() == 1)
+                                        {
+                                            const basegfx::B2DPolygon aPolygon 
= aPolyPolygon.getB2DPolygon(0);
+                                            if (sal_uInt32 nPolySize = 
aPolygon.count())
+                                            {
+                                                const vcl::Window* pWin = 
dynamic_cast<const vcl::Window*>(this->GetFirstOutputDevice());
+                                                const vcl::Window* 
pViewShellWindow = pViewShell->GetEditWindowForActiveOLEObj();
+                                                if (pWin && pViewShellWindow 
&& pViewShellWindow->IsAncestorOf(*pWin))
+                                                {
+                                                    // in the following code 
escaping sequences used inside raw literal strings
+                                                    // are for making them 
understandable by the JSON parser
+
+                                                    Point aOffsetPx = 
pWin->GetOffsetPixelFrom(*pViewShellWindow);
+                                                    Point aLogicOffset = 
pWin->PixelToLogic(aOffsetPx);
+                                                    OString 
sPolygonElem("<polygon points=\\\"");
+                                                    for (sal_uInt32 nIndex = 
0; nIndex < nPolySize; ++nIndex)
+                                                    {
+                                                        const 
basegfx::B2DPoint aB2Point = aPolygon.getB2DPoint(nIndex);
+                                                        Point 
aPoint(aB2Point.getX(), aB2Point.getY());
+                                                        
aPoint.Move(aLogicOffset.getX(), aLogicOffset.getY());
+                                                        if (nIndex > 0)
+                                                            sPolygonElem += " 
";
+                                                        sPolygonElem += 
aPoint.toString();
+                                                    }
+                                                    sPolygonElem += R"elem(\" 
style=\"stroke: none; fill: rgb(114,159,207); fill-opacity: 0.8\"/>)elem";
+
+                                                    aSelection = 
OutputDevice::LogicToLogic(aSelection, MapMode(MapUnit::MapTwip), 
MapMode(MapUnit::Map100thMM));
+
+                                                    OString 
sSVGElem(R"elem(<svg version=\"1.2\" width=\")elem");
+                                                    sSVGElem += 
OString::number(aSelection.GetWidth() / 100.0);
+                                                    sSVGElem += R"elem(mm\" 
height=\")elem";
+                                                    sSVGElem += 
OString::number(aSelection.GetHeight() / 100.0);
+                                                    sSVGElem += R"elem(mm\" 
viewBox=\")elem";
+                                                    sSVGElem += 
aSelection.toString();
+                                                    sSVGElem += R"elem(\" 
preserveAspectRatio=\"xMidYMid\" xmlns=\"http://www.w3.org/2000/svg\";>)elem";
+
+                                                    aExtraInfo.append(", 
\"svg\": \"");
+                                                    
aExtraInfo.append(sSVGElem);
+                                                    aExtraInfo.append("\\n  ");
+                                                    
aExtraInfo.append(sPolygonElem);
+                                                    
aExtraInfo.append("\\n</svg>");
+                                                    aExtraInfo.append("\""); 
// svg
+                                                }
+                                            }
+                                        }
+                                    }
+                                    aExtraInfo.append("}"); // dragInfo
+                                }
                             }
-                            sProperties += " }";
+                            aExtraInfo.append(" }");
                         }
                     }
                 }
 
-                if (!sProperties.isEmpty())
+                if (!aExtraInfo.isEmpty())
                 {
                     sSelection += ", ";
-                    sSelection += sProperties;
+                    sSelection += aExtraInfo.makeStringAndClear();
                 }
             }
 
commit 9287a4178cd5f09309467eaede1a68021636af93
Author:     Marco Cecchetti <mrcek...@gmail.com>
AuthorDate: Thu Mar 14 23:17:16 2019 +0100
Commit:     Jan Holesovsky <ke...@collabora.com>
CommitDate: Tue Apr 30 12:06:02 2019 +0200

    lok: chart: informing the client about selection handling properties
    
    We hijack the chart CID protocol (CID:/classification/ObjectID) by
    inserting information about selection handling properties (draggable,
    resizable, rotatable) btw the classification section and the ObjectID
    section.
    This new section has the form: /Draggable=?:Resizable=?:Rotatable=?
    where in place of '?' there is 0 or 1.
    The hijacking occurs at the ChartController.getSelection method which
    is available through the XSelectionSupplier interface.
    
    Change-Id: Iaf920fe68e59c2595000e43d3fc1f976632cef18

diff --git a/chart2/source/controller/inc/ChartController.hxx 
b/chart2/source/controller/inc/ChartController.hxx
index b7b759e6d2e2..c2b3756601a6 100644
--- a/chart2/source/controller/inc/ChartController.hxx
+++ b/chart2/source/controller/inc/ChartController.hxx
@@ -313,6 +313,10 @@ public:
 
     static bool isObjectDeleteable( const css::uno::Any& rSelection );
 
+    bool isSelectedObjectDraggable() const;
+    bool isSelectedObjectResizable() const;
+    bool isSelectedObjectRotatable() const;
+
     void setDrawMode( ChartDrawMode eMode ) { m_eDrawMode = eMode; }
 
     bool isShapeContext() const;
diff --git a/chart2/source/controller/inc/SelectionHelper.hxx 
b/chart2/source/controller/inc/SelectionHelper.hxx
index b40d8fe8592c..7369ab18b2c3 100644
--- a/chart2/source/controller/inc/SelectionHelper.hxx
+++ b/chart2/source/controller/inc/SelectionHelper.hxx
@@ -40,9 +40,9 @@ public: //methods
     css::uno::Reference< css::drawing::XShape > getSelectedAdditionalShape();
     const ObjectIdentifier& getSelectedOID() const { return m_aSelectedOID;}
 
-    bool isResizeableObjectSelected();
-    bool isRotateableObjectSelected( const css::uno::Reference< 
css::frame::XModel >& xChartModel );
-    bool isDragableObjectSelected();
+    bool isResizeableObjectSelected() const;
+    bool isRotateableObjectSelected( const css::uno::Reference< 
css::frame::XModel >& xChartModel ) const;
+    bool isDragableObjectSelected() const;
 
     bool isAdditionalShapeSelected() const;
 
diff --git a/chart2/source/controller/main/ChartController_Tools.cxx 
b/chart2/source/controller/main/ChartController_Tools.cxx
index ae1d02a106fa..d80e09f78ab8 100644
--- a/chart2/source/controller/main/ChartController_Tools.cxx
+++ b/chart2/source/controller/main/ChartController_Tools.cxx
@@ -577,6 +577,23 @@ bool ChartController::isObjectDeleteable( const uno::Any& 
rSelection )
     return false;
 }
 
+bool ChartController::isSelectedObjectDraggable() const
+{
+    return m_aSelection.isDragableObjectSelected();
+}
+
+bool ChartController::isSelectedObjectResizable() const
+{
+    return m_aSelection.isResizeableObjectSelected();
+}
+
+bool ChartController::isSelectedObjectRotatable() const
+{
+    const ChartController* pThis = this;
+    const uno::Reference< frame::XModel >& xChartModel = 
const_cast<ChartController*>(pThis)->getModel();
+    return m_aSelection.isRotateableObjectSelected(xChartModel);
+}
+
 bool ChartController::isShapeContext() const
 {
     return m_aSelection.isAdditionalShapeSelected() ||
diff --git a/chart2/source/controller/main/ChartController_Window.cxx 
b/chart2/source/controller/main/ChartController_Window.cxx
index 0b0053e479a9..7973abb0aedf 100644
--- a/chart2/source/controller/main/ChartController_Window.cxx
+++ b/chart2/source/controller/main/ChartController_Window.cxx
@@ -1661,6 +1661,17 @@ uno::Any SAL_CALL ChartController::getSelection()
         OUString aCID( m_aSelection.getSelectedCID() );
         if ( !aCID.isEmpty() )
         {
+            if ( comphelper::LibreOfficeKit::isActive() )
+            {
+                sal_Int32 nPos = aCID.lastIndexOf('/');
+                OUString sFirst = aCID.copy(0, nPos);
+                OUString sSecond = aCID.copy(nPos);
+                aCID = sFirst;
+                aCID += "/Draggable=" + 
OUString::number(isSelectedObjectDraggable());
+                aCID += ":Resizable=" + 
OUString::number(isSelectedObjectResizable());
+                aCID += ":Rotatable=" + 
OUString::number(isSelectedObjectRotatable());
+                aCID += sSecond;
+            }
             aReturn <<= aCID;
         }
         else
diff --git a/chart2/source/controller/main/SelectionHelper.cxx 
b/chart2/source/controller/main/SelectionHelper.cxx
index cf6ebddf102e..fd9db1f48a30 100644
--- a/chart2/source/controller/main/SelectionHelper.cxx
+++ b/chart2/source/controller/main/SelectionHelper.cxx
@@ -287,7 +287,7 @@ void Selection::adaptSelectionToNewPos( const Point& 
rMousePos, DrawViewWrapper
     }
 }
 
-bool Selection::isResizeableObjectSelected()
+bool Selection::isResizeableObjectSelected() const
 {
     ObjectType eObjectType = m_aSelectedOID.getObjectType();
     switch( eObjectType )
@@ -302,12 +302,12 @@ bool Selection::isResizeableObjectSelected()
     }
 }
 
-bool Selection::isRotateableObjectSelected( const uno::Reference< 
frame::XModel >& xChartModel )
+bool Selection::isRotateableObjectSelected( const uno::Reference< 
frame::XModel >& xChartModel ) const
 {
     return SelectionHelper::isRotateableObject( m_aSelectedOID.getObjectCID(), 
xChartModel );
 }
 
-bool Selection::isDragableObjectSelected()
+bool Selection::isDragableObjectSelected() const
 {
     return m_aSelectedOID.isDragableObject();
 }
diff --git a/chart2/source/inc/ObjectIdentifier.hxx 
b/chart2/source/inc/ObjectIdentifier.hxx
index e2b81c617a15..84d647acdf99 100644
--- a/chart2/source/inc/ObjectIdentifier.hxx
+++ b/chart2/source/inc/ObjectIdentifier.hxx
@@ -163,7 +163,7 @@ public:
     static OUString getDragMethodServiceName( const OUString& 
rClassifiedIdentifier );
     static OUString getDragParameterString( const OUString& rCID );
     static bool isDragableObject( const OUString& rClassifiedIdentifier );
-    bool isDragableObject();
+    bool isDragableObject() const;
     static bool isRotateableObject( const OUString& rClassifiedIdentifier );
     static bool isMultiClickObject( const OUString& rClassifiedIdentifier );
     static bool areSiblings( const OUString& rCID1, const OUString& rCID2 
);//identical object is no sibling
@@ -171,7 +171,7 @@ public:
 
     static OUString getStringForType( ObjectType eObjectType );
     static ObjectType    getObjectType( const OUString& rCID );
-    ObjectType getObjectType();
+    ObjectType getObjectType() const;
 
     static OUString createSeriesSubObjectStub( ObjectType eSubObjectType
                     , const OUString& rSeriesParticle
diff --git a/chart2/source/tools/ObjectIdentifier.cxx 
b/chart2/source/tools/ObjectIdentifier.cxx
index cb25bb066101..34321e003159 100644
--- a/chart2/source/tools/ObjectIdentifier.cxx
+++ b/chart2/source/tools/ObjectIdentifier.cxx
@@ -822,7 +822,7 @@ bool ObjectIdentifier::isDragableObject( const OUString& 
rClassifiedIdentifier )
     return bReturn;
 }
 
-bool ObjectIdentifier::isDragableObject()
+bool ObjectIdentifier::isDragableObject() const
 {
     bool bReturn = false;
     if ( isAutoGeneratedObject() )
@@ -1067,7 +1067,7 @@ ObjectType ObjectIdentifier::getObjectType( const 
OUString& rCID )
     return eRet;
 }
 
-ObjectType ObjectIdentifier::getObjectType()
+ObjectType ObjectIdentifier::getObjectType() const
 {
     ObjectType eObjectType( OBJECTTYPE_UNKNOWN );
     if ( isAutoGeneratedObject() )
diff --git a/svx/source/svdraw/svdmrkv.cxx b/svx/source/svdraw/svdmrkv.cxx
index 93f885f30572..69366b3d4a63 100644
--- a/svx/source/svdraw/svdmrkv.cxx
+++ b/svx/source/svdraw/svdmrkv.cxx
@@ -54,6 +54,7 @@
 #include <LibreOfficeKit/LibreOfficeKitEnums.h>
 #include <comphelper/lok.hxx>
 #include <sfx2/lokhelper.hxx>
+#include <sfx2/lokcharthelper.hxx>
 #include <sfx2/viewsh.hxx>
 
 using namespace com::sun::star;
@@ -759,6 +760,7 @@ void SdrMarkView::SetMarkHandles(SfxViewShell* pOtherShell)
     tools::Rectangle aRect(GetMarkedObjRect());
     tools::Rectangle aSelection(aRect);
 
+    bool bIsChart = false;
     if (bTiledRendering && !aRect.IsEmpty())
     {
         sal_uInt32 nTotalPaintWindows = this->PaintWindowCount();
@@ -767,6 +769,7 @@ void SdrMarkView::SetMarkHandles(SfxViewShell* pOtherShell)
             const vcl::Window* pWin = dynamic_cast<const 
vcl::Window*>(this->GetFirstOutputDevice());
             if (pWin && pWin->IsChart())
             {
+                bIsChart = true;
                 const vcl::Window* pViewShellWindow = 
GetSfxViewShell()->GetEditWindowForActiveOLEObj();
                 if (pViewShellWindow && pViewShellWindow->IsAncestorOf(*pWin))
                 {
@@ -824,6 +827,34 @@ void SdrMarkView::SetMarkHandles(SfxViewShell* pOtherShell)
                 {
                     sProperties = "{ WriterGraphic=true }";
                 }
+                else if (bIsChart)
+                {
+                    LokChartHelper aChartHelper(pViewShell);
+                    css::uno::Reference<css::frame::XController>& 
xChartController = aChartHelper.GetXController();
+                    css::uno::Reference<css::view::XSelectionSupplier> 
xSelectionSupplier( xChartController, uno::UNO_QUERY);
+                    if (xSelectionSupplier.is())
+                    {
+                        uno::Any aSel = xSelectionSupplier->getSelection();
+                        OUString aValue;
+                        if (aSel >>= aValue)
+                        {
+                            OString aObjectCID(aValue.getStr(), 
aValue.getLength(), osl_getThreadTextEncoding());
+                            sProperties += "{ ";
+                            const std::vector<OString> aProps{"Draggable=", 
"Resizable=", "Rotatable="};
+                            for (const auto& rProp: aProps)
+                            {
+                                sal_Int32 nPos = aObjectCID.indexOf(rProp);
+                                if (nPos == -1) continue;
+                                nPos += rProp.getLength();
+                                if (sProperties.getLength() > 2)
+                                    sProperties += ", ";
+                                sProperties += rProp;
+                                sProperties += 
OString::boolean(aObjectCID[nPos] == '1');
+                            }
+                            sProperties += " }";
+                        }
+                    }
+                }
 
                 if (!sProperties.isEmpty())
                 {
commit 05157f967b23a7b35e988d7fe136e8869feaeb35
Author:     Marco Cecchetti <mrcek...@gmail.com>
AuthorDate: Mon Mar 11 16:31:20 2019 +0100
Commit:     Jan Holesovsky <ke...@collabora.com>
CommitDate: Tue Apr 30 12:05:50 2019 +0200

    lok: dragging and resizing chart elements
    
    This patch make possible to set the new position or size of a chart
    object through setting directly the property value instead of sending
    mouse events to the core.
    
    Change-Id: Ifc06dac6bdad78081d63e0ea0db55563a1ae57bc

diff --git a/chart2/source/controller/inc/ChartController.hxx 
b/chart2/source/controller/inc/ChartController.hxx
index 5a47a8838e55..b7b759e6d2e2 100644
--- a/chart2/source/controller/inc/ChartController.hxx
+++ b/chart2/source/controller/inc/ChartController.hxx
@@ -473,7 +473,7 @@ private:
     bool EndTextEdit();
 
     void executeDispatch_View3D();
-    void executeDispatch_PositionAndSize();
+    void executeDispatch_PositionAndSize( const ::css::uno::Sequence< 
::css::beans::PropertyValue >* pArgs = nullptr );
 
     void executeDispatch_EditData();
 
diff --git a/chart2/source/controller/main/ChartController.cxx 
b/chart2/source/controller/main/ChartController.cxx
index 702c84a2f53c..eb0d5fbfed78 100644
--- a/chart2/source/controller/main/ChartController.cxx
+++ b/chart2/source/controller/main/ChartController.cxx
@@ -1106,6 +1106,10 @@ void SAL_CALL ChartController::dispatch(
             executeDispatch_LOKSetTextSelection(nType, nX, nY);
         }
     }
+    else if (aCommand == "LOKTransform")
+    {
+        this->executeDispatch_PositionAndSize(&rArgs);
+    }
     else if(aCommand == "Paste")
         this->executeDispatch_Paste();
     else if(aCommand == "Copy" )
diff --git a/chart2/source/controller/main/ChartController_Position.cxx 
b/chart2/source/controller/main/ChartController_Position.cxx
index 1421fc1cbc12..19972c1e4634 100644
--- a/chart2/source/controller/main/ChartController_Position.cxx
+++ b/chart2/source/controller/main/ChartController_Position.cxx
@@ -107,7 +107,7 @@ void lcl_getPositionAndSizeFromItemSet( const SfxItemSet& 
rItemSet, awt::Rectang
     rPosAndSize = awt::Rectangle(nPosX,nPosY,nSizX,nSizY);
 }
 
-void ChartController::executeDispatch_PositionAndSize()
+void ChartController::executeDispatch_PositionAndSize(const 
::css::uno::Sequence< ::css::beans::PropertyValue >* pArgs)
 {
     const OUString aCID( m_aSelection.getSelectedCID() );
 
@@ -130,41 +130,75 @@ void ChartController::executeDispatch_PositionAndSize()
     try
     {
         SfxItemSet aItemSet = 
m_pDrawViewWrapper->getPositionAndSizeItemSetFromMarkedObject();
-
-        //prepare and open dialog
-        SdrView* pSdrView = m_pDrawViewWrapper;
-        bool bResizePossible = m_aSelection.isResizeableObjectSelected();
-
-        SolarMutexGuard aGuard;
-        SvxAbstractDialogFactory * pFact = SvxAbstractDialogFactory::Create();
-        OSL_ENSURE( pFact, "No dialog factory" );
-        ScopedVclPtr<SfxAbstractTabDialog> 
pDlg(pFact->CreateSchTransformTabDialog(
-            GetChartWindow(), &aItemSet, pSdrView, bResizePossible ));
-        OSL_ENSURE( pDlg, "Couldn't create SchTransformTabDialog" );
-
-        if( pDlg->Execute() == RET_OK )
+        const SfxItemSet* pOutItemSet = nullptr;
+        if (!pArgs)
         {
-            const SfxItemSet* pOutItemSet = pDlg->GetOutputItemSet();
-            if(pOutItemSet)
+            //prepare and open dialog
+            SdrView* pSdrView = m_pDrawViewWrapper;
+            bool bResizePossible = m_aSelection.isResizeableObjectSelected();
+
+            SolarMutexGuard aGuard;
+            SvxAbstractDialogFactory * pFact = 
SvxAbstractDialogFactory::Create();
+            OSL_ENSURE( pFact, "No dialog factory" );
+            ScopedVclPtr<SfxAbstractTabDialog> 
pDlg(pFact->CreateSchTransformTabDialog(
+                GetChartWindow(), &aItemSet, pSdrView, bResizePossible ));
+            OSL_ENSURE( pDlg, "Couldn't create SchTransformTabDialog" );
+
+            if( pDlg->Execute() == RET_OK )
             {
-                awt::Rectangle aObjectRect;
-                aItemSet.Put(*pOutItemSet);//overwrite old values with new 
values (-> all items are set)
-                lcl_getPositionAndSizeFromItemSet( aItemSet, aObjectRect, 
aSelectedSize );
-                awt::Size aPageSize( ChartModelHelper::getPageSize( getModel() 
) );
-                awt::Rectangle aPageRect( 0,0,aPageSize.Width,aPageSize.Height 
);
-
-                bool bChanged = false;
-                if ( eObjectType == OBJECTTYPE_LEGEND )
-                {
-                    ChartModel& rModel = 
dynamic_cast<ChartModel&>(*getModel().get());
-                    bChanged = 
DiagramHelper::switchDiagramPositioningToExcludingPositioning(rModel, false , 
true);
+                pOutItemSet = pDlg->GetOutputItemSet();
+                if (pOutItemSet)
+                    aItemSet.Put(*pOutItemSet);//overwrite old values with new 
values (-> all items are set)
+            }
+        }
+        else
+        {
+            const SfxItemPool* pPool = aItemSet.GetPool();
+            if (!pPool)
+                return;
+
+            sal_uInt16 nWhich;
+            for (const auto& aProp: *pArgs)
+            {
+                sal_Int32 nValue = 0;
+                aProp.Value >>= nValue;
+                if (aProp.Name == "TransformPosX") {
+                    nWhich = pPool->GetWhich(SID_ATTR_TRANSFORM_POS_X);
+                    aItemSet.Put(SfxInt32Item(nWhich, nValue));
+                }
+                else if (aProp.Name == "TransformPosY") {
+                    nWhich = pPool->GetWhich(SID_ATTR_TRANSFORM_POS_Y);
+                    aItemSet.Put(SfxInt32Item(nWhich, nValue));
                 }
+                else if (aProp.Name == "TransformWidth") {
+                    nWhich = pPool->GetWhich(SID_ATTR_TRANSFORM_WIDTH);
+                    aItemSet.Put(SfxUInt32Item(nWhich, 
static_cast<sal_uInt32>(nValue)));
+                }
+                else if (aProp.Name == "TransformHeight") {
+                    nWhich = pPool->GetWhich(SID_ATTR_TRANSFORM_HEIGHT);
+                    aItemSet.Put(SfxUInt32Item(nWhich, 
static_cast<sal_uInt32>(nValue)));
+                }
+            }
+        }
 
-                bool bMoved = PositionAndSizeHelper::moveObject( 
m_aSelection.getSelectedCID(), getModel()
-                            , aObjectRect, aPageRect );
-                if( bMoved || bChanged )
-                    aUndoGuard.commit();
+        if(pOutItemSet || pArgs)
+        {
+            awt::Rectangle aObjectRect;
+            lcl_getPositionAndSizeFromItemSet( aItemSet, aObjectRect, 
aSelectedSize );
+            awt::Size aPageSize( ChartModelHelper::getPageSize( getModel() ) );
+            awt::Rectangle aPageRect( 0,0,aPageSize.Width,aPageSize.Height );
+
+            bool bChanged = false;
+            if ( eObjectType == OBJECTTYPE_LEGEND )
+            {
+                ChartModel& rModel = 
dynamic_cast<ChartModel&>(*getModel().get());
+                bChanged = 
DiagramHelper::switchDiagramPositioningToExcludingPositioning(rModel, false , 
true);
             }
+
+            bool bMoved = PositionAndSizeHelper::moveObject( 
m_aSelection.getSelectedCID(), getModel()
+                        , aObjectRect, aPageRect );
+            if( bMoved || bChanged )
+                aUndoGuard.commit();
         }
     }
     catch(const uno::Exception& e)
diff --git a/desktop/source/lib/init.cxx b/desktop/source/lib/init.cxx
index 8c4fdb7b4494..3443fe4d4b9c 100644
--- a/desktop/source/lib/init.cxx
+++ b/desktop/source/lib/init.cxx
@@ -963,7 +963,14 @@ void CallbackFlushHandler::queue(const int type, const 
char* data)
     }
 #endif
 
-    if (m_bPartTilePainting)
+    bool bIsChartActive = false;
+    if (type == LOK_CALLBACK_GRAPHIC_SELECTION)
+    {
+        LokChartHelper aChartHelper(SfxViewShell::Current());
+        bIsChartActive = aChartHelper.GetWindow() != nullptr;
+    }
+
+    if (m_bPartTilePainting && !bIsChartActive)
     {
         // We drop notifications when this is set, except for important ones.
         // When we issue a complex command (such as .uno:InsertAnnotation)
@@ -3059,13 +3066,20 @@ static void doc_postUnoCommand(LibreOfficeKitDocument* 
pThis, const char* pComma
     {
         bool bNeedConversion = false;
         SfxViewShell* pViewShell = SfxViewShell::Current();
-        if (const SdrView* pView = pViewShell->GetDrawView())
+        LokChartHelper aChartHelper(pViewShell);
+
+        if (aChartHelper.GetWindow() )
+        {
+            bNeedConversion = true;
+        }
+        else if (const SdrView* pView = pViewShell->GetDrawView())
         {
             if (OutputDevice* pOutputDevice = pView->GetFirstOutputDevice())
             {
                 bNeedConversion = (pOutputDevice->GetMapMode().GetMapUnit() == 
MapUnit::Map100thMM);
             }
         }
+
         if (bNeedConversion)
         {
             sal_Int32 value;
@@ -3082,8 +3096,35 @@ static void doc_postUnoCommand(LibreOfficeKitDocument* 
pThis, const char* pComma
                     value = OutputDevice::LogicToLogic(value, 
MapUnit::MapTwip, MapUnit::Map100thMM);
                     rPropValue.Value <<= value;
                 }
+            }
+        }
+
+        if (aChartHelper.GetWindow())
+        {
+            tools::Rectangle aChartBB = aChartHelper.GetChartBoundingBox();
+            int nLeft = OutputDevice::LogicToLogic(aChartBB.Left(), 
MapUnit::MapTwip, MapUnit::Map100thMM);
+            int nTop = OutputDevice::LogicToLogic(aChartBB.Top(), 
MapUnit::MapTwip, MapUnit::Map100thMM);
 
+            sal_Int32 value;
+            for (beans::PropertyValue& rPropValue: aPropertyValuesVector)
+            {
+                if (rPropValue.Name == "TransformPosX" || rPropValue.Name == 
"TransformRotationX")
+                {
+                    rPropValue.Value >>= value;
+                    rPropValue.Value <<= value - nLeft;
+                }
+                else if (rPropValue.Name == "TransformPosY" || rPropValue.Name 
== "TransformRotationY")
+                {
+                    rPropValue.Value >>= value;
+                    rPropValue.Value <<= value - nTop;
+                }
             }
+
+            util::URL aCommandURL;
+            aCommandURL.Path = "LOKTransform";
+            css::uno::Reference<css::frame::XDispatch>& aChartDispatcher = 
aChartHelper.GetXDispatcher();
+            aChartDispatcher->dispatch(aCommandURL, 
comphelper::containerToSequence(aPropertyValuesVector));
+            return;
         }
     }
 
commit 3fb298f673db169a38c1258d66ec24821386eb40
Author:     Marco Cecchetti <mrcek...@gmail.com>
AuthorDate: Tue Mar 26 14:34:42 2019 +0100
Commit:     Jan Holesovsky <ke...@collabora.com>
CommitDate: Tue Apr 30 12:04:10 2019 +0200

    lok: writer: svg export transformed images
    
    Change-Id: I908a6e01573c35c0641519f4995730af0b033c33

diff --git a/filter/source/svg/svgexport.cxx b/filter/source/svg/svgexport.cxx
index e78f546a0c1b..85edd0f3140e 100644
--- a/filter/source/svg/svgexport.cxx
+++ b/filter/source/svg/svgexport.cxx
@@ -677,7 +677,7 @@ bool SVGFilter::implExportWriterTextGraphic( const 
Reference< view::XSelectionSu
     {
         uno::Reference<beans::XPropertySet> xPropertySet(xSelection, 
uno::UNO_QUERY);
         uno::Reference<graphic::XGraphic> xGraphic;
-        xPropertySet->getPropertyValue("Graphic") >>= xGraphic;
+        xPropertySet->getPropertyValue("TransformedGraphic") >>= xGraphic;
 
         if (!xGraphic.is())
             return false;
diff --git a/offapi/com/sun/star/text/TextGraphicObject.idl 
b/offapi/com/sun/star/text/TextGraphicObject.idl
index 32c7dde0db03..8c16c4992ad7 100644
--- a/offapi/com/sun/star/text/TextGraphicObject.idl
+++ b/offapi/com/sun/star/text/TextGraphicObject.idl
@@ -122,6 +122,9 @@ published service TextGraphicObject
     /** contains the graphic.
      */
     [optional, property] com::sun::star::graphic::XGraphic    Graphic;
+    /** contains the transformed graphic.
+     */
+    [readonly, optional, property] com::sun::star::graphic::XGraphic    
TransformedGraphic;
 
 };
 
diff --git a/sd/qa/unit/tiledrendering/tiledrendering.cxx 
b/sd/qa/unit/tiledrendering/tiledrendering.cxx
index 1765db27be7d..1feb91f37efa 100644
--- a/sd/qa/unit/tiledrendering/tiledrendering.cxx
+++ b/sd/qa/unit/tiledrendering/tiledrendering.cxx
@@ -864,11 +864,11 @@ void SdTiledRenderingTest::testResizeTable()
     auto pTableObject = dynamic_cast<sdr::table::SdrTableObj*>(pObject);
     CPPUNIT_ASSERT(pTableObject);
 
-    SdrHdlList handleList(nullptr);
-    pObject->AddToHdlList(handleList);
-    CPPUNIT_ASSERT_EQUAL(static_cast<size_t>(14), handleList.GetHdlCount());
-    // Take the top left handle
-    SdrHdl* pHdl = handleList.GetHdl(0);
+    // Select the table by marking it + starting and ending text edit.
+    SdrView* pView = pViewShell->GetView();
+    pView->MarkObj(pObject, pView->GetSdrPageView());
+    pView->SdrBeginTextEdit(pObject);
+    pView->SdrEndTextEdit();
 
     // Remember the original row heights.
     uno::Reference<table::XColumnRowRange> xTable(pTableObject->getTable(), 
uno::UNO_QUERY);
@@ -879,14 +879,15 @@ void SdTiledRenderingTest::testResizeTable()
     sal_Int32 nExpectedRow2 = xRow2->getPropertyValue("Size").get<sal_Int32>();
 
     // Resize the upper row, decrease its height by 1 cm.
-    pXImpressDocument->setGraphicSelection(LOK_SETGRAPHICSELECTION_START, 
convertMm100ToTwip(pHdl->GetPos().getX()), 
convertMm100ToTwip(pHdl->GetPos().getY()));
-    pXImpressDocument->setGraphicSelection(LOK_SETGRAPHICSELECTION_END, 
convertMm100ToTwip(pHdl->GetPos().getX()), 
convertMm100ToTwip(pHdl->GetPos().getY() + 1000));
+    Point aInnerRowEdge = pObject->GetSnapRect().Center();
+    pXImpressDocument->setGraphicSelection(LOK_SETGRAPHICSELECTION_START, 
convertMm100ToTwip(aInnerRowEdge.getX()), 
convertMm100ToTwip(aInnerRowEdge.getY()));
+    pXImpressDocument->setGraphicSelection(LOK_SETGRAPHICSELECTION_END, 
convertMm100ToTwip(aInnerRowEdge.getX()), 
convertMm100ToTwip(aInnerRowEdge.getY() - 1000));
 
     // Remember the resized row heights.
     sal_Int32 nResizedRow1 = xRow1->getPropertyValue("Size").get<sal_Int32>();
     CPPUNIT_ASSERT(nResizedRow1 < nExpectedRow1);
     sal_Int32 nResizedRow2 = xRow2->getPropertyValue("Size").get<sal_Int32>();
-    CPPUNIT_ASSERT(nResizedRow2 < nExpectedRow2);
+    CPPUNIT_ASSERT_EQUAL(nExpectedRow2, nResizedRow2);
 
     // Now undo the resize.
     pXImpressDocument->GetDocShell()->GetUndoManager()->Undo();
@@ -896,7 +897,7 @@ void SdTiledRenderingTest::testResizeTable()
     CPPUNIT_ASSERT_EQUAL(nExpectedRow1, nActualRow1);
     sal_Int32 nActualRow2 = xRow2->getPropertyValue("Size").get<sal_Int32>();
     // Expected was 4000, actual was 4572, i.e. the second row after undo was 
larger than expected.
-    CPPUNIT_ASSERT_DOUBLES_EQUAL(nExpectedRow2, nActualRow2, 1.0);
+    CPPUNIT_ASSERT_EQUAL(nExpectedRow2, nActualRow2);
     comphelper::LibreOfficeKit::setActive(false);
 }
 
@@ -911,11 +912,11 @@ void SdTiledRenderingTest::testResizeTableColumn()
     auto pTableObject = dynamic_cast<sdr::table::SdrTableObj*>(pObject);
     CPPUNIT_ASSERT(pTableObject);
 
-    SdrHdlList handleList(nullptr);
-    pObject->AddToHdlList(handleList);
-    CPPUNIT_ASSERT_EQUAL(static_cast<size_t>(14), handleList.GetHdlCount());
-    // Take the top left handle
-    SdrHdl* pHdl = handleList.GetHdl(0);
+    // Select the table by marking it + starting and ending text edit.
+    SdrView* pView = pViewShell->GetView();
+    pView->MarkObj(pObject, pView->GetSdrPageView());
+    pView->SdrBeginTextEdit(pObject);
+    pView->SdrEndTextEdit();
 
     // Remember the original cell widths.
     xmlDocPtr pXmlDoc = parseXmlDump();
@@ -926,15 +927,16 @@ void SdTiledRenderingTest::testResizeTableColumn()
     pXmlDoc = nullptr;
 
     // Resize the left column, decrease its width by 1 cm.
-    pXImpressDocument->setGraphicSelection(LOK_SETGRAPHICSELECTION_START, 
convertMm100ToTwip(pHdl->GetPos().getX()), 
convertMm100ToTwip(pHdl->GetPos().getY()));
-    pXImpressDocument->setGraphicSelection(LOK_SETGRAPHICSELECTION_END, 
convertMm100ToTwip(pHdl->GetPos().getX() + 1000), 
convertMm100ToTwip(pHdl->GetPos().getY()));
+    Point aInnerRowEdge = pObject->GetSnapRect().Center();
+    pXImpressDocument->setGraphicSelection(LOK_SETGRAPHICSELECTION_START, 
convertMm100ToTwip(aInnerRowEdge.getX()), 
convertMm100ToTwip(aInnerRowEdge.getY()));
+    pXImpressDocument->setGraphicSelection(LOK_SETGRAPHICSELECTION_END, 
convertMm100ToTwip(aInnerRowEdge.getX() - 1000), 
convertMm100ToTwip(aInnerRowEdge.getY()));
 
     // Remember the resized column widths.
     pXmlDoc = parseXmlDump();
     sal_Int32 nResizedColumn1 = getXPath(pXmlDoc, aPrefix + 
"TableLayouter_Layout[1]", "size").toInt32();
     CPPUNIT_ASSERT(nResizedColumn1 < nExpectedColumn1);
     sal_Int32 nResizedColumn2 = getXPath(pXmlDoc, aPrefix + 
"TableLayouter_Layout[2]", "size").toInt32();
-    CPPUNIT_ASSERT(nResizedColumn2 < nExpectedColumn2);
+    CPPUNIT_ASSERT(nResizedColumn2 > nExpectedColumn2);
     xmlFreeDoc(pXmlDoc);
     pXmlDoc = nullptr;
 
diff --git a/svx/source/svdraw/svdmrkv.cxx b/svx/source/svdraw/svdmrkv.cxx
index 442466d37295..93f885f30572 100644
--- a/svx/source/svdraw/svdmrkv.cxx
+++ b/svx/source/svdraw/svdmrkv.cxx
@@ -579,13 +579,10 @@ void SdrMarkView::showMarkHandles()
 
 bool SdrMarkView::ImpIsFrameHandles() const
 {
-    // There can be multiple mark views, but we're only interested in the one 
that has a window associated.
-    const bool bTiledRendering = comphelper::LibreOfficeKit::isActive() && 
GetFirstOutputDevice() && GetFirstOutputDevice()->GetOutDevType() == 
OUTDEV_WINDOW;
-
     const size_t nMarkCount=GetMarkedObjectCount();
     bool bFrmHdl=nMarkCount>static_cast<size_t>(mnFrameHandlesLimit) || 
mbForceFrameHandles;
     bool bStdDrag=meDragMode==SdrDragMode::Move;
-    if (!bTiledRendering && nMarkCount==1 && bStdDrag && bFrmHdl)
+    if (nMarkCount==1 && bStdDrag && bFrmHdl)
     {
         const SdrObject* pObj=GetMarkedObjectByIndex(0);
         if (pObj->GetObjInventor()==SdrInventor::Default)
@@ -667,7 +664,7 @@ void SdrMarkView::SetMarkHandles(SfxViewShell* pOtherShell)
     bool bSingleTextObjMark=false;
     bool bLimitedRotation(false);
 
-    if (!bTiledRendering && nMarkCount==1)
+    if (nMarkCount==1)
     {
         mpMarkedObj=GetMarkedObjectByIndex(0);
 
@@ -806,15 +803,33 @@ void SdrMarkView::SetMarkHandles(SfxViewShell* 
pOtherShell)
         }
         if(SfxViewShell* pViewShell = GetSfxViewShell())
         {
-
-            long nRotAngle(0);
-            if(GetMarkedObjectCount())
+            if (GetMarkedObjectCount())
             {
-                SdrMark* pM = GetSdrMarkByIndex(0);
-                SdrObject* pO = pM->GetMarkedSdrObj();
+                SdrObject* pO = mpMarkedObj;
+                long nRotAngle = pO->GetRotateAngle();
+                // true if we are delaing with a RotGrfFlyFrame
+                // (SwVirtFlyDrawObj with a SwGrfNode)
+                bool bWriterGraphic = pO->HasLimitedRotation();
+
+                if (bWriterGraphic)
+                {
+                    nRotAngle *= 10;
+                }
 
-                nRotAngle = pO->GetRotateAngle();
                 sSelection += OString(", ") + OString::number(nRotAngle);
+
+                OString sProperties;
+
+                if (bWriterGraphic)
+                {
+                    sProperties = "{ WriterGraphic=true }";
+                }
+
+                if (!sProperties.isEmpty())
+                {
+                    sSelection += ", ";
+                    sSelection += sProperties;
+                }
             }
 
             if (pOtherShell)
diff --git a/sw/inc/cmdid.h b/sw/inc/cmdid.h
index 471db4f40353..cafbd2b4ab1f 100644
--- a/sw/inc/cmdid.h
+++ b/sw/inc/cmdid.h
@@ -605,6 +605,8 @@
 #define FN_UNO_STYLE_INTEROP_GRAB_BAG       (FN_EXTRA2 + 123)
 #define FN_UNO_TABLE_TEMPLATE_NAME          (FN_EXTRA2 + 124)
 
+#define FN_UNO_TRANSFORMED_GRAPHIC          (FN_EXTRA2 + 125)
+
 // Area: Help
 // Region: Traveling & Selection
 #define FN_CHAR_LEFT                (FN_SELECTION + 1 ) /* */
diff --git a/sw/inc/unoprnms.hxx b/sw/inc/unoprnms.hxx
index ecb8dfbc88a5..708046de4f20 100644
--- a/sw/inc/unoprnms.hxx
+++ b/sw/inc/unoprnms.hxx
@@ -157,6 +157,7 @@
 #define UNO_NAME_DROP_CAP_CHAR_STYLE_NAME "DropCapCharStyleName"
 #define UNO_NAME_FILE_LINK "FileLink"
 #define UNO_NAME_GRAPHIC "Graphic"
+#define UNO_NAME_TRANSFORMED_GRAPHIC "TransformedGraphic"
 #define UNO_NAME_IS_PROTECTED "IsProtected"
 #define UNO_NAME_PARA_KEEP_TOGETHER "ParaKeepTogether"
 #define UNO_NAME_KEEP_TOGETHER "KeepTogether"
diff --git a/sw/source/core/draw/dflyobj.cxx b/sw/source/core/draw/dflyobj.cxx
index e9f93c295fd8..653e3ebb75f7 100644
--- a/sw/source/core/draw/dflyobj.cxx
+++ b/sw/source/core/draw/dflyobj.cxx
@@ -1169,6 +1169,19 @@ sal_uInt16 
SwVirtFlyDrawObj::getPossibleRotationFromFraphicFrame(Size& rSize) co
     return nRetval;
 }
 
+long SwVirtFlyDrawObj::GetRotateAngle() const
+{
+    if(ContainsSwGrfNode())
+    {
+        Size aSize;
+        return getPossibleRotationFromFraphicFrame(aSize);
+    }
+    else
+    {
+        return SdrVirtObj::GetRotateAngle();
+    }
+}
+
 SdrObject* SwVirtFlyDrawObj::getFullDragClone() const
 {
     // call parent
diff --git a/sw/source/core/inc/dflyobj.hxx b/sw/source/core/inc/dflyobj.hxx
index a0cf7fd28d3a..ca0d5cdf939c 100644
--- a/sw/source/core/inc/dflyobj.hxx
+++ b/sw/source/core/inc/dflyobj.hxx
@@ -89,6 +89,7 @@ public:
     // we treat the size calculation completely on ourself here
     virtual const tools::Rectangle& GetCurrentBoundRect() const override;
     virtual const tools::Rectangle& GetLastBoundRect() const override;
+    virtual       long       GetRotateAngle() const override;
     virtual       void       RecalcBoundRect() override;
     virtual       void       RecalcSnapRect() override;
     virtual const tools::Rectangle& GetSnapRect()  const override;
diff --git a/sw/source/core/unocore/unoframe.cxx 
b/sw/source/core/unocore/unoframe.cxx
index 76ea5752dc97..4f5ffff31b7c 100644
--- a/sw/source/core/unocore/unoframe.cxx
+++ b/sw/source/core/unocore/unoframe.cxx
@@ -44,6 +44,7 @@
 #include <memory>
 #include <utility>
 #include <hints.hxx>
+#include <cntfrm.hxx>
 #include <doc.hxx>
 #include <drawdoc.hxx>
 #include <IDocumentUndoRedo.hxx>
@@ -2129,6 +2130,36 @@ uno::Any SwXFrame::getPropertyValue(const OUString& 
rPropertyName)
                 aAny <<= pGrfNode->GetGrf().GetXGraphic();
             }
         }
+        else if( FN_UNO_TRANSFORMED_GRAPHIC == pEntry->nWID )
+        {
+            const SwNodeIndex* pIdx = pFormat->GetContent().GetContentIdx();
+            if(pIdx)
+            {
+                SwNodeIndex aIdx(*pIdx, 1);
+                SwGrfNode* pGrfNode = aIdx.GetNode().GetGrfNode();
+                if(!pGrfNode)
+                    throw uno::RuntimeException();
+
+                SwDoc* pDoc = pFormat->GetDoc();
+                if (pDoc)
+                {
+                    const SwEditShell* pEditShell = pDoc->GetEditShell();
+                    if (pEditShell)
+                    {
+                        SwFrame* pCurrFrame = pEditShell->GetCurrFrame(false);
+                        GraphicAttr aGraphicAttr;
+                        pGrfNode->GetGraphicAttr( aGraphicAttr, pCurrFrame );
+                        const GraphicObject aGraphicObj = 
pGrfNode->GetGrfObj();
+
+                        awt::Size aFrameSize = getSize();
+                        Size aSize100thmm(aFrameSize.Width, aFrameSize.Height);
+                        Size aSize = OutputDevice::LogicToLogic(aSize100thmm, 
MapMode(MapUnit::Map100thMM), aGraphicObj.GetPrefMapMode());
+                        Graphic aGraphic = 
aGraphicObj.GetTransformedGraphic(aSize, aGraphicObj.GetPrefMapMode(), 
aGraphicAttr);
+                        aAny <<= aGraphic.GetXGraphic();
+                    }
+                }
+            }
+        }
         else if(FN_UNO_FRAME_STYLE_NAME == pEntry->nWID)
         {
             aAny <<= 
SwStyleNameMapper::GetProgName(pFormat->DerivedFrom()->GetName(), 
SwGetPoolIdFromName::FrmFmt );
diff --git a/sw/source/core/unocore/unomap1.cxx 
b/sw/source/core/unocore/unomap1.cxx
index d610e76d09f0..f3cfdd9eccc8 100644
--- a/sw/source/core/unocore/unomap1.cxx
+++ b/sw/source/core/unocore/unomap1.cxx
@@ -844,6 +844,7 @@ const SfxItemPropertyMapEntry*  
SwUnoPropertyMapProvider::GetGraphicPropertyMap(
         { OUString(UNO_NAME_REPLACEMENT_GRAPHIC_URL), 
FN_UNO_REPLACEMENT_GRAPHIC_U_R_L, cppu::UnoType<OUString>::get(), 0, 0 },
         { OUString(UNO_NAME_GRAPHIC_FILTER), FN_UNO_GRAPHIC_FILTER,      
cppu::UnoType<OUString>::get(), 0, 0 },
         { OUString(UNO_NAME_GRAPHIC), FN_UNO_GRAPHIC, 
cppu::UnoType<css::graphic::XGraphic>::get(), 0, 0 },
+        { OUString(UNO_NAME_TRANSFORMED_GRAPHIC), FN_UNO_TRANSFORMED_GRAPHIC, 
cppu::UnoType<css::graphic::XGraphic>::get(), 0, 0 },
         { OUString(UNO_NAME_ACTUAL_SIZE), FN_UNO_ACTUAL_SIZE,    
cppu::UnoType<css::awt::Size>::get(),  PropertyAttribute::READONLY, 
CONVERT_TWIPS},
         { OUString(UNO_NAME_CONTOUR_POLY_POLYGON), FN_PARAM_CONTOUR_PP, 
cppu::UnoType<css::drawing::PointSequenceSequence>::get(), 
PropertyAttribute::MAYBEVOID, 0 },
         { OUString(UNO_NAME_IS_PIXEL_CONTOUR), FN_UNO_IS_PIXEL_CONTOUR, 
cppu::UnoType<bool>::get(), PROPERTY_NONE, 0 },
_______________________________________________
Libreoffice-commits mailing list
libreoffice-comm...@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/libreoffice-commits

Reply via email to