[Libreoffice-commits] core.git: drawinglayer/source

Luboš Luňák (via logerrit) logerrit at kemper.freedesktop.org
Fri Apr 30 22:18:26 UTC 2021


 drawinglayer/source/processor2d/vclmetafileprocessor2d.cxx |   91 ++++++++-----
 1 file changed, 59 insertions(+), 32 deletions(-)

New commits:
commit 565824df07913f47851804daed9efa28a4a95e9d
Author:     Luboš Luňák <l.lunak at collabora.com>
AuthorDate: Fri Apr 30 16:41:19 2021 +0200
Commit:     Luboš Luňák <l.lunak at collabora.com>
CommitDate: Sat May 1 00:17:46 2021 +0200

    fix dashed line info conversion for metafile (tdf#136957)
    
    My previous change had two problems:
    - It didn't handle correctly the case when something repeated,
      such as dash-dot-dot.
    - The rounding when setting lengths was a left-over from my first
      attempt when LineInfo used integers and not floats.
    
    Change-Id: I914241590b1ddec22df04c05dfe65e76e921ee52
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/114940
    Tested-by: Jenkins
    Reviewed-by: Luboš Luňák <l.lunak at collabora.com>

diff --git a/drawinglayer/source/processor2d/vclmetafileprocessor2d.cxx b/drawinglayer/source/processor2d/vclmetafileprocessor2d.cxx
index 0dc0904015f0..8837354fc706 100644
--- a/drawinglayer/source/processor2d/vclmetafileprocessor2d.cxx
+++ b/drawinglayer/source/processor2d/vclmetafileprocessor2d.cxx
@@ -1591,40 +1591,67 @@ void VclMetafileProcessor2D::processPolygonStrokePrimitive2D(
             {
                 aHairLinePolyPolygon.append(rBasePolygon);
             }
-            else if (rStroke.getDotDashArray().size() == 2)
-            {
-                aHairLinePolyPolygon.append(rBasePolygon);
-                // This will be used by setupStrokeAttributes() in cppcanvas.
-                aLineInfo.SetStyle(LineStyle::Dash);
-                aLineInfo.SetDashCount(1);
-                aLineInfo.SetDashLen(
-                    basegfx::fround(getTransformedLineWidth(rStroke.getDotDashArray()[0])));
-                aLineInfo.SetDistance(
-                    basegfx::fround(getTransformedLineWidth(rStroke.getDotDashArray()[1])));
-            }
-            else if (rStroke.getDotDashArray().size() == 4
-                     && rStroke.getDotDashArray()[1] == rStroke.getDotDashArray()[3])
-            {
-                aHairLinePolyPolygon.append(rBasePolygon);
-                // This will be used by setupStrokeAttributes() in cppcanvas.
-                aLineInfo.SetStyle(LineStyle::Dash);
-                aLineInfo.SetDashCount(1);
-                aLineInfo.SetDashLen(
-                    basegfx::fround(getTransformedLineWidth(rStroke.getDotDashArray()[0])));
-                aLineInfo.SetDistance(
-                    basegfx::fround(getTransformedLineWidth(rStroke.getDotDashArray()[1])));
-                aLineInfo.SetDotCount(1);
-                aLineInfo.SetDotLen(
-                    basegfx::fround(getTransformedLineWidth(rStroke.getDotDashArray()[2])));
-            }
             else
             {
-                // LineInfo can hold only limited info about dashing, apply dashing manually
-                // if LineInfo cannot describe it. That should not happen though.
-                SAL_WARN("drawinglayer", "dotdash array cannot be converted to LineInfo");
-                basegfx::utils::applyLineDashing(rBasePolygon, rStroke.getDotDashArray(),
-                                                 &aHairLinePolyPolygon, nullptr,
-                                                 rStroke.getFullDotDashLen());
+                bool done = false;
+                const std::vector<double>& array = rStroke.getDotDashArray();
+                // The dotdash array should generally have the form
+                // (<dashLen> <distance>)+ (<dotLen> <distance>)*
+                // (where (,),+ and * have their regex meaning).
+                // Find out what the lengths and their counts are.
+                if (!array.empty() && array.size() % 2 == 0)
+                {
+                    double dashLen = array[0];
+                    double distance = array[1];
+                    int dashCount = 1;
+                    double dotLen = 0;
+                    int dotCount = 0;
+                    size_t pos = 2;
+                    while (pos + 2 <= array.size())
+                    {
+                        if (array[pos] != dashLen || array[pos + 1] != distance)
+                            break;
+                        ++dashCount;
+                        pos += 2;
+                    }
+                    if (pos + 2 <= array.size() && array[pos + 1] == distance)
+                    {
+                        dotLen = array[pos];
+                        ++dotCount;
+                        pos += 2;
+                        while (pos + 2 <= array.size())
+                        {
+                            if (array[pos] != dotLen || array[pos + 1] != distance)
+                                break;
+                            ++dotCount;
+                            pos += 2;
+                        }
+                    }
+                    if (array.size() == pos)
+                    {
+                        aHairLinePolyPolygon.append(rBasePolygon);
+                        // This will be used by setupStrokeAttributes() in cppcanvas.
+                        aLineInfo.SetStyle(LineStyle::Dash);
+                        aLineInfo.SetDashCount(dashCount);
+                        aLineInfo.SetDashLen(getTransformedLineWidth(dashLen));
+                        aLineInfo.SetDistance(getTransformedLineWidth(distance));
+                        if (dotCount != 0)
+                        {
+                            aLineInfo.SetDotCount(dotCount);
+                            aLineInfo.SetDotLen(getTransformedLineWidth(dotLen));
+                        }
+                        done = true;
+                    }
+                }
+                if (!done)
+                {
+                    // LineInfo can hold only limited info about dashing, apply dashing manually
+                    // if LineInfo cannot describe it. That should not happen though.
+                    SAL_WARN("drawinglayer", "dotdash array cannot be converted to LineInfo");
+                    basegfx::utils::applyLineDashing(rBasePolygon, rStroke.getDotDashArray(),
+                                                     &aHairLinePolyPolygon, nullptr,
+                                                     rStroke.getFullDotDashLen());
+                }
             }
             aHairLinePolyPolygon.transform(maCurrentTransformation);
 


More information about the Libreoffice-commits mailing list