Coverage Report

Created: 2026-09-28 10:59

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/libreoffice/drawinglayer/source/primitive2d/PolyPolygonGraphicPrimitive2D.cxx
Line
Count
Source
1
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2
/*
3
 * This file is part of the LibreOffice project.
4
 *
5
 * This Source Code Form is subject to the terms of the Mozilla Public
6
 * License, v. 2.0. If a copy of the MPL was not distributed with this
7
 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
 *
9
 * This file incorporates work covered by the following license notice:
10
 *
11
 *   Licensed to the Apache Software Foundation (ASF) under one or more
12
 *   contributor license agreements. See the NOTICE file distributed
13
 *   with this work for additional information regarding copyright
14
 *   ownership. The ASF licenses this file to you under the Apache
15
 *   License, Version 2.0 (the "License"); you may not use this file
16
 *   except in compliance with the License. You may obtain a copy of
17
 *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
18
 */
19
20
#include <drawinglayer/primitive2d/PolyPolygonGraphicPrimitive2D.hxx>
21
22
#include <basegfx/matrix/b2dhommatrix.hxx>
23
#include <basegfx/matrix/b2dhommatrixtools.hxx>
24
#include <drawinglayer/primitive2d/drawinglayer_primitivetypes2d.hxx>
25
#include <drawinglayer/primitive2d/maskprimitive2d.hxx>
26
#include <drawinglayer/primitive2d/graphicprimitivehelper2d.hxx>
27
#include <utility>
28
#include <vcl/graph.hxx>
29
30
using namespace com::sun::star;
31
32
namespace drawinglayer::primitive2d
33
{
34
Primitive2DReference PolyPolygonGraphicPrimitive2D::create2DDecomposition(
35
    const geometry::ViewInformation2D& /*rViewInformation*/) const
36
0
{
37
0
    if (basegfx::fTools::equal(getTransparency(), 1.0))
38
0
    {
39
        // completely transparent, done
40
0
        return nullptr;
41
0
    }
42
43
0
    if (getFillGraphic().isDefault())
44
0
    {
45
        // no geometry data, done
46
0
        return nullptr;
47
0
    }
48
49
0
    const Graphic& rGraphic(getFillGraphic().getGraphic());
50
0
    const GraphicType aType(rGraphic.GetType());
51
52
    // is there a bitmap or a metafile (do we have content)?
53
0
    if (GraphicType::Bitmap != aType && GraphicType::GdiMetafile != aType)
54
0
    {
55
        // no geometry data, done
56
0
        return nullptr;
57
0
    }
58
59
0
    const Size aPrefSize(rGraphic.GetPrefSize());
60
61
    // does content have a size?
62
0
    if (!(aPrefSize.Width() && aPrefSize.Height()))
63
0
    {
64
        // no geometry data with size, done
65
0
        return nullptr;
66
0
    }
67
68
    // create SubSequence with FillGraphicPrimitive2D based on polygon range
69
0
    const basegfx::B2DRange aOutRange(getB2DPolyPolygon().getB2DRange());
70
0
    const basegfx::B2DHomMatrix aTransform(basegfx::utils::createScaleTranslateB2DHomMatrix(
71
0
        aOutRange.getRange(), aOutRange.getMinimum()));
72
0
    drawinglayer::attribute::FillGraphicAttribute aFillGraphicAttribute(getFillGraphic());
73
74
0
    if (aOutRange != getDefinitionRange())
75
0
    {
76
        // we want to paint (tiled) content which is defined relative to DefinitionRange
77
        // with the same tiling and offset(s) in the target range of the geometry (the
78
        // polygon). The range given in the local FillGraphicAttribute defines the position
79
        // of the graphic in unit coordinates relative to the DefinitionRange. Transform
80
        // this using DefinitionRange to get to the global definition and then with the
81
        // inverse transformation from the target range to go to unit coordinates relative
82
        // to that target coordinate system.
83
0
        basegfx::B2DRange aAdaptedRange(getFillGraphic().getGraphicRange());
84
85
0
        const basegfx::B2DHomMatrix aFromDefinitionRangeToGlobal(
86
0
            basegfx::utils::createScaleTranslateB2DHomMatrix(getDefinitionRange().getRange(),
87
0
                                                             getDefinitionRange().getMinimum()));
88
89
0
        aAdaptedRange.transform(aFromDefinitionRangeToGlobal);
90
91
0
        basegfx::B2DHomMatrix aFromGlobalToOutRange(
92
0
            basegfx::utils::createScaleTranslateB2DHomMatrix(aOutRange.getRange(),
93
0
                                                             aOutRange.getMinimum()));
94
0
        aFromGlobalToOutRange.invert();
95
96
0
        aAdaptedRange.transform(aFromGlobalToOutRange);
97
98
0
        aFillGraphicAttribute = drawinglayer::attribute::FillGraphicAttribute(
99
0
            getFillGraphic().getGraphic(), aAdaptedRange, getFillGraphic().getTiling(),
100
0
            getFillGraphic().getOffsetX(), getFillGraphic().getOffsetY());
101
0
    }
102
103
    // use tooling due to evtl. animation info needs to be created if
104
    // the Graphic is animated somehow
105
0
    Primitive2DReference aContent(
106
0
        createFillGraphicPrimitive2D(aTransform, aFillGraphicAttribute, getTransparency()));
107
108
    // embed to mask primitive
109
0
    return new MaskPrimitive2D(getB2DPolyPolygon(), Primitive2DContainer{ aContent });
110
0
}
111
112
PolyPolygonGraphicPrimitive2D::PolyPolygonGraphicPrimitive2D(
113
    basegfx::B2DPolyPolygon aPolyPolygon, const basegfx::B2DRange& rDefinitionRange,
114
    const attribute::FillGraphicAttribute& rFillGraphic, double fTransparency)
115
0
    : maPolyPolygon(std::move(aPolyPolygon))
116
0
    , maDefinitionRange(rDefinitionRange)
117
0
    , maFillGraphic(rFillGraphic)
118
0
    , mfTransparency(std::max(0.0, std::min(1.0, fTransparency)))
119
0
{
120
0
}
121
122
bool PolyPolygonGraphicPrimitive2D::operator==(const BasePrimitive2D& rPrimitive) const
123
0
{
124
0
    if (BufferedDecompositionPrimitive2D::operator==(rPrimitive))
125
0
    {
126
0
        const PolyPolygonGraphicPrimitive2D& rCompare
127
0
            = static_cast<const PolyPolygonGraphicPrimitive2D&>(rPrimitive);
128
129
0
        return (getB2DPolyPolygon() == rCompare.getB2DPolyPolygon()
130
0
                && getDefinitionRange() == rCompare.getDefinitionRange()
131
0
                && getFillGraphic() == rCompare.getFillGraphic()
132
0
                && basegfx::fTools::equal(getTransparency(), rCompare.getTransparency()));
133
0
    }
134
135
0
    return false;
136
0
}
137
138
// provide unique ID
139
sal_uInt32 PolyPolygonGraphicPrimitive2D::getPrimitive2DID() const
140
0
{
141
0
    return PRIMITIVE2D_ID_POLYPOLYGONGRAPHICPRIMITIVE2D;
142
0
}
143
144
} // end drawinglayer::primitive2d namespace
145
146
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */