diff options
86 files changed, 1713 insertions, 1805 deletions
diff --git a/basctl/inc/pch/precompiled_basctl.hxx b/basctl/inc/pch/precompiled_basctl.hxx index 4f3566f3f6ea..257159149a3b 100644 --- a/basctl/inc/pch/precompiled_basctl.hxx +++ b/basctl/inc/pch/precompiled_basctl.hxx @@ -499,7 +499,6 @@ #include <svx/svxdllapi.h> #include <svx/xdash.hxx> #include <svx/xdef.hxx> -#include <svx/xgrad.hxx> #include <svx/xhatch.hxx> #include <svx/xpoly.hxx> #include <svx/xtable.hxx> diff --git a/basegfx/Library_basegfx.mk b/basegfx/Library_basegfx.mk index 2f9830d0dcfd..da257e2c9797 100644 --- a/basegfx/Library_basegfx.mk +++ b/basegfx/Library_basegfx.mk @@ -67,6 +67,7 @@ $(eval $(call gb_Library_add_exception_objects,basegfx,\ basegfx/source/range/b3drange \ basegfx/source/raster/rasterconvert3d \ basegfx/source/tools/b2dclipstate \ + basegfx/source/tools/bgradient \ basegfx/source/tools/canvastools \ basegfx/source/tools/gradienttools \ basegfx/source/tools/keystoplerp \ diff --git a/basegfx/source/tools/bgradient.cxx b/basegfx/source/tools/bgradient.cxx new file mode 100644 index 000000000000..7cb1ed85e859 --- /dev/null +++ b/basegfx/source/tools/bgradient.cxx @@ -0,0 +1,770 @@ +/* -*- 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 <basegfx/utils/bgradient.hxx> +#include <basegfx/utils/gradienttools.hxx> +#include <com/sun/star/awt/Gradient2.hpp> +#include <boost/property_tree/json_parser.hpp> +#include <map> + +typedef std::map<OUString, OUString> StringMap; + +namespace +{ +css::awt::GradientStyle lcl_getStyleFromString(std::u16string_view rStyle) +{ + if (rStyle == u"LINEAR") + return css::awt::GradientStyle_LINEAR; + else if (rStyle == u"AXIAL") + return css::awt::GradientStyle_AXIAL; + else if (rStyle == u"RADIAL") + return css::awt::GradientStyle_RADIAL; + else if (rStyle == u"ELLIPTICAL") + return css::awt::GradientStyle_ELLIPTICAL; + else if (rStyle == u"SQUARE") + return css::awt::GradientStyle_SQUARE; + else if (rStyle == u"RECT") + return css::awt::GradientStyle_RECT; + + return css::awt::GradientStyle_LINEAR; +} + +StringMap lcl_jsonToStringMap(std::u16string_view rJSON) +{ + StringMap aArgs; + if (rJSON.size() && rJSON[0] != '\0') + { + std::stringstream aStream(std::string(OUStringToOString(rJSON, RTL_TEXTENCODING_ASCII_US))); + boost::property_tree::ptree aTree; + boost::property_tree::read_json(aStream, aTree); + + for (const auto& rPair : aTree) + { + aArgs[OUString::fromUtf8(rPair.first)] + = OUString::fromUtf8(rPair.second.get_value<std::string>(".")); + } + } + return aArgs; +} + +basegfx::BGradient lcl_buildGradientFromStringMap(StringMap& rMap) +{ + basegfx::BGradient aGradient( + basegfx::BColorStops(ColorToBColorConverter(rMap["startcolor"].toInt32(16)).getBColor(), + ColorToBColorConverter(rMap["endcolor"].toInt32(16)).getBColor())); + + aGradient.SetGradientStyle(lcl_getStyleFromString(rMap["style"])); + aGradient.SetAngle(Degree10(rMap["angle"].toInt32())); + + return aGradient; +} +} + +namespace basegfx +{ +void BColorStops::setColorStopSequence(const css::awt::ColorStopSequence& rColorStops) +{ + const sal_Int32 nLen(rColorStops.getLength()); + + if (0 != nLen) + { + // we have ColorStops + reserve(nLen); + const css::awt::ColorStop* pSourceColorStop(rColorStops.getConstArray()); + + for (sal_Int32 a(0); a < nLen; a++, pSourceColorStop++) + { + emplace_back(pSourceColorStop->StopOffset, + BColor(pSourceColorStop->StopColor.Red, pSourceColorStop->StopColor.Green, + pSourceColorStop->StopColor.Blue)); + } + } +} + +BColorStops::BColorStops(const css::awt::ColorStopSequence& rColorStops) +{ + setColorStopSequence(rColorStops); +} + +BColorStops::BColorStops(const css::uno::Any& rVal) +{ + css::awt::Gradient2 aGradient2; + if (rVal >>= aGradient2) + { + setColorStopSequence(aGradient2.ColorStops); + } +} + +// constuctor with two colors to explicitly create a +// BColorStops for a single StartColor @0.0 & EndColor @1.0 +BColorStops::BColorStops(const BColor& rStart, const BColor& rEnd) +{ + emplace_back(0.0, rStart); + emplace_back(1.0, rEnd); +} + +/* Helper to grep the correct ColorStop out of + ColorStops and interpolate as needed for given + relative value in fPosition in the range of [0.0 .. 1.0]. + It also takes care of evtl. given RequestedSteps. + */ +BColor BColorStops::getInterpolatedBColor(double fPosition, sal_uInt32 nRequestedSteps, + BColorStopRange& rLastColorStopRange) const +{ + // no color at all, done + if (empty()) + return BColor(); + + // outside range -> at start + const double fMin(front().getStopOffset()); + if (fPosition < fMin) + return front().getStopColor(); + + // outside range -> at end + const double fMax(back().getStopOffset()); + if (fPosition > fMax) + return back().getStopColor(); + + // special case for the 'classic' case with just two colors: + // we can optimize that and keep the speed/resources low + // by avoiding some calculations and an O(log(N)) array access + if (2 == size()) + { + // if same StopOffset use front color + if (fTools::equal(fMin, fMax)) + return front().getStopColor(); + + const basegfx::BColor aCStart(front().getStopColor()); + const basegfx::BColor aCEnd(back().getStopColor()); + + // if colors are equal just return one + if (aCStart == aCEnd) + return aCStart; + + // calculate Steps + const sal_uInt32 nSteps( + basegfx::utils::calculateNumberOfSteps(nRequestedSteps, aCStart, aCEnd)); + + // we need to extend the interpolation to the local + // range of ColorStops. Despite having two ColorStops + // these are not necessarily at 0.0 and 1.0, so may be + // not the classical Start/EndColor (what is allowed) + fPosition = (fPosition - fMin) / (fMax - fMin); + return basegfx::interpolate(aCStart, aCEnd, + nSteps > 1 ? floor(fPosition * nSteps) / double(nSteps - 1) + : fPosition); + } + + // check if we need to newly populate the needed interpolation data + // or if we can re-use from last time. + // If this scope is not entered, we do not need the binary search. It's + // only a single buffered entry, and only used when more than three + // ColorStops exist, but makes a huge difference compared with accessing + // the sorted ColorStop vector each time. + // NOTE: with this simple change I get very high hit rates, e.g. rotating + // a donut with gradient test '1' hit rate is at 0.99909440357755486 + if (rLastColorStopRange.mfOffsetStart == rLastColorStopRange.mfOffsetEnd + || fPosition < rLastColorStopRange.mfOffsetStart + || fPosition > rLastColorStopRange.mfOffsetEnd) + { + // access needed spot in sorted array using binary search + // NOTE: This *seems* slow(er) when developing compared to just + // looping/accessing, but that's just due to the extensive + // debug test code created by the stl. In a pro version, + // all is good/fast as expected + const auto upperBound(std::upper_bound(begin(), end(), BColorStop(fPosition), + [](const BColorStop& x, const BColorStop& y) { + return x.getStopOffset() < y.getStopOffset(); + })); + + // no upper bound, done + if (end() == upperBound) + return back().getStopColor(); + + // lower bound is one entry back, access that + const auto lowerBound(upperBound - 1); + + // no lower bound, done + if (end() == lowerBound) + return back().getStopColor(); + + // we have lower and upper bound, get colors and offsets + rLastColorStopRange.maColorStart = lowerBound->getStopColor(); + rLastColorStopRange.maColorEnd = upperBound->getStopColor(); + rLastColorStopRange.mfOffsetStart = lowerBound->getStopOffset(); + rLastColorStopRange.mfOffsetEnd = upperBound->getStopOffset(); + } + + // when there are just two color steps this cannot happen, but when using + // a range of colors this *may* be used inside the range to represent + // single-colored regions inside a ColorRange. Use that color & done + if (rLastColorStopRange.maColorStart == rLastColorStopRange.maColorEnd) + return rLastColorStopRange.maColorStart; + + // calculate number of steps and adapted proportional + // range for scaler in [0.0 .. 1.0] + const double fAdaptedScaler( + (fPosition - rLastColorStopRange.mfOffsetStart) + / (rLastColorStopRange.mfOffsetEnd - rLastColorStopRange.mfOffsetStart)); + const sal_uInt32 nSteps(basegfx::utils::calculateNumberOfSteps( + nRequestedSteps, rLastColorStopRange.maColorStart, rLastColorStopRange.maColorEnd)); + + // interpolate & evtl. apply steps + return interpolate(rLastColorStopRange.maColorStart, rLastColorStopRange.maColorEnd, + nSteps > 1 ? floor(fAdaptedScaler * nSteps) / double(nSteps - 1) + : fAdaptedScaler); +} + +/* Tooling method that allows to replace the StartColor in a + vector of ColorStops. A vector in 'ordered state' is expected, + so you may use/have used sortAndCorrect. + This method is for convenience & backwards compatibility, please + think about handling multi-colored gradients directly. + */ +void BColorStops::replaceStartColor(const BColor& rStart) +{ + BColorStops::iterator a1stNonStartColor(begin()); + + // search for highest existing non-StartColor - CAUTION, + // there might be none, one or multiple with StopOffset 0.0 + while (a1stNonStartColor != end() + && basegfx::fTools::lessOrEqual(a1stNonStartColor->getStopOffset(), 0.0)) + a1stNonStartColor++; + + // create new ColorStops by 1st adding new one and then all + // non-StartColor entries + BColorStops aNewColorStops; + + aNewColorStops.reserve(size() + 1); + aNewColorStops.emplace_back(0.0, rStart); + aNewColorStops.insert(aNewColorStops.end(), a1stNonStartColor, end()); + + // assign & done + *this = aNewColorStops; +} + +/* Tooling method that allows to replace the EndColor in a + vector of ColorStops. A vector in 'ordered state' is expected, + so you may use/have used sortAndCorrectColorStops. + This method is for convenience & backwards compatibility, please + think about handling multi-colored gradients directly. + */ +void BColorStops::replaceEndColor(const BColor& rEnd) +{ + // erase all evtl. existing EndColor(s) + while (!empty() && basegfx::fTools::moreOrEqual(back().getStopOffset(), 1.0)) + pop_back(); + + // add at the end of existing ColorStops + emplace_back(1.0, rEnd); +} + +/* Tooling method to linearly blend the Colors contained in + a given ColorStop vector against a given Color using the + given intensity values. + The intensity values fStartIntensity, fEndIntensity are + in the range of [0.0 .. 1.0] and describe how much the + blend is supposed to be done at the start color position + and the end color position respectively, where 0.0 means + to fully use the given BlendColor, 1.0 means to not change + the existing color in the ColorStop. + Every color entry in the given ColorStop is blended + relative to it's StopPosition, interpolating the + given intensities with the range [0.0 .. 1.0] to do so. + */ +void BColorStops::blendToIntensity(double fStartIntensity, double fEndIntensity, + const BColor& rBlendColor) +{ + // no entries, done + if (empty()) + return; + + // correct intensities (maybe assert when input was wrong) + fStartIntensity = std::max(std::min(1.0, fStartIntensity), 0.0); + fEndIntensity = std::max(std::min(1.0, fEndIntensity), 0.0); + + // all 100%, no real blend, done + if (basegfx::fTools::equal(fStartIntensity, 1.0) && basegfx::fTools::equal(fEndIntensity, 1.0)) + return; + + // blend relative to StopOffset position + for (auto& candidate : *this) + { + const double fOffset(candidate.getStopOffset()); + const double fIntensity((fStartIntensity * (1.0 - fOffset)) + (fEndIntensity * fOffset)); + candidate = basegfx::BColorStop( + fOffset, basegfx::interpolate(rBlendColor, candidate.getStopColor(), fIntensity)); + } +} + +/* Tooling method to guarantee sort and correctness for + the given ColorStops vector. + A vector fulfilling these conditions is called to be + in 'ordered state'. + + At return, the following conditions are guaranteed: + - contains no ColorStops with offset < 0.0 (will + be removed) + - contains no ColorStops with offset > 1.0 (will + be removed) + - ColorStops with identical offsets are now allowed + - will be sorted from lowest offset to highest + + Some more notes: + - It can happen that the result is empty + - It is allowed to have consecutive entries with + the same color, this represents single-color + regions inside the gradient + - A entry with 0.0 is not required or forced, so + no 'StartColor' is technically required + - A entry with 1.0 is not required or forced, so + no 'EndColor' is technically required + + All this is done in one run (sort + O(N)) without + creating a copy of the data in any form + */ +void BColorStops::sortAndCorrect() +{ + // no content, we are done + if (empty()) + return; + + if (1 == size()) + { + // no gradient at all, but preserve given color + // evtl. correct offset to be in valid range [0.0 .. 1.0] + // NOTE: This does not move it to 0.0 or 1.0, it *can* still + // be somewhere in-between what is allowed + const BColorStop aEntry(front()); + clear(); + emplace_back(std::max(0.0, std::min(1.0, aEntry.getStopOffset())), aEntry.getStopColor()); + + // done + return; + } + + // start with sorting the input data. Remember that + // this preserves the order of equal entries, where + // equal is defined here by offset (see use operator==) + std::sort(begin(), end()); + + // prepare status values + size_t write(0); + + // use the paradigm of a band machine with two heads, read + // and write with write <= read all the time. Step over the + // data using read and check for valid entry. If valid, decide + // how to keep it + for (size_t read(0); read < size(); read++) + { + // get offset of entry at read position + double fOff((*this)[read].getStopOffset()); + + if (basegfx::fTools::less(fOff, 0.0) && read + 1 < size()) + { + // value < 0.0 and we have a next entry. check for gradient snippet + // containing 0.0 resp. StartColor + const double fOff2((*this)[read + 1].getStopOffset()); + + if (basegfx::fTools::more(fOff2, 0.0)) + { + // read is the start of a gradient snippet containing 0.0. Correct + // entry to StartColor, interpolate to correct StartColor + (*this)[read] + = BColorStop(0.0, basegfx::interpolate((*this)[read].getStopColor(), + (*this)[read + 1].getStopColor(), + (0.0 - fOff) / (fOff2 - fOff))); + + // adapt fOff + fOff = 0.0; + } + } + + // step over < 0 values, these are outside and will be removed + if (basegfx::fTools::less(fOff, 0.0)) + { + continue; + } + + if (basegfx::fTools::less(fOff, 1.0) && read + 1 < size()) + { + // value < 1.0 and we have a next entry. check for gradient snippet + // containing 1.0 resp. EndColor + const double fOff2((*this)[read + 1].getStopOffset()); + + if (basegfx::fTools::more(fOff2, 1.0)) + { + // read is the start of a gradient snippet containing 1.0. Correct + // next entry to EndColor, interpolate to correct EndColor + (*this)[read + 1] + = BColorStop(1.0, basegfx::interpolate((*this)[read].getStopColor(), + (*this)[read + 1].getStopColor(), + (1.0 - fOff) / (fOff2 - fOff))); + + // adapt fOff + fOff = 1.0; + } + } + + // step over > 1 values; even break, since all following + // entries will also be bigger due to being sorted, so done + if (basegfx::fTools::more(fOff, 1.0)) + { + break; + } + + // entry is valid value at read position + // copy if write target is empty (write at start) or when + // write target is different to read in color or offset + if (0 == write || !((*this)[read] == (*this)[write - 1])) + { + if (write != read) + { + // copy read to write backwards to close gaps + (*this)[write] = (*this)[read]; + } + + // always forward write position + write++; + } + } + + // correct size when length is reduced. write is always at + // last used position + 1 + if (size() > write) + { + if (0 == write) + { + // no valid entries at all, but not empty. This can only happen + // when all entries are below 0.0 or above 1.0 (else a gradient + // snippet spawning over both would have been detected) + if (basegfx::fTools::less(back().getStopOffset(), 0.0)) + { + // all outside too low, rescue last due to being closest to content + const BColor aBackColor(back().getStopColor()); + clear(); + emplace_back(0.0, aBackColor); + } + else // if (basegfx::fTools::more(front().getStopOffset(), 1.0)) + { + // all outside too high, rescue first due to being closest to content + const BColor aFrontColor(front().getStopColor()); + clear(); + emplace_back(1.0, aFrontColor); + } + } + else + { + resize(write); + } + } +} + +bool BColorStops::checkPenultimate() const +{ + // not needed when no ColorStops + if (empty()) + return false; + + // not needed when last ColorStop at the end or outside + if (basegfx::fTools::moreOrEqual(back().getStopOffset(), 1.0)) + return false; + + // get penultimate entry + const auto penultimate(rbegin() + 1); + + // if there is none, we need no correction and are done + if (penultimate == rend()) + return false; + + // not needed when the last two ColorStops have different offset, then + // a visible range will be processed already + if (!basegfx::fTools::equal(back().getStopOffset(), penultimate->getStopOffset())) + return false; + + // not needed when the last two ColorStops have the same Color, then the + // range before solves the problem + if (back().getStopColor() == penultimate->getStopColor()) + return false; + + return true; +} + +/* Tooling method to fill a awt::ColorStopSequence with + the data from the given ColorStops. This is used in + UNO API implementations. + */ +css::awt::ColorStopSequence BColorStops::getAsColorStopSequence() const +{ + css::awt::ColorStopSequence aRetval(size()); + // rColorStopSequence.realloc(rColorStops.size()); + css::awt::ColorStop* pTargetColorStop(aRetval.getArray()); + + for (const auto& candidate : *this) + { + pTargetColorStop->StopOffset = candidate.getStopOffset(); + pTargetColorStop->StopColor = css::rendering::RGBColor(candidate.getStopColor().getRed(), + candidate.getStopColor().getGreen(), + candidate.getStopColor().getBlue()); + pTargetColorStop++; + } + + return aRetval; +} + +/* Tooling method to check if a ColorStop vector is defined + by a single color. It returns true if this is the case. + If true is returned, rSingleColor contains that single + color for convenience. + NOTE: If no ColorStop is defined, a fallback to BColor-default + (which is black) and true will be returned + */ +bool BColorStops::isSingleColor(BColor& rSingleColor) const +{ + if (empty()) + { + rSingleColor = BColor(); + return true; + } + + if (1 == size()) + { + rSingleColor = front().getStopColor(); + return true; + } + + rSingleColor = front().getStopColor(); + + for (auto const& rCandidate : *this) + { + if (rCandidate.getStopColor() != rSingleColor) + return false; + } + + return true; +} + +/* Tooling method to reverse ColorStops, including offsets. + When also mirroring offsets a valid sort keeps valid. + */ +void BColorStops::reverseColorStops() +{ + // can use std::reverse, but also need to adapt offset(s) + std::reverse(begin(), end()); + for (auto& candidate : *this) + candidate = BColorStop(1.0 - candidate.getStopOffset(), candidate.getStopColor()); +} + +std::string BGradient::GradientStyleToString(css::awt::GradientStyle eStyle) +{ + switch (eStyle) + { + case css::awt::GradientStyle::GradientStyle_LINEAR: + return "LINEAR"; + + case css::awt::GradientStyle::GradientStyle_AXIAL: + return "AXIAL"; + + case css::awt::GradientStyle::GradientStyle_RADIAL: + return "RADIAL"; + + case css::awt::GradientStyle::GradientStyle_ELLIPTICAL: + return "ELLIPTICAL"; + + case css::awt::GradientStyle::GradientStyle_SQUARE: + return "SQUARE"; + + case css::awt::GradientStyle::GradientStyle_RECT: + return "RECT"; + + case css::awt::GradientStyle::GradientStyle_MAKE_FIXED_SIZE: + return "MAKE_FIXED_SIZE"; + } + + return ""; +} + +BGradient BGradient::fromJSON(std::u16string_view rJSON) +{ + StringMap aMap(lcl_jsonToStringMap(rJSON)); + return lcl_buildGradientFromStringMap(aMap); +} + +BGradient::BGradient() + : eStyle(css::awt::GradientStyle_LINEAR) + , aColorStops() + , nAngle(0) + , nBorder(0) + , nOfsX(50) + , nOfsY(50) + , nIntensStart(100) + , nIntensEnd(100) + , nStepCount(0) +{ + aColorStops.emplace_back(0.0, BColor(0.0, 0.0, 0.0)); // COL_BLACK + aColorStops.emplace_back(1.0, BColor(1.0, 1.0, 1.0)); // COL_WHITE +} + +BGradient::BGradient(const basegfx::BColorStops& rColorStops, css::awt::GradientStyle eTheStyle, + Degree10 nTheAngle, sal_uInt16 nXOfs, sal_uInt16 nYOfs, sal_uInt16 nTheBorder, + sal_uInt16 nStartIntens, sal_uInt16 nEndIntens, sal_uInt16 nSteps) + : eStyle(eTheStyle) + , aColorStops(rColorStops) + , nAngle(nTheAngle) + , nBorder(nTheBorder) + , nOfsX(nXOfs) + , nOfsY(nYOfs) + , nIntensStart(nStartIntens) + , nIntensEnd(nEndIntens) + , nStepCount(nSteps) +{ + SetColorStops(aColorStops); +} + +BGradient::BGradient(const css::awt::Gradient2& rGradient2) +{ + // set values + SetGradientStyle(rGradient2.Style); + SetAngle(Degree10(rGradient2.Angle)); + SetBorder(rGradient2.Border); + SetXOffset(rGradient2.XOffset); + SetYOffset(rGradient2.YOffset); + SetStartIntens(rGradient2.StartIntensity); + SetEndIntens(rGradient2.EndIntensity); + SetSteps(rGradient2.StepCount); + + // set ColorStops + aColorStops = BColorStops(rGradient2.ColorStops); + aColorStops.sortAndCorrect(); +} + +BGradient::BGradient(const css::uno::Any& rVal) + : BGradient() +{ + if (rVal.has<css::awt::Gradient2>()) + { + // we can use awt::Gradient2 directly + css::awt::Gradient2 aGradient2; + rVal >>= aGradient2; + + // set values + SetGradientStyle(aGradient2.Style); + SetAngle(Degree10(aGradient2.Angle)); + SetBorder(aGradient2.Border); + SetXOffset(aGradient2.XOffset); + SetYOffset(aGradient2.YOffset); + SetStartIntens(aGradient2.StartIntensity); + SetEndIntens(aGradient2.EndIntensity); + SetSteps(aGradient2.StepCount); + + // set ColorStops + aColorStops = BColorStops(aGradient2.ColorStops); + aColorStops.sortAndCorrect(); + } + else if (rVal.has<css::awt::Gradient>()) + { + // use awt::Gradient + css::awt::Gradient aGradient; + rVal >>= aGradient; + + // set values + SetGradientStyle(aGradient.Style); + SetAngle(Degree10(aGradient.Angle)); + SetBorder(aGradient.Border); + SetXOffset(aGradient.XOffset); + SetYOffset(aGradient.YOffset); + SetStartIntens(aGradient.StartIntensity); + SetEndIntens(aGradient.EndIntensity); + SetSteps(aGradient.StepCount); + + // complete data by creating ColorStops from fixe Start/EndColor + aColorStops = BColorStops{ + BColorStop(0.0, ColorToBColorConverter(aGradient.StartColor).getBColor()), + BColorStop(1.0, ColorToBColorConverter(aGradient.EndColor).getBColor()) + }; + } +} + +bool BGradient::operator==(const BGradient& rGradient) const +{ + return (eStyle == rGradient.eStyle && aColorStops == rGradient.aColorStops + && nAngle == rGradient.nAngle && nBorder == rGradient.nBorder + && nOfsX == rGradient.nOfsX && nOfsY == rGradient.nOfsY + && nIntensStart == rGradient.nIntensStart && nIntensEnd == rGradient.nIntensEnd + && nStepCount == rGradient.nStepCount); +} + +void BGradient::SetColorStops(const basegfx::BColorStops& rSteps) +{ + aColorStops = rSteps; + aColorStops.sortAndCorrect(); + if (aColorStops.empty()) + aColorStops.emplace_back(0.0, basegfx::BColor()); +} + +namespace +{ +OUString AsRGBHexString(const ColorToBColorConverter& rVal) +{ + std::stringstream ss; + ss << std::hex << std::setfill('0') << std::setw(6) << sal_uInt32(rVal); + return OUString::createFromAscii(ss.str()); +} +} + +boost::property_tree::ptree BGradient::dumpAsJSON() const +{ + boost::property_tree::ptree aTree; + + aTree.put("style", BGradient::GradientStyleToString(eStyle)); + const ColorToBColorConverter aStart(GetColorStops().front().getStopColor()); + aTree.put("startcolor", AsRGBHexString(aStart.GetRGBColor())); + const ColorToBColorConverter aEnd(GetColorStops().back().getStopColor()); + aTree.put("endcolor", AsRGBHexString(aEnd.GetRGBColor())); + aTree.put("angle", std::to_string(nAngle.get())); + aTree.put("border", std::to_string(nBorder)); + aTree.put("x", std::to_string(nOfsX)); + aTree.put("y", std::to_string(nOfsY)); + aTree.put("intensstart", std::to_string(nIntensStart)); + aTree.put("intensend", std::to_string(nIntensEnd)); + aTree.put("stepcount", std::to_string(nStepCount)); + + return aTree; +} + +css::awt::Gradient2 BGradient::getAsGradient2() const +{ + css::awt::Gradient2 aRetval; + + // standard values + aRetval.Style = GetGradientStyle(); + aRetval.Angle = static_cast<short>(GetAngle()); + aRetval.Border = GetBorder(); + aRetval.XOffset = GetXOffset(); + aRetval.YOffset = GetYOffset(); + aRetval.StartIntensity = GetStartIntens(); + aRetval.EndIntensity = GetEndIntens(); + aRetval.StepCount = GetSteps(); + + // for compatibility, still set StartColor/EndColor + // const basegfx::BColorStops& rColorStops(GetColorStops()); + aRetval.StartColor + = static_cast<sal_Int32>(ColorToBColorConverter(aColorStops.front().getStopColor())); + aRetval.EndColor + = static_cast<sal_Int32>(ColorToBColorConverter(aColorStops.back().getStopColor())); + + // fill ColorStops to extended Gradient2 + aRetval.ColorStops = aColorStops.getAsColorStopSequence(); + // fillColorStopSequenceFromColorStops(rGradient2.ColorStops, rColorStops); + + return aRetval; +} +} + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/basegfx/source/tools/gradienttools.cxx b/basegfx/source/tools/gradienttools.cxx index 372abe08254b..c778a5237676 100644 --- a/basegfx/source/tools/gradienttools.cxx +++ b/basegfx/source/tools/gradienttools.cxx @@ -265,38 +265,6 @@ namespace basegfx namespace utils { - /* Internal helper to convert ::Color from tools::color.hxx to BColor - without the need to link against tools library. Be on the - safe side by using the same union - */ - namespace { - struct ColorToBColorConverter - { - union { - sal_uInt32 mValue; - struct { -#ifdef OSL_BIGENDIAN - sal_uInt8 T; - sal_uInt8 R; - sal_uInt8 G; - sal_uInt8 B; -#else - sal_uInt8 B; - sal_uInt8 G; - sal_uInt8 R; - sal_uInt8 T; -#endif - }; - }; - - ColorToBColorConverter(sal_uInt32 nColor) : mValue(nColor) { T=0; } - BColor getBColor() const - { - return BColor(R / 255.0, G / 255.0, B / 255.0); - } - }; - } - /// Tooling method to fill awt::Gradient2 from data contained in the given Any bool fillGradient2FromAny(css::awt::Gradient2& rGradient, const css::uno::Any& rVal) { @@ -327,11 +295,10 @@ namespace basegfx rGradient.StepCount = aTmp.StepCount; // complete data by creating ColorStops for awt::Gradient2 - fillColorStopSequenceFromColorStops( - rGradient.ColorStops, - ColorStops { - ColorStop(0.0, ColorToBColorConverter(aTmp.StartColor).getBColor()), - ColorStop(1.0, ColorToBColorConverter(aTmp.EndColor).getBColor()) }); + const BColorStops aTempColorStops { + BColorStop(0.0, ColorToBColorConverter(aTmp.StartColor).getBColor()), + BColorStop(1.0, ColorToBColorConverter(aTmp.EndColor).getBColor()) }; + rGradient.ColorStops = aTempColorStops.getAsColorStopSequence(); bRetval = true; } } @@ -355,12 +322,12 @@ namespace basegfx */ void prepareColorStops( const com::sun::star::awt::Gradient2& rGradient, - ColorStops& rColorStops, + BColorStops& rColorStops, BColor& rSingleColor) { - fillColorStopsFromGradient2(rColorStops, rGradient); + rColorStops = BColorStops(rGradient.ColorStops); - if (isSingleColor(rColorStops, rSingleColor)) + if (rColorStops.isSingleColor(rSingleColor)) { // when single color, preserve value in rSingleColor // and clear the ColorStops, done. @@ -371,15 +338,14 @@ namespace basegfx if (rGradient.StartIntensity != 100 || rGradient.EndIntensity != 100) { // apply 'old' blend stuff, blend against black - blendColorStopsToIntensity( - rColorStops, + rColorStops.blendToIntensity( rGradient.StartIntensity * 0.01, rGradient.EndIntensity * 0.01, basegfx::BColor()); // COL_BLACK // can lead to single color (e.g. both zero, so all black), // so check again - if (isSingleColor(rColorStops, rSingleColor)) + if (rColorStops.isSingleColor(rSingleColor)) { rColorStops.clear(); return; @@ -393,7 +359,7 @@ namespace basegfx // mechanism does not need entries at 0.0 and 1.0. // In case this is needed, do that in the caller const double fFactor(rGradient.Border * 0.01); - ColorStops aNewStops; + BColorStops aNewStops; for (const auto& candidate : rColorStops) { @@ -437,8 +403,8 @@ namespace basegfx 'FillTransparenceGradient' method (at import time). */ void synchronizeColorStops( - ColorStops& rColorStops, - ColorStops& rAlphaStops, + BColorStops& rColorStops, + BColorStops& rAlphaStops, const BColor& rSingleColor, const BColor& rSingleAlpha) { @@ -448,12 +414,12 @@ namespace basegfx { // no AlphaStops and no ColorStops // create two-stop fallbacks for both - rColorStops = ColorStops { - ColorStop(0.0, rSingleColor), - ColorStop(1.0, rSingleColor) }; - rAlphaStops = ColorStops { - ColorStop(0.0, rSingleAlpha), - ColorStop(1.0, rSingleAlpha) }; + rColorStops = BColorStops { + BColorStop(0.0, rSingleColor), + BColorStop(1.0, rSingleColor) }; + rAlphaStops = BColorStops { + BColorStop(0.0, rSingleAlpha), + BColorStop(1.0, rSingleAlpha) }; } else { @@ -489,8 +455,8 @@ namespace basegfx if (!bNeedToSyncronize) { // check for same StopOffsets - ColorStops::const_iterator aCurrColor(rColorStops.begin()); - ColorStops::const_iterator aCurrAlpha(rAlphaStops.begin()); + BColorStops::const_iterator aCurrColor(rColorStops.begin()); + BColorStops::const_iterator aCurrAlpha(rAlphaStops.begin()); while (!bNeedToSyncronize && aCurrColor != rColorStops.end() && @@ -511,12 +477,12 @@ namespace basegfx if (bNeedToSyncronize) { // synchronize sizes & StopOffsets - ColorStops::const_iterator aCurrColor(rColorStops.begin()); - ColorStops::const_iterator aCurrAlpha(rAlphaStops.begin()); - ColorStops aNewColor; - ColorStops aNewAlpha; - ColorStopRange aColorStopRange; - ColorStopRange aAlphaStopRange; + BColorStops::const_iterator aCurrColor(rColorStops.begin()); + BColorStops::const_iterator aCurrAlpha(rAlphaStops.begin()); + BColorStops aNewColor; + BColorStops aNewAlpha; + BColorStops::BColorStopRange aColorStopRange; + BColorStops::BColorStopRange aAlphaStopRange; bool bRealChange(false); do { @@ -532,14 +498,14 @@ namespace basegfx { // copy color, create alpha aNewColor.emplace_back(fColorOff, aCurrColor->getStopColor()); - aNewAlpha.emplace_back(fColorOff, utils::modifyBColor(rAlphaStops, fColorOff, 0, aAlphaStopRange)); + aNewAlpha.emplace_back(fColorOff, rAlphaStops.getInterpolatedBColor(fColorOff, 0, aAlphaStopRange)); bRealChange = true; aCurrColor++; } else if (fTools::more(fColorOff, fAlphaOff)) { // copy alpha, create color - aNewColor.emplace_back(fAlphaOff, utils::modifyBColor(rColorStops, fAlphaOff, 0, aColorStopRange)); + aNewColor.emplace_back(fAlphaOff, rColorStops.getInterpolatedBColor(fAlphaOff, 0, aColorStopRange)); aNewAlpha.emplace_back(fAlphaOff, aCurrAlpha->getStopColor()); bRealChange = true; aCurrAlpha++; @@ -556,14 +522,14 @@ namespace basegfx else if (bColor) { const double fColorOff(aCurrColor->getStopOffset()); - aNewAlpha.emplace_back(fColorOff, utils::modifyBColor(rAlphaStops, fColorOff, 0, aAlphaStopRange)); + aNewAlpha.emplace_back(fColorOff, rAlphaStops.getInterpolatedBColor(fColorOff, 0, aAlphaStopRange)); bRealChange = true; aCurrColor++; } else if (bAlpha) { const double fAlphaOff(aCurrAlpha->getStopOffset()); - aNewColor.emplace_back(fAlphaOff, utils::modifyBColor(rColorStops, fAlphaOff, 0, aColorStopRange)); + aNewColor.emplace_back(fAlphaOff, rColorStops.getInterpolatedBColor(fAlphaOff, 0, aColorStopRange)); bRealChange = true; aCurrAlpha++; } @@ -586,467 +552,6 @@ namespace basegfx } } - /* Tooling method to linearly blend the Colors contained in - a given ColorStop vector against a given Color using the - given intensity values. - The intensity values fStartIntensity, fEndIntensity are - in the range of [0.0 .. 1.0] and describe how much the - blend is supposed to be done at the start color position - and the end color position respectively, where 0.0 means - to fully use the given BlendColor, 1.0 means to not change - the existing color in the ColorStop. - Every color entry in the given ColorStop is blended - relative to it's StopPosition, interpolating the - given intensities with the range [0.0 .. 1.0] to do so. - */ - void blendColorStopsToIntensity(ColorStops& rColorStops, double fStartIntensity, double fEndIntensity, const basegfx::BColor& rBlendColor) - { - // no entries, done - if (rColorStops.empty()) - return; - - // correct intensities (maybe assert when input was wrong) - fStartIntensity = std::max(std::min(1.0, fStartIntensity), 0.0); - fEndIntensity = std::max(std::min(1.0, fEndIntensity), 0.0); - - // all 100%, no real blend, done - if (basegfx::fTools::equal(fStartIntensity, 1.0) && basegfx::fTools::equal(fEndIntensity, 1.0)) - return; - - // blend relative to StopOffset position - for (auto& candidate : rColorStops) - { - const double fOffset(candidate.getStopOffset()); - const double fIntensity((fStartIntensity * (1.0 - fOffset)) + (fEndIntensity * fOffset)); - candidate = basegfx::ColorStop( - fOffset, - basegfx::interpolate(rBlendColor, candidate.getStopColor(), fIntensity)); - } - } - - /* Tooling method to check if a ColorStop vector is defined - by a single color. It returns true if this is the case. - If true is returned, rSingleColor contains that single - color for convenience. - NOTE: If no ColorStop is defined, a fallback to BColor-default - (which is black) and true will be returned - */ - bool isSingleColor(const ColorStops& rColorStops, BColor& rSingleColor) - { - if (rColorStops.empty()) - { - rSingleColor = BColor(); - return true; - } - - if (1 == rColorStops.size()) - { - rSingleColor = rColorStops.front().getStopColor(); - return true; - } - - rSingleColor = rColorStops.front().getStopColor(); - - for (auto const& rCandidate : rColorStops) - { - if (rCandidate.getStopColor() != rSingleColor) - return false; - } - - return true; - } - - /* Tooling method to reverse ColorStops, including offsets. - When also mirroring offsets a valid sort keeps valid. - */ - void reverseColorStops(ColorStops& rColorStops) - { - // can use std::reverse, but also need to adapt offset(s) - std::reverse(rColorStops.begin(), rColorStops.end()); - for (auto& candidate : rColorStops) - candidate = ColorStop(1.0 - candidate.getStopOffset(), candidate.getStopColor()); - } - - /* Tooling method to convert UNO API data to ColorStops. - This will try to extract ColorStop data from the given - awt::Gradient2. - */ - void fillColorStopsFromGradient2(ColorStops& rColorStops, const com::sun::star::awt::Gradient2& rGradient) - { - const sal_Int32 nLen(rGradient.ColorStops.getLength()); - - if (0 == nLen) - return; - - // we have ColorStops - rColorStops.clear(); - rColorStops.reserve(nLen); - const css::awt::ColorStop* pSourceColorStop(rGradient.ColorStops.getConstArray()); - - for (sal_Int32 a(0); a < nLen; a++, pSourceColorStop++) - { - rColorStops.emplace_back( - pSourceColorStop->StopOffset, - BColor(pSourceColorStop->StopColor.Red, pSourceColorStop->StopColor.Green, pSourceColorStop->StopColor.Blue)); - } - } - - /* Tooling method to convert UNO API data to ColorStops. - This will try to extract ColorStop data from the given - Any, so if it's of type awt::Gradient2 that data will be - extracted, converted and copied into the given ColorStops. - */ - void fillColorStopsFromAny(ColorStops& rColorStops, const css::uno::Any& rVal) - { - css::awt::Gradient2 aGradient2; - if (!(rVal >>= aGradient2)) - return; - - fillColorStopsFromGradient2(rColorStops, aGradient2); - } - - /* Tooling method to fill a awt::ColorStopSequence with - the data from the given ColorStops. This is used in - UNO API implementations. - */ - void fillColorStopSequenceFromColorStops(css::awt::ColorStopSequence& rColorStopSequence, const ColorStops& rColorStops) - { - // fill ColorStops to extended Gradient2 - rColorStopSequence.realloc(rColorStops.size()); - css::awt::ColorStop* pTargetColorStop(rColorStopSequence.getArray()); - - for (const auto& candidate : rColorStops) - { - pTargetColorStop->StopOffset = candidate.getStopOffset(); - pTargetColorStop->StopColor = css::rendering::RGBColor( - candidate.getStopColor().getRed(), - candidate.getStopColor().getGreen(), - candidate.getStopColor().getBlue()); - pTargetColorStop++; - } - } - - /* Tooling method that allows to replace the StartColor in a - vector of ColorStops. A vector in 'ordered state' is expected, - so you may use/have used sortAndCorrectColorStops, see below. - This method is for convenience & backwards compatibility, please - think about handling multi-colored gradients directly. - */ - void replaceStartColor(ColorStops& rColorStops, const BColor& rStart) - { - ColorStops::iterator a1stNonStartColor(rColorStops.begin()); - - // search for highest existing non-StartColor - while (a1stNonStartColor != rColorStops.end() && basegfx::fTools::lessOrEqual(a1stNonStartColor->getStopOffset(), 0.0)) - a1stNonStartColor++; - - // create new ColorStops by 1st adding new one and then all - // non-StartColor entries - ColorStops aNewColorStops; - - aNewColorStops.reserve(rColorStops.size() + 1); - aNewColorStops.emplace_back(0.0, rStart); - aNewColorStops.insert(aNewColorStops.end(), a1stNonStartColor, rColorStops.end()); - - // assign & done - rColorStops = aNewColorStops; - } - - /* Tooling method that allows to replace the EndColor in a - vector of ColorStops. A vector in 'ordered state' is expected, - so you may use/have used sortAndCorrectColorStops, see below. - This method is for convenience & backwards compatibility, please - think about handling multi-colored gradients directly. - */ - void replaceEndColor(ColorStops& rColorStops, const BColor& rEnd) - { - // erase all evtl. existing EndColor(s) - while (!rColorStops.empty() && basegfx::fTools::moreOrEqual(rColorStops.back().getStopOffset(), 1.0)) - rColorStops.pop_back(); - - // add at the end of existing ColorStops - rColorStops.emplace_back(1.0, rEnd); - } - - // Tooling method to quickly create a ColorStop vector for a given set of Start/EndColor - ColorStops createColorStopsFromStartEndColor(const BColor& rStart, const BColor& rEnd) - { - return ColorStops { - ColorStop(0.0, rStart), - ColorStop(1.0, rEnd) }; - } - - /* Tooling method to guarantee sort and correctness for - the given ColorStops vector. - A vector fulfilling these conditions is called to be - in 'ordered state'. - - At return, the following conditions are guaranteed: - - contains no ColorStops with offset < 0.0 (will - be removed) - - contains no ColorStops with offset > 1.0 (will - be removed) - - ColorStops with identical offsets are now allowed - - will be sorted from lowest offset to highest - - Some more notes: - - It can happen that the result is empty - - It is allowed to have consecutive entries with - the same color, this represents single-color - regions inside the gradient - - A entry with 0.0 is not required or forced, so - no 'StartColor' is technically required - - A entry with 1.0 is not required or forced, so - no 'EndColor' is technically required - - All this is done in one run (sort + O(N)) without - creating a copy of the data in any form - */ - void sortAndCorrectColorStops(ColorStops& rColorStops) - { - // no content, we are done - if (rColorStops.empty()) - return; - - if (1 == rColorStops.size()) - { - // no gradient at all, but preserve given color - // evtl. correct offset to be in valid range [0.0 .. 1.0] - // NOTE: This does not move it to 0.0 or 1.0, it *can* still - // be somewhere in-between what is allowed - rColorStops[0] = ColorStop( - std::max(0.0, std::min(1.0, rColorStops[0].getStopOffset())), - rColorStops[0].getStopColor()); - - // done - return; - } - - // start with sorting the input data. Remember that - // this preserves the order of equal entries, where - // equal is defined here by offset (see use operator==) - std::sort(rColorStops.begin(), rColorStops.end()); - - // prepare status values - size_t write(0); - - // use the paradigm of a band machine with two heads, read - // and write with write <= read all the time. Step over the - // data using read and check for valid entry. If valid, decide - // how to keep it - for (size_t read(0); read < rColorStops.size(); read++) - { - // get offset of entry at read position - double fOff(rColorStops[read].getStopOffset()); - - if (basegfx::fTools::less(fOff, 0.0) && read + 1 < rColorStops.size()) - { - // value < 0.0 and we have a next entry. check for gradient snippet - // containing 0.0 resp. StartColor - const double fOff2(rColorStops[read + 1].getStopOffset()); - - if (basegfx::fTools::more(fOff2, 0.0)) - { - // read is the start of a gradient snippet containing 0.0. Correct - // entry to StartColor, interpolate to correct StartColor - rColorStops[read] = ColorStop(0.0, basegfx::interpolate( - rColorStops[read].getStopColor(), - rColorStops[read + 1].getStopColor(), - (0.0 - fOff) / (fOff2 - fOff))); - - // adapt fOff - fOff = 0.0; - } - } - - // step over < 0 values, these are outside and will be removed - if (basegfx::fTools::less(fOff, 0.0)) - { - continue; - } - - if (basegfx::fTools::less(fOff, 1.0) && read + 1 < rColorStops.size()) - { - // value < 1.0 and we have a next entry. check for gradient snippet - // containing 1.0 resp. EndColor - const double fOff2(rColorStops[read + 1].getStopOffset()); - - if (basegfx::fTools::more(fOff2, 1.0)) - { - // read is the start of a gradient snippet containing 1.0. Correct - // next entry to EndColor, interpolate to correct EndColor - rColorStops[read + 1] = ColorStop(1.0, basegfx::interpolate( - rColorStops[read].getStopColor(), - rColorStops[read + 1].getStopColor(), - (1.0 - fOff) / (fOff2 - fOff))); - - // adapt fOff - fOff = 1.0; - } - } - - // step over > 1 values; even break, since all following - // entries will also be bigger due to being sorted, so done - if (basegfx::fTools::more(fOff, 1.0)) - { - break; - } - - // entry is valid value at read position - // copy if write target is empty (write at start) or when - // write target is different to read in color or offset - if (0 == write || !(rColorStops[read] == rColorStops[write-1])) - { - if (write != read) - { - // copy read to write backwards to close gaps - rColorStops[write] = rColorStops[read]; - } - - // always forward write position - write++; - } - } - - // correct size when length is reduced. write is always at - // last used position + 1 - if (rColorStops.size() > write) - { - if (0 == write) - { - // no valid entries at all, but not empty. This can only happen - // when all entries are below 0.0 or above 1.0 (else a gradient - // snippet spawning over both would have been detected) - if (basegfx::fTools::less(rColorStops.back().getStopOffset(), 0.0)) - { - // all outside too low, rescue last due to being closest to content - rColorStops = ColorStops { ColorStop(0.0, rColorStops.back().getStopColor()) }; - } - else // if (basegfx::fTools::more(rColorStops.front().getStopOffset(), 1.0)) - { - // all outside too high, rescue first due to being closest to content - rColorStops = ColorStops { ColorStop(1.0, rColorStops.front().getStopColor()) }; - } - } - else - { - rColorStops.resize(write); - } - } - } - - BColor modifyBColor( - const ColorStops& rColorStops, - double fScaler, - sal_uInt32 nRequestedSteps, - ColorStopRange& rLastColorStopRange) - { - // no color at all, done - if (rColorStops.empty()) - return BColor(); - - // outside range -> at start - const double fMin(rColorStops.front().getStopOffset()); - if (fScaler < fMin) - return rColorStops.front().getStopColor(); - - // outside range -> at end - const double fMax(rColorStops.back().getStopOffset()); - if (fScaler > fMax) - return rColorStops.back().getStopColor(); - - // special case for the 'classic' case with just two colors: - // we can optimize that and keep the speed/resources low - // by avoiding some calculations and an O(log(N)) array access - if (2 == rColorStops.size()) - { - if (fTools::equal(fMin, fMax)) - return rColorStops.front().getStopColor(); - - const basegfx::BColor aCStart(rColorStops.front().getStopColor()); - const basegfx::BColor aCEnd(rColorStops.back().getStopColor()); - const sal_uInt32 nSteps( - calculateNumberOfSteps( - nRequestedSteps, - aCStart, - aCEnd)); - - // we need to extend the interpolation to the local - // range of ColorStops. Despite having two ColorStops - // these are not necessarily at 0.0 and 1.0, so may be - // not the classical Start/EndColor (what is allowed) - fScaler = (fScaler - fMin) / (fMax - fMin); - return basegfx::interpolate( - aCStart, - aCEnd, - nSteps > 1 ? floor(fScaler * nSteps) / double(nSteps - 1) : fScaler); - } - - // check if we need to newly populate the needed interpolation data - // or if we can re-use from last time. - // If this scope is not entered, we do not need the binary search. It's - // only a single buffered entry, and only used when more than three - // ColorStops exist, but makes a huge difference compared with accessing - // the sorted ColorStop vector each time. - // NOTE: with this simple change I get very high hit rates, e.g. rotating - // a donut with gradient test '1' hit rate is at 0.99909440357755486 - if (rLastColorStopRange.mfOffsetStart == rLastColorStopRange.mfOffsetEnd - || fScaler < rLastColorStopRange.mfOffsetStart - || fScaler > rLastColorStopRange.mfOffsetEnd) - { - // access needed spot in sorted array using binary search - // NOTE: This *seems* slow(er) when developing compared to just - // looping/accessing, but that's just due to the extensive - // debug test code created by the stl. In a pro version, - // all is good/fast as expected - const auto upperBound( - std::upper_bound( - rColorStops.begin(), - rColorStops.end(), - ColorStop(fScaler), - [](const ColorStop& x, const ColorStop& y) { return x.getStopOffset() < y.getStopOffset(); })); - - // no upper bound, done - if (rColorStops.end() == upperBound) - return rColorStops.back().getStopColor(); - - // lower bound is one entry back, access that - const auto lowerBound(upperBound - 1); - - // no lower bound, done - if (rColorStops.end() == lowerBound) - return rColorStops.back().getStopColor(); - - // we have lower and upper bound, get colors and offsets - rLastColorStopRange.maColorStart = lowerBound->getStopColor(); - rLastColorStopRange.maColorEnd = upperBound->getStopColor(); - rLastColorStopRange.mfOffsetStart = lowerBound->getStopOffset(); - rLastColorStopRange.mfOffsetEnd = upperBound->getStopOffset(); - } - - // when there are just two color steps this cannot happen, but when using - // a range of colors this *may* be used inside the range to represent - // single-colored regions inside a ColorRange. Use that color & done - if (rLastColorStopRange.maColorStart == rLastColorStopRange.maColorEnd) - return rLastColorStopRange.maColorStart; - - // calculate number of steps and adapted proportional - // range for scaler in [0.0 .. 1.0] - const double fAdaptedScaler((fScaler - rLastColorStopRange.mfOffsetStart) / - (rLastColorStopRange.mfOffsetEnd - rLastColorStopRange.mfOffsetStart)); - const sal_uInt32 nSteps( - calculateNumberOfSteps( - nRequestedSteps, - rLastColorStopRange.maColorStart, - rLastColorStopRange.maColorEnd)); - - // interpolate & evtl. apply steps - return interpolate( - rLastColorStopRange.maColorStart, - rLastColorStopRange.maColorEnd, - nSteps > 1 ? floor(fAdaptedScaler * nSteps) / double(nSteps - 1) : fAdaptedScaler); - } - sal_uInt32 calculateNumberOfSteps( sal_uInt32 nRequestedSteps, const BColor& rStart, diff --git a/chart2/inc/pch/precompiled_chartcontroller.hxx b/chart2/inc/pch/precompiled_chartcontroller.hxx index 6839b807696d..ba4ccbddf15e 100644 --- a/chart2/inc/pch/precompiled_chartcontroller.hxx +++ b/chart2/inc/pch/precompiled_chartcontroller.hxx @@ -409,7 +409,6 @@ #include <svx/svxdllapi.h> #include <svx/xdash.hxx> #include <svx/xdef.hxx> -#include <svx/xgrad.hxx> #include <svx/xhatch.hxx> #include <svx/xit.hxx> #include <svx/xpoly.hxx> diff --git a/chart2/qa/extras/chart2import.cxx b/chart2/qa/extras/chart2import.cxx index fc5caf42c3a7..890841a79849 100644 --- a/chart2/qa/extras/chart2import.cxx +++ b/chart2/qa/extras/chart2import.cxx @@ -628,9 +628,7 @@ CPPUNIT_TEST_FIXTURE(Chart2ImportTest, testBnc889755) uno::Reference<beans::XPropertySet> xShapeProps(xPage->getByIndex(4), uno::UNO_QUERY_THROW); awt::Gradient2 aTransparence; xShapeProps->getPropertyValue("FillTransparenceGradient") >>= aTransparence; - - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aTransparence); + const basegfx::BColorStops aColorStops(aTransparence.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(3), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); @@ -673,9 +671,7 @@ CPPUNIT_TEST_FIXTURE(Chart2ImportTest, testTransparencyGradientValue) uno::Reference< container::XNameAccess > xTransparenceGradient(xFact->createInstance("com.sun.star.drawing.TransparencyGradientTable"), uno::UNO_QUERY); uno::Any rTransparenceValue = xTransparenceGradient->getByName(sTranspGradientName); CPPUNIT_ASSERT(rTransparenceValue >>= aTransparenceGradient); - - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aTransparenceGradient); + const basegfx::BColorStops aColorStops(aTransparenceGradient.ColorStops); // MCGR: Use the whole completely imported transparency gradient to check for correctness CPPUNIT_ASSERT_EQUAL(size_t(2), aColorStops.size()); diff --git a/chart2/source/controller/main/ChartController_Tools.cxx b/chart2/source/controller/main/ChartController_Tools.cxx index acc5dd950391..1a8f5071982f 100644 --- a/chart2/source/controller/main/ChartController_Tools.cxx +++ b/chart2/source/controller/main/ChartController_Tools.cxx @@ -74,7 +74,6 @@ #include <svx/unoapi.hxx> #include <svx/unopage.hxx> #include <svx/unoshape.hxx> -#include <svx/xgrad.hxx> #include <PropertyHelper.hxx> #include <LibreOfficeKit/LibreOfficeKitEnums.h> @@ -957,8 +956,8 @@ void ChartController::executeDispatch_FillColor(sal_uInt32 nColor) void ChartController::executeDispatch_FillGradient(std::u16string_view sJSONGradient) { - XGradient aXGradient = XGradient::fromJSON(sJSONGradient); - css::awt::Gradient aGradient = aXGradient.toGradientUNO(); + basegfx::BGradient aBGradient = basegfx::BGradient::fromJSON(sJSONGradient); + css::awt::Gradient aGradient = aBGradient.getAsGradient2(); try { @@ -973,9 +972,9 @@ void ChartController::executeDispatch_FillGradient(std::u16string_view sJSONGrad if( xPropSet.is() ) { OUString aPrefferedName = - OUString::number(static_cast<sal_Int32>(Color(aXGradient.GetColorStops().front().getStopColor()))) - + OUString::number(static_cast<sal_Int32>(Color(aXGradient.GetColorStops().back().getStopColor()))) - + OUString::number(static_cast<sal_Int32>(aXGradient.GetAngle().get())); + OUString::number(static_cast<sal_Int32>(Color(aBGradient.GetColorStops().front().getStopColor()))) + + OUString::number(static_cast<sal_Int32>(Color(aBGradient.GetColorStops().back().getStopColor()))) + + OUString::number(static_cast<sal_Int32>(aBGradient.GetAngle().get())); OUString aNewName = PropertyHelper::addGradientUniqueNameToTable(css::uno::Any(aGradient), xChartModel, diff --git a/cui/source/inc/cuitabarea.hxx b/cui/source/inc/cuitabarea.hxx index 2db104f53c8c..64ec01ef5abf 100644 --- a/cui/source/inc/cuitabarea.hxx +++ b/cui/source/inc/cuitabarea.hxx @@ -170,7 +170,7 @@ class SvxTransparenceTabPage : public SfxTabPage std::unique_ptr<weld::CustomWeld> m_xCtlXRectPreview; // MCGR: Preserve in-between ColorStops until we have an UI to edit these - basegfx::ColorStops maColorStops; + basegfx::BColorStops maColorStops; DECL_LINK(ClickTransOffHdl_Impl, weld::Toggleable&, void); DECL_LINK(ClickTransLinearHdl_Impl, weld::Toggleable&, void); @@ -188,7 +188,7 @@ class SvxTransparenceTabPage : public SfxTabPage void InvalidatePreview (bool bEnable = true ); // MCGR: Preserve in-between ColorStops until we have an UI to edit these - basegfx::ColorStops createColorStops(); + basegfx::BColorStops createColorStops(); public: SvxTransparenceTabPage(weld::Container* pPage, weld::DialogController* pController, const SfxItemSet& rInAttrs); @@ -368,7 +368,7 @@ private: SfxItemSet& m_rXFSet; // MCGR: Preserve in-between ColorStops until we have an UI to edit these - basegfx::ColorStops m_aColorStops; + basegfx::BColorStops m_aColorStops; SvxXRectPreview m_aCtlPreview; std::unique_ptr<weld::ComboBox> m_xLbGradientType; @@ -410,7 +410,7 @@ private: sal_Int32 SearchGradientList(std::u16string_view rGradientName); // MCGR: Preserve in-between ColorStops until we have an UI to edit these - basegfx::ColorStops createColorStops(); + basegfx::BColorStops createColorStops(); public: SvxGradientTabPage(weld::Container* pPage, weld::DialogController* pController, const SfxItemSet& rInAttrs); diff --git a/cui/source/tabpages/tpgradnt.cxx b/cui/source/tabpages/tpgradnt.cxx index 57eed4dd4ce5..7f6630747a42 100644 --- a/cui/source/tabpages/tpgradnt.cxx +++ b/cui/source/tabpages/tpgradnt.cxx @@ -84,8 +84,7 @@ SvxGradientTabPage::SvxGradientTabPage(weld::Container* pPage, weld::DialogContr // setting the output device m_rXFSet.Put( XFillStyleItem(drawing::FillStyle_GRADIENT) ); - // XGradient() default already creates [COL_BLACK, COL_WHITE] as defaults - m_rXFSet.Put( XFillGradientItem(OUString(), XGradient())); + m_rXFSet.Put( XFillGradientItem(OUString(), basegfx::BGradient())); m_aCtlPreview.SetAttributes(m_aXFillAttr.GetItemSet()); // set handler @@ -185,18 +184,18 @@ DeactivateRC SvxGradientTabPage::DeactivatePage( SfxItemSet* _pSet ) bool SvxGradientTabPage::FillItemSet( SfxItemSet* rSet ) { - std::unique_ptr<XGradient> pXGradient; + std::unique_ptr<basegfx::BGradient> pBGradient; size_t nPos = m_xGradientLB->IsNoSelection() ? VALUESET_ITEM_NOTFOUND : m_xGradientLB->GetSelectItemPos(); if( nPos != VALUESET_ITEM_NOTFOUND ) { - pXGradient.reset(new XGradient( m_pGradientList->GetGradient( static_cast<sal_uInt16>(nPos) )->GetGradient() )); + pBGradient.reset(new basegfx::BGradient( m_pGradientList->GetGradient( static_cast<sal_uInt16>(nPos) )->GetGradient() )); OUString aString = m_xGradientLB->GetItemText( m_xGradientLB->GetSelectedItemId() ); - rSet->Put( XFillGradientItem( aString, *pXGradient ) ); + rSet->Put( XFillGradientItem( aString, *pBGradient ) ); } else // gradient was passed (unidentified) { - pXGradient.reset(new XGradient( + pBGradient.reset(new basegfx::BGradient( createColorStops(), static_cast<css::awt::GradientStyle>(m_xLbGradientType->get_active()), Degree10(static_cast<sal_Int16>(m_xMtrAngle->get_value(FieldUnit::NONE) * 10)), // should be changed in resource @@ -206,14 +205,14 @@ bool SvxGradientTabPage::FillItemSet( SfxItemSet* rSet ) static_cast<sal_uInt16>(m_xMtrColorFrom->get_value(FieldUnit::NONE)), static_cast<sal_uInt16>(m_xMtrColorTo->get_value(FieldUnit::NONE)), static_cast<sal_uInt16>(m_xMtrIncrement->get_value()) )); - rSet->Put( XFillGradientItem( OUString(), *pXGradient ) ); + rSet->Put( XFillGradientItem( OUString(), *pBGradient ) ); } sal_uInt16 nValue = 0; if (!m_xCbIncrement->get_active()) nValue = m_xMtrIncrement->get_value(); - assert( pXGradient && "XGradient could not be created" ); + assert( pBGradient && "basegfx::BGradient could not be created" ); rSet->Put( XFillStyleItem( drawing::FillStyle_GRADIENT ) ); rSet->Put( XGradientStepCountItem( nValue ) ); return true; @@ -294,7 +293,7 @@ void SvxGradientTabPage::ModifiedHdl_Impl( void const * pControl ) css::awt::GradientStyle eXGS = static_cast<css::awt::GradientStyle>(m_xLbGradientType->get_active()); - XGradient aXGradient( + basegfx::BGradient aBGradient( createColorStops(), eXGS, Degree10(static_cast<sal_Int16>(m_xMtrAngle->get_value(FieldUnit::NONE) * 10)), // should be changed in resource @@ -315,7 +314,7 @@ void SvxGradientTabPage::ModifiedHdl_Impl( void const * pControl ) m_rXFSet.Put( XGradientStepCountItem( nValue ) ); // displaying in XOutDev - m_rXFSet.Put( XFillGradientItem( OUString(), aXGradient ) ); + m_rXFSet.Put( XFillGradientItem( OUString(), aBGradient ) ); m_aCtlPreview.SetAttributes(m_aXFillAttr.GetItemSet()); m_aCtlPreview.Invalidate(); } @@ -361,7 +360,7 @@ IMPL_LINK_NOARG(SvxGradientTabPage, ClickAddHdl_Impl, weld::Button&, void) if( !nError ) { - XGradient aXGradient( + basegfx::BGradient aBGradient( createColorStops(), static_cast<css::awt::GradientStyle>(m_xLbGradientType->get_active()), Degree10(static_cast<sal_Int16>(m_xMtrAngle->get_value(FieldUnit::NONE) * 10)), // should be changed in resource @@ -372,7 +371,7 @@ IMPL_LINK_NOARG(SvxGradientTabPage, ClickAddHdl_Impl, weld::Button&, void) static_cast<sal_uInt16>(m_xMtrColorTo->get_value(FieldUnit::NONE)), static_cast<sal_uInt16>(m_xMtrIncrement->get_value()) ); - m_pGradientList->Insert(std::make_unique<XGradientEntry>(aXGradient, aName), nCount); + m_pGradientList->Insert(std::make_unique<XGradientEntry>(aBGradient, aName), nCount); sal_Int32 nId = m_xGradientLB->GetItemId(nCount - 1); //calculate the last ID BitmapEx aBitmap = m_pGradientList->GetBitmapForPreview( nCount, m_xGradientLB->GetIconSize() ); @@ -401,7 +400,7 @@ IMPL_LINK_NOARG(SvxGradientTabPage, ClickModifyHdl_Impl, weld::Button&, void) OUString aName( m_pGradientList->GetGradient( static_cast<sal_uInt16>(nPos) )->GetName() ); - XGradient aXGradient( + basegfx::BGradient aBGradient( createColorStops(), static_cast<css::awt::GradientStyle>(m_xLbGradientType->get_active()), Degree10(static_cast<sal_Int16>(m_xMtrAngle->get_value(FieldUnit::NONE) * 10)), // should be changed in resource @@ -412,7 +411,7 @@ IMPL_LINK_NOARG(SvxGradientTabPage, ClickModifyHdl_Impl, weld::Button&, void) static_cast<sal_uInt16>(m_xMtrColorTo->get_value(FieldUnit::NONE)), static_cast<sal_uInt16>(m_xMtrIncrement->get_value()) ); - m_pGradientList->Replace(std::make_unique<XGradientEntry>(aXGradient, aName), nPos); + m_pGradientList->Replace(std::make_unique<XGradientEntry>(aBGradient, aName), nPos); BitmapEx aBitmap = m_pGradientList->GetBitmapForPreview( static_cast<sal_uInt16>(nPos), m_xGradientLB->GetIconSize() ); m_xGradientLB->RemoveItem( nId ); @@ -498,11 +497,11 @@ IMPL_LINK_NOARG(SvxGradientTabPage, ChangeGradientHdl, ValueSet*, void) void SvxGradientTabPage::ChangeGradientHdl_Impl() { - std::unique_ptr<XGradient> pGradient; + std::unique_ptr<basegfx::BGradient> pGradient; size_t nPos = m_xGradientLB->GetSelectItemPos(); if( nPos != VALUESET_ITEM_NOTFOUND ) - pGradient.reset(new XGradient( m_pGradientList->GetGradient( static_cast<sal_uInt16>( nPos ) )->GetGradient() )); + pGradient.reset(new basegfx::BGradient( m_pGradientList->GetGradient( static_cast<sal_uInt16>( nPos ) )->GetGradient() )); else { if( const XFillStyleItem* pFillStyleItem = m_rOutAttrs.GetItemIfSet( GetWhich( XATTR_FILLSTYLE ) ) ) @@ -511,7 +510,7 @@ void SvxGradientTabPage::ChangeGradientHdl_Impl() if( ( drawing::FillStyle_GRADIENT == pFillStyleItem->GetValue() ) && ( pGradientItem = m_rOutAttrs.GetItemIfSet( GetWhich( XATTR_FILLGRADIENT ) ) ) ) { - pGradient.reset(new XGradient( pGradientItem->GetGradientValue() )); + pGradient.reset(new basegfx::BGradient( pGradientItem->GetGradientValue() )); } } if( !pGradient ) @@ -519,7 +518,7 @@ void SvxGradientTabPage::ChangeGradientHdl_Impl() sal_uInt16 nPosition = m_xGradientLB->GetItemId(0); m_xGradientLB->SelectItem( nPosition ); if( nPosition != 0 ) - pGradient.reset(new XGradient( m_pGradientList->GetGradient( 0 )->GetGradient() )); + pGradient.reset(new basegfx::BGradient( m_pGradientList->GetGradient( 0 )->GetGradient() )); } } @@ -551,7 +550,7 @@ void SvxGradientTabPage::ChangeGradientHdl_Impl() // MCGR: preserve in-between ColorStops if given if (pGradient->GetColorStops().size() > 2) - m_aColorStops = basegfx::ColorStops(pGradient->GetColorStops().begin() + 1, pGradient->GetColorStops().end() - 1); + m_aColorStops = basegfx::BColorStops(pGradient->GetColorStops().begin() + 1, pGradient->GetColorStops().end() - 1); else m_aColorStops.clear(); @@ -638,9 +637,9 @@ sal_Int32 SvxGradientTabPage::SearchGradientList(std::u16string_view rGradientNa return nPos; } -basegfx::ColorStops SvxGradientTabPage::createColorStops() +basegfx::BColorStops SvxGradientTabPage::createColorStops() { - basegfx::ColorStops aColorStops; + basegfx::BColorStops aColorStops; aColorStops.emplace_back(0.0, m_xLbColorFrom->GetSelectEntryColor().getBColor()); diff --git a/cui/source/tabpages/tptrans.cxx b/cui/source/tabpages/tptrans.cxx index ef604e6470d5..ce77d61d2fc7 100644 --- a/cui/source/tabpages/tptrans.cxx +++ b/cui/source/tabpages/tptrans.cxx @@ -119,7 +119,7 @@ void SvxTransparenceTabPage::ModifiedTrgrHdl_Impl(const weld::ComboBox* pControl } // preview - XGradient aTmpGradient( + basegfx::BGradient aTmpGradient( createColorStops(), static_cast<css::awt::GradientStyle>(m_xLbTrgrGradientType->get_active()), Degree10(static_cast<sal_Int16>(m_xMtrTrgrAngle->get_value(FieldUnit::DEGREE)) * 10), @@ -287,7 +287,7 @@ bool SvxTransparenceTabPage::FillItemSet(SfxItemSet* rAttrs) || m_xMtrTrgrStartValue->get_value_changed_from_saved() || m_xMtrTrgrEndValue->get_value_changed_from_saved()) { - XGradient aTmpGradient( + basegfx::BGradient aTmpGradient( createColorStops(), static_cast<css::awt::GradientStyle>(m_xLbTrgrGradientType->get_active()), Degree10(static_cast<sal_Int16>(m_xMtrTrgrAngle->get_value(FieldUnit::DEGREE)) * 10), @@ -317,9 +317,9 @@ bool SvxTransparenceTabPage::FillItemSet(SfxItemSet* rAttrs) // disable unused XFillFloatTransparenceItem if(bSwitchOffGradient && (bGradActive || bGradUsed)) { - // XGradient() default already creates [COL_BLACK, COL_WHITE] with same defaults - // XGradient() default also sets the Start/EndIntensity to 100 already - XGradient aGrad; + // basegfx::BGradient() default already creates [COL_BLACK, COL_WHITE] with same defaults + // basegfx::BGradient() default also sets the Start/EndIntensity to 100 already + basegfx::BGradient aGrad; XFillFloatTransparenceItem aItem(aGrad); aItem.SetEnabled(false); @@ -355,7 +355,7 @@ void SvxTransparenceTabPage::Reset(const SfxItemSet* rAttrs) pLinearItem = &rAttrs->Get(XATTR_FILLTRANSPARENCE); // transparence gradient - const XGradient& rGradient = pGradientItem->GetGradientValue(); + const basegfx::BGradient& rGradient = pGradientItem->GetGradientValue(); css::awt::GradientStyle eXGS(rGradient.GetGradientStyle()); m_xLbTrgrGradientType->set_active(sal::static_int_cast< sal_Int32 >(eXGS)); m_xMtrTrgrAngle->set_value(rGradient.GetAngle().get() / 10, FieldUnit::DEGREE); @@ -369,7 +369,7 @@ void SvxTransparenceTabPage::Reset(const SfxItemSet* rAttrs) // MCGR: preserve in-between ColorStops if given if (rGradient.GetColorStops().size() > 2) - maColorStops = basegfx::ColorStops(rGradient.GetColorStops().begin() + 1, rGradient.GetColorStops().end() - 1); + maColorStops = basegfx::BColorStops(rGradient.GetColorStops().begin() + 1, rGradient.GetColorStops().end() - 1); else maColorStops.clear(); @@ -508,9 +508,9 @@ void SvxTransparenceTabPage::InvalidatePreview (bool bEnable) } } -basegfx::ColorStops SvxTransparenceTabPage::createColorStops() +basegfx::BColorStops SvxTransparenceTabPage::createColorStops() { - basegfx::ColorStops aColorStops; + basegfx::BColorStops aColorStops; const sal_uInt8 nStartCol(static_cast<sal_uInt8>((static_cast<sal_uInt16>(m_xMtrTrgrStartValue->get_value(FieldUnit::PERCENT)) * 255) / 100)); const sal_uInt8 nEndCol(static_cast<sal_uInt8>((static_cast<sal_uInt16>(m_xMtrTrgrEndValue->get_value(FieldUnit::PERCENT)) * 255) / 100)); diff --git a/drawinglayer/inc/texture/texture.hxx b/drawinglayer/inc/texture/texture.hxx index 01d3ec5c64c5..5128a30cf2a8 100644 --- a/drawinglayer/inc/texture/texture.hxx +++ b/drawinglayer/inc/texture/texture.hxx @@ -49,21 +49,18 @@ namespace drawinglayer::texture basegfx::ODFGradientInfo maGradientInfo; basegfx::B2DRange maDefinitionRange; sal_uInt32 mnRequestedSteps; - basegfx::ColorStops mnColorStops; + basegfx::BColorStops mnColorStops; double mfBorder; // provide a single buffer entry used for gradient texture // mapping, see ::modifyBColor implementations - mutable basegfx::ColorStopRange maLastColorStopRange; - - // check if we need last-ColorStop-correction - bool checkPenultimate(); + mutable basegfx::BColorStops::BColorStopRange maLastColorStopRange; public: GeoTexSvxGradient( const basegfx::B2DRange& rDefinitionRange, sal_uInt32 nRequestedSteps, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, double fBorder); virtual ~GeoTexSvxGradient() override; @@ -86,7 +83,7 @@ namespace drawinglayer::texture const basegfx::B2DRange& rDefinitionRange, const basegfx::B2DRange& rOutputRange, sal_uInt32 nRequestedSteps, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, double fBorder, double fAngle); virtual ~GeoTexSvxGradientLinear() override; @@ -106,7 +103,7 @@ namespace drawinglayer::texture const basegfx::B2DRange& rDefinitionRange, const basegfx::B2DRange& rOutputRange, sal_uInt32 nRequestedSteps, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, double fBorder, double fAngle); virtual ~GeoTexSvxGradientAxial() override; @@ -122,7 +119,7 @@ namespace drawinglayer::texture GeoTexSvxGradientRadial( const basegfx::B2DRange& rDefinitionRange, sal_uInt32 nRequestedSteps, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, double fBorder, double fOffsetX, double fOffsetY); @@ -139,7 +136,7 @@ namespace drawinglayer::texture GeoTexSvxGradientElliptical( const basegfx::B2DRange& rDefinitionRange, sal_uInt32 nRequestedSteps, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, double fBorder, double fOffsetX, double fOffsetY, @@ -157,7 +154,7 @@ namespace drawinglayer::texture GeoTexSvxGradientSquare( const basegfx::B2DRange& rDefinitionRange, sal_uInt32 nRequestedSteps, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, double fBorder, double fOffsetX, double fOffsetY, @@ -175,7 +172,7 @@ namespace drawinglayer::texture GeoTexSvxGradientRect( const basegfx::B2DRange& rDefinitionRange, sal_uInt32 nRequestedSteps, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, double fBorder, double fOffsetX, double fOffsetY, diff --git a/drawinglayer/qa/unit/vclpixelprocessor2d.cxx b/drawinglayer/qa/unit/vclpixelprocessor2d.cxx index 6ccf1e7c55ab..7f59e7e3edd0 100644 --- a/drawinglayer/qa/unit/vclpixelprocessor2d.cxx +++ b/drawinglayer/qa/unit/vclpixelprocessor2d.cxx @@ -16,8 +16,10 @@ #include <tools/stream.hxx> #include <drawinglayer/geometry/viewinformation2d.hxx> #include <drawinglayer/primitive2d/fillgradientprimitive2d.hxx> +#include <drawinglayer/primitive2d/maskprimitive2d.hxx> #include <drawinglayer/processor2d/baseprocessor2d.hxx> #include <drawinglayer/processor2d/processor2dtools.hxx> +#include <basegfx/polygon/b2dpolygontools.hxx> #include <basegfx/utils/gradienttools.hxx> using namespace drawinglayer; @@ -58,16 +60,59 @@ public: processor2d::createProcessor2DFromOutputDevice(*device, view)); CPPUNIT_ASSERT(processor); + // I stumbled over this when hunting another problem, but I have to correct + // this: This test does test something that is not supported. It seems to be + // based on the *misunderstanding* that in the version of the constructor of + // FillGradientPrimitive2D (and similar others) with two ranges the 2nd + // B2DRange parameter 'OutputRange' is a 'clipping' parameter. This is *not* + // the case --- it is in fact the *contrary*, it is there to *extend* the + // usual definition/paintRange of a gradient: + // It was originally needed to correctly display TextFrames (TF) in Writer: If you + // have a TF in SW filled with a gradient and that TF has sub-frames, it inhertits + // the gradient fill. Since you can freely move those sub-TFs even outside the + // parent TF there has to be a way to not only paint gradients in ther definition + // range (classical, all DrawObjects do that), but extended from that. This is + // needed e.g. for linerar gradients, but - dependent of e.g. the center settings - + // also for all other ones, all can have geometry 'outside' the DefinitionRange. + // This is now also used in various other locations which is proof that this is + // useful and needed. It is possible to see that basic history/reason for this + // parameter by following the git history and why and under which circumstances + // that parameter was originally added. Other hints are: It is *not* named + // 'ClipRange'. Using a B2DRange to define a ClipRange topology would be bad due + // to not being transformable, a PolyPolygon would be used in that case. Using as + // clipping mechanism would offer a 2nd pinciple to add clipping for primitives + // besides MaskPrimitive2D - always bad style in a sub-system. A quick look + // on it's usages gives hints, too. + // This means that when defining a outputRange tat resides completely *inside* + // the definitionRange *no change* at all is done by definition since this does + // not *extend* the target area of the gradient paint region at all. If an + // implementation does clip and limit output to 'outputRange' that should do no + // harm, but is not the expected/reliable way to paint primitives clipped. + // That's why all DrawObjects with gradient fill (and other fills do the same) + // embed the fill that is defined for a range (usually the BoundRange of a + // PolyPolygon) in a MaskPrimitive2D defined by the outline PolyPolygon of the + // shape. Nothing speaks against renderers detecting that combination and do + // something optimized if they want to, especially SDPRs, but this is not + // required. The standard embedded clipping of the mplementations of the + // MaskPrimitive2D do the right thing. + // This test intends to paint the lower part of a gradient, so define the + // gradient for the full target range and embed it to a MaskPrimitive2D + // defining the lower part of that area to do that. + basegfx::B2DRange definitionRange(0, 0, 100, 200); basegfx::B2DRange outputRange(0, 100, 100, 200); // Paint only lower half of the gradient. - attribute::FillGradientAttribute attributes( - css::awt::GradientStyle_LINEAR, 0, 0, 0, 0, - basegfx::utils::createColorStopsFromStartEndColor(COL_WHITE.getBColor(), - COL_BLACK.getBColor())); - rtl::Reference<primitive2d::FillGradientPrimitive2D> gradientPrimitive( - new primitive2d::FillGradientPrimitive2D(outputRange, definitionRange, attributes)); - primitive2d::Primitive2DContainer primitives; - primitives.push_back(primitive2d::Primitive2DReference(gradientPrimitive)); + + const primitive2d::Primitive2DContainer primitives{ + rtl::Reference<primitive2d::MaskPrimitive2D>(new primitive2d::MaskPrimitive2D( + basegfx::B2DPolyPolygon(basegfx::utils::createPolygonFromRect(outputRange)), + primitive2d::Primitive2DContainer{ + rtl::Reference<primitive2d::FillGradientPrimitive2D>( + new primitive2d::FillGradientPrimitive2D( + definitionRange, attribute::FillGradientAttribute( + css::awt::GradientStyle_LINEAR, 0, 0, 0, 0, + basegfx::BColorStops(COL_WHITE.getBColor(), + COL_BLACK.getBColor())))) })) + }; processor->process(primitives); exportDevice("test-tdf139000.png", device); diff --git a/drawinglayer/source/attribute/fillgradientattribute.cxx b/drawinglayer/source/attribute/fillgradientattribute.cxx index 0233195113af..e02fdd4a5dad 100644 --- a/drawinglayer/source/attribute/fillgradientattribute.cxx +++ b/drawinglayer/source/attribute/fillgradientattribute.cxx @@ -30,7 +30,7 @@ namespace drawinglayer::attribute double mfOffsetX; double mfOffsetY; double mfAngle; - basegfx::ColorStops maColorStops; + basegfx::BColorStops maColorStops; css::awt::GradientStyle meStyle; sal_uInt16 mnSteps; @@ -40,7 +40,7 @@ namespace drawinglayer::attribute double fOffsetX, double fOffsetY, double fAngle, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, sal_uInt16 nSteps) : mfBorder(fBorder), mfOffsetX(fOffsetX), @@ -57,7 +57,7 @@ namespace drawinglayer::attribute // This is what the usages of this in primitives need. // Since FillGradientAttribute is read-only doing this // once here in the constructor is sufficient - basegfx::utils::sortAndCorrectColorStops(maColorStops); + maColorStops.sortAndCorrect(); // sortAndCorrectColorStops is rigid and can return // an empty result. To keep things simple, add a single @@ -87,18 +87,9 @@ namespace drawinglayer::attribute double getOffsetX() const { return mfOffsetX; } double getOffsetY() const { return mfOffsetY; } double getAngle() const { return mfAngle; } - const basegfx::ColorStops& getColorStops() const { return maColorStops; } + const basegfx::BColorStops& getColorStops() const { return maColorStops; } sal_uInt16 getSteps() const { return mnSteps; } - bool hasSingleColor() const - { - // No entry (should not happen, see comments for startColor above) - // or single entry -> no gradient. - // No need to check for all-the-same color since this is checked/done - // in the constructor already, see there - return maColorStops.size() < 2; - } - bool operator==(const ImpFillGradientAttribute& rCandidate) const { return (getStyle() == rCandidate.getStyle() @@ -126,7 +117,7 @@ namespace drawinglayer::attribute double fOffsetX, double fOffsetY, double fAngle, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, sal_uInt16 nSteps) : mpFillGradientAttribute(ImpFillGradientAttribute( eStyle, fBorder, fOffsetX, fOffsetY, fAngle, rColorStops, nSteps)) @@ -149,11 +140,6 @@ namespace drawinglayer::attribute return mpFillGradientAttribute.same_object(theGlobalDefault()); } - bool FillGradientAttribute::hasSingleColor() const - { - return mpFillGradientAttribute->hasSingleColor(); - } - // MCGR: Check if rendering cannot be handled by old vcl stuff bool FillGradientAttribute::cannotBeHandledByVCL() const { @@ -202,7 +188,7 @@ namespace drawinglayer::attribute return rCandidate.mpFillGradientAttribute == mpFillGradientAttribute; } - const basegfx::ColorStops& FillGradientAttribute::getColorStops() const + const basegfx::BColorStops& FillGradientAttribute::getColorStops() const { return mpFillGradientAttribute->getColorStops(); } diff --git a/drawinglayer/source/primitive3d/textureprimitive3d.cxx b/drawinglayer/source/primitive3d/textureprimitive3d.cxx index ebae584e9dbf..ceeca0489487 100644 --- a/drawinglayer/source/primitive3d/textureprimitive3d.cxx +++ b/drawinglayer/source/primitive3d/textureprimitive3d.cxx @@ -95,9 +95,9 @@ namespace drawinglayer::primitive3d const basegfx::BColor aGray(getTransparence(), getTransparence(), getTransparence()); // create ColorStops with StartColor == EndColor == aGray - const basegfx::ColorStops aColorStops { - basegfx::ColorStop(0.0, aGray), - basegfx::ColorStop(1.0, aGray) }; + const basegfx::BColorStops aColorStops { + basegfx::BColorStop(0.0, aGray), + basegfx::BColorStop(1.0, aGray) }; const attribute::FillGradientAttribute aFillGradient(css::awt::GradientStyle_LINEAR, 0.0, 0.0, 0.0, 0.0, aColorStops); const Primitive3DReference xRef(new TransparenceTexturePrimitive3D(aFillGradient, getChildren(), getTextureSize())); diff --git a/drawinglayer/source/processor3d/defaultprocessor3d.cxx b/drawinglayer/source/processor3d/defaultprocessor3d.cxx index 20d81871dbd7..0d07b0a5c343 100644 --- a/drawinglayer/source/processor3d/defaultprocessor3d.cxx +++ b/drawinglayer/source/processor3d/defaultprocessor3d.cxx @@ -61,8 +61,9 @@ namespace drawinglayer::processor3d const basegfx::B2DRange aOutlineRange(0.0, 0.0, rPrimitive.getTextureSize().getX(), rPrimitive.getTextureSize().getY()); const css::awt::GradientStyle aGradientStyle(rFillGradient.getStyle()); std::shared_ptr< texture::GeoTexSvx > pNewTex; + basegfx::BColor aSingleColor; - if(!rFillGradient.hasSingleColor()) + if (!rFillGradient.getColorStops().isSingleColor(aSingleColor)) { switch(aGradientStyle) { @@ -147,8 +148,7 @@ namespace drawinglayer::processor3d else { // only one color, so no real gradient -> use simple texture - const basegfx::BColor aStart(rFillGradient.getColorStops().front().getStopColor()); - pNewTex = std::make_shared<texture::GeoTexSvxMono>(aStart, 1.0 - aStart.luminance()); + pNewTex = std::make_shared<texture::GeoTexSvxMono>(aSingleColor, 1.0 - aSingleColor.luminance()); mbSimpleTextureActive = true; } diff --git a/drawinglayer/source/texture/texture.cxx b/drawinglayer/source/texture/texture.cxx index eb9df6469225..5176838d610e 100644 --- a/drawinglayer/source/texture/texture.cxx +++ b/drawinglayer/source/texture/texture.cxx @@ -73,7 +73,7 @@ namespace drawinglayer::texture GeoTexSvxGradient::GeoTexSvxGradient( const basegfx::B2DRange& rDefinitionRange, sal_uInt32 nRequestedSteps, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, double fBorder) : maDefinitionRange(rDefinitionRange) , mnRequestedSteps(nRequestedSteps) @@ -99,47 +99,11 @@ namespace drawinglayer::texture && mfBorder == pCompare->mfBorder); } - bool GeoTexSvxGradient::checkPenultimate() - { - // not needed when no ColorStops - if (mnColorStops.empty()) - return false; - - // not needed when last ColorStop at the end or outside - if (basegfx::fTools::moreOrEqual(mnColorStops.back().getStopOffset(), 1.0)) - return false; - - // get penultimate entry - const auto penultimate(mnColorStops.rbegin() + 1); - - // if there is none, we need no correction and are done - if (penultimate == mnColorStops.rend()) - return false; - - // not needed when the last two ColorStops have different offset, then - // a visible range will be processed already - if (!basegfx::fTools::equal(mnColorStops.back().getStopOffset(), penultimate->getStopOffset())) - return false; - - // not needed when the last two ColorStops have the same Color, then the - // range before solves the problem - if (mnColorStops.back().getStopColor() == penultimate->getStopColor()) - return false; - - // Here we need to temporarily add a ColorStop entry with the - // same color as the last entry to correctly 'close' the - // created gradient geometry. - // The simplest way is to temporarily add an entry to the local - // ColorStops for this at 1.0 (using same color) - mnColorStops.emplace_back(1.0, mnColorStops.back().getStopColor()); - return true; - } - GeoTexSvxGradientLinear::GeoTexSvxGradientLinear( const basegfx::B2DRange& rDefinitionRange, const basegfx::B2DRange& rOutputRange, sal_uInt32 nRequestedSteps, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, double fBorder, double fAngle) : GeoTexSvxGradient(rDefinitionRange, nRequestedSteps, rColorStops, fBorder) @@ -180,7 +144,17 @@ namespace drawinglayer::texture return; // check if we need last-ColorStop-correction - const bool bPenultimateUsed(checkPenultimate()); + const bool bPenultimateUsed(mnColorStops.checkPenultimate()); + + if (bPenultimateUsed) + { + // Here we need to temporarily add a ColorStop entry with the + // same color as the last entry to correctly 'close' the + // created gradient geometry. + // The simplest way is to temporarily add an entry to the local + // ColorStops for this at 1.0 (using same color) + mnColorStops.emplace_back(1.0, mnColorStops.back().getStopColor()); + } // prepare unit range transform basegfx::B2DHomMatrix aPattern; @@ -200,7 +174,7 @@ namespace drawinglayer::texture const double fOffsetStart(cs_l->getStopOffset()); const double fOffsetEnd(cs_r->getStopOffset()); - // same offset, empty ColorStopRange, continue with next step + // same offset, empty BColorStopRange, continue with next step if (basegfx::fTools::equal(fOffsetStart, fOffsetEnd)) continue; @@ -249,7 +223,10 @@ namespace drawinglayer::texture } if (bPenultimateUsed) + { + // correct temporary change mnColorStops.pop_back(); + } } void GeoTexSvxGradientLinear::modifyBColor(const basegfx::B2DPoint& rUV, basegfx::BColor& rBColor, double& /*rfOpacity*/) const @@ -267,14 +244,14 @@ namespace drawinglayer::texture // texture-back-transform X/Y -> t [0.0..1.0] and determine color const double fScaler(basegfx::utils::getLinearGradientAlpha(rUV, maGradientInfo)); - rBColor = basegfx::utils::modifyBColor(mnColorStops, fScaler, mnRequestedSteps, maLastColorStopRange); + rBColor = mnColorStops.getInterpolatedBColor(fScaler, mnRequestedSteps, maLastColorStopRange); } GeoTexSvxGradientAxial::GeoTexSvxGradientAxial( const basegfx::B2DRange& rDefinitionRange, const basegfx::B2DRange& rOutputRange, sal_uInt32 nRequestedSteps, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, double fBorder, double fAngle) : GeoTexSvxGradient(rDefinitionRange, nRequestedSteps, rColorStops, fBorder) @@ -285,7 +262,7 @@ namespace drawinglayer::texture // with the other gradients. Either stay 'thinking reverse' for the // rest of time or adapt it here and go in same order as the other five, // so unifications/tooling will be possible - basegfx::utils::reverseColorStops(mnColorStops); + mnColorStops.reverseColorStops(); maGradientInfo = basegfx::utils::createAxialODFGradientInfo( rDefinitionRange, @@ -319,7 +296,13 @@ namespace drawinglayer::texture return; // check if we need last-ColorStop-correction - const bool bPenultimateUsed(checkPenultimate()); + const bool bPenultimateUsed(mnColorStops.checkPenultimate()); + + if (bPenultimateUsed) + { + // temporarily add a ColorStop entry + mnColorStops.emplace_back(1.0, mnColorStops.back().getStopColor()); + } // prepare unit range transform basegfx::B2DHomMatrix aPattern; @@ -339,7 +322,7 @@ namespace drawinglayer::texture const double fOffsetStart(cs_l->getStopOffset()); const double fOffsetEnd(cs_r->getStopOffset()); - // same offset, empty ColorStopRange, continue with next step + // same offset, empty BColorStopRange, continue with next step if (basegfx::fTools::equal(fOffsetStart, fOffsetEnd)) continue; @@ -373,7 +356,10 @@ namespace drawinglayer::texture } if (bPenultimateUsed) + { + // correct temporary change mnColorStops.pop_back(); + } } void GeoTexSvxGradientAxial::modifyBColor(const basegfx::B2DPoint& rUV, basegfx::BColor& rBColor, double& /*rfOpacity*/) const @@ -394,14 +380,14 @@ namespace drawinglayer::texture const double fScaler(basegfx::utils::getAxialGradientAlpha(rUV, maGradientInfo)); // we use the reverse ColorSteps here, so mirror scaler value - rBColor = basegfx::utils::modifyBColor(mnColorStops, 1.0 - fScaler, mnRequestedSteps, maLastColorStopRange); + rBColor = mnColorStops.getInterpolatedBColor(1.0 - fScaler, mnRequestedSteps, maLastColorStopRange); } GeoTexSvxGradientRadial::GeoTexSvxGradientRadial( const basegfx::B2DRange& rDefinitionRange, sal_uInt32 nRequestedSteps, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, double fBorder, double fOffsetX, double fOffsetY) @@ -430,7 +416,13 @@ namespace drawinglayer::texture return; // check if we need last-ColorStop-correction - const bool bPenultimateUsed(checkPenultimate()); + const bool bPenultimateUsed(mnColorStops.checkPenultimate()); + + if (bPenultimateUsed) + { + // temporarily add a ColorStop entry + mnColorStops.emplace_back(1.0, mnColorStops.back().getStopColor()); + } // outer loop over ColorStops, each is from cs_l to cs_r for (auto cs_l(mnColorStops.begin()), cs_r(cs_l + 1); cs_r != mnColorStops.end(); cs_l++, cs_r++) @@ -439,7 +431,7 @@ namespace drawinglayer::texture const double fOffsetStart(cs_l->getStopOffset()); const double fOffsetEnd(cs_r->getStopOffset()); - // same offset, empty ColorStopRange, continue with next step + // same offset, empty BColorStopRange, continue with next step if (basegfx::fTools::equal(fOffsetStart, fOffsetEnd)) continue; @@ -468,7 +460,10 @@ namespace drawinglayer::texture } if (bPenultimateUsed) + { + // correct temporary change mnColorStops.pop_back(); + } } void GeoTexSvxGradientRadial::modifyBColor(const basegfx::B2DPoint& rUV, basegfx::BColor& rBColor, double& /*rfOpacity*/) const @@ -486,14 +481,14 @@ namespace drawinglayer::texture // texture-back-transform X/Y -> t [0.0..1.0] and determine color const double fScaler(basegfx::utils::getRadialGradientAlpha(rUV, maGradientInfo)); - rBColor = basegfx::utils::modifyBColor(mnColorStops, fScaler, mnRequestedSteps, maLastColorStopRange); + rBColor = mnColorStops.getInterpolatedBColor(fScaler, mnRequestedSteps, maLastColorStopRange); } GeoTexSvxGradientElliptical::GeoTexSvxGradientElliptical( const basegfx::B2DRange& rDefinitionRange, sal_uInt32 nRequestedSteps, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, double fBorder, double fOffsetX, double fOffsetY, @@ -524,7 +519,13 @@ namespace drawinglayer::texture return; // check if we need last-ColorStop-correction - const bool bPenultimateUsed(checkPenultimate()); + const bool bPenultimateUsed(mnColorStops.checkPenultimate()); + + if (bPenultimateUsed) + { + // temporarily add a ColorStop entry + mnColorStops.emplace_back(1.0, mnColorStops.back().getStopColor()); + } // prepare vars dependent on aspect ratio const double fAR(maGradientInfo.getAspectRatio()); @@ -537,7 +538,7 @@ namespace drawinglayer::texture const double fOffsetStart(cs_l->getStopOffset()); const double fOffsetEnd(cs_r->getStopOffset()); - // same offset, empty ColorStopRange, continue with next step + // same offset, empty BColorStopRange, continue with next step if (basegfx::fTools::equal(fOffsetStart, fOffsetEnd)) continue; @@ -569,7 +570,10 @@ namespace drawinglayer::texture } if (bPenultimateUsed) + { + // correct temporary change mnColorStops.pop_back(); + } } void GeoTexSvxGradientElliptical::modifyBColor(const basegfx::B2DPoint& rUV, basegfx::BColor& rBColor, double& /*rfOpacity*/) const @@ -587,14 +591,14 @@ namespace drawinglayer::texture // texture-back-transform X/Y -> t [0.0..1.0] and determine color const double fScaler(basegfx::utils::getEllipticalGradientAlpha(rUV, maGradientInfo)); - rBColor = basegfx::utils::modifyBColor(mnColorStops, fScaler, mnRequestedSteps, maLastColorStopRange); + rBColor = mnColorStops.getInterpolatedBColor(fScaler, mnRequestedSteps, maLastColorStopRange); } GeoTexSvxGradientSquare::GeoTexSvxGradientSquare( const basegfx::B2DRange& rDefinitionRange, sal_uInt32 nRequestedSteps, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, double fBorder, double fOffsetX, double fOffsetY, @@ -625,7 +629,13 @@ namespace drawinglayer::texture return; // check if we need last-ColorStop-correction - const bool bPenultimateUsed(checkPenultimate()); + const bool bPenultimateUsed(mnColorStops.checkPenultimate()); + + if (bPenultimateUsed) + { + // temporarily add a ColorStop entry + mnColorStops.emplace_back(1.0, mnColorStops.back().getStopColor()); + } // outer loop over ColorStops, each is from cs_l to cs_r for (auto cs_l(mnColorStops.begin()), cs_r(cs_l + 1); cs_r != mnColorStops.end(); cs_l++, cs_r++) @@ -634,7 +644,7 @@ namespace drawinglayer::texture const double fOffsetStart(cs_l->getStopOffset()); const double fOffsetEnd(cs_r->getStopOffset()); - // same offset, empty ColorStopRange, continue with next step + // same offset, empty BColorStopRange, continue with next step if (basegfx::fTools::equal(fOffsetStart, fOffsetEnd)) continue; @@ -663,7 +673,10 @@ namespace drawinglayer::texture } if (bPenultimateUsed) + { + // correct temporary change mnColorStops.pop_back(); + } } void GeoTexSvxGradientSquare::modifyBColor(const basegfx::B2DPoint& rUV, basegfx::BColor& rBColor, double& /*rfOpacity*/) const @@ -681,14 +694,14 @@ namespace drawinglayer::texture // texture-back-transform X/Y -> t [0.0..1.0] and determine color const double fScaler(basegfx::utils::getSquareGradientAlpha(rUV, maGradientInfo)); - rBColor = basegfx::utils::modifyBColor(mnColorStops, fScaler, mnRequestedSteps, maLastColorStopRange); + rBColor = mnColorStops.getInterpolatedBColor(fScaler, mnRequestedSteps, maLastColorStopRange); } GeoTexSvxGradientRect::GeoTexSvxGradientRect( const basegfx::B2DRange& rDefinitionRange, sal_uInt32 nRequestedSteps, - const basegfx::ColorStops& rColorStops, + const basegfx::BColorStops& rColorStops, double fBorder, double fOffsetX, double fOffsetY, @@ -719,7 +732,13 @@ namespace drawinglayer::texture return; // check if we need last-ColorStop-correction - const bool bPenultimateUsed(checkPenultimate()); + const bool bPenultimateUsed(mnColorStops.checkPenultimate()); + + if (bPenultimateUsed) + { + // temporarily add a ColorStop entry + mnColorStops.emplace_back(1.0, mnColorStops.back().getStopColor()); + } // prepare vars dependent on aspect ratio const double fAR(maGradientInfo.getAspectRatio()); @@ -732,7 +751,7 @@ namespace drawinglayer::texture const double fOffsetStart(cs_l->getStopOffset()); const double fOffsetEnd(cs_r->getStopOffset()); - // same offset, empty ColorStopRange, continue with next step + // same offset, empty BColorStopRange, continue with next step if (basegfx::fTools::equal(fOffsetStart, fOffsetEnd)) continue; @@ -764,7 +783,10 @@ namespace drawinglayer::texture } if (bPenultimateUsed) + { + // correct temporary change mnColorStops.pop_back(); + } } void GeoTexSvxGradientRect::modifyBColor(const basegfx::B2DPoint& rUV, basegfx::BColor& rBColor, double& /*rfOpacity*/) const @@ -782,7 +804,7 @@ namespace drawinglayer::texture // texture-back-transform X/Y -> t [0.0..1.0] and determine color const double fScaler(basegfx::utils::getRectangularGradientAlpha(rUV, maGradientInfo)); - rBColor = basegfx::utils::modifyBColor(mnColorStops, fScaler, mnRequestedSteps, maLastColorStopRange); + rBColor = mnColorStops.getInterpolatedBColor(fScaler, mnRequestedSteps, maLastColorStopRange); } diff --git a/drawinglayer/source/tools/wmfemfhelper.cxx b/drawinglayer/source/tools/wmfemfhelper.cxx index 1b2b2d0a5abd..aa48149219f3 100644 --- a/drawinglayer/source/tools/wmfemfhelper.cxx +++ b/drawinglayer/source/tools/wmfemfhelper.cxx @@ -681,7 +681,7 @@ namespace wmfemfhelper static_cast<double>(rGradient.GetOfsX()) * 0.01, static_cast<double>(rGradient.GetOfsY()) * 0.01, toRadians(rGradient.GetAngle()), - basegfx::utils::createColorStopsFromStartEndColor(aStart, aEnd), + basegfx::BColorStops(aStart, aEnd), rGradient.GetSteps()); } @@ -882,11 +882,12 @@ namespace wmfemfhelper PropertyHolder const & rPropertyHolder) { drawinglayer::attribute::FillGradientAttribute aAttribute(createFillGradientAttribute(rGradient)); + basegfx::BColor aSingleColor; - if(aAttribute.hasSingleColor()) + if (aAttribute.getColorStops().isSingleColor(aSingleColor)) { // not really a gradient. Create filled rectangle - return CreateColorWallpaper(rRange, aAttribute.getColorStops().front().getStopColor(), rPropertyHolder); + return CreateColorWallpaper(rRange, aSingleColor, rPropertyHolder); } else { @@ -2052,8 +2053,9 @@ namespace wmfemfhelper const Gradient& rGradient = pA->GetGradient(); drawinglayer::attribute::FillGradientAttribute aAttribute(createFillGradientAttribute(rGradient)); basegfx::B2DPolyPolygon aOutline(basegfx::utils::createPolygonFromRect(aRange)); + basegfx::BColor aSingleColor; - if(aAttribute.hasSingleColor()) + if (aAttribute.getColorStops().isSingleColor(aSingleColor)) { // not really a gradient. Create filled rectangle createFillPrimitive( @@ -2762,14 +2764,15 @@ namespace wmfemfhelper // check if gradient is a real gradient const Gradient& rGradient = pA->GetGradient(); drawinglayer::attribute::FillGradientAttribute aAttribute(createFillGradientAttribute(rGradient)); + basegfx::BColor aSingleColor; - if(aAttribute.hasSingleColor()) + if (aAttribute.getColorStops().isSingleColor(aSingleColor)) { // not really a gradient; create UnifiedTransparencePrimitive2D rTargetHolders.Current().append( new drawinglayer::primitive2d::UnifiedTransparencePrimitive2D( std::move(xSubContent), - aAttribute.getColorStops().front().getStopColor().luminance())); + aSingleColor.luminance())); } else { @@ -2882,14 +2885,15 @@ namespace wmfemfhelper // get and check if gradient is a real gradient const Gradient& rGradient = pMetaGradientExAction->GetGradient(); drawinglayer::attribute::FillGradientAttribute aAttribute(createFillGradientAttribute(rGradient)); + basegfx::BColor aSingleColor; - if(aAttribute.hasSingleColor()) + if (aAttribute.getColorStops().isSingleColor(aSingleColor)) { // not really a gradient rTargetHolders.Current().append( new drawinglayer::primitive2d::PolyPolygonColorPrimitive2D( std::move(aPolyPolygon), - aAttribute.getColorStops().front().getStopColor())); + aSingleColor)); } else { diff --git a/filter/source/msfilter/msdffimp.cxx b/filter/source/msfilter/msdffimp.cxx index b397630f028a..1b4d214035fe 100644 --- a/filter/source/msfilter/msdffimp.cxx +++ b/filter/source/msfilter/msdffimp.cxx @@ -2924,8 +2924,8 @@ void DffPropertyReader::ImportGradientColor( SfxItemSet& aSet, sal_uInt32 eMSO_F } //Construct gradient item - XGradient aGrad( - basegfx::utils::createColorStopsFromStartEndColor(aCol2.getBColor(), aCol1.getBColor()), + basegfx::BGradient aGrad( + basegfx::BColorStops(aCol2.getBColor(), aCol1.getBColor()), eGrad, nAngle, nFocusX, nFocusY ); //Intensity has been merged into color. So here just set is as 100 aGrad.SetStartIntens( 100 ); @@ -2939,8 +2939,8 @@ void DffPropertyReader::ImportGradientColor( SfxItemSet& aSet, sal_uInt32 eMSO_F aCol1 = Color(nStartCol, nStartCol, nStartCol); aCol2 = Color(nEndCol, nEndCol, nEndCol); - XGradient aGrad2( - basegfx::utils::createColorStopsFromStartEndColor(aCol2.getBColor(), aCol1.getBColor()), + basegfx::BGradient aGrad2( + basegfx::BColorStops(aCol2.getBColor(), aCol1.getBColor()), eGrad, nAngle, nFocusX, nFocusY ); aSet.Put( XFillFloatTransparenceItem( OUString(), aGrad2 ) ); } diff --git a/filter/source/msfilter/svdfppt.cxx b/filter/source/msfilter/svdfppt.cxx index 013ff44ce528..b6dc298d44b4 100644 --- a/filter/source/msfilter/svdfppt.cxx +++ b/filter/source/msfilter/svdfppt.cxx @@ -7395,19 +7395,19 @@ static void ApplyCellAttributes( const SdrObject* pObj, Reference< XCell > const case drawing::FillStyle_GRADIENT : { eFS = css::drawing::FillStyle_GRADIENT; - XGradient aXGradient(pObj->GetMergedItem(XATTR_FILLGRADIENT).GetGradientValue()); + basegfx::BGradient aBGradient(pObj->GetMergedItem(XATTR_FILLGRADIENT).GetGradientValue()); css::awt::Gradient aGradient; - aGradient.Style = aXGradient.GetGradientStyle(); - aGradient.StartColor = static_cast<sal_Int32>(Color(aXGradient.GetColorStops().front().getStopColor())); - aGradient.EndColor = static_cast<sal_Int32>(Color(aXGradient.GetColorStops().back().getStopColor())); - aGradient.Angle = static_cast<short>(aXGradient.GetAngle()); - aGradient.Border = aXGradient.GetBorder(); - aGradient.XOffset = aXGradient.GetXOffset(); - aGradient.YOffset = aXGradient.GetYOffset(); - aGradient.StartIntensity = aXGradient.GetStartIntens(); - aGradient.EndIntensity = aXGradient.GetEndIntens(); - aGradient.StepCount = aXGradient.GetSteps(); + aGradient.Style = aBGradient.GetGradientStyle(); + aGradient.StartColor = static_cast<sal_Int32>(Color(aBGradient.GetColorStops().front().getStopColor())); + aGradient.EndColor = static_cast<sal_Int32>(Color(aBGradient.GetColorStops().back().getStopColor())); + aGradient.Angle = static_cast<short>(aBGradient.GetAngle()); + aGradient.Border = aBGradient.GetBorder(); + aGradient.XOffset = aBGradient.GetXOffset(); + aGradient.YOffset = aBGradient.GetYOffset(); + aGradient.StartIntensity = aBGradient.GetStartIntens(); + aGradient.EndIntensity = aBGradient.GetEndIntens(); + aGradient.StepCount = aBGradient.GetSteps(); xPropSet->setPropertyValue( "FillGradient", Any( aGradient ) ); } diff --git a/include/basegfx/utils/bgradient.hxx b/include/basegfx/utils/bgradient.hxx new file mode 100644 index 000000000000..37de614faba7 --- /dev/null +++ b/include/basegfx/utils/bgradient.hxx @@ -0,0 +1,323 @@ +/* -*- 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 <config_options.h> +#include <basegfx/color/bcolor.hxx> +#include <basegfx/basegfxdllapi.h> +#include <vector> +#include <com/sun/star/awt/Gradient2.hpp> +#include <com/sun/star/awt/GradientStyle.hpp> +#include <tools/degree.hxx> +#include <boost/property_tree/ptree_fwd.hpp> + +namespace com +{ +namespace sun +{ +namespace star +{ +namespace uno +{ +class Any; +} +} +} +} + +namespace basegfx +{ +/* MCGR: Provide ColorStop definition + + This is the needed combination of offset and color: + + Offset is defined as: + - being in the range of [0.0 .. 1.0] (unit range) + - 0.0 being reserved for StartColor + - 1.0 being reserved for EndColor + - in-between offsets thus being in the range of ]0.0 .. 1.0[ + - no two equal offsets are allowed + - this is an error + - missing 1.0 entry (EndColor) is allowed + - it means that EndColor == StartColor + - at least one value (usually 0.0, StartColor) is required + - this allows to avoid massive testing in all places where + this data has to be accessed + + Color is defined as: + - RGB with unit values [0.0 .. 1.0] + + These definitions are packed in a std::vector<ColorStop> ColorStops, + see typedef below. + */ +class BASEGFX_DLLPUBLIC BColorStop +{ +private: + // offset in the range of [0.0 .. 1.0] + double mfStopOffset; + + // RGB color of ColorStop entry + BColor maStopColor; + +public: + // constructor - defaults are needed to have a default constructor + // e.g. for usage in std::vector::insert (even when only reducing) + // ensure [0.0 .. 1.0] range for mfStopOffset + BColorStop(double fStopOffset = 0.0, const BColor& rStopColor = BColor()) + : mfStopOffset(fStopOffset) + , maStopColor(rStopColor) + { + // NOTE: I originally *corrected* mfStopOffset here by using + // mfStopOffset(std::max(0.0, std::min(fOffset, 1.0))) + // While that is formally correct, it moves an invalid + // entry to 0.0 or 1.0, thus creating additional wrong + // Start/EndColor entries. That may then 'overlay' the + // correct entry when corrections are applied to the + // vector of entries (see sortAndCorrectColorStops) + // which leads to getting the wanted Start/EndColor + // to be factically deleted, what is an error. + } + + double getStopOffset() const { return mfStopOffset; } + const BColor& getStopColor() const { return maStopColor; } + + // needed for std::sort + bool operator<(const BColorStop& rCandidate) const + { + return getStopOffset() < rCandidate.getStopOffset(); + } + + bool operator==(const BColorStop& rCandidate) const + { + return getStopOffset() == rCandidate.getStopOffset() + && getStopColor() == rCandidate.getStopColor(); + } +}; + +/* MCGR: Provide ColorStops definition to the FillGradientAttribute + + This array should be sorted ascending by offsets, from lowest to + highest. Since all the primitive data definition where it is used + is read-only, this can/will be guaranteed by forcing/checking this + in the constructor, see ::FillGradientAttribute + */ +class BASEGFX_DLLPUBLIC BColorStops final : public std::vector<BColorStop> +{ +private: + void setColorStopSequence(const css::awt::ColorStopSequence& rColorStops); + +public: + explicit BColorStops() + : vector() + { + } + BColorStops(const BColorStops& other) + : vector(other) + { + } + BColorStops(BColorStops&& other) noexcept + : vector(std::move(other)) + { + } + BColorStops(std::initializer_list<BColorStop> init) + : vector(init) + { + } + BColorStops(const_iterator first, const_iterator last) + : vector(first, last) + { + } + BColorStops(const css::awt::ColorStopSequence& rColorStops); + BColorStops(const css::uno::Any& rVal); + + // constuctor with two colors to explicitly create a + // BColorStops for StartColor @0.0 & EndColor @1.0 + BColorStops(const BColor& rStart, const BColor& rEnd); + + BColorStops& operator=(const BColorStops& r) + { + vector::operator=(r); + return *this; + } + BColorStops& operator=(BColorStops&& r) noexcept + { + vector::operator=(std::move(r)); + return *this; + } + + // helper data struct to support buffering entries in + // gradient texture mapping, see usages for more info + struct BColorStopRange + { + basegfx::BColor maColorStart; + basegfx::BColor maColorEnd; + double mfOffsetStart; + double mfOffsetEnd; + + BColorStopRange() + : maColorStart() + , maColorEnd() + , mfOffsetStart(0.0) + , mfOffsetEnd(0.0) + { + } + }; + + /* Helper to grep the correct ColorStop out of + ColorStops and interpolate as needed for given + relative value in fPosition in the range of [0.0 .. 1.0]. + It also takes care of evtl. given RequestedSteps. + */ + BColor getInterpolatedBColor(double fPosition, sal_uInt32 nRequestedSteps, + BColorStopRange& rLastColorStopRange) const; + + /* Tooling method that allows to replace the StartColor in a + vector of ColorStops. A vector in 'ordered state' is expected, + so you may use/have used sortAndCorrect. + This method is for convenience & backwards compatibility, please + think about handling multi-colored gradients directly. + */ + void replaceStartColor(const BColor& rStart); + + /* Tooling method that allows to replace the EndColor in a + vector of ColorStops. A vector in 'ordered state' is expected, + so you may use/have used sortAndCorrect. + This method is for convenience & backwards compatibility, please + think about handling multi-colored gradients directly. + */ + void replaceEndColor(const BColor& rEnd); + + /* Tooling method to linearly blend the Colors contained in + a given ColorStop vector against a given Color using the + given intensity values. + The intensity values fStartIntensity, fEndIntensity are + in the range of [0.0 .. 1.0] and describe how much the + blend is supposed to be done at the start color position + and the end color position respectively, where 0.0 means + to fully use the given BlendColor, 1.0 means to not change + the existing color in the ColorStop. + Every color entry in the given ColorStop is blended + relative to it's StopPosition, interpolating the + given intensities with the range [0.0 .. 1.0] to do so. + */ + void blendToIntensity(double fStartIntensity, double fEndIntensity, const BColor& rBlendColor); + + /* Tooling method to guarantee sort and correctness for + the given ColorStops vector. + A vector fulfilling these conditions is called to be + in 'ordered state'. + + At return, the following conditions are guaranteed: + - contains no ColorStops with offset < 0.0 (will + be removed) + - contains no ColorStops with offset > 1.0 (will + be removed) + - ColorStops with identical offsets are now allowed + - will be sorted from lowest offset to highest + + Some more notes: + - It can happen that the result is empty + - It is allowed to have consecutive entries with + the same color, this represents single-color + regions inside the gradient + - A entry with 0.0 is not required or forced, so + no 'StartColor' is technically required + - A entry with 1.0 is not required or forced, so + no 'EndColor' is technically required + + All this is done in one run (sort + O(N)) without + creating a copy of the data in any form + */ + void sortAndCorrect(); + + // check if we need last-ColorStop-correction. This returns true if the last + // two ColorStops have the same offset but different Colors. In that case the + // tesselation for gradients does have to create an extra ending/closing enty + bool checkPenultimate() const; + + /* Tooling method to fill a awt::ColorStopSequence with + the data from the given ColorStops. This is used in + UNO API implementations. + */ + css::awt::ColorStopSequence getAsColorStopSequence() const; + + /* Tooling method to check if a ColorStop vector is defined + by a single color. It returns true if this is the case. + If true is returned, rSingleColor contains that single + color for convenience. + NOTE: If no ColorStop is defined, a fallback to BColor-default + (which is black) and true will be returned + */ + bool isSingleColor(BColor& rSingleColor) const; + + /* Tooling method to reverse ColorStops, including offsets. + When also mirroring offsets a valid sort keeps valid. + */ + void reverseColorStops(); +}; + +class BASEGFX_DLLPUBLIC BGradient final +{ + css::awt::GradientStyle eStyle; + + // MCGS: ColorStops in the range [0.0 .. 1.0], including StartColor/EndColor + basegfx::BColorStops aColorStops; + + Degree10 nAngle; + sal_uInt16 nBorder; + sal_uInt16 nOfsX; + sal_uInt16 nOfsY; + sal_uInt16 nIntensStart; + sal_uInt16 nIntensEnd; + sal_uInt16 nStepCount; + + static std::string GradientStyleToString(css::awt::GradientStyle eStyle); + +public: + BGradient(); + BGradient(const basegfx::BColorStops& rColorStops, + css::awt::GradientStyle eStyle = css::awt::GradientStyle_LINEAR, + Degree10 nAngle = 0_deg10, sal_uInt16 nXOfs = 50, sal_uInt16 nYOfs = 50, + sal_uInt16 nBorder = 0, sal_uInt16 nStartIntens = 100, sal_uInt16 nEndIntens = 100, + sal_uInt16 nSteps = 0); + BGradient(const css::awt::Gradient2& rGradient2); + BGradient(const css::uno::Any& rVal); + + bool operator==(const BGradient& rGradient) const; + + void SetGradientStyle(css::awt::GradientStyle eNewStyle) { eStyle = eNewStyle; } + void SetColorStops(const basegfx::BColorStops& rSteps); + void SetAngle(Degree10 nNewAngle) { nAngle = nNewAngle; } + void SetBorder(sal_uInt16 nNewBorder) { nBorder = nNewBorder; } + void SetXOffset(sal_uInt16 nNewOffset) { nOfsX = nNewOffset; } + void SetYOffset(sal_uInt16 nNewOffset) { nOfsY = nNewOffset; } + void SetStartIntens(sal_uInt16 nNewIntens) { nIntensStart = nNewIntens; } + void SetEndIntens(sal_uInt16 nNewIntens) { nIntensEnd = nNewIntens; } + void SetSteps(sal_uInt16 nSteps) { nStepCount = nSteps; } + + css::awt::GradientStyle GetGradientStyle() const { return eStyle; } + const basegfx::BColorStops& GetColorStops() const { return aColorStops; } + Degree10 GetAngle() const { return nAngle; } + sal_uInt16 GetBorder() const { return nBorder; } + sal_uInt16 GetXOffset() const { return nOfsX; } + sal_uInt16 GetYOffset() const { return nOfsY; } + sal_uInt16 GetStartIntens() const { return nIntensStart; } + sal_uInt16 GetEndIntens() const { return nIntensEnd; } + sal_uInt16 GetSteps() const { return nStepCount; } + + boost::property_tree::ptree dumpAsJSON() const; + static BGradient fromJSON(std::u16string_view rJSON); + + /// Tooling method to fill awt::Gradient2 from data contained in the given basegfx::BGradient + css::awt::Gradient2 getAsGradient2() const; +}; +} + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/basegfx/utils/gradienttools.hxx b/include/basegfx/utils/gradienttools.hxx index 502ef190b8ce..d9e685a87fb6 100644 --- a/include/basegfx/utils/gradienttools.hxx +++ b/include/basegfx/utils/gradienttools.hxx @@ -28,88 +28,77 @@ #include <basegfx/basegfxdllapi.h> #include <vector> #include <com/sun/star/awt/ColorStopSequence.hdl> +#include <basegfx/utils/bgradient.hxx> +#include <osl/endian.h> namespace com { namespace sun { namespace star { namespace uno { class Any; } } } } namespace com { namespace sun { namespace star { namespace awt { struct Gradient2; } } } } namespace basegfx { class B2DRange; } -namespace basegfx +namespace { - /* MCGR: Provide ColorStop definition - - This is the needed combination of offset and color: - - Offset is defined as: - - being in the range of [0.0 .. 1.0] (unit range) - - 0.0 being reserved for StartColor - - 1.0 being reserved for EndColor - - in-between offsets thus being in the range of ]0.0 .. 1.0[ - - no two equal offsets are allowed - - this is an error - - missing 1.0 entry (EndColor) is allowed - - it means that EndColor == StartColor - - at least one value (usually 0.0, StartColor) is required - - this allows to avoid massive testing in all places where - this data has to be accessed - - Color is defined as: - - RGB with unit values [0.0 .. 1.0] - - These definitions are packed in a std::vector<ColorStop> ColorStops, - see typedef below. + /* Internal helper to convert ::Color from tools::color.hxx to BColor + without the need to link against tools library. Be on the + safe side by using the same union */ - class UNLESS_MERGELIBS(BASEGFX_DLLPUBLIC) ColorStop + struct ColorToBColorConverter { - private: - // offset in the range of [0.0 .. 1.0] - double mfStopOffset; + union { + sal_uInt32 mValue; + struct { +#ifdef OSL_BIGENDIAN + sal_uInt8 T; + sal_uInt8 R; + sal_uInt8 G; + sal_uInt8 B; +#else + sal_uInt8 B; + sal_uInt8 G; + sal_uInt8 R; + sal_uInt8 T; +#endif + }; + }; + + ColorToBColorConverter GetRGBColor() const + { + return {R, G, B}; + } - // RGB color of ColorStop entry - BColor maStopColor; + ColorToBColorConverter(sal_uInt32 nColor) + : mValue(nColor) + { T=0; } - public: - // constructor - defaults are needed to have a default constructor - // e.g. for usage in std::vector::insert (even when only reducing) - // ensure [0.0 .. 1.0] range for mfStopOffset - ColorStop(double fStopOffset = 0.0, const BColor& rStopColor = BColor()) - : mfStopOffset(fStopOffset) - , maStopColor(rStopColor) + constexpr ColorToBColorConverter(sal_uInt8 nRed, sal_uInt8 nGreen, sal_uInt8 nBlue) + : mValue(sal_uInt32(nBlue) | (sal_uInt32(nGreen) << 8) | (sal_uInt32(nRed) << 16)) + {} + + explicit ColorToBColorConverter(const basegfx::BColor& rBColor) + : ColorToBColorConverter( + sal_uInt8(std::lround(rBColor.getRed() * 255.0)), + sal_uInt8(std::lround(rBColor.getGreen() * 255.0)), + sal_uInt8(std::lround(rBColor.getBlue() * 255.0))) + {} + + basegfx::BColor getBColor() const { - // NOTE: I originally *corrected* mfStopOffset here by using - // mfStopOffset(std::max(0.0, std::min(fOffset, 1.0))) - // While that is formally correct, it moves an invalid - // entry to 0.0 or 1.0, thus creating additional wrong - // Start/EndColor entries. That may then 'overlay' the - // correct entry when corrections are applied to the - // vector of entries (see sortAndCorrectColorStops) - // which leads to getting the wanted Start/EndColor - // to be factically deleted, what is an error. + return basegfx::BColor(R / 255.0, G / 255.0, B / 255.0); } - double getStopOffset() const { return mfStopOffset; } - const BColor& getStopColor() const { return maStopColor; } - - // needed for std::sort - bool operator<(const ColorStop& rCandidate) const + constexpr explicit operator sal_Int32() const { - return getStopOffset() < rCandidate.getStopOffset(); + return sal_Int32(mValue); } - bool operator==(const ColorStop& rCandidate) const + constexpr explicit operator sal_uInt32() const { - return getStopOffset() == rCandidate.getStopOffset() && getStopColor() == rCandidate.getStopColor(); + return mValue; } }; +} - /* MCGR: Provide ColorStops definition to the FillGradientAttribute - - This array should be sorted ascending by offsets, from lowest to - highest. Since all the primitive data definition where it is used - is read-only, this can/will be guaranteed by forcing/checking this - in the constructor, see ::FillGradientAttribute - */ - typedef std::vector<ColorStop> ColorStops; - +namespace basegfx +{ /** Gradient definition as used in ODF 1.2 This struct collects all data necessary for rendering ODF @@ -195,23 +184,6 @@ namespace basegfx } }; - // helper data struct to support buffering entries in - // gradient texture mapping, see usages for more info - struct UNLESS_MERGELIBS(BASEGFX_DLLPUBLIC) ColorStopRange - { - basegfx::BColor maColorStart; - basegfx::BColor maColorEnd; - double mfOffsetStart; - double mfOffsetEnd; - - ColorStopRange() - : maColorStart() - , maColorEnd() - , mfOffsetStart(0.0) - , mfOffsetEnd(0.0) - {} - }; - namespace utils { /// Tooling method to fill awt::Gradient2 from data contained in the given Any @@ -235,7 +207,7 @@ namespace basegfx */ BASEGFX_DLLPUBLIC void prepareColorStops( const com::sun::star::awt::Gradient2& rGradient, - ColorStops& rColorStops, + BColorStops& rColorStops, BColor& rSingleColor); /* Tooling method to synchronize the given ColorStops. @@ -256,117 +228,11 @@ namespace basegfx 'FillTransparenceGradient' method (at import time). */ BASEGFX_DLLPUBLIC void synchronizeColorStops( - ColorStops& rColorStops, - ColorStops& rAlphaStops, + BColorStops& rColorStops, + BColorStops& rAlphaStops, const BColor& rSingleColor, const BColor& rSingleAlpha); - /* Tooling method to linearly blend the Colors contained in - a given ColorStop vector against a given Color using the - given intensity values. - The intensity values fStartIntensity, fEndIntensity are - in the range of [0.0 .. 1.0] and describe how much the - blend is supposed to be done at the start color position - and the end color position respectively, where 0.0 means - to fully use the given BlendColor, 1.0 means to not change - the existing color in the ColorStop. - Every color entry in the given ColorStop is blended - relative to it's StopPosition, interpolating the - given intensities with the range [0.0 .. 1.0] to do so. - */ - BASEGFX_DLLPUBLIC void blendColorStopsToIntensity(ColorStops& rColorStops, double fStartIntensity, double fEndIntensity, const basegfx::BColor& rBlendColor); - - /* Tooling method to check if a ColorStop vector is defined - by a single color. It returns true if this is the case. - If true is returned, rSingleColor contains that single - color for convenience. - NOTE: If no ColorStop is defined, a fallback to BColor-default - (which is black) and true will be returned - */ - BASEGFX_DLLPUBLIC bool isSingleColor(const ColorStops& rColorStops, BColor& rSingleColor); - - /* Tooling method to reverse ColorStops, including offsets. - When also mirroring offsets a valid sort keeps valid. - */ - BASEGFX_DLLPUBLIC void reverseColorStops(ColorStops& rColorStops); - - /* Tooling method to convert UNO API data to ColorStops. - This will try to extract ColorStop data from the given - awt::Gradient2. - */ - BASEGFX_DLLPUBLIC void fillColorStopsFromGradient2(ColorStops& rColorStops, const com::sun::star::awt::Gradient2& rGradient); - - /* Tooling method to convert UNO API data to ColorStops. - This will try to extract ColorStop data from the given - Any, so if it's of type awt::Gradient2 that data will be - extracted, converted and copied into the given ColorStops. - */ - BASEGFX_DLLPUBLIC void fillColorStopsFromAny(ColorStops& rColorStops, const css::uno::Any& rVal); - - /* Tooling method to fill a awt::ColorStopSequence with - the data from the given ColorStops. This is used in - UNO API implementations. - */ - BASEGFX_DLLPUBLIC void fillColorStopSequenceFromColorStops(css::awt::ColorStopSequence& rColorStopSequence, const ColorStops& rColorStops); - - /* Tooling method that allows to replace the StartColor in a - vector of ColorStops. A vector in 'ordered state' is expected, - so you may use/have used sortAndCorrectColorStops, see below. - This method is for convenience & backwards compatibility, please - think about handling multi-colored gradients directly. - */ - BASEGFX_DLLPUBLIC void replaceStartColor(ColorStops& rColorStops, const BColor& rStart); - - /* Tooling method that allows to replace the EndColor in a - vector of ColorStops. A vector in 'ordered state' is expected, - so you may use/have used sortAndCorrectColorStops, see below. - This method is for convenience & backwards compatibility, please - think about handling multi-colored gradients directly. - */ - BASEGFX_DLLPUBLIC void replaceEndColor(ColorStops& rColorStops, const BColor& rEnd); - - // Tooling method to quickly create a ColorStop vector for a given set of Start/EndColor - BASEGFX_DLLPUBLIC ColorStops createColorStopsFromStartEndColor(const BColor& rStart, const BColor& rEnd); - - /* Tooling method to guarantee sort and correctness for - the given ColorStops vector. - A vector fulfilling these conditions is called to be - in 'ordered state'. - - At return, the following conditions are guaranteed: - - contains no ColorStops with offset < 0.0 (will - be removed) - - contains no ColorStops with offset > 1.0 (will - be removed) - - ColorStops with identical offsets are now allowed - - will be sorted from lowest offset to highest - - Some more notes: - - It can happen that the result is empty - - It is allowed to have consecutive entries with - the same color, this represents single-color - regions inside the gradient - - A entry with 0.0 is not required or forced, so - no 'StartColor' is technically required - - A entry with 1.0 is not required or forced, so - no 'EndColor' is technically required - - All this is done in one run (sort + O(N)) without - creating a copy of the data in any form - */ - BASEGFX_DLLPUBLIC void sortAndCorrectColorStops(ColorStops& rColorStops); - - /* Helper to grep the correct ColorStop out of - ColorStops and interpolate as needed for given - relative value in fScaler in the range of [0.0 .. 1.0]. - It also takes care of evtl. given RequestedSteps. - */ - BASEGFX_DLLPUBLIC BColor modifyBColor( - const ColorStops& rColorStops, - double fScaler, - sal_uInt32 nRequestedSteps, - ColorStopRange& rLastColorStopRange); - /* Helper to calculate numberOfSteps needed to represent gradient for the given two colors: - to define only based on color distance, give 0 == nRequestedSteps diff --git a/include/drawinglayer/attribute/fillgradientattribute.hxx b/include/drawinglayer/attribute/fillgradientattribute.hxx index da4cf9564705..124afddea18c 100644 --- a/include/drawinglayer/attribute/fillgradientattribute.hxx +++ b/include/drawinglayer/attribute/fillgradientattribute.hxx @@ -26,9 +26,9 @@ namespace basegfx { -class ColorStop; +class BColorStop; class BColor; -typedef std::vector<ColorStop> ColorStops; +class BColorStops; } namespace drawinglayer::attribute @@ -49,12 +49,12 @@ public: Direct Start/EndCOlor is no longer required, instead the full color gradient is handed over as ColorStops vector. To add the former Start/EndColor in a compatible way, just - prepare an instance of basegfx::ColorStops with the + prepare an instance of basegfx::BColorStops with the StartColor at 0.0 and the EndColor at 1.0. A rigid correction/input data will be done by the constructor, including to sort the ColorStops by offset and removing invalid - entries (see sortAndCorrectColorStops) + entries (see sortAndCorrect) To access e.g. the StartColor, use getColorStops().front(), and getColorStops().back(), accordingly, for EndColor. The existence @@ -65,7 +65,7 @@ public: */ /// constructors/assignmentoperator/destructor FillGradientAttribute(css::awt::GradientStyle eStyle, double fBorder, double fOffsetX, - double fOffsetY, double fAngle, const basegfx::ColorStops& rColorStops, + double fOffsetY, double fAngle, const basegfx::BColorStops& rColorStops, sal_uInt16 nSteps = 0); FillGradientAttribute(); FillGradientAttribute(const FillGradientAttribute&); @@ -77,9 +77,6 @@ public: // checks if the incarnation is default constructed bool isDefault() const; - // check if it is defined by a single color, then it is no gradient at all - bool hasSingleColor() const; - // MCGR: Check if rendering cannot be handled by old vcl stuff // due to various restrictions, based on local parameters. There // may be even more reasons on caller's side, e.g. a @@ -96,7 +93,7 @@ public: double getOffsetX() const; double getOffsetY() const; double getAngle() const; - const basegfx::ColorStops& getColorStops() const; + const basegfx::BColorStops& getColorStops() const; sal_uInt16 getSteps() const; }; diff --git a/include/svx/sidebar/AreaPropertyPanelBase.hxx b/include/svx/sidebar/AreaPropertyPanelBase.hxx index 6cf613cad26d..8e822dfd4f47 100644 --- a/include/svx/sidebar/AreaPropertyPanelBase.hxx +++ b/include/svx/sidebar/AreaPropertyPanelBase.hxx @@ -23,7 +23,7 @@ #include <svx/sidebar/AreaTransparencyGradientPopup.hxx> #include <sfx2/sidebar/ControllerItem.hxx> #include <svx/colorbox.hxx> -#include <svx/xgrad.hxx> +#include <basegfx/utils/bgradient.hxx> #include <svx/xfilluseslidebackgrounditem.hxx> #include <svx/xfillit0.hxx> #include <svx/xflclit.hxx> @@ -68,8 +68,8 @@ public: const static sal_Int32 DEFAULT_ENDVALUE; const static sal_Int32 DEFAULT_BORDER; - const XGradient& GetGradient (const css::awt::GradientStyle eStyle) const; - void SetGradient (const XGradient& rGradient); + const basegfx::BGradient& GetGradient (const css::awt::GradientStyle eStyle) const; + void SetGradient (const basegfx::BGradient& rGradient); sal_Int32 GetSelectedTransparencyTypeIndex() const; // constructor/destructor @@ -110,12 +110,12 @@ protected: sal_Int32 mnLastPosPattern; sal_uInt16 mnLastTransSolid; - XGradient maGradientLinear; - XGradient maGradientAxial; - XGradient maGradientRadial; - XGradient maGradientElliptical; - XGradient maGradientSquare; - XGradient maGradientRect; + basegfx::BGradient maGradientLinear; + basegfx::BGradient maGradientAxial; + basegfx::BGradient maGradientRadial; + basegfx::BGradient maGradientElliptical; + basegfx::BGradient maGradientSquare; + basegfx::BGradient maGradientRect; //ui controls std::unique_ptr<weld::Label> mxColorTextFT; @@ -152,7 +152,7 @@ protected: std::unique_ptr< SfxUInt16Item > mpTransparenceItem; // MCGR: Preserve in-between ColorStops until we have an UI to edit these - basegfx::ColorStops maColorStops; + basegfx::BColorStops maColorStops; DECL_DLLPRIVATE_LINK(SelectFillTypeHdl, weld::ComboBox&, void ); DECL_DLLPRIVATE_LINK(SelectFillAttrHdl, weld::ComboBox&, void ); @@ -170,7 +170,7 @@ protected: void FillStyleChanged(bool bUpdateModel); // MCGR: Preserve in-between ColorStops until we have an UI to edit these - basegfx::ColorStops createColorStops(); + basegfx::BColorStops createColorStops(); }; } // end of namespace svx::sidebar diff --git a/include/svx/sidebar/AreaTransparencyGradientPopup.hxx b/include/svx/sidebar/AreaTransparencyGradientPopup.hxx index 78848246c75e..bd6b24b6c828 100644 --- a/include/svx/sidebar/AreaTransparencyGradientPopup.hxx +++ b/include/svx/sidebar/AreaTransparencyGradientPopup.hxx @@ -46,7 +46,7 @@ private: std::unique_ptr<weld::MetricSpinButton> mxMtrTrgrBorder; // MCGR: Preserve in-between ColorStops until we have an UI to edit these - basegfx::ColorStops maColorStops; + basegfx::BColorStops maColorStops; void InitStatus(XFillFloatTransparenceItem const* pGradientItem); void ExecuteValueModify(sal_uInt8 nStartCol, sal_uInt8 nEndCol); diff --git a/include/svx/xflftrit.hxx b/include/svx/xflftrit.hxx index bd8a54a240ce..9b13616916ec 100644 --- a/include/svx/xflftrit.hxx +++ b/include/svx/xflftrit.hxx @@ -37,8 +37,8 @@ public: static SfxPoolItem* CreateDefault(); XFillFloatTransparenceItem(); - XFillFloatTransparenceItem(const OUString& rName, const XGradient& rGradient, bool bEnable = true ); - XFillFloatTransparenceItem( const XGradient& rTheGradient, bool bEnable = true ); + XFillFloatTransparenceItem(const OUString& rName, const basegfx::BGradient& rGradient, bool bEnable = true ); + XFillFloatTransparenceItem( const basegfx::BGradient& rTheGradient, bool bEnable = true ); XFillFloatTransparenceItem( const XFillFloatTransparenceItem& rItem ); virtual bool operator==( const SfxPoolItem& rItem ) const override; diff --git a/include/svx/xflgrit.hxx b/include/svx/xflgrit.hxx index 0c02e44a8d09..c8594753e5c0 100644 --- a/include/svx/xflgrit.hxx +++ b/include/svx/xflgrit.hxx @@ -22,7 +22,6 @@ #include <svx/xdef.hxx> #include <svx/xit.hxx> -#include <svx/xgrad.hxx> #include <svx/svxdllapi.h> class SdrModel; @@ -31,14 +30,14 @@ class SdrModel; class SVXCORE_DLLPUBLIC XFillGradientItem : public NameOrIndex { - XGradient aGradient; + basegfx::BGradient aGradient; public: static SfxPoolItem* CreateDefault(); XFillGradientItem() : NameOrIndex(XATTR_FILLGRADIENT, -1) {} - XFillGradientItem(sal_Int32 nIndex, const XGradient& rTheGradient); - XFillGradientItem(const OUString& rName, const XGradient& rTheGradient, TypedWhichId<XFillGradientItem> nWhich = XATTR_FILLGRADIENT); - XFillGradientItem(const XGradient& rTheGradient); + XFillGradientItem(sal_Int32 nIndex, const basegfx::BGradient& rTheGradient); + XFillGradientItem(const OUString& rName, const basegfx::BGradient& rTheGradient, TypedWhichId<XFillGradientItem> nWhich = XATTR_FILLGRADIENT); + XFillGradientItem(const basegfx::BGradient& rTheGradient); XFillGradientItem(const XFillGradientItem& rItem); virtual bool operator==(const SfxPoolItem& rItem) const override; @@ -50,8 +49,8 @@ public: MapUnit eCoreMetric, MapUnit ePresMetric, OUString &rText, const IntlWrapper& ) const override; - const XGradient& GetGradientValue() const; // GetValue -> GetGradientValue - void SetGradientValue(const XGradient& rNew) { aGradient = rNew; Detach(); } // SetValue -> SetGradientValue + const basegfx::BGradient& GetGradientValue() const; // GetValue -> GetGradientValue + void SetGradientValue(const basegfx::BGradient& rNew) { aGradient = rNew; Detach(); } // SetValue -> SetGradientValue static bool CompareValueFunc( const NameOrIndex* p1, const NameOrIndex* p2 ); std::unique_ptr<XFillGradientItem> checkForUniqueItem( SdrModel* pModel ) const; diff --git a/include/svx/xgrad.hxx b/include/svx/xgrad.hxx deleted file mode 100644 index 9dda79d06c7c..000000000000 --- a/include/svx/xgrad.hxx +++ /dev/null @@ -1,85 +0,0 @@ -/* -*- 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/. - * - * This file incorporates work covered by the following license notice: - * - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed - * with this work for additional information regarding copyright - * ownership. The ASF licenses this file to you under the Apache - * License, Version 2.0 (the "License"); you may not use this file - * except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 . - */ - -#ifndef INCLUDED_SVX_XGRAD_HXX -#define INCLUDED_SVX_XGRAD_HXX - -#include <tools/color.hxx> -#include <tools/degree.hxx> -#include <svx/svxdllapi.h> -#include <com/sun/star/awt/GradientStyle.hpp> -#include <boost/property_tree/ptree_fwd.hpp> -#include <com/sun/star/awt/Gradient2.hpp> -#include <basegfx/utils/gradienttools.hxx> - -class SAL_WARN_UNUSED SVXCORE_DLLPUBLIC XGradient final -{ - css::awt::GradientStyle eStyle; - - // MCGS: ColorStops in the range [0.0 .. 1.0], including StartColor/EndColor - basegfx::ColorStops aColorStops; - - Degree10 nAngle; - sal_uInt16 nBorder; - sal_uInt16 nOfsX; - sal_uInt16 nOfsY; - sal_uInt16 nIntensStart; - sal_uInt16 nIntensEnd; - sal_uInt16 nStepCount; - - static std::string GradientStyleToString(css::awt::GradientStyle eStyle); - -public: - XGradient(); - XGradient( const basegfx::ColorStops& rColorStops, - css::awt::GradientStyle eStyle = css::awt::GradientStyle_LINEAR, Degree10 nAngle = 0_deg10, - sal_uInt16 nXOfs = 50, sal_uInt16 nYOfs = 50, sal_uInt16 nBorder = 0, - sal_uInt16 nStartIntens = 100, sal_uInt16 nEndIntens = 100, - sal_uInt16 nSteps = 0 ); - - bool operator==(const XGradient& rGradient) const; - - void SetGradientStyle(css::awt::GradientStyle eNewStyle) { eStyle = eNewStyle; } - void SetColorStops(const basegfx::ColorStops& rSteps); - void SetAngle(Degree10 nNewAngle) { nAngle = nNewAngle; } - void SetBorder(sal_uInt16 nNewBorder) { nBorder = nNewBorder; } - void SetXOffset(sal_uInt16 nNewOffset) { nOfsX = nNewOffset; } - void SetYOffset(sal_uInt16 nNewOffset) { nOfsY = nNewOffset; } - void SetStartIntens(sal_uInt16 nNewIntens) { nIntensStart = nNewIntens; } - void SetEndIntens(sal_uInt16 nNewIntens) { nIntensEnd = nNewIntens; } - void SetSteps(sal_uInt16 nSteps) { nStepCount = nSteps; } - - css::awt::GradientStyle GetGradientStyle() const { return eStyle; } - const basegfx::ColorStops& GetColorStops() const { return aColorStops; } - Degree10 GetAngle() const { return nAngle; } - sal_uInt16 GetBorder() const { return nBorder; } - sal_uInt16 GetXOffset() const { return nOfsX; } - sal_uInt16 GetYOffset() const { return nOfsY; } - sal_uInt16 GetStartIntens() const { return nIntensStart; } - sal_uInt16 GetEndIntens() const { return nIntensEnd; } - sal_uInt16 GetSteps() const { return nStepCount; } - - boost::property_tree::ptree dumpAsJSON() const; - static XGradient fromJSON(std::u16string_view rJSON); - css::awt::Gradient2 toGradientUNO() const; -}; - -#endif - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/svx/xtable.hxx b/include/svx/xtable.hxx index 695064dcab1d..e84f459511e2 100644 --- a/include/svx/xtable.hxx +++ b/include/svx/xtable.hxx @@ -23,7 +23,7 @@ #include <rtl/ustring.hxx> #include <svx/xdash.hxx> #include <svx/xhatch.hxx> -#include <svx/xgrad.hxx> +#include <basegfx/utils/bgradient.hxx> #include <tools/color.hxx> @@ -101,13 +101,13 @@ public: class SVXCORE_DLLPUBLIC XGradientEntry final : public XPropertyEntry { private: - XGradient aGradient; + basegfx::BGradient aGradient; public: - XGradientEntry(const XGradient& rGradient, const OUString& rName); + XGradientEntry(const basegfx::BGradient& rGradient, const OUString& rName); XGradientEntry(const XGradientEntry& rOther); - const XGradient& GetGradient() const + const basegfx::BGradient& GetGradient() const { return aGradient; } diff --git a/oox/qa/unit/drawingml.cxx b/oox/qa/unit/drawingml.cxx index 10dc88e4954d..27bd3984a1c7 100644 --- a/oox/qa/unit/drawingml.cxx +++ b/oox/qa/unit/drawingml.cxx @@ -191,8 +191,7 @@ CPPUNIT_TEST_FIXTURE(OoxDrawingmlTest, testGradientMultiStepTransparency) // i.e. the end transparency was not 100%, but was 21%, leading to an unexpected visible line on // the right of this shape. // MCGR: Use the completely imported transparency gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aTransparence); + const basegfx::BColorStops aColorStops(aTransparence.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(5), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[4].getStopOffset(), 1.0)); diff --git a/oox/qa/unit/shape.cxx b/oox/qa/unit/shape.cxx index ad43fb52b4a1..722d7d6d644b 100644 --- a/oox/qa/unit/shape.cxx +++ b/oox/qa/unit/shape.cxx @@ -471,8 +471,7 @@ CPPUNIT_TEST_FIXTURE(OoxShapeTest, testWriterFontwork3) xShapeProps->getPropertyValue(u"FillGradient") >>= aGradient; // MCGR: Use the completely imported transparency gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + const basegfx::BColorStops aColorStops(aGradient.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(2), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); @@ -497,8 +496,7 @@ CPPUNIT_TEST_FIXTURE(OoxShapeTest, testWriterFontwork3) xShapeProps->getPropertyValue(u"FillGradient") >>= aGradient; // MCGR: Use the completely imported transparency gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + const basegfx::BColorStops aColorStops(aGradient.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(2), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.40000000000000002)); @@ -523,8 +521,7 @@ CPPUNIT_TEST_FIXTURE(OoxShapeTest, testWriterFontwork3) xShapeProps->getPropertyValue(u"FillGradient") >>= aGradient; // MCGR: Use the completely imported transparency gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + const basegfx::BColorStops aColorStops(aGradient.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(2), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); @@ -641,8 +638,7 @@ CPPUNIT_TEST_FIXTURE(OoxShapeTest, testImportWordArtGradient) xShapeProps->getPropertyValue(u"FillGradient") >>= aGradient; // MCGR: Use the completely imported transparency gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + const basegfx::BColorStops aColorStops(aGradient.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(2), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); @@ -675,8 +671,7 @@ CPPUNIT_TEST_FIXTURE(OoxShapeTest, testImportWordArtGradient) xShapeProps->getPropertyValue(u"FillGradient") >>= aGradient; // MCGR: Use the completely imported transparency gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + basegfx::BColorStops aColorStops(aGradient.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(2), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); @@ -692,7 +687,7 @@ CPPUNIT_TEST_FIXTURE(OoxShapeTest, testImportWordArtGradient) xShapeProps->getPropertyValue(u"FillTransparenceGradient") >>= aGradient; // MCGR: Use the completely imported transparency gradient to check for correctness - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + aColorStops = basegfx::BColorStops(aGradient.ColorStops); // Transparency is encoded in gray color. CPPUNIT_ASSERT_EQUAL(size_t(2), aColorStops.size()); @@ -733,8 +728,7 @@ CPPUNIT_TEST_FIXTURE(OoxShapeTest, testImportWordArtGradient) xShapeProps->getPropertyValue(u"FillGradient") >>= aGradient; // MCGR: Use the completely imported transparency gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + basegfx::BColorStops aColorStops(aGradient.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(2), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); @@ -752,7 +746,7 @@ CPPUNIT_TEST_FIXTURE(OoxShapeTest, testImportWordArtGradient) xShapeProps->getPropertyValue(u"FillTransparenceGradient") >>= aGradient; // MCGR: Use the completely imported transparency gradient to check for correctness - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + aColorStops = basegfx::BColorStops(aGradient.ColorStops); // Transparency is encoded in gray color. CPPUNIT_ASSERT_EQUAL(size_t(2), aColorStops.size()); diff --git a/oox/source/drawingml/fillproperties.cxx b/oox/source/drawingml/fillproperties.cxx index e6cded7e64c7..a42418198c12 100644 --- a/oox/source/drawingml/fillproperties.cxx +++ b/oox/source/drawingml/fillproperties.cxx @@ -461,8 +461,8 @@ void FillProperties::pushToPropMap(ShapePropertyMap& rPropMap, const GraphicHelp // use awt::Gradient2, prepare ColorStops awt::Gradient2 aGradient; assert(aGradient.ColorStops.get() && "cid#1524676 aGradient.ColorStops._pSequence won't be null here"); - basegfx::ColorStops aColorStops; - basegfx::ColorStops aTransparencyStops; + basegfx::BColorStops aColorStops; + basegfx::BColorStops aTransparencyStops; bool bContainsTransparency(false); // set defaults @@ -471,7 +471,7 @@ void FillProperties::pushToPropMap(ShapePropertyMap& rPropMap, const GraphicHelp aGradient.EndIntensity = 100; aGradient.Style = awt::GradientStyle_LINEAR; - // convert to ColorStops, check for contained transparency + // convert to BColorStops, check for contained transparency for (const auto& rCandidate : maGradientProps.maGradientStops) { const ::Color aColor(rCandidate.second.getColor(rGraphicHelper, nPhClr)); @@ -479,7 +479,7 @@ void FillProperties::pushToPropMap(ShapePropertyMap& rPropMap, const GraphicHelp bContainsTransparency = bContainsTransparency || rCandidate.second.hasTransparency(); } - // if we have transparency, convert to ColorStops + // if we have transparency, convert to BColorStops if (bContainsTransparency) { for (const auto& rCandidate : maGradientProps.maGradientStops) @@ -526,8 +526,8 @@ void FillProperties::pushToPropMap(ShapePropertyMap& rPropMap, const GraphicHelp aGradient.Style = awt::GradientStyle_RECT; } - basegfx::utils::reverseColorStops(aColorStops); - basegfx::utils::reverseColorStops(aTransparencyStops); + aColorStops.reverseColorStops(); + aTransparencyStops.reverseColorStops(); } else if (!maGradientProps.maGradientStops.empty()) { @@ -543,8 +543,8 @@ void FillProperties::pushToPropMap(ShapePropertyMap& rPropMap, const GraphicHelp aGradient.Angle = static_cast< sal_Int16 >( (8100 - (nDmlAngle / (PER_DEGREE / 10))) % 3600 ); } - // set ColorStops using UNO API - basegfx::utils::fillColorStopSequenceFromColorStops(aGradient.ColorStops, aColorStops); + // set BColorStops using UNO API + aGradient.ColorStops = aColorStops.getAsColorStopSequence(); // for compatibility, still set StartColor/EndColor // NOTE: All code after adapting to multi color gradients works @@ -577,7 +577,7 @@ void FillProperties::pushToPropMap(ShapePropertyMap& rPropMap, const GraphicHelp // push gradient transparency to property map if it exists if (!aTransparencyStops.empty()) { - basegfx::utils::fillColorStopSequenceFromColorStops(aGradient.ColorStops, aTransparencyStops); + aGradient.ColorStops = aTransparencyStops.getAsColorStopSequence(); rPropMap.setProperty(ShapeProperty::GradientTransparency, aGradient); } } diff --git a/oox/source/export/chartexport.cxx b/oox/source/export/chartexport.cxx index da8ef4924615..0c223bb452aa 100644 --- a/oox/source/export/chartexport.cxx +++ b/oox/source/export/chartexport.cxx @@ -1916,10 +1916,9 @@ void ChartExport::exportSolidFill(const Reference< XPropertySet >& xPropSet) if (basegfx::utils::fillGradient2FromAny(aTransparenceGradient, rTransparenceValue)) { - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromAny(aColorStops, rTransparenceValue); + const basegfx::BColorStops aColorStops(rTransparenceValue); basegfx::BColor aSingleColor; - bNeedGradientFill = !basegfx::utils::isSingleColor(aColorStops, aSingleColor); + bNeedGradientFill = !aColorStops.isSingleColor(aSingleColor); } if (!bNeedGradientFill && 0 != aTransparenceGradient.StartColor) diff --git a/oox/source/export/drawingml.cxx b/oox/source/export/drawingml.cxx index fa587d6190bf..11d562ff41b9 100644 --- a/oox/source/export/drawingml.cxx +++ b/oox/source/export/drawingml.cxx @@ -479,10 +479,9 @@ void DrawingML::WriteSolidFill( const Reference< XPropertySet >& rXPropSet ) { if (basegfx::utils::fillGradient2FromAny(aTransparenceGradient, mAny)) { - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromAny(aColorStops, mAny); + const basegfx::BColorStops aColorStops(mAny); basegfx::BColor aSingleColor; - bNeedGradientFill = !basegfx::utils::isSingleColor(aColorStops, aSingleColor); + bNeedGradientFill = !aColorStops.isSingleColor(aSingleColor); } if (!bNeedGradientFill && 0 != aTransparenceGradient.StartColor) @@ -779,8 +778,8 @@ void DrawingML::WriteGradientFill( const awt::Gradient2* pColorGradient, sal_Int32 nFixColor, const awt::Gradient2* pTransparenceGradient, double fFixTransparence) { - basegfx::ColorStops aColorStops; - basegfx::ColorStops aAlphaStops; + basegfx::BColorStops aColorStops; + basegfx::BColorStops aAlphaStops; basegfx::BColor aSingleColor(::Color(ColorTransparency, nFixColor).getBColor()); basegfx::BColor aSingleAlpha(fFixTransparence); awt::Gradient2 aGradient; @@ -835,12 +834,12 @@ void DrawingML::WriteGradientFill( { // we need to 'double' the gradient to make it appear as what we call // 'axial', but also scale and mirror in doing so - basegfx::ColorStops aNewColorStops; - basegfx::ColorStops aNewAlphaStops; + basegfx::BColorStops aNewColorStops; + basegfx::BColorStops aNewAlphaStops; // add mirrored gradients, scaled to [0.0 .. 0.5] - basegfx::ColorStops::const_reverse_iterator aRevCurrColor(aColorStops.rbegin()); - basegfx::ColorStops::const_reverse_iterator aRevCurrAlpha(aAlphaStops.rbegin()); + basegfx::BColorStops::const_reverse_iterator aRevCurrColor(aColorStops.rbegin()); + basegfx::BColorStops::const_reverse_iterator aRevCurrAlpha(aAlphaStops.rbegin()); while (aRevCurrColor != aColorStops.rend() && aRevCurrAlpha != aAlphaStops.rend()) { @@ -850,8 +849,8 @@ void DrawingML::WriteGradientFill( aRevCurrAlpha++; } - basegfx::ColorStops::const_iterator aCurrColor(aColorStops.begin()); - basegfx::ColorStops::const_iterator aCurrAlpha(aAlphaStops.begin()); + basegfx::BColorStops::const_iterator aCurrColor(aColorStops.begin()); + basegfx::BColorStops::const_iterator aCurrAlpha(aAlphaStops.begin()); if (basegfx::fTools::equalZero(aCurrColor->getStopOffset())) { @@ -887,8 +886,8 @@ void DrawingML::WriteGradientFill( // case awt::GradientStyle_SQUARE: { // all these types need the gradients to be mirrored - basegfx::utils::reverseColorStops(aColorStops); - basegfx::utils::reverseColorStops(aAlphaStops); + aColorStops.reverseColorStops(); + aAlphaStops.reverseColorStops(); bRadialOrEllipticalOrRectOrSquare = true; break; @@ -898,8 +897,8 @@ void DrawingML::WriteGradientFill( // export GradientStops (with alpha) mpFS->startElementNS(XML_a, XML_gsLst); - basegfx::ColorStops::const_iterator aCurrColor(aColorStops.begin()); - basegfx::ColorStops::const_iterator aCurrAlpha(aAlphaStops.begin()); + basegfx::BColorStops::const_iterator aCurrColor(aColorStops.begin()); + basegfx::BColorStops::const_iterator aCurrAlpha(aAlphaStops.begin()); while (aCurrColor != aColorStops.end() && aCurrAlpha != aAlphaStops.end()) { diff --git a/reportdesign/Library_rptui.mk b/reportdesign/Library_rptui.mk index c64e57994c07..e27068a24392 100644 --- a/reportdesign/Library_rptui.mk +++ b/reportdesign/Library_rptui.mk @@ -46,6 +46,7 @@ $(eval $(call gb_Library_use_libraries,rptui,\ tl \ utl \ vcl \ + basegfx \ )) $(eval $(call gb_Library_set_componentfile,rptui,reportdesign/util/rptui,services)) diff --git a/reportdesign/inc/pch/precompiled_rptui.hxx b/reportdesign/inc/pch/precompiled_rptui.hxx index 561a56432e90..46c40c5437d3 100644 --- a/reportdesign/inc/pch/precompiled_rptui.hxx +++ b/reportdesign/inc/pch/precompiled_rptui.hxx @@ -417,7 +417,6 @@ #include <svx/svxdllapi.h> #include <svx/xdash.hxx> #include <svx/xdef.hxx> -#include <svx/xgrad.hxx> #include <svx/xhatch.hxx> #include <svx/xit.hxx> #include <svx/xpoly.hxx> diff --git a/reportdesign/source/ui/misc/UITools.cxx b/reportdesign/source/ui/misc/UITools.cxx index e928bbd7cf2b..5cf63586033d 100644 --- a/reportdesign/source/ui/misc/UITools.cxx +++ b/reportdesign/source/ui/misc/UITools.cxx @@ -625,8 +625,8 @@ bool openCharDialog( const uno::Reference<report::XReportControlFormat >& _rxRep XColorListRef pColorList( XColorList::CreateStdColorList() ); const ::Color aNullLineCol(COL_DEFAULT_SHAPE_STROKE); // #i121448# Use defined default color const ::Color aNullFillCol(COL_DEFAULT_SHAPE_FILLING); // #i121448# Use defined default color - // XGradient() default already creates [COL_BLACK, COL_WHITE] as defaults - const XGradient aNullGrad; + // basegfx::BGradient() default already creates [COL_BLACK, COL_WHITE] as defaults + const basegfx::BGradient aNullGrad; const XHatch aNullHatch(aNullLineCol); std::vector<SfxPoolItem*> pDefaults diff --git a/reportdesign/source/ui/report/ReportController.cxx b/reportdesign/source/ui/report/ReportController.cxx index 4fa68d296b17..510e046e47bc 100644 --- a/reportdesign/source/ui/report/ReportController.cxx +++ b/reportdesign/source/ui/report/ReportController.cxx @@ -2373,8 +2373,8 @@ void OReportController::openPageDialog(const uno::Reference<report::XSection>& _ const ::Color aNullLineCol(COL_DEFAULT_SHAPE_STROKE); // #i121448# Use defined default color const ::Color aNullFillCol(COL_DEFAULT_SHAPE_FILLING); // #i121448# Use defined default color - // XGradient() default already creates [COL_BLACK, COL_WHITE] as defaults - const XGradient aNullGrad; + // basegfx::BGradient() default already creates [COL_BLACK, COL_WHITE] as defaults + const basegfx::BGradient aNullGrad; const XHatch aNullHatch(aNullLineCol); std::vector<SfxPoolItem*> pDefaults diff --git a/sc/inc/pch/precompiled_sc.hxx b/sc/inc/pch/precompiled_sc.hxx index bf57c56fdbfb..f2f14653ab09 100644 --- a/sc/inc/pch/precompiled_sc.hxx +++ b/sc/inc/pch/precompiled_sc.hxx @@ -443,7 +443,6 @@ #include <svx/svxdllapi.h> #include <svx/xdash.hxx> #include <svx/xdef.hxx> -#include <svx/xgrad.hxx> #include <svx/xhatch.hxx> #include <svx/xit.hxx> #include <svx/xpoly.hxx> diff --git a/sc/qa/unit/subsequent_filters_test3.cxx b/sc/qa/unit/subsequent_filters_test3.cxx index 779e07fe4589..44cd7024506c 100644 --- a/sc/qa/unit/subsequent_filters_test3.cxx +++ b/sc/qa/unit/subsequent_filters_test3.cxx @@ -1628,7 +1628,7 @@ CPPUNIT_TEST_FIXTURE(ScFiltersTest3, testTdf129789) CPPUNIT_ASSERT_EQUAL(drawing::FillStyle_GRADIENT, rStyleItemH2.GetValue()); const XFillGradientItem& rGradientItem = pCaptionH2->GetMergedItem(XATTR_FILLGRADIENT); - const basegfx::ColorStops& rColorStops(rGradientItem.GetGradientValue().GetColorStops()); + const basegfx::BColorStops& rColorStops(rGradientItem.GetGradientValue().GetColorStops()); CPPUNIT_ASSERT_EQUAL(size_t(2), rColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(rColorStops[0].getStopOffset(), 0.0)); @@ -1645,7 +1645,7 @@ CPPUNIT_TEST_FIXTURE(ScFiltersTest3, testTdf129789) CPPUNIT_ASSERT_EQUAL(drawing::FillStyle_GRADIENT, rStyleItemH9.GetValue()); const XFillGradientItem& rGradientItem2 = pCaptionH2->GetMergedItem(XATTR_FILLGRADIENT); - const basegfx::ColorStops& rColorStops2(rGradientItem2.GetGradientValue().GetColorStops()); + const basegfx::BColorStops& rColorStops2(rGradientItem2.GetGradientValue().GetColorStops()); CPPUNIT_ASSERT_EQUAL(size_t(2), rColorStops2.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(rColorStops2[0].getStopOffset(), 0.0)); diff --git a/sc/source/ui/drawfunc/drawsh.cxx b/sc/source/ui/drawfunc/drawsh.cxx index d5f50377a8a8..291ec3e236bc 100644 --- a/sc/source/ui/drawfunc/drawsh.cxx +++ b/sc/source/ui/drawfunc/drawsh.cxx @@ -82,7 +82,7 @@ namespace } if (const SfxStringItem* pJSON = rArgs.GetItemIfSet(SID_FILL_GRADIENT_JSON, false)) { - XGradient aGradient = XGradient::fromJSON(pJSON->GetValue()); + basegfx::BGradient aGradient = basegfx::BGradient::fromJSON(pJSON->GetValue()); XFillGradientItem aItem(aGradient); rArgs.Put(aItem); } diff --git a/sd/inc/pch/precompiled_sdui.hxx b/sd/inc/pch/precompiled_sdui.hxx index a0ca2927e3d8..37682da2f713 100644 --- a/sd/inc/pch/precompiled_sdui.hxx +++ b/sd/inc/pch/precompiled_sdui.hxx @@ -442,7 +442,6 @@ #include <svx/unomod.hxx> #include <svx/xdash.hxx> #include <svx/xdef.hxx> -#include <svx/xgrad.hxx> #include <svx/xhatch.hxx> #include <svx/xpoly.hxx> #include <svx/xtable.hxx> diff --git a/sd/qa/unit/export-tests-ooxml1.cxx b/sd/qa/unit/export-tests-ooxml1.cxx index 703eac601174..9140eddf143c 100644 --- a/sd/qa/unit/export-tests-ooxml1.cxx +++ b/sd/qa/unit/export-tests-ooxml1.cxx @@ -1226,8 +1226,7 @@ CPPUNIT_TEST_FIXTURE(SdOOXMLExportTest1, testTdf94238) CPPUNIT_ASSERT_EQUAL(static_cast<sal_Int16>(0), aGradient.Border); // MCGR: Use the completely imported gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + const basegfx::BColorStops aColorStops(aGradient.ColorStops); // Without the accompanying fix in place, this test would have failed with // 'Expected: 0, Actual : 10592673', i.e. the start color of the gradient @@ -1486,8 +1485,7 @@ CPPUNIT_TEST_FIXTURE(SdOOXMLExportTest1, testTdf128345GradientAxial) xShapePropSet->getPropertyValue("FillTransparenceGradient") >>= aTransparenceGradient; // MCGR: Use the completely imported gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aTransparenceGradient); + const basegfx::BColorStops aColorStops(aTransparenceGradient.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(3), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); diff --git a/sd/qa/unit/export-tests-ooxml2.cxx b/sd/qa/unit/export-tests-ooxml2.cxx index a656b37857ea..d4521b1ad87f 100644 --- a/sd/qa/unit/export-tests-ooxml2.cxx +++ b/sd/qa/unit/export-tests-ooxml2.cxx @@ -1011,8 +1011,7 @@ CPPUNIT_TEST_FIXTURE(SdOOXMLExportTest2, testTdf105739) aXBackgroundPropSet->getPropertyValue("FillGradient") >>= aFillGradient; // MCGR: Use the completely imported gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aFillGradient); + const basegfx::BColorStops aColorStops(aFillGradient.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(2), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); diff --git a/sd/qa/unit/export-tests-ooxml3.cxx b/sd/qa/unit/export-tests-ooxml3.cxx index 7b3bc17da941..bd343497ff59 100644 --- a/sd/qa/unit/export-tests-ooxml3.cxx +++ b/sd/qa/unit/export-tests-ooxml3.cxx @@ -1247,8 +1247,7 @@ CPPUNIT_TEST_FIXTURE(SdOOXMLExportTest3, testTdf127372) xShape->getPropertyValue("FillTransparenceGradient") >>= aTransparenceGradient; // MCGR: Use the completely imported gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aTransparenceGradient); + const basegfx::BColorStops aColorStops(aTransparenceGradient.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(2), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); @@ -1280,8 +1279,7 @@ CPPUNIT_TEST_FIXTURE(SdOOXMLExportTest3, testTdf127379) CPPUNIT_ASSERT(aXBackgroundPropSet->getPropertyValue("FillGradient") >>= aGradient); // MCGR: Use the completely imported gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + const basegfx::BColorStops aColorStops(aGradient.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(2), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); diff --git a/sd/qa/unit/misc-tests.cxx b/sd/qa/unit/misc-tests.cxx index cfa4f6a037c0..485feb5bbbd8 100644 --- a/sd/qa/unit/misc-tests.cxx +++ b/sd/qa/unit/misc-tests.cxx @@ -286,8 +286,7 @@ void SdMiscTest::testFillGradient() CPPUNIT_ASSERT(xPropSet2->getPropertyValue("FillGradient") >>= aGradient2); // MCGR: Use the completely imported gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient2); + const basegfx::BColorStops aColorStops(aGradient2.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(2), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); diff --git a/sd/qa/unit/uiimpress.cxx b/sd/qa/unit/uiimpress.cxx index b1614d6eb8ca..e3a9c86e91d1 100644 --- a/sd/qa/unit/uiimpress.cxx +++ b/sd/qa/unit/uiimpress.cxx @@ -764,8 +764,8 @@ CPPUNIT_TEST_FIXTURE(SdUiImpressTest, testPageFillGradient) drawing::FillStyle eXFS = pFillStyle->GetValue(); CPPUNIT_ASSERT_EQUAL(drawing::FillStyle_GRADIENT, eXFS); - XGradient aGradient = rPageAttr.GetItem(XATTR_FILLGRADIENT)->GetGradientValue(); - const basegfx::ColorStops& rColorStops(aGradient.GetColorStops()); + basegfx::BGradient aGradient(rPageAttr.GetItem(XATTR_FILLGRADIENT)->GetGradientValue()); + const basegfx::BColorStops& rColorStops(aGradient.GetColorStops()); CPPUNIT_ASSERT_EQUAL(size_t(2), rColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(rColorStops[0].getStopOffset(), 0.0)); diff --git a/sd/source/core/drawdoc4.cxx b/sd/source/core/drawdoc4.cxx index b697be203095..91c4dc600703 100644 --- a/sd/source/core/drawdoc4.cxx +++ b/sd/source/core/drawdoc4.cxx @@ -154,8 +154,8 @@ void SdDrawDocument::CreateLayoutTemplates() Color aNullCol(COL_DEFAULT_SHAPE_STROKE); XDash aNullDash; - XGradient aNullGrad( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BGradient aNullGrad( + basegfx::BColorStops( aNullCol.getBColor(), COL_WHITE.getBColor())); aNullGrad.SetStartIntens( 100 ); @@ -392,7 +392,7 @@ void SdDrawDocument::CreateLayoutTemplates() // Graphic OUString aGraphicName; XFillGradientItem aFillGradient; - XGradient aGradient; + basegfx::BGradient aGradient; { aGraphicName = SdResId(STR_POOLSHEET_GRAPHIC); @@ -419,7 +419,7 @@ void SdDrawDocument::CreateLayoutTemplates() aGradient.SetAngle( 0_deg10 ); // 0° angle aGradient.SetColorStops( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BColorStops( Color(0xcccccc).getBColor(), // light gray 3 COL_WHITE.getBColor())); // white @@ -443,7 +443,7 @@ void SdDrawDocument::CreateLayoutTemplates() aGradient.SetAngle( 300_deg10 ); aGradient.SetColorStops( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BColorStops( COL_WHITE.getBColor(), // white Color(0xcccccc).getBColor())); // light gray 3 @@ -461,7 +461,7 @@ void SdDrawDocument::CreateLayoutTemplates() pISet = &pSheet->GetItemSet(); aGradient.SetColorStops( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BColorStops( Color(0x00729fcf).getBColor(), // light blue 2 Color(0x00355269).getBColor())); // dark blue 2 @@ -479,7 +479,7 @@ void SdDrawDocument::CreateLayoutTemplates() pISet = &pSheet->GetItemSet(); aGradient.SetColorStops( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BColorStops( Color(0x0077bc65).getBColor(), // light green 2 Color(0x00127622).getBColor())); // dark green 2 @@ -498,7 +498,7 @@ void SdDrawDocument::CreateLayoutTemplates() pISet = &pSheet->GetItemSet(); aGradient.SetColorStops( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BColorStops( Color(0x00ff6d6d).getBColor(), // light red 2 Color(0x00c9211e).getBColor())); // dark red 2 @@ -516,7 +516,7 @@ void SdDrawDocument::CreateLayoutTemplates() pISet = &pSheet->GetItemSet(); aGradient.SetColorStops( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BColorStops( Color(0x00ffde59).getBColor(), // light gold 2 Color(0x00b47804).getBColor())); // dark gold 2 diff --git a/sd/source/ui/sidebar/SlideBackground.cxx b/sd/source/ui/sidebar/SlideBackground.cxx index dc7f8f0fd024..274789cf523b 100644 --- a/sd/source/ui/sidebar/SlideBackground.cxx +++ b/sd/source/ui/sidebar/SlideBackground.cxx @@ -48,7 +48,6 @@ #include <svx/svxids.hrc> #include <svx/xfillit0.hxx> #include <svx/xflclit.hxx> -#include <svx/xgrad.hxx> #include <svx/xbtmpit.hxx> #include <svx/xflhtit.hxx> #include <svx/svdpage.hxx> @@ -398,15 +397,15 @@ void SlideBackground::Update() mxFillGrad1->show(); mxFillGrad2->show(); - const XGradient xGradient = GetGradientSetOrDefault(); - const Color aStartColor(xGradient.GetColorStops().front().getStopColor()); + const basegfx::BGradient aBGradient = GetGradientSetOrDefault(); + const Color aStartColor(aBGradient.GetColorStops().front().getStopColor()); mxFillGrad1->SelectEntry(aStartColor); - const Color aEndColor(xGradient.GetColorStops().back().getStopColor()); + const Color aEndColor(aBGradient.GetColorStops().back().getStopColor()); mxFillGrad2->SelectEntry(aEndColor); // MCGR: preserve in-between ColorStops if given - if (xGradient.GetColorStops().size() > 2) - maColorStops = basegfx::ColorStops(xGradient.GetColorStops().begin() + 1, xGradient.GetColorStops().end() - 1); + if (aBGradient.GetColorStops().size() > 2) + maColorStops = basegfx::BColorStops(aBGradient.GetColorStops().begin() + 1, aBGradient.GetColorStops().end() - 1); else maColorStops.clear(); } @@ -756,11 +755,11 @@ Color const & SlideBackground::GetColorSetOrDefault() return mpColorItem->GetColorValue(); } -XGradient const & SlideBackground::GetGradientSetOrDefault() +basegfx::BGradient const & SlideBackground::GetGradientSetOrDefault() { if( !mpGradientItem ) { - XGradient aGradient; + basegfx::BGradient aGradient; OUString aGradientName; if (SfxObjectShell* pSh = SfxObjectShell::Current()) { @@ -1133,7 +1132,7 @@ IMPL_LINK_NOARG(SlideBackground, FillColorHdl, ColorListBox&, void) break; case drawing::FillStyle_GRADIENT: { - XGradient aGradient(createColorStops()); + basegfx::BGradient aGradient(createColorStops()); // the name doesn't really matter, it'll be converted to unique one eventually, // but it has to be non-empty @@ -1286,9 +1285,9 @@ IMPL_LINK_NOARG( SlideBackground, ModifyMarginHdl, weld::ComboBox&, void ) } } -basegfx::ColorStops SlideBackground::createColorStops() +basegfx::BColorStops SlideBackground::createColorStops() { - basegfx::ColorStops aColorStops; + basegfx::BColorStops aColorStops; aColorStops.emplace_back(0.0, mxFillGrad1->GetSelectEntryColor().getBColor()); diff --git a/sd/source/ui/sidebar/SlideBackground.hxx b/sd/source/ui/sidebar/SlideBackground.hxx index 5d029296c357..3a2dd2475680 100644 --- a/sd/source/ui/sidebar/SlideBackground.hxx +++ b/sd/source/ui/sidebar/SlideBackground.hxx @@ -36,7 +36,6 @@ class SvxPageItem; class SvxLongLRSpaceItem; class SvxLongULSpaceItem; class XFillColorItem; -class XGradient; class XFillGradientItem; class XFillBitmapItem; class XFillHatchItem; @@ -140,7 +139,7 @@ private: MapUnit meUnit; // MCGR: Preserve in-between ColorStops until we have an UI to edit these - basegfx::ColorStops maColorStops; + basegfx::BColorStops maColorStops; DECL_LINK(FillBackgroundHdl, weld::ComboBox&, void); DECL_LINK(FillStyleModifyHdl, weld::ComboBox&, void); @@ -162,7 +161,7 @@ private: void SetMarginsFieldUnit(); Color const & GetColorSetOrDefault(); - XGradient const & GetGradientSetOrDefault(); + basegfx::BGradient const & GetGradientSetOrDefault(); OUString const & GetHatchingSetOrDefault(); OUString const & GetBitmapSetOrDefault(); OUString const & GetPatternSetOrDefault(); @@ -178,7 +177,7 @@ private: static FieldUnit GetCurrentUnit(SfxItemState eState, const SfxPoolItem* pState); // MCGR: Preserve in-between ColorStops until we have an UI to edit these - basegfx::ColorStops createColorStops(); + basegfx::BColorStops createColorStops(); }; } diff --git a/sd/source/ui/view/drviews2.cxx b/sd/source/ui/view/drviews2.cxx index 5c5aa56e960d..90560323842b 100644 --- a/sd/source/ui/view/drviews2.cxx +++ b/sd/source/ui/view/drviews2.cxx @@ -562,7 +562,7 @@ public: const SfxStringItem* pJSON = static_cast<const SfxStringItem*>(pItem); if (pJSON) { - XGradient aGradient = XGradient::fromJSON(pJSON->GetValue()); + basegfx::BGradient aGradient = basegfx::BGradient::fromJSON(pJSON->GetValue()); XFillGradientItem aItem(aGradient); pArgs->Put(aItem); } diff --git a/sd/source/ui/view/drviews7.cxx b/sd/source/ui/view/drviews7.cxx index bdb46dacbe3a..a2f12e9ccaef 100644 --- a/sd/source/ui/view/drviews7.cxx +++ b/sd/source/ui/view/drviews7.cxx @@ -1817,7 +1817,7 @@ void DrawViewShell::SetPageProperties (SfxRequest& rReq) if (SfxItemState::SET == pArgs->GetItemState(SID_FILL_GRADIENT_JSON, false, &pItem)) { const SfxStringItem* pJSON = static_cast<const SfxStringItem*>(pItem); - XFillGradientItem aGradientItem( XGradient::fromJSON(pJSON->GetValue()) ); + XFillGradientItem aGradientItem( basegfx::BGradient::fromJSON(pJSON->GetValue()) ); // MigrateItemSet guarantees unique gradient names SfxItemSetFixed<XATTR_FILLGRADIENT, XATTR_FILLGRADIENT> aMigrateSet(mpDrawView->GetModel().GetItemPool()); diff --git a/sd/source/ui/view/drviews9.cxx b/sd/source/ui/view/drviews9.cxx index f0a6cae461a5..1ae793e4d60a 100644 --- a/sd/source/ui/view/drviews9.cxx +++ b/sd/source/ui/view/drviews9.cxx @@ -20,7 +20,6 @@ #include <config_features.h> #include <DrawViewShell.hxx> -#include <svx/xgrad.hxx> #include <svx/svdpagv.hxx> #include <svx/xfillit0.hxx> #include <svx/xlineit0.hxx> @@ -346,16 +345,16 @@ void DrawViewShell::AttrExec (SfxRequest &rReq) if (pEntry->GetName () == pName->GetValue ()) { - XGradient aGradient(pEntry->GetGradient()); - basegfx::ColorStops aNewColorStops(aGradient.GetColorStops()); + basegfx::BGradient aGradient(pEntry->GetGradient()); + basegfx::BColorStops aNewColorStops(aGradient.GetColorStops()); if (SID_SETGRADSTARTCOLOR == rReq.GetSlot ()) { - basegfx::utils::replaceStartColor(aNewColorStops, aColor.getBColor()); + aNewColorStops.replaceStartColor(aColor.getBColor()); } else { - basegfx::utils::replaceEndColor(aNewColorStops, aColor.getBColor()); + aNewColorStops.replaceEndColor(aColor.getBColor()); } aGradient.SetColorStops(aNewColorStops); @@ -373,8 +372,8 @@ void DrawViewShell::AttrExec (SfxRequest &rReq) if (i >= nCounts) { Color aBlack (0, 0, 0); - XGradient aGradient ( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BGradient aGradient ( + basegfx::BColorStops( (rReq.GetSlot () == SID_SETGRADSTARTCOLOR) ? aColor.getBColor() : aBlack.getBColor(), @@ -556,7 +555,7 @@ void DrawViewShell::AttrExec (SfxRequest &rReq) if (pEntry->GetName () == pName->GetValue ()) { - XGradient aGradient(pEntry->GetGradient()); + basegfx::BGradient aGradient(pEntry->GetGradient()); aGradient.SetGradientStyle (static_cast<css::awt::GradientStyle>(pStyle->GetValue ())); aGradient.SetAngle (Degree10(pAngle->GetValue () * 10)); @@ -579,8 +578,8 @@ void DrawViewShell::AttrExec (SfxRequest &rReq) if (i >= nCounts) { Color aBlack (0, 0, 0); - XGradient aGradient ( - basegfx::utils::createColorStopsFromStartEndColor(aBlack.getBColor(), aBlack.getBColor()), + basegfx::BGradient aGradient ( + basegfx::BColorStops(aBlack.getBColor(), aBlack.getBColor()), static_cast<css::awt::GradientStyle>(pStyle->GetValue ()), Degree10(pAngle->GetValue () * 10), static_cast<short>(pCenterX->GetValue ()), static_cast<short>(pCenterY->GetValue ()), static_cast<short>(pBorder->GetValue ()), @@ -864,7 +863,7 @@ void DrawViewShell::AttrState (SfxItemSet& rSet) case 4 : { const XFillGradientItem &rFillGradientItem = aAttr.Get (XATTR_FILLGRADIENT); - const XGradient &rGradient = rFillGradientItem.GetGradientValue (); + const basegfx::BGradient &rGradient = rFillGradientItem.GetGradientValue (); aColor = (rWhatKind.GetValue () == 3) ? Color(rGradient.GetColorStops().front().getStopColor()) diff --git a/solenv/clang-format/excludelist b/solenv/clang-format/excludelist index ed5d2b053000..70211a98369f 100644 --- a/solenv/clang-format/excludelist +++ b/solenv/clang-format/excludelist @@ -6041,7 +6041,6 @@ include/svx/xftouit.hxx include/svx/xftshit.hxx include/svx/xftshxy.hxx include/svx/xftstit.hxx -include/svx/xgrad.hxx include/svx/xgrscit.hxx include/svx/xhatch.hxx include/svx/xit.hxx diff --git a/svx/inc/pch/precompiled_svx.hxx b/svx/inc/pch/precompiled_svx.hxx index 8ccbe5900922..f424a84556f8 100644 --- a/svx/inc/pch/precompiled_svx.hxx +++ b/svx/inc/pch/precompiled_svx.hxx @@ -426,7 +426,6 @@ #include <svx/xflclit.hxx> #include <svx/xflftrit.hxx> #include <svx/xfltrit.hxx> -#include <svx/xgrad.hxx> #include <svx/xit.hxx> #include <svx/xlineit0.hxx> #include <svx/xlnclit.hxx> diff --git a/svx/source/customshapes/EnhancedCustomShape2d.cxx b/svx/source/customshapes/EnhancedCustomShape2d.cxx index e6b0173c5bc2..bca864f05fe3 100644 --- a/svx/source/customshapes/EnhancedCustomShape2d.cxx +++ b/svx/source/customshapes/EnhancedCustomShape2d.cxx @@ -41,7 +41,6 @@ #include <svx/xflgrit.hxx> #include <svx/xflhtit.hxx> #include <svx/xbtmpit.hxx> -#include <svx/xgrad.hxx> #include <svx/xhatch.hxx> #include <svx/sdshitm.hxx> #include <com/sun/star/awt/Size.hpp> @@ -2800,24 +2799,24 @@ void EnhancedCustomShape2d::AdaptObjColor( } case drawing::FillStyle_GRADIENT: { - XGradient aXGradient(rObj.GetMergedItem(XATTR_FILLGRADIENT).GetGradientValue()); + basegfx::BGradient aBGradient(rObj.GetMergedItem(XATTR_FILLGRADIENT).GetGradientValue()); if ( nColorCount || 0.0 != dBrightness ) { - basegfx::ColorStops aColorStops(aXGradient.GetColorStops()); + basegfx::BColorStops aColorStops(aBGradient.GetColorStops()); for (auto& candidate : aColorStops) { - candidate = basegfx::ColorStop( + candidate = basegfx::BColorStop( candidate.getStopOffset(), GetColorData( Color(candidate.getStopColor()), std::min(nColorIndex, nColorCount-1), dBrightness ).getBColor()); } - aXGradient.SetColorStops(aColorStops); + aBGradient.SetColorStops(aColorStops); } - rObj.SetMergedItem( XFillGradientItem( "", aXGradient ) ); + rObj.SetMergedItem( XFillGradientItem( "", aBGradient ) ); break; } case drawing::FillStyle_HATCH: diff --git a/svx/source/sdr/primitive2d/sdrattributecreator.cxx b/svx/source/sdr/primitive2d/sdrattributecreator.cxx index d620f8468395..aad8ba4576e4 100644 --- a/svx/source/sdr/primitive2d/sdrattributecreator.cxx +++ b/svx/source/sdr/primitive2d/sdrattributecreator.cxx @@ -415,9 +415,9 @@ namespace drawinglayer::primitive2d if((pGradientItem = rSet.GetItemIfSet(XATTR_FILLFLOATTRANSPARENCE, true)) && pGradientItem->IsEnabled()) { - const XGradient& rGradient = pGradientItem->GetGradientValue(); + const basegfx::BGradient& rGradient = pGradientItem->GetGradientValue(); basegfx::BColor aSingleColor; - const bool bSingleColor(basegfx::utils::isSingleColor(rGradient.GetColorStops(), aSingleColor)); + const bool bSingleColor(rGradient.GetColorStops().isSingleColor(aSingleColor)); const bool bCompletelyTransparent(bSingleColor && basegfx::fTools::equal(aSingleColor.luminance(), 1.0)); if(bCompletelyTransparent) @@ -443,309 +443,27 @@ namespace drawinglayer::primitive2d } case drawing::FillStyle_GRADIENT : { - XGradient aXGradient(rSet.Get(XATTR_FILLGRADIENT).GetGradientValue()); - basegfx::ColorStops aColorStops(aXGradient.GetColorStops()); + basegfx::BGradient aBGradient(rSet.Get(XATTR_FILLGRADIENT).GetGradientValue()); + basegfx::BColorStops aColorStops(aBGradient.GetColorStops()); - // test code here, can/will be removed later - static const char* pUseGradientSteps(std::getenv("MCGR_TEST")); - static int nUseGradientSteps(pUseGradientSteps ? std::atoi(pUseGradientSteps) : 0); - switch(nUseGradientSteps) - { - case 1: - { - // just test a nice valid gradient - aColorStops.clear(); - aColorStops.emplace_back(0.0, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.25, COL_LIGHTGREEN.getBColor()); // green@25% - aColorStops.emplace_back(0.50, COL_YELLOW.getBColor()); // yellow@50% - aColorStops.emplace_back(0.75, COL_LIGHTMAGENTA.getBColor()); // pink@75% - aColorStops.emplace_back(1.0, COL_LIGHTBLUE.getBColor()); // blue - break; - } - - case 2: - { - // single added in-between, no change of start/end - aColorStops.clear(); - aColorStops.emplace_back(0.0, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.5, COL_YELLOW.getBColor()); // yellow@50% - aColorStops.emplace_back(1.0, COL_LIGHTBLUE.getBColor()); // blue - break; - } - - case 3: - { - // check additional StartColor, the second one has to win - aColorStops.clear(); - aColorStops.emplace_back(0.0, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.0, COL_YELLOW.getBColor()); // yellow@50% - aColorStops.emplace_back(1.0, COL_LIGHTBLUE.getBColor()); // blue - break; - } - - case 4: - { - // check additional EndColor, the first one has to win - aColorStops.clear(); - aColorStops.emplace_back(0.0, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(1.0, COL_YELLOW.getBColor()); // yellow@50% - aColorStops.emplace_back(1.0, COL_LIGHTBLUE.getBColor()); // blue - break; - } - - case 5: - { - // check invalid color (too low index), has to be ignored - aColorStops.clear(); - aColorStops.emplace_back(0.0, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(1.0, COL_LIGHTBLUE.getBColor()); // blue - aColorStops.emplace_back(-1.0, COL_YELLOW.getBColor()); // yellow@50% - break; - } - - case 6: - { - // check invalid color (too high index), has to be ignored - aColorStops.clear(); - aColorStops.emplace_back(0.0, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(1.0, COL_LIGHTBLUE.getBColor()); // blue - aColorStops.emplace_back(2.0, COL_YELLOW.getBColor()); // yellow@50% - break; - } - - case 7: - { - // check in-between single-color section - aColorStops.clear(); - aColorStops.emplace_back(0.0, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.3, COL_YELLOW.getBColor()); // yellow@50% - aColorStops.emplace_back(0.7, COL_YELLOW.getBColor()); // yellow@50% - aColorStops.emplace_back(1.0, COL_LIGHTBLUE.getBColor()); // blue - break; - } - - case 8: - { - // check in-between single-color sections - aColorStops.clear(); - aColorStops.emplace_back(0.0, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.2, COL_YELLOW.getBColor()); // yellow@50% - aColorStops.emplace_back(0.4, COL_YELLOW.getBColor()); // yellow@50% - aColorStops.emplace_back(0.5, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.6, COL_YELLOW.getBColor()); // yellow@50% - aColorStops.emplace_back(0.8, COL_YELLOW.getBColor()); // yellow@50% - aColorStops.emplace_back(1.0, COL_LIGHTBLUE.getBColor()); // blue - break; - } - - case 9: - { - // check single-color start area - aColorStops.clear(); - aColorStops.emplace_back(0.0, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.6, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(1.0, COL_LIGHTBLUE.getBColor()); // blue - break; - } - - case 10: - { - // check single-color end area - aColorStops.clear(); - aColorStops.emplace_back(0.0, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.4, COL_LIGHTBLUE.getBColor()); // blue - aColorStops.emplace_back(1.0, COL_LIGHTBLUE.getBColor()); // blue - break; - } - - case 11: - { - // check case without direct Start/EndColor - aColorStops.clear(); - aColorStops.emplace_back(0.4, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.6, COL_LIGHTBLUE.getBColor()); // blue - break; - } - - case 12: - { - // check case without colors at all - aColorStops.clear(); - break; - } - - case 13: - { - // check case with single stop - aColorStops.clear(); - aColorStops.emplace_back(0.5, COL_LIGHTRED.getBColor()); // red - break; - } - - case 14: - { - // check case with single-double stop - aColorStops.clear(); - aColorStops.emplace_back(0.5, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.5, COL_LIGHTRED.getBColor()); // red - break; - } - - case 15: - { - // check case with single stop diff colors - aColorStops.clear(); - aColorStops.emplace_back(0.5, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.5, COL_LIGHTBLUE.getBColor()); // blue - break; - } - - case 16: - { - // check case with gradient, hard change, gradient - aColorStops.clear(); - aColorStops.emplace_back(0.0, COL_LIGHTGREEN.getBColor()); // green - aColorStops.emplace_back(0.2, COL_LIGHTGREEN.getBColor()); // green - aColorStops.emplace_back(0.2, COL_LIGHTBLUE.getBColor()); // blue - aColorStops.emplace_back(0.5, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.5, COL_LIGHTBLUE.getBColor()); // blue - aColorStops.emplace_back(0.8, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.8, COL_LIGHTGREEN.getBColor()); // green - aColorStops.emplace_back(1.0, COL_LIGHTGREEN.getBColor()); // green - break; - } - - case 17: - { - // check case with single stop < 0.0 - aColorStops.clear(); - aColorStops.emplace_back(-0.5, COL_LIGHTRED.getBColor()); // red - break; - } - - case 18: - { - // check case with single stop > 1.0 - aColorStops.clear(); - aColorStops.emplace_back(1.5, COL_LIGHTRED.getBColor()); // red - break; - } - - case 19: - { - // check case with stops overlapping 0.0 - aColorStops.clear(); - aColorStops.emplace_back(-0.5, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.5, COL_LIGHTBLUE.getBColor()); // blue - break; - } - - case 20: - { - // check case with stops overlapping 1.0 - aColorStops.clear(); - aColorStops.emplace_back(0.5, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(1.5, COL_LIGHTBLUE.getBColor()); // blue - break; - } - - case 21: - { - // check case with multiple stops < 0.0 - aColorStops.clear(); - aColorStops.emplace_back(-0.5, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(-0.4, COL_LIGHTBLUE.getBColor()); // blue - aColorStops.emplace_back(-0.3, COL_LIGHTGREEN.getBColor()); // green - break; - } - - case 22: - { - // check case with multiple stops > 1.0 - aColorStops.clear(); - aColorStops.emplace_back(1.3, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(1.4, COL_LIGHTBLUE.getBColor()); // blue - aColorStops.emplace_back(1.5, COL_LIGHTGREEN.getBColor()); // green - break; - } - - case 23: - { - // check case with stops overlapping 0.0 and 1.0 - aColorStops.clear(); - aColorStops.emplace_back(-0.5, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.5, COL_LIGHTBLUE.getBColor()); // blue - aColorStops.emplace_back(0.5, COL_LIGHTGREEN.getBColor()); // green - aColorStops.emplace_back(1.5, COL_LIGHTRED.getBColor()); // red - break; - } - - case 24: - { - // check case with stops overlapping 0.0 and 1.0 and multiple entries - aColorStops.clear(); - aColorStops.emplace_back(-0.5, COL_LIGHTGREEN.getBColor()); // green - aColorStops.emplace_back(-0.5, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(0.4, COL_LIGHTBLUE.getBColor()); // blue - aColorStops.emplace_back(0.5, COL_YELLOW.getBColor()); // yellow - aColorStops.emplace_back(0.6, COL_LIGHTGREEN.getBColor()); // green - aColorStops.emplace_back(1.5, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(1.5, COL_LIGHTGREEN.getBColor()); // green - break; - } - - case 25: - { - // check case with just two stops overlapping 0.0 and 1.0 - aColorStops.clear(); - aColorStops.emplace_back(-0.5, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(1.5, COL_LIGHTGREEN.getBColor()); // green - break; - } - - case 26: - { - // check case with just two stops overlapping 0.0 and 1.0 faaaar out - aColorStops.clear(); - aColorStops.emplace_back(-5.5, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(5.5, COL_LIGHTGREEN.getBColor()); // green - break; - } - - case 27: - { - // check case with just two stops overlapping 0.0 and 1.0 faaaar out but closer to one - aColorStops.clear(); - aColorStops.emplace_back(-1.5, COL_LIGHTRED.getBColor()); // red - aColorStops.emplace_back(5.5, COL_LIGHTGREEN.getBColor()); // green - break; - } - - default: - { - break; - } - } - - if (aXGradient.GetStartIntens() != 100 || aXGradient.GetEndIntens() != 100) + if (aBGradient.GetStartIntens() != 100 || aBGradient.GetEndIntens() != 100) { // Need to do the (old, crazy) blend against black for a // used intensity, but now for all ColorStops relative to their // offsets, where 0 means black and 100 means original color - basegfx::utils::blendColorStopsToIntensity( - aColorStops, - aXGradient.GetStartIntens() * 0.01, - aXGradient.GetEndIntens() * 0.01, + aColorStops.blendToIntensity( + aBGradient.GetStartIntens() * 0.01, + aBGradient.GetEndIntens() * 0.01, basegfx::BColor()); // COL_BLACK } aGradient = attribute::FillGradientAttribute( - aXGradient.GetGradientStyle(), - static_cast<double>(aXGradient.GetBorder()) * 0.01, - static_cast<double>(aXGradient.GetXOffset()) * 0.01, - static_cast<double>(aXGradient.GetYOffset()) * 0.01, - toRadians(aXGradient.GetAngle()), + aBGradient.GetGradientStyle(), + static_cast<double>(aBGradient.GetBorder()) * 0.01, + static_cast<double>(aBGradient.GetXOffset()) * 0.01, + static_cast<double>(aBGradient.GetYOffset()) * 0.01, + toRadians(aBGradient.GetAngle()), aColorStops, rSet.Get(XATTR_GRADIENTSTEPCOUNT).GetValue()); @@ -885,9 +603,9 @@ namespace drawinglayer::primitive2d && pGradientItem->IsEnabled()) { // test if float transparency is completely transparent - const XGradient& rGradient(pGradientItem->GetGradientValue()); + const basegfx::BGradient& rGradient(pGradientItem->GetGradientValue()); basegfx::BColor aSingleColor; - const bool bSingleColor(basegfx::utils::isSingleColor(rGradient.GetColorStops(), aSingleColor)); + const bool bSingleColor(rGradient.GetColorStops().isSingleColor(aSingleColor)); const bool bCompletelyTransparent(bSingleColor && basegfx::fTools::equal(aSingleColor.luminance(), 1.0)); const bool bNotTransparent(bSingleColor && basegfx::fTools::equalZero(aSingleColor.luminance())); @@ -897,13 +615,12 @@ namespace drawinglayer::primitive2d // Both cases are optimizations, always creating FillGradientAttribute will work, too if (!bNotTransparent && !bCompletelyTransparent) { - basegfx::ColorStops aColorStops(rGradient.GetColorStops()); + basegfx::BColorStops aColorStops(rGradient.GetColorStops()); if (rGradient.GetStartIntens() != 100 || rGradient.GetEndIntens() != 100) { // this may also be set for transparence, so need to take care of it - basegfx::utils::blendColorStopsToIntensity( - aColorStops, + aColorStops.blendToIntensity( rGradient.GetStartIntens() * 0.01, rGradient.GetEndIntens() * 0.01, basegfx::BColor()); // COL_BLACK diff --git a/svx/source/sidebar/area/AreaPropertyPanelBase.cxx b/svx/source/sidebar/area/AreaPropertyPanelBase.cxx index bb79b0086fd6..a1ff31c7186a 100644 --- a/svx/source/sidebar/area/AreaPropertyPanelBase.cxx +++ b/svx/source/sidebar/area/AreaPropertyPanelBase.cxx @@ -128,7 +128,7 @@ void AreaPropertyPanelBase::Initialize() maGradientLinear.SetYOffset(DEFAULT_CENTERY); maGradientLinear.SetAngle(Degree10(DEFAULT_ANGLE)); maGradientLinear.SetColorStops( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BColorStops( Color(DEFAULT_STARTVALUE).getBColor(), Color(DEFAULT_ENDVALUE).getBColor())); maGradientLinear.SetBorder(DEFAULT_BORDER); @@ -297,7 +297,7 @@ void AreaPropertyPanelBase::SelectFillAttrHdl_Impl() if (pSh && pSh->GetItem(SID_COLOR_TABLE)) { - XGradient aGradient(createColorStops()); + basegfx::BGradient aGradient(createColorStops()); aGradient.SetAngle(Degree10(mxMTRAngle->get_value(FieldUnit::DEGREE) * 10)); aGradient.SetGradientStyle(static_cast<css::awt::GradientStyle>(mxGradientStyle->get_active())); @@ -477,7 +477,7 @@ void AreaPropertyPanelBase::FillStyleChanged(bool bUpdateModel) const SvxGradientListItem* pItem = pSh->GetItem(SID_GRADIENT_LIST); if (pItem->GetGradientList()->Count() > 0) { - const XGradient aGradient + const basegfx::BGradient aGradient = pItem->GetGradientList()->GetGradient(0)->GetGradient(); const OUString aName = pItem->GetGradientList()->GetGradient(0)->GetName(); const XFillGradientItem aXFillGradientItem(aName, aGradient); @@ -490,7 +490,7 @@ void AreaPropertyPanelBase::FillStyleChanged(bool bUpdateModel) // MCGR: preserve in-between ColorStops if given if (aGradient.GetColorStops().size() > 2) - maColorStops = basegfx::ColorStops(aGradient.GetColorStops().begin() + 1, aGradient.GetColorStops().end() - 1); + maColorStops = basegfx::BColorStops(aGradient.GetColorStops().begin() + 1, aGradient.GetColorStops().end() - 1); else maColorStops.clear(); @@ -511,13 +511,13 @@ void AreaPropertyPanelBase::FillStyleChanged(bool bUpdateModel) { const OUString aString(mpFillGradientItem->GetName()); mxLbFillAttr->set_active_text(aString); - const XGradient aGradient = mpFillGradientItem->GetGradientValue(); + const basegfx::BGradient aGradient = mpFillGradientItem->GetGradientValue(); mxLbFillGradFrom->SelectEntry(Color(aGradient.GetColorStops().front().getStopColor())); mxLbFillGradTo->SelectEntry(Color(aGradient.GetColorStops().back().getStopColor())); // MCGR: preserve in-between ColorStops if given if (aGradient.GetColorStops().size() > 2) - maColorStops = basegfx::ColorStops(aGradient.GetColorStops().begin() + 1, aGradient.GetColorStops().end() - 1); + maColorStops = basegfx::BColorStops(aGradient.GetColorStops().begin() + 1, aGradient.GetColorStops().end() - 1); else maColorStops.clear(); @@ -715,7 +715,7 @@ void AreaPropertyPanelBase::ImpUpdateTransparencies() { if(mpFloatTransparenceItem->IsEnabled()) { - const XGradient& rGradient = mpFloatTransparenceItem->GetGradientValue(); + const basegfx::BGradient& rGradient = mpFloatTransparenceItem->GetGradientValue(); sal_Int32 nEntryPos(0); OUString* pImage = nullptr; @@ -1267,7 +1267,7 @@ IMPL_LINK_NOARG(AreaPropertyPanelBase, ChangeTrgrTypeHdl_Impl, weld::ComboBox&, nSelectType -= 2; } - XGradient aTmpGradient; + basegfx::BGradient aTmpGradient; switch(static_cast<css::awt::GradientStyle>(nSelectType)) { @@ -1313,7 +1313,7 @@ IMPL_LINK_NOARG(AreaPropertyPanelBase, ModifyTransparentHdl_Impl, weld::MetricSp setFillTransparence(aLinearItem); } -const XGradient& AreaPropertyPanelBase::GetGradient (const css::awt::GradientStyle eStyle) const +const basegfx::BGradient& AreaPropertyPanelBase::GetGradient (const css::awt::GradientStyle eStyle) const { switch (eStyle) { @@ -1333,7 +1333,7 @@ const XGradient& AreaPropertyPanelBase::GetGradient (const css::awt::GradientSty } } -void AreaPropertyPanelBase::SetGradient (const XGradient& rGradient) +void AreaPropertyPanelBase::SetGradient (const basegfx::BGradient& rGradient) { switch (rGradient.GetGradientStyle()) { @@ -1365,9 +1365,9 @@ sal_Int32 AreaPropertyPanelBase::GetSelectedTransparencyTypeIndex() const return mxLBTransType->get_active(); } -basegfx::ColorStops AreaPropertyPanelBase::createColorStops() +basegfx::BColorStops AreaPropertyPanelBase::createColorStops() { - basegfx::ColorStops aColorStops; + basegfx::BColorStops aColorStops; aColorStops.emplace_back(0.0, mxLbFillGradFrom->GetSelectEntryColor().getBColor()); diff --git a/svx/source/sidebar/area/AreaTransparencyGradientPopup.cxx b/svx/source/sidebar/area/AreaTransparencyGradientPopup.cxx index 34d618e8a2cd..df943359ff19 100644 --- a/svx/source/sidebar/area/AreaTransparencyGradientPopup.cxx +++ b/svx/source/sidebar/area/AreaTransparencyGradientPopup.cxx @@ -20,7 +20,6 @@ #include <svx/sidebar/AreaTransparencyGradientPopup.hxx> #include <svx/sidebar/AreaPropertyPanelBase.hxx> #include <svx/xflftrit.hxx> -#include <svx/xgrad.hxx> namespace svx::sidebar { @@ -56,9 +55,9 @@ AreaTransparencyGradientPopup::~AreaTransparencyGradientPopup() void AreaTransparencyGradientPopup::InitStatus(XFillFloatTransparenceItem const * pGradientItem) { - const XGradient& rGradient = pGradientItem->GetGradientValue(); + const basegfx::BGradient& rGradient = pGradientItem->GetGradientValue(); - XGradient aGradient; + basegfx::BGradient aGradient; Color aStart(rGradient.GetColorStops().front().getStopColor()); Color aEnd(rGradient.GetColorStops().back().getStopColor()); @@ -87,7 +86,7 @@ void AreaTransparencyGradientPopup::InitStatus(XFillFloatTransparenceItem const // MCGR: preserve in-between ColorStops if given if (aGradient.GetColorStops().size() > 2) - maColorStops = basegfx::ColorStops(aGradient.GetColorStops().begin() + 1, aGradient.GetColorStops().end() - 1); + maColorStops = basegfx::BColorStops(aGradient.GetColorStops().begin() + 1, aGradient.GetColorStops().end() - 1); else maColorStops.clear(); @@ -97,7 +96,7 @@ void AreaTransparencyGradientPopup::InitStatus(XFillFloatTransparenceItem const void AreaTransparencyGradientPopup::Rearrange(XFillFloatTransparenceItem const * pGradientItem) { InitStatus(pGradientItem); - const XGradient& rGradient = pGradientItem->GetGradientValue(); + const basegfx::BGradient& rGradient = pGradientItem->GetGradientValue(); css::awt::GradientStyle eXGS(rGradient.GetGradientStyle()); switch(eXGS) @@ -133,13 +132,13 @@ void AreaTransparencyGradientPopup::ExecuteValueModify(sal_uInt8 nStartCol, sal_ mxMtrTrgrAngle->set_value(nVal, FieldUnit::DEGREE); //End of new code - basegfx::ColorStops aColorStops; + basegfx::BColorStops aColorStops; aColorStops.emplace_back(0.0, Color(nStartCol, nStartCol, nStartCol).getBColor()); if(!maColorStops.empty()) aColorStops.insert(aColorStops.begin(), maColorStops.begin(), maColorStops.end()); aColorStops.emplace_back(1.0, Color(nEndCol, nEndCol, nEndCol).getBColor()); - XGradient aTmpGradient( + basegfx::BGradient aTmpGradient( aColorStops, static_cast<css::awt::GradientStyle>(mrAreaPropertyPanel.GetSelectedTransparencyTypeIndex()-2), Degree10(static_cast<sal_Int16>(mxMtrTrgrAngle->get_value(FieldUnit::DEGREE)) * 10), diff --git a/svx/source/svdraw/gradtrns.cxx b/svx/source/svdraw/gradtrns.cxx index c559e580cf67..82a4ea0a29d1 100644 --- a/svx/source/svdraw/gradtrns.cxx +++ b/svx/source/svdraw/gradtrns.cxx @@ -188,15 +188,15 @@ void GradTransformer::VecToGrad(GradTransVector const & rV, GradTransGradient& r // handle color changes if(rV.aCol1 != Color(rGOld.aGradient.GetColorStops().front().getStopColor())) { - basegfx::ColorStops aNewColorStops(rG.aGradient.GetColorStops()); - basegfx::utils::replaceStartColor(aNewColorStops, rV.aCol1.getBColor()); + basegfx::BColorStops aNewColorStops(rG.aGradient.GetColorStops()); + aNewColorStops.replaceStartColor(rV.aCol1.getBColor()); rG.aGradient.SetColorStops(aNewColorStops); rG.aGradient.SetStartIntens(100); } if(rV.aCol2 != Color(rGOld.aGradient.GetColorStops().back().getStopColor())) { - basegfx::ColorStops aNewColorStops(rG.aGradient.GetColorStops()); - basegfx::utils::replaceEndColor(aNewColorStops, rV.aCol2.getBColor()); + basegfx::BColorStops aNewColorStops(rG.aGradient.GetColorStops()); + aNewColorStops.replaceEndColor(rV.aCol2.getBColor()); rG.aGradient.SetColorStops(aNewColorStops); rG.aGradient.SetEndIntens(100); } diff --git a/svx/source/svdraw/gradtrns.hxx b/svx/source/svdraw/gradtrns.hxx index eee35582a9b0..f53e236b73d7 100644 --- a/svx/source/svdraw/gradtrns.hxx +++ b/svx/source/svdraw/gradtrns.hxx @@ -20,8 +20,9 @@ #ifndef INCLUDED_SVX_SOURCE_SVDRAW_GRADTRNS_HXX #define INCLUDED_SVX_SOURCE_SVDRAW_GRADTRNS_HXX -#include <svx/xgrad.hxx> +#include <tools/color.hxx> #include <basegfx/point/b2dpoint.hxx> +#include <basegfx/utils/bgradient.hxx> class SdrObject; @@ -37,7 +38,7 @@ public: class GradTransGradient { public: - XGradient aGradient; + basegfx::BGradient aGradient; }; struct GradTransformer diff --git a/svx/source/svdraw/svdetc.cxx b/svx/source/svdraw/svdetc.cxx index 97da36957306..acd15f7cc265 100644 --- a/svx/source/svdraw/svdetc.cxx +++ b/svx/source/svdraw/svdetc.cxx @@ -31,7 +31,6 @@ #include <editeng/eeitem.hxx> #include <svl/itemset.hxx> #include <svl/whiter.hxx> -#include <svx/xgrad.hxx> #include <svx/xfillit0.hxx> #include <svx/xflclit.hxx> #include <svx/xflhtit.hxx> @@ -271,7 +270,7 @@ bool GetDraftFillColor(const SfxItemSet& rSet, Color& rCol) break; } case drawing::FillStyle_GRADIENT: { - const XGradient& rGrad=rSet.Get(XATTR_FILLGRADIENT).GetGradientValue(); + const basegfx::BGradient& rGrad=rSet.Get(XATTR_FILLGRADIENT).GetGradientValue(); Color aCol1(Color(rGrad.GetColorStops().front().getStopColor())); Color aCol2(Color(rGrad.GetColorStops().back().getStopColor())); const basegfx::BColor aAverageColor(basegfx::average(aCol1.getBColor(), aCol2.getBColor())); diff --git a/svx/source/svdraw/svdfmtf.cxx b/svx/source/svdraw/svdfmtf.cxx index acd8b321a7f8..839fff3bdb15 100644 --- a/svx/source/svdraw/svdfmtf.cxx +++ b/svx/source/svdraw/svdfmtf.cxx @@ -32,7 +32,6 @@ #include <svx/xlnwtit.hxx> #include <svx/xfillit0.hxx> #include <svx/xflclit.hxx> -#include <svx/xgrad.hxx> #include <svx/xflgrit.hxx> #include <editeng/fontitem.hxx> #include <editeng/wrlmitem.hxx> @@ -1245,19 +1244,19 @@ void ImpSdrGDIMetaFileImport::DoAction( MetaCommentAction const & rAct, GDIMetaF std::move(aSource)); // #i125211# Use the ranges from the SdrObject to create a new empty SfxItemSet SfxItemSet aGradAttr(mpModel->GetItemPool(), pPath->GetMergedItemSet().GetRanges()); - XGradient aXGradient( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BGradient aBGradient( + basegfx::BColorStops( rGrad.GetStartColor().getBColor(), rGrad.GetEndColor().getBColor())); - aXGradient.SetGradientStyle(rGrad.GetStyle()); - aXGradient.SetAngle(rGrad.GetAngle()); - aXGradient.SetBorder(rGrad.GetBorder()); - aXGradient.SetXOffset(rGrad.GetOfsX()); - aXGradient.SetYOffset(rGrad.GetOfsY()); - aXGradient.SetStartIntens(rGrad.GetStartIntensity()); - aXGradient.SetEndIntens(rGrad.GetEndIntensity()); - aXGradient.SetSteps(rGrad.GetSteps()); + aBGradient.SetGradientStyle(rGrad.GetStyle()); + aBGradient.SetAngle(rGrad.GetAngle()); + aBGradient.SetBorder(rGrad.GetBorder()); + aBGradient.SetXOffset(rGrad.GetOfsX()); + aBGradient.SetYOffset(rGrad.GetOfsY()); + aBGradient.SetStartIntens(rGrad.GetStartIntensity()); + aBGradient.SetEndIntens(rGrad.GetEndIntensity()); + aBGradient.SetSteps(rGrad.GetSteps()); // no need to use SetAttributes(..) here since line and fill style // need to be set individually @@ -1269,7 +1268,7 @@ void ImpSdrGDIMetaFileImport::DoAction( MetaCommentAction const & rAct, GDIMetaF // add detected gradient fillstyle aGradAttr.Put(XFillStyleItem(drawing::FillStyle_GRADIENT)); - aGradAttr.Put(XFillGradientItem(aXGradient)); + aGradAttr.Put(XFillGradientItem(aBGradient)); pPath->SetMergedItemSet(aGradAttr); @@ -1413,8 +1412,8 @@ void ImpSdrGDIMetaFileImport::DoAction(MetaGradientAction const & rAct) // #i125211# Use the ranges from the SdrObject to create a new empty SfxItemSet SfxItemSet aGradientAttr(mpModel->GetItemPool(), pRect->GetMergedItemSet().GetRanges()); const XFillGradientItem aXFillGradientItem( - XGradient( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BGradient( + basegfx::BColorStops( rGradient.GetStartColor().getBColor(), rGradient.GetEndColor().getBColor()), rGradient.GetStyle(), @@ -1475,8 +1474,8 @@ void ImpSdrGDIMetaFileImport::DoAction(MetaGradientExAction const & rAct) // #i125211# Use the ranges from the SdrObject to create a new empty SfxItemSet SfxItemSet aGradientAttr(mpModel->GetItemPool(), pPath->GetMergedItemSet().GetRanges()); const XFillGradientItem aXFillGradientItem( - XGradient( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BGradient( + basegfx::BColorStops( rGradient.GetStartColor().getBColor(), rGradient.GetEndColor().getBColor()), rGradient.GetStyle(), diff --git a/svx/source/svdraw/svdmrkv.cxx b/svx/source/svdraw/svdmrkv.cxx index 5d6ccea9a55c..fa0ec5aa084f 100644 --- a/svx/source/svdraw/svdmrkv.cxx +++ b/svx/source/svdraw/svdmrkv.cxx @@ -29,7 +29,6 @@ #include <osl/thread.h> #include <rtl/strbuf.hxx> #include <svx/svdoole2.hxx> -#include <svx/xgrad.hxx> #include <svx/xfillit0.hxx> #include <svx/xflgrit.hxx> #include "gradtrns.hxx" @@ -1559,7 +1558,7 @@ void SdrMarkView::AddDragModeHdl(SdrDragMode eMode) { // add this item, it's not yet there XFillFloatTransparenceItem aNewItem(rSet.Get(XATTR_FILLFLOATTRANSPARENCE)); - XGradient aGrad = aNewItem.GetGradientValue(); + basegfx::BGradient aGrad = aNewItem.GetGradientValue(); aNewItem.SetEnabled(true); aGrad.SetStartIntens(100); diff --git a/svx/source/svdraw/svdoashp.cxx b/svx/source/svdraw/svdoashp.cxx index a2db44a795c6..c86c9ad0e194 100644 --- a/svx/source/svdraw/svdoashp.cxx +++ b/svx/source/svdraw/svdoashp.cxx @@ -302,7 +302,7 @@ static rtl::Reference<SdrObject> ImpCreateShadowObjectClone(const SdrObject& rOr // gradient and transparency like shadow if(bGradientFillUsed) { - XGradient aGradient(rOriginalSet.Get(XATTR_FILLGRADIENT).GetGradientValue()); + basegfx::BGradient aGradient(rOriginalSet.Get(XATTR_FILLGRADIENT).GetGradientValue()); sal_uInt8 nStartLuminance(Color(aGradient.GetColorStops().front().getStopColor()).GetLuminance()); sal_uInt8 nEndLuminance(Color(aGradient.GetColorStops().back().getStopColor()).GetLuminance()); @@ -327,7 +327,7 @@ static rtl::Reference<SdrObject> ImpCreateShadowObjectClone(const SdrObject& rOr static_cast<sal_uInt8>((nEndLuminance * aShadowColor.GetBlue()) / 256)); aGradient.SetColorStops( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BColorStops( aStartColor.getBColor(), aEndColor.getBColor())); aTempSet.Put(XFillGradientItem(aGradient)); diff --git a/svx/source/tbxctrls/fillctrl.cxx b/svx/source/tbxctrls/fillctrl.cxx index ced69cbdf2c7..9ca978e07331 100644 --- a/svx/source/tbxctrls/fillctrl.cxx +++ b/svx/source/tbxctrls/fillctrl.cxx @@ -765,7 +765,7 @@ IMPL_LINK_NOARG(SvxFillToolBoxControl, SelectFillTypeHdl, weld::ComboBox&, void) if(mnLastPosGradient < pItem->GetGradientList()->Count()) { - const XGradient aGradient = pItem->GetGradientList()->GetGradient(mnLastPosGradient)->GetGradient(); + const basegfx::BGradient aGradient = pItem->GetGradientList()->GetGradient(mnLastPosGradient)->GetGradient(); const XFillGradientItem aXFillGradientItem(mpLbFillAttr->get_text(mnLastPosGradient), aGradient); // #i122676# change FillStyle and Gradient in one call @@ -941,7 +941,7 @@ IMPL_LINK_NOARG(SvxFillToolBoxControl, SelectFillAttrHdl, weld::ComboBox&, void) if(nPos < pItem->GetGradientList()->Count()) { - const XGradient aGradient = pItem->GetGradientList()->GetGradient(nPos)->GetGradient(); + const basegfx::BGradient aGradient = pItem->GetGradientList()->GetGradient(nPos)->GetGradient(); const XFillGradientItem aXFillGradientItem(mpLbFillAttr->get_active_text(), aGradient); // #i122676# Change FillStyle and Gradient in one call diff --git a/svx/source/unodraw/XPropertyTable.cxx b/svx/source/unodraw/XPropertyTable.cxx index 45b0cd39c1ed..d88a37c4462d 100644 --- a/svx/source/unodraw/XPropertyTable.cxx +++ b/svx/source/unodraw/XPropertyTable.cxx @@ -532,29 +532,27 @@ uno::Reference< container::XNameContainer > SvxUnoXGradientTable_createInstance( // SvxUnoXPropertyTable uno::Any SvxUnoXGradientTable::getAny( const XPropertyEntry* pEntry ) const noexcept { - const XGradient& aXGradient = static_cast<const XGradientEntry*>(pEntry)->GetGradient(); + const basegfx::BGradient& aBGradient = static_cast<const XGradientEntry*>(pEntry)->GetGradient(); awt::Gradient2 aGradient; assert(aGradient.ColorStops.get() && "cid#1524745 aGradient.ColorStops._pSequence won't be null here"); // standard values - aGradient.Style = aXGradient.GetGradientStyle(); - // aGradient.StartColor = static_cast<sal_Int32>(Color(aXGradient.GetColorStops().front().getStopColor())); - // aGradient.EndColor = static_cast<sal_Int32>(Color(aXGradient.GetColorStops().back().getStopColor())); - aGradient.Angle = static_cast<short>(aXGradient.GetAngle()); - aGradient.Border = aXGradient.GetBorder(); - aGradient.XOffset = aXGradient.GetXOffset(); - aGradient.YOffset = aXGradient.GetYOffset(); - aGradient.StartIntensity = aXGradient.GetStartIntens(); - aGradient.EndIntensity = aXGradient.GetEndIntens(); - aGradient.StepCount = aXGradient.GetSteps(); + aGradient.Style = aBGradient.GetGradientStyle(); + aGradient.Angle = static_cast<short>(aBGradient.GetAngle()); + aGradient.Border = aBGradient.GetBorder(); + aGradient.XOffset = aBGradient.GetXOffset(); + aGradient.YOffset = aBGradient.GetYOffset(); + aGradient.StartIntensity = aBGradient.GetStartIntens(); + aGradient.EndIntensity = aBGradient.GetEndIntens(); + aGradient.StepCount = aBGradient.GetSteps(); // for compatibility, still set StartColor/EndColor - const basegfx::ColorStops& rColorStops(aXGradient.GetColorStops()); - aGradient.StartColor = static_cast<sal_Int32>(Color(rColorStops.front().getStopColor())); - aGradient.EndColor = static_cast<sal_Int32>(Color(rColorStops.back().getStopColor())); + const basegfx::BColorStops& rBColorStops(aBGradient.GetColorStops()); + aGradient.StartColor = static_cast<sal_Int32>(Color(rBColorStops.front().getStopColor())); + aGradient.EndColor = static_cast<sal_Int32>(Color(rBColorStops.back().getStopColor())); // fill ColorStops to extended Gradient2 - basegfx::utils::fillColorStopSequenceFromColorStops(aGradient.ColorStops, rColorStops); + aGradient.ColorStops = rBColorStops.getAsColorStopSequence(); return uno::Any(aGradient); } @@ -565,27 +563,26 @@ std::unique_ptr<XPropertyEntry> SvxUnoXGradientTable::createEntry(const OUString if(!(rAny >>= aGradient)) return std::unique_ptr<XPropertyEntry>(); - XGradient aXGradient( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BGradient aBGradient( + basegfx::BColorStops( Color(ColorTransparency, aGradient.StartColor).getBColor(), Color(ColorTransparency, aGradient.EndColor).getBColor())); - aXGradient.SetGradientStyle( aGradient.Style ); - aXGradient.SetAngle( Degree10(aGradient.Angle) ); - aXGradient.SetBorder( aGradient.Border ); - aXGradient.SetXOffset( aGradient.XOffset ); - aXGradient.SetYOffset( aGradient.YOffset ); - aXGradient.SetStartIntens( aGradient.StartIntensity ); - aXGradient.SetEndIntens( aGradient.EndIntensity ); - aXGradient.SetSteps( aGradient.StepCount ); + aBGradient.SetGradientStyle( aGradient.Style ); + aBGradient.SetAngle( Degree10(aGradient.Angle) ); + aBGradient.SetBorder( aGradient.Border ); + aBGradient.SetXOffset( aGradient.XOffset ); + aBGradient.SetYOffset( aGradient.YOffset ); + aBGradient.SetStartIntens( aGradient.StartIntensity ); + aBGradient.SetEndIntens( aGradient.EndIntensity ); + aBGradient.SetSteps( aGradient.StepCount ); // check if we have a awt::Gradient2 with a ColorStopSequence - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromAny(aColorStops, rAny); + const basegfx::BColorStops aColorStops(rAny); if (!aColorStops.empty()) - aXGradient.SetColorStops(aColorStops); + aBGradient.SetColorStops(aColorStops); - return std::make_unique<XGradientEntry>(aXGradient, rName); + return std::make_unique<XGradientEntry>(aBGradient, rName); } // XElementAccess diff --git a/svx/source/unodraw/unobrushitemhelper.cxx b/svx/source/unodraw/unobrushitemhelper.cxx index ba0924be803f..65d80cf282ca 100644 --- a/svx/source/unodraw/unobrushitemhelper.cxx +++ b/svx/source/unodraw/unobrushitemhelper.cxx @@ -156,7 +156,7 @@ static sal_uInt16 getTransparenceForSvxBrushItem(const SfxItemSet& rSourceSet, b if((pGradientItem = rSourceSet.GetItemIfSet(XATTR_FILLFLOATTRANSPARENCE, bSearchInParents)) && pGradientItem->IsEnabled()) { - const XGradient& rGradient = pGradientItem->GetGradientValue(); + const basegfx::BGradient& rGradient = pGradientItem->GetGradientValue(); const sal_uInt16 nStartLuminance(Color(rGradient.GetColorStops().front().getStopColor()).GetLuminance()); const sal_uInt16 nEndLuminance(Color(rGradient.GetColorStops().back().getStopColor()).GetLuminance()); @@ -223,9 +223,9 @@ std::unique_ptr<SvxBrushItem> getSvxBrushItemFromSourceSet(const SfxItemSet& rSo case drawing::FillStyle_GRADIENT: { // cannot be directly supported, but do the best possible - const XGradient aXGradient(rSourceSet.Get(XATTR_FILLGRADIENT).GetGradientValue()); - const basegfx::BColor aStartColor(aXGradient.GetColorStops().front().getStopColor() * (aXGradient.GetStartIntens() * 0.01)); - const basegfx::BColor aEndColor(aXGradient.GetColorStops().back().getStopColor() * (aXGradient.GetEndIntens() * 0.01)); + const basegfx::BGradient aBGradient(rSourceSet.Get(XATTR_FILLGRADIENT).GetGradientValue()); + const basegfx::BColor aStartColor(aBGradient.GetColorStops().front().getStopColor() * (aBGradient.GetStartIntens() * 0.01)); + const basegfx::BColor aEndColor(aBGradient.GetColorStops().back().getStopColor() * (aBGradient.GetEndIntens() * 0.01)); // use half/half mixed color from gradient start and end Color aMixedColor((aStartColor + aEndColor) * 0.5); diff --git a/svx/source/xoutdev/xattr.cxx b/svx/source/xoutdev/xattr.cxx index 3b31b852a835..8c4c7af9eb11 100644 --- a/svx/source/xoutdev/xattr.cxx +++ b/svx/source/xoutdev/xattr.cxx @@ -2092,209 +2092,17 @@ bool XSecondaryFillColorItem::GetPresentation return true; } -std::string XGradient::GradientStyleToString(css::awt::GradientStyle eStyle) -{ - switch (eStyle) - { - case css::awt::GradientStyle::GradientStyle_LINEAR: - return "LINEAR"; - - case css::awt::GradientStyle::GradientStyle_AXIAL: - return "AXIAL"; - - case css::awt::GradientStyle::GradientStyle_RADIAL: - return "RADIAL"; - - case css::awt::GradientStyle::GradientStyle_ELLIPTICAL: - return "ELLIPTICAL"; - - case css::awt::GradientStyle::GradientStyle_SQUARE: - return "SQUARE"; - - case css::awt::GradientStyle::GradientStyle_RECT: - return "RECT"; - - case css::awt::GradientStyle::GradientStyle_MAKE_FIXED_SIZE: - return "MAKE_FIXED_SIZE"; - } - - return ""; -} - -namespace -{ - css::awt::GradientStyle lcl_getStyleFromString(std::u16string_view rStyle) - { - if (rStyle == u"LINEAR") - return css::awt::GradientStyle_LINEAR; - else if (rStyle == u"AXIAL") - return css::awt::GradientStyle_AXIAL; - else if (rStyle == u"RADIAL") - return css::awt::GradientStyle_RADIAL; - else if (rStyle == u"ELLIPTICAL") - return css::awt::GradientStyle_ELLIPTICAL; - else if (rStyle == u"SQUARE") - return css::awt::GradientStyle_SQUARE; - else if (rStyle == u"RECT") - return css::awt::GradientStyle_RECT; - - return css::awt::GradientStyle_LINEAR; - } - - StringMap lcl_jsonToStringMap(std::u16string_view rJSON) - { - StringMap aArgs; - if (rJSON.size() && rJSON[0] != '\0') - { - std::stringstream aStream(std::string(OUStringToOString(rJSON, RTL_TEXTENCODING_ASCII_US))); - boost::property_tree::ptree aTree; - boost::property_tree::read_json(aStream, aTree); - - for (const auto& rPair : aTree) - { - aArgs[OUString::fromUtf8(rPair.first)] = OUString::fromUtf8(rPair.second.get_value<std::string>(".")); - } - } - return aArgs; - } - - XGradient lcl_buildGradientFromStringMap(StringMap& rMap) - { - XGradient aGradient( - basegfx::utils::createColorStopsFromStartEndColor( - Color(ColorTransparency, rMap["startcolor"].toInt32(16)).getBColor(), - Color(ColorTransparency, rMap["endcolor"].toInt32(16)).getBColor())); - - aGradient.SetGradientStyle(lcl_getStyleFromString(rMap["style"])); - aGradient.SetAngle(Degree10(rMap["angle"].toInt32())); - - return aGradient; - } -} - -XGradient XGradient::fromJSON(std::u16string_view rJSON) -{ - StringMap aMap(lcl_jsonToStringMap(rJSON)); - return lcl_buildGradientFromStringMap(aMap); -} - -namespace -{ - void fillGradient2FromXGradient(css::awt::Gradient2& rGradient2, const XGradient& rXGradient) - { - // standard values - rGradient2.Style = rXGradient.GetGradientStyle(); - rGradient2.Angle = static_cast<short>(rXGradient.GetAngle()); - rGradient2.Border = rXGradient.GetBorder(); - rGradient2.XOffset = rXGradient.GetXOffset(); - rGradient2.YOffset = rXGradient.GetYOffset(); - rGradient2.StartIntensity = rXGradient.GetStartIntens(); - rGradient2.EndIntensity = rXGradient.GetEndIntens(); - rGradient2.StepCount = rXGradient.GetSteps(); - - // for compatibility, still set StartColor/EndColor - const basegfx::ColorStops& rColorStops(rXGradient.GetColorStops()); - rGradient2.StartColor = static_cast<sal_Int32>(Color(rColorStops.front().getStopColor())); - rGradient2.EndColor = static_cast<sal_Int32>(Color(rColorStops.back().getStopColor())); - - // fill ColorStops to extended Gradient2 - basegfx::utils::fillColorStopSequenceFromColorStops(rGradient2.ColorStops, rColorStops); - } -} - -css::awt::Gradient2 XGradient::toGradientUNO() const -{ - css::awt::Gradient2 aGradient2; - - // fill values - fillGradient2FromXGradient(aGradient2, *this); - - return aGradient2; -} - -XGradient::XGradient() : - eStyle( css::awt::GradientStyle_LINEAR ), - aColorStops(), - nAngle( 0 ), - nBorder( 0 ), - nOfsX( 50 ), - nOfsY( 50 ), - nIntensStart( 100 ), - nIntensEnd( 100 ), - nStepCount( 0 ) -{ - aColorStops.emplace_back(0.0, COL_BLACK.getBColor()); - aColorStops.emplace_back(1.0, COL_WHITE.getBColor()); -} - -XGradient::XGradient(const basegfx::ColorStops& rColorStops, - css::awt::GradientStyle eTheStyle, Degree10 nTheAngle, sal_uInt16 nXOfs, - sal_uInt16 nYOfs, sal_uInt16 nTheBorder, - sal_uInt16 nStartIntens, sal_uInt16 nEndIntens, - sal_uInt16 nSteps) : - eStyle(eTheStyle), - aColorStops(rColorStops), - nAngle(nTheAngle), - nBorder(nTheBorder), - nOfsX(nXOfs), - nOfsY(nYOfs), - nIntensStart(nStartIntens), - nIntensEnd(nEndIntens), - nStepCount(nSteps) -{ - SetColorStops(aColorStops); -} - -bool XGradient::operator==(const XGradient& rGradient) const -{ - return ( eStyle == rGradient.eStyle && - aColorStops == rGradient.aColorStops && - nAngle == rGradient.nAngle && - nBorder == rGradient.nBorder && - nOfsX == rGradient.nOfsX && - nOfsY == rGradient.nOfsY && - nIntensStart == rGradient.nIntensStart && - nIntensEnd == rGradient.nIntensEnd && - nStepCount == rGradient.nStepCount ); -} - -void XGradient::SetColorStops(const basegfx::ColorStops& rSteps) -{ - aColorStops = rSteps; - basegfx::utils::sortAndCorrectColorStops(aColorStops); - if (aColorStops.empty()) - aColorStops.emplace_back(0.0, basegfx::BColor()); -} - -boost::property_tree::ptree XGradient::dumpAsJSON() const -{ - boost::property_tree::ptree aTree; - - aTree.put("style", XGradient::GradientStyleToString(eStyle)); - aTree.put("startcolor", Color(GetColorStops().front().getStopColor()).AsRGBHexString()); - aTree.put("endcolor", Color(GetColorStops().back().getStopColor()).AsRGBHexString()); - aTree.put("angle", std::to_string(nAngle.get())); - aTree.put("border", std::to_string(nBorder)); - aTree.put("x", std::to_string(nOfsX)); - aTree.put("y", std::to_string(nOfsY)); - aTree.put("intensstart", std::to_string(nIntensStart)); - aTree.put("intensend", std::to_string(nIntensEnd)); - aTree.put("stepcount", std::to_string(nStepCount)); - - return aTree; -} - SfxPoolItem* XFillGradientItem::CreateDefault() { return new XFillGradientItem; } XFillGradientItem::XFillGradientItem(sal_Int32 nIndex, - const XGradient& rTheGradient) : + const basegfx::BGradient& rTheGradient) : NameOrIndex(XATTR_FILLGRADIENT, nIndex), aGradient(rTheGradient) { } XFillGradientItem::XFillGradientItem(const OUString& rName, - const XGradient& rTheGradient, TypedWhichId<XFillGradientItem> nWhich) + const basegfx::BGradient& rTheGradient, TypedWhichId<XFillGradientItem> nWhich) : NameOrIndex(nWhich, rName) , aGradient(rTheGradient) { @@ -2306,7 +2114,7 @@ XFillGradientItem::XFillGradientItem(const XFillGradientItem& rItem) : { } -XFillGradientItem::XFillGradientItem( const XGradient& rTheGradient ) +XFillGradientItem::XFillGradientItem( const basegfx::BGradient& rTheGradient ) : NameOrIndex( XATTR_FILLGRADIENT, -1 ), aGradient(rTheGradient) { @@ -2323,7 +2131,7 @@ bool XFillGradientItem::operator==(const SfxPoolItem& rItem) const aGradient == static_cast<const XFillGradientItem&>(rItem).aGradient ); } -const XGradient& XFillGradientItem::GetGradientValue() const // GetValue -> GetGradientValue +const basegfx::BGradient& XFillGradientItem::GetGradientValue() const // GetValue -> GetGradientValue { if (!IsIndex()) return aGradient; @@ -2346,32 +2154,32 @@ bool XFillGradientItem::GetPresentation namespace { - void fillXGradientFromAny(XGradient& rXGradient, const css::uno::Any& rVal) + void fillXGradientFromAny(basegfx::BGradient& rBGradient, const css::uno::Any& rVal) { css::awt::Gradient aGradient; if (!(rVal >>= aGradient)) return; // for compatibility, read and set StartColor/EndColor - rXGradient.SetColorStops(basegfx::utils::createColorStopsFromStartEndColor( - Color(ColorTransparency, aGradient.StartColor).getBColor(), - Color(ColorTransparency, aGradient.EndColor).getBColor())); + rBGradient.SetColorStops( + basegfx::BColorStops( + Color(ColorTransparency, aGradient.StartColor).getBColor(), + Color(ColorTransparency, aGradient.EndColor).getBColor())); // set values - rXGradient.SetGradientStyle( aGradient.Style ); - rXGradient.SetAngle( Degree10(aGradient.Angle) ); - rXGradient.SetBorder( aGradient.Border ); - rXGradient.SetXOffset( aGradient.XOffset ); - rXGradient.SetYOffset( aGradient.YOffset ); - rXGradient.SetStartIntens( aGradient.StartIntensity ); - rXGradient.SetEndIntens( aGradient.EndIntensity ); - rXGradient.SetSteps( aGradient.StepCount ); + rBGradient.SetGradientStyle( aGradient.Style ); + rBGradient.SetAngle( Degree10(aGradient.Angle) ); + rBGradient.SetBorder( aGradient.Border ); + rBGradient.SetXOffset( aGradient.XOffset ); + rBGradient.SetYOffset( aGradient.YOffset ); + rBGradient.SetStartIntens( aGradient.StartIntensity ); + rBGradient.SetEndIntens( aGradient.EndIntensity ); + rBGradient.SetSteps( aGradient.StepCount ); // check if we have a awt::Gradient2 with a ColorStopSequence - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromAny(aColorStops, rVal); + const basegfx::BColorStops aColorStops(rVal); if (!aColorStops.empty()) - rXGradient.SetColorStops(aColorStops); + rBGradient.SetColorStops(aColorStops); } } @@ -2382,10 +2190,8 @@ bool XFillGradientItem::QueryValue( css::uno::Any& rVal, sal_uInt8 nMemberId ) c { case 0: { - css::awt::Gradient2 aGradient2; - // fill values - fillGradient2FromXGradient(aGradient2, GetGradientValue()); + const css::awt::Gradient2 aGradient2(GetGradientValue().getAsGradient2()); // create sequence uno::Sequence< beans::PropertyValue > aPropSeq{ @@ -2398,10 +2204,8 @@ bool XFillGradientItem::QueryValue( css::uno::Any& rVal, sal_uInt8 nMemberId ) c case MID_FILLGRADIENT: { - css::awt::Gradient2 aGradient2; - // fill values - fillGradient2FromXGradient(aGradient2, GetGradientValue()); + const css::awt::Gradient2 aGradient2(GetGradientValue().getAsGradient2()); // create sequence rVal <<= aGradient2; @@ -2416,10 +2220,9 @@ bool XFillGradientItem::QueryValue( css::uno::Any& rVal, sal_uInt8 nMemberId ) c case MID_GRADIENT_COLORSTOPSEQUENCE: { - css::awt::ColorStopSequence aColorStopSequence; - // fill values - basegfx::utils::fillColorStopSequenceFromColorStops(aColorStopSequence, GetGradientValue().GetColorStops()); + const css::awt::ColorStopSequence aColorStopSequence( + GetGradientValue().GetColorStops().getAsColorStopSequence()); // create sequence rVal <<= aColorStopSequence; @@ -2470,9 +2273,9 @@ bool XFillGradientItem::PutValue( const css::uno::Any& rVal, sal_uInt8 nMemberId if ( aGradientAny.hasValue() ) { - XGradient aXGradient; - fillXGradientFromAny(aXGradient, aGradientAny); - SetGradientValue(aXGradient); + basegfx::BGradient aBGradient; + fillXGradientFromAny(aBGradient, aGradientAny); + SetGradientValue(aBGradient); } return true; @@ -2492,22 +2295,22 @@ bool XFillGradientItem::PutValue( const css::uno::Any& rVal, sal_uInt8 nMemberId case MID_FILLGRADIENT: { - XGradient aXGradient; - fillXGradientFromAny(aXGradient, rVal); - SetGradientValue(aXGradient); + basegfx::BGradient aBGradient; + fillXGradientFromAny(aBGradient, rVal); + SetGradientValue(aBGradient); break; } case MID_GRADIENT_COLORSTOPSEQUENCE: { // check if we have a awt::Gradient2 with a ColorStopSequence - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromAny(aColorStops, rVal); + const basegfx::BColorStops aColorStops(rVal); + if (!aColorStops.empty()) { - XGradient aXGradient(GetGradientValue()); - aXGradient.SetColorStops(aColorStops); - SetGradientValue(aXGradient); + basegfx::BGradient aBGradient(GetGradientValue()); + aBGradient.SetColorStops(aColorStops); + SetGradientValue(aBGradient); } break; } @@ -2519,20 +2322,20 @@ bool XFillGradientItem::PutValue( const css::uno::Any& rVal, sal_uInt8 nMemberId if(!(rVal >>= nVal )) return false; - XGradient aXGradient(GetGradientValue()); - basegfx::ColorStops aNewColorStops(aXGradient.GetColorStops()); + basegfx::BGradient aBGradient(GetGradientValue()); + basegfx::BColorStops aNewColorStops(aBGradient.GetColorStops()); if ( nMemberId == MID_GRADIENT_STARTCOLOR ) { - basegfx::utils::replaceStartColor(aNewColorStops, nVal.getBColor()); + aNewColorStops.replaceStartColor(nVal.getBColor()); } else { - basegfx::utils::replaceEndColor(aNewColorStops, nVal.getBColor()); + aNewColorStops.replaceEndColor(nVal.getBColor()); } - aXGradient.SetColorStops(aNewColorStops); - SetGradientValue( aXGradient ); + aBGradient.SetColorStops(aNewColorStops); + SetGradientValue( aBGradient ); break; } @@ -2549,29 +2352,29 @@ bool XFillGradientItem::PutValue( const css::uno::Any& rVal, sal_uInt8 nMemberId if(!(rVal >>= nVal )) return false; - XGradient aXGradient = GetGradientValue(); + basegfx::BGradient aBGradient = GetGradientValue(); switch ( nMemberId ) { case MID_GRADIENT_STYLE: - aXGradient.SetGradientStyle( static_cast<css::awt::GradientStyle>(nVal) ); break; + aBGradient.SetGradientStyle( static_cast<css::awt::GradientStyle>(nVal) ); break; case MID_GRADIENT_ANGLE: - aXGradient.SetAngle( Degree10(nVal) ); break; + aBGradient.SetAngle( Degree10(nVal) ); break; case MID_GRADIENT_BORDER: - aXGradient.SetBorder( nVal ); break; + aBGradient.SetBorder( nVal ); break; case MID_GRADIENT_STARTINTENSITY: - aXGradient.SetStartIntens( nVal ); break; + aBGradient.SetStartIntens( nVal ); break; case MID_GRADIENT_ENDINTENSITY: - aXGradient.SetEndIntens( nVal ); break; + aBGradient.SetEndIntens( nVal ); break; case MID_GRADIENT_STEPCOUNT: - aXGradient.SetSteps( nVal ); break; + aBGradient.SetSteps( nVal ); break; case MID_GRADIENT_XOFFSET: - aXGradient.SetXOffset( nVal ); break; + aBGradient.SetXOffset( nVal ); break; case MID_GRADIENT_YOFFSET: - aXGradient.SetYOffset( nVal ); break; + aBGradient.SetYOffset( nVal ); break; } - SetGradientValue( aXGradient ); + SetGradientValue( aBGradient ); break; } } @@ -2622,7 +2425,7 @@ XFillFloatTransparenceItem::XFillFloatTransparenceItem() : SetWhich( XATTR_FILLFLOATTRANSPARENCE ); } -XFillFloatTransparenceItem::XFillFloatTransparenceItem(const OUString& rName, const XGradient& rGradient, bool bEnable ) : +XFillFloatTransparenceItem::XFillFloatTransparenceItem(const OUString& rName, const basegfx::BGradient& rGradient, bool bEnable ) : XFillGradientItem ( rName, rGradient ), bEnabled ( bEnable ) { @@ -2636,7 +2439,7 @@ XFillFloatTransparenceItem::XFillFloatTransparenceItem( const XFillFloatTranspar SetWhich( XATTR_FILLFLOATTRANSPARENCE ); } -XFillFloatTransparenceItem::XFillFloatTransparenceItem(const XGradient& rTheGradient, bool bEnable ) +XFillFloatTransparenceItem::XFillFloatTransparenceItem(const basegfx::BGradient& rTheGradient, bool bEnable ) : XFillGradientItem ( -1, rTheGradient ), bEnabled ( bEnable ) { diff --git a/svx/source/xoutdev/xpool.cxx b/svx/source/xoutdev/xpool.cxx index 5294092a3183..e0a280791b30 100644 --- a/svx/source/xoutdev/xpool.cxx +++ b/svx/source/xoutdev/xpool.cxx @@ -109,8 +109,8 @@ XOutdevItemPool::XOutdevItemPool(SfxItemPool* _pMaster) rPoolDefaults[XATTR_FILLSTYLE -XATTR_START] = new XFillStyleItem; rPoolDefaults[XATTR_FILLCOLOR -XATTR_START] = new XFillColorItem (aNullStr,aNullFillCol); - // XGradient() default already creates [COL_BLACK, COL_WHITE] as defaults - rPoolDefaults[XATTR_FILLGRADIENT -XATTR_START] = new XFillGradientItem(XGradient()); + // basegfx::BGradient() default already creates [COL_BLACK, COL_WHITE] as defaults + rPoolDefaults[XATTR_FILLGRADIENT -XATTR_START] = new XFillGradientItem(basegfx::BGradient()); rPoolDefaults[XATTR_FILLHATCH -XATTR_START] = new XFillHatchItem (aNullHatch); rPoolDefaults[XATTR_FILLBITMAP -XATTR_START] = new XFillBitmapItem (Graphic()); @@ -128,8 +128,8 @@ XOutdevItemPool::XOutdevItemPool(SfxItemPool* _pMaster) rPoolDefaults[XATTR_FILLBMP_POSOFFSETY -XATTR_START] = new XFillBmpPosOffsetYItem; rPoolDefaults[XATTR_FILLFLOATTRANSPARENCE -XATTR_START] = new XFillFloatTransparenceItem( - XGradient( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BGradient( + basegfx::BColorStops( COL_BLACK.getBColor(), COL_BLACK.getBColor())), false); diff --git a/svx/source/xoutdev/xtabgrdt.cxx b/svx/source/xoutdev/xtabgrdt.cxx index 4ae0bf68ff23..40d881c19dae 100644 --- a/svx/source/xoutdev/xtabgrdt.cxx +++ b/svx/source/xoutdev/xtabgrdt.cxx @@ -70,18 +70,18 @@ bool XGradientList::Create() sal_Int32 nLen = aStr.getLength() - 1; // XGradient() default already creates [COL_BLACK, COL_WHITE] as defaults - Insert(std::make_unique<XGradientEntry>(XGradient(),aStr.toString())); + Insert(std::make_unique<XGradientEntry>(basegfx::BGradient(),aStr.toString())); aStr[nLen] = '2'; - Insert(std::make_unique<XGradientEntry>(XGradient(basegfx::utils::createColorStopsFromStartEndColor(COL_BLUE.getBColor(), COL_RED.getBColor()), css::awt::GradientStyle_AXIAL , 300_deg10,20,20,10,100,100),aStr.toString())); + Insert(std::make_unique<XGradientEntry>(basegfx::BGradient(basegfx::BColorStops(COL_BLUE.getBColor(), COL_RED.getBColor()), css::awt::GradientStyle_AXIAL , 300_deg10,20,20,10,100,100),aStr.toString())); aStr[nLen] = '3'; - Insert(std::make_unique<XGradientEntry>(XGradient(basegfx::utils::createColorStopsFromStartEndColor(COL_RED.getBColor(), COL_YELLOW.getBColor()), css::awt::GradientStyle_RADIAL , 600_deg10,30,30,20,100,100),aStr.toString())); + Insert(std::make_unique<XGradientEntry>(basegfx::BGradient(basegfx::BColorStops(COL_RED.getBColor(), COL_YELLOW.getBColor()), css::awt::GradientStyle_RADIAL , 600_deg10,30,30,20,100,100),aStr.toString())); aStr[nLen] = '4'; - Insert(std::make_unique<XGradientEntry>(XGradient(basegfx::utils::createColorStopsFromStartEndColor(COL_YELLOW.getBColor(), COL_GREEN.getBColor()), css::awt::GradientStyle_ELLIPTICAL, 900_deg10,40,40,30,100,100),aStr.toString())); + Insert(std::make_unique<XGradientEntry>(basegfx::BGradient(basegfx::BColorStops(COL_YELLOW.getBColor(), COL_GREEN.getBColor()), css::awt::GradientStyle_ELLIPTICAL, 900_deg10,40,40,30,100,100),aStr.toString())); aStr[nLen] = '5'; - Insert(std::make_unique<XGradientEntry>(XGradient(basegfx::utils::createColorStopsFromStartEndColor(COL_GREEN.getBColor(), COL_MAGENTA.getBColor()), css::awt::GradientStyle_SQUARE , 1200_deg10,50,50,40,100,100),aStr.toString())); + Insert(std::make_unique<XGradientEntry>(basegfx::BGradient(basegfx::BColorStops(COL_GREEN.getBColor(), COL_MAGENTA.getBColor()), css::awt::GradientStyle_SQUARE , 1200_deg10,50,50,40,100,100),aStr.toString())); aStr[nLen] = '6'; - Insert(std::make_unique<XGradientEntry>(XGradient(basegfx::utils::createColorStopsFromStartEndColor(COL_MAGENTA.getBColor(), COL_YELLOW.getBColor()), css::awt::GradientStyle_RECT , 1900_deg10,60,60,50,100,100),aStr.toString())); + Insert(std::make_unique<XGradientEntry>(basegfx::BGradient(basegfx::BColorStops(COL_MAGENTA.getBColor(), COL_YELLOW.getBColor()), css::awt::GradientStyle_RECT , 1900_deg10,60,60,50,100,100),aStr.toString())); return true; } @@ -100,15 +100,14 @@ BitmapEx XGradientList::CreateBitmap( tools::Long nIndex, const Size& rSize ) co basegfx::utils::createPolygonFromRect( basegfx::B2DRange(0.0, 0.0, rSize.Width(), rSize.Height()))); - const XGradient& rGradient = GetGradient(nIndex)->GetGradient(); - basegfx::ColorStops aColorStops(rGradient.GetColorStops()); + const basegfx::BGradient& rGradient = GetGradient(nIndex)->GetGradient(); + basegfx::BColorStops aColorStops(rGradient.GetColorStops()); if (rGradient.GetStartIntens() != 100 || rGradient.GetEndIntens() != 100) { // Need to do the (old, crazy) blend against black - basegfx::utils::blendColorStopsToIntensity( - aColorStops, - rGradient.GetStartIntens() * 0.01, + aColorStops.blendToIntensity( + rGradient.GetStartIntens() * 0.01, rGradient.GetEndIntens() * 0.01, basegfx::BColor()); // COL_BLACK } diff --git a/svx/source/xoutdev/xtable.cxx b/svx/source/xoutdev/xtable.cxx index bc8834e868b5..9818fd1939f4 100644 --- a/svx/source/xoutdev/xtable.cxx +++ b/svx/source/xoutdev/xtable.cxx @@ -72,7 +72,7 @@ XHatchEntry::XHatchEntry(const XHatchEntry& rOther) { } -XGradientEntry::XGradientEntry(const XGradient& rGradient, const OUString& rName) +XGradientEntry::XGradientEntry(const basegfx::BGradient& rGradient, const OUString& rName) : XPropertyEntry(rName), aGradient(rGradient) { diff --git a/sw/inc/pch/precompiled_msword.hxx b/sw/inc/pch/precompiled_msword.hxx index e1e4b0a4f0ac..5750fdf09267 100644 --- a/sw/inc/pch/precompiled_msword.hxx +++ b/sw/inc/pch/precompiled_msword.hxx @@ -494,7 +494,6 @@ #include <svx/xdef.hxx> #include <svx/xfillit0.hxx> #include <svx/xflclit.hxx> -#include <svx/xgrad.hxx> #include <svx/xhatch.hxx> #include <svx/xit.hxx> #include <svx/xpoly.hxx> diff --git a/sw/inc/pch/precompiled_sw.hxx b/sw/inc/pch/precompiled_sw.hxx index 7ef065db0814..c3b9f28a4777 100644 --- a/sw/inc/pch/precompiled_sw.hxx +++ b/sw/inc/pch/precompiled_sw.hxx @@ -395,7 +395,6 @@ #include <svx/xdef.hxx> #include <svx/xfillit0.hxx> #include <svx/xflclit.hxx> -#include <svx/xgrad.hxx> #include <toolkit/helper/vclunohelper.hxx> #include <tools/UnitConversion.hxx> #include <tools/color.hxx> diff --git a/sw/inc/pch/precompiled_swui.hxx b/sw/inc/pch/precompiled_swui.hxx index 6b7eed00a85b..0892da517c9e 100644 --- a/sw/inc/pch/precompiled_swui.hxx +++ b/sw/inc/pch/precompiled_swui.hxx @@ -470,7 +470,6 @@ #include <svx/unomod.hxx> #include <svx/xdash.hxx> #include <svx/xdef.hxx> -#include <svx/xgrad.hxx> #include <svx/xhatch.hxx> #include <tools/color.hxx> #include <tools/date.hxx> diff --git a/sw/qa/extras/odfexport/odfexport.cxx b/sw/qa/extras/odfexport/odfexport.cxx index 1b2c83309e79..f8f972d20a46 100644 --- a/sw/qa/extras/odfexport/odfexport.cxx +++ b/sw/qa/extras/odfexport/odfexport.cxx @@ -795,8 +795,7 @@ DECLARE_ODFEXPORT_TEST(testTextframeGradient, "textframe-gradient.odt") awt::Gradient2 aGradient = getProperty<awt::Gradient2>(xFrame, "FillGradient"); // MCGR: Use the completely imported gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + basegfx::BColorStops aColorStops(aGradient.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(2), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); @@ -810,7 +809,7 @@ DECLARE_ODFEXPORT_TEST(testTextframeGradient, "textframe-gradient.odt") aGradient = getProperty<awt::Gradient2>(xFrame, "FillGradient"); // MCGR: Use the completely imported gradient to check for correctness - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + aColorStops = basegfx::BColorStops(aGradient.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(2), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); diff --git a/sw/qa/extras/ooxmlexport/ooxmlexport2.cxx b/sw/qa/extras/ooxmlexport/ooxmlexport2.cxx index 9248670760ac..2335caa6f17c 100644 --- a/sw/qa/extras/ooxmlexport/ooxmlexport2.cxx +++ b/sw/qa/extras/ooxmlexport/ooxmlexport2.cxx @@ -582,8 +582,7 @@ DECLARE_OOXMLEXPORT_TEST(testTextframeGradient, "textframe-gradient.docx") awt::Gradient2 aGradient(getProperty<awt::Gradient2>(xFrame, "FillGradient")); // MCGR: Use the completely imported transparency gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + basegfx::BColorStops aColorStops(aGradient.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(3), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); @@ -599,7 +598,7 @@ DECLARE_OOXMLEXPORT_TEST(testTextframeGradient, "textframe-gradient.docx") aGradient = getProperty<awt::Gradient2>(xFrame, "FillGradient"); // MCGR: Use the completely imported transparency gradient to check for correctness - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + aColorStops = basegfx::BColorStops(aGradient.ColorStops); CPPUNIT_ASSERT_EQUAL(size_t(3), aColorStops.size()); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); diff --git a/sw/qa/extras/rtfexport/rtfexport.cxx b/sw/qa/extras/rtfexport/rtfexport.cxx index 0a5bd68c3b26..341e688bad8e 100644 --- a/sw/qa/extras/rtfexport/rtfexport.cxx +++ b/sw/qa/extras/rtfexport/rtfexport.cxx @@ -622,8 +622,8 @@ DECLARE_RTFEXPORT_TEST(testTextframeGradient, "textframe-gradient.rtf") const basegfx::BColor aColD(0.0, 0.0, 0.0); // MCGR: Use the completely imported transparency gradient to check for correctness - basegfx::ColorStops aColorStops; - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + basegfx::BColorStops aColorStops(aGradient.ColorStops); + CPPUNIT_ASSERT_EQUAL(size_t(3), aColorStops.size()); CPPUNIT_ASSERT_EQUAL(awt::GradientStyle_LINEAR, aGradient.Style); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); @@ -639,7 +639,8 @@ DECLARE_RTFEXPORT_TEST(testTextframeGradient, "textframe-gradient.rtf") aGradient = getProperty<awt::Gradient2>(xFrame, "FillGradient"); // MCGR: Use the completely imported transparency gradient to check for correctness - basegfx::utils::fillColorStopsFromGradient2(aColorStops, aGradient); + aColorStops = basegfx::BColorStops(aGradient.ColorStops); + CPPUNIT_ASSERT_EQUAL(size_t(3), aColorStops.size()); CPPUNIT_ASSERT_EQUAL(awt::GradientStyle_LINEAR, aGradient.Style); CPPUNIT_ASSERT(basegfx::fTools::equal(aColorStops[0].getStopOffset(), 0.0)); diff --git a/sw/source/core/unocore/unoframe.cxx b/sw/source/core/unocore/unoframe.cxx index 930976fdf88e..9a44be4045bc 100644 --- a/sw/source/core/unocore/unoframe.cxx +++ b/sw/source/core/unocore/unoframe.cxx @@ -377,8 +377,8 @@ bool BaseFrameProperties_Impl::FillBaseProperties(SfxItemSet& rToSet, const SfxI { if(pXFillGradientItem) { - // XGradient() default already creates [COL_BLACK, COL_WHITE] as defaults - const XGradient aNullGrad; + // basegfx::BGradient() default already creates [COL_BLACK, COL_WHITE] as defaults + const basegfx::BGradient aNullGrad; XFillGradientItem aXFillGradientItem(aNullGrad); aXFillGradientItem.PutValue(*pXFillGradientItem, MID_FILLGRADIENT); @@ -520,8 +520,8 @@ bool BaseFrameProperties_Impl::FillBaseProperties(SfxItemSet& rToSet, const SfxI { if(pXFillFloatTransparenceItem) { - // XGradient() default already creates [COL_BLACK, COL_WHITE] as defaults - const XGradient aNullGrad; + // basegfx::BGradient() default already creates [COL_BLACK, COL_WHITE] as defaults + const basegfx::BGradient aNullGrad; XFillFloatTransparenceItem aXFillFloatTransparenceItem(aNullGrad, false); aXFillFloatTransparenceItem.PutValue(*pXFillFloatTransparenceItem, MID_FILLGRADIENT); diff --git a/sw/source/filter/ww8/docxattributeoutput.cxx b/sw/source/filter/ww8/docxattributeoutput.cxx index 6a2b62904325..2b859c06383e 100644 --- a/sw/source/filter/ww8/docxattributeoutput.cxx +++ b/sw/source/filter/ww8/docxattributeoutput.cxx @@ -9452,7 +9452,7 @@ void DocxAttributeOutput::FormatFillGradient( const XFillGradientItem& rFillGrad { AddToAttrList( m_rExport.SdrExporter().getFlyFillAttrList(), XML_type, "gradient" ); - const XGradient& rGradient = rFillGradient.GetGradientValue(); + const basegfx::BGradient& rGradient = rFillGradient.GetGradientValue(); OString sStartColor = msfilter::util::ConvertColor(Color(rGradient.GetColorStops().front().getStopColor())); OString sEndColor = msfilter::util::ConvertColor(Color(rGradient.GetColorStops().back().getStopColor())); diff --git a/sw/source/filter/ww8/rtfattributeoutput.cxx b/sw/source/filter/ww8/rtfattributeoutput.cxx index e545c6c9a734..1780a6182fdf 100644 --- a/sw/source/filter/ww8/rtfattributeoutput.cxx +++ b/sw/source/filter/ww8/rtfattributeoutput.cxx @@ -3707,8 +3707,8 @@ void RtfAttributeOutput::FormatFillGradient(const XFillGradientItem& rFillGradie m_aFlyProperties.push_back(std::make_pair<OString, OString>( "fillType", OString::number(7))); // Shade using the fillAngle - const XGradient& rGradient(rFillGradient.GetGradientValue()); - const basegfx::ColorStops& rColorStops(rGradient.GetColorStops()); + const basegfx::BGradient& rGradient(rFillGradient.GetGradientValue()); + const basegfx::BColorStops& rColorStops(rGradient.GetColorStops()); // MCGR: It would be best to export the full MCGR definition here // with all ColorStops in rColorStops, but rtf does not support this. diff --git a/sw/source/uibase/docvw/HeaderFooterWin.cxx b/sw/source/uibase/docvw/HeaderFooterWin.cxx index 0ea4a37937f0..64e34e01f6bd 100644 --- a/sw/source/uibase/docvw/HeaderFooterWin.cxx +++ b/sw/source/uibase/docvw/HeaderFooterWin.cxx @@ -153,7 +153,7 @@ void SwFrameButtonPainter::PaintButton(drawinglayer::primitive2d::Primitive2DCon nAngle = 0; FillGradientAttribute aFillAttrs(css::awt::GradientStyle_LINEAR, 0.0, 0.0, 0.0, nAngle, - basegfx::utils::createColorStopsFromStartEndColor(aLighterColor, aFillColor)); + basegfx::BColorStops(aLighterColor, aFillColor)); rSeq.push_back(drawinglayer::primitive2d::Primitive2DReference( new drawinglayer::primitive2d::FillGradientPrimitive2D(aGradientRect, std::move(aFillAttrs)))); } diff --git a/sw/source/uibase/docvw/ShadowOverlayObject.cxx b/sw/source/uibase/docvw/ShadowOverlayObject.cxx index afabffb44e66..0d0450876d2e 100644 --- a/sw/source/uibase/docvw/ShadowOverlayObject.cxx +++ b/sw/source/uibase/docvw/ShadowOverlayObject.cxx @@ -90,7 +90,7 @@ void ShadowPrimitive::create2DDecomposition( 0.5, 0.5, M_PI, - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BColorStops( basegfx::BColor(230.0/255.0,230.0/255.0,230.0/255.0), basegfx::BColor(180.0/255.0,180.0/255.0,180.0/255.0))); @@ -109,7 +109,7 @@ void ShadowPrimitive::create2DDecomposition( 0.5, 0.5, M_PI, - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BColorStops( basegfx::BColor(230.0/255.0,230.0/255.0,230.0/255.0), basegfx::BColor(180.0/255.0,180.0/255.0,180.0/255.0))); @@ -128,7 +128,7 @@ void ShadowPrimitive::create2DDecomposition( 0.5, 0.5, M_PI, - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BColorStops( basegfx::BColor(230.0/255.0,230.0/255.0,230.0/255.0), basegfx::BColor(83.0/255.0,83.0/255.0,83.0/255.0))); diff --git a/sw/source/uibase/shells/drawdlg.cxx b/sw/source/uibase/shells/drawdlg.cxx index 6117cf0dc32a..ec93f35029b0 100644 --- a/sw/source/uibase/shells/drawdlg.cxx +++ b/sw/source/uibase/shells/drawdlg.cxx @@ -235,7 +235,7 @@ namespace } if (const SfxStringItem* pJSON = pArgs->GetItemIfSet(SID_FILL_GRADIENT_JSON, false)) { - XGradient aGradient = XGradient::fromJSON(pJSON->GetValue()); + basegfx::BGradient aGradient = basegfx::BGradient::fromJSON(pJSON->GetValue()); XFillGradientItem aItem(aGradient); pArgs->Put(aItem); } @@ -319,7 +319,7 @@ static void lcl_unifyFillTransparencyItems(const SfxItemSet& rSet) if (!pFillTranspItem) return; - XGradient aTmpGradient = pFillFloatTranspItem->GetGradientValue(); + basegfx::BGradient aTmpGradient = pFillFloatTranspItem->GetGradientValue(); sal_uInt16 nTranspPercent = pFillTranspItem->GetValue(); // Encode transparency percentage as intensity sal_uInt16 nIntensity = 100 - std::min<sal_uInt16> diff --git a/sw/source/uibase/sidebar/PageStylesPanel.cxx b/sw/source/uibase/sidebar/PageStylesPanel.cxx index 05774730daea..9565b177b84d 100644 --- a/sw/source/uibase/sidebar/PageStylesPanel.cxx +++ b/sw/source/uibase/sidebar/PageStylesPanel.cxx @@ -192,10 +192,10 @@ void PageStylesPanel::Update() mxBgColorLB->show(); mxBgGradientLB->show(); - const XGradient xGradient = GetGradientSetOrDefault(); - const Color aStartColor(xGradient.GetColorStops().front().getStopColor()); + const basegfx::BGradient aBGradient = GetGradientSetOrDefault(); + const Color aStartColor(aBGradient.GetColorStops().front().getStopColor()); mxBgColorLB->SelectEntry(aStartColor); - const Color aEndColor(xGradient.GetColorStops().back().getStopColor()); + const Color aEndColor(aBGradient.GetColorStops().back().getStopColor()); mxBgGradientLB->SelectEntry(aEndColor); } break; @@ -256,11 +256,11 @@ Color const & PageStylesPanel::GetColorSetOrDefault() return mpBgColorItem->GetColorValue(); } -XGradient const & PageStylesPanel::GetGradientSetOrDefault() +basegfx::BGradient const & PageStylesPanel::GetGradientSetOrDefault() { if( !mpBgGradientItem ) { - XGradient aGradient; + basegfx::BGradient aGradient; OUString aGradientName; if (SfxObjectShell* pSh = SfxObjectShell::Current()) { @@ -550,8 +550,8 @@ void PageStylesPanel::ModifyFillColor() break; case GRADIENT: { - XGradient aGradient( - basegfx::utils::createColorStopsFromStartEndColor( + basegfx::BGradient aGradient( + basegfx::BColorStops( mxBgColorLB->GetSelectEntryColor().getBColor(), mxBgGradientLB->GetSelectEntryColor().getBColor())); diff --git a/sw/source/uibase/sidebar/PageStylesPanel.hxx b/sw/source/uibase/sidebar/PageStylesPanel.hxx index d39d2a073e67..5395b2784eb5 100644 --- a/sw/source/uibase/sidebar/PageStylesPanel.hxx +++ b/sw/source/uibase/sidebar/PageStylesPanel.hxx @@ -93,7 +93,7 @@ private: void Initialize(); void Update(); Color const & GetColorSetOrDefault(); - XGradient const & GetGradientSetOrDefault(); + basegfx::BGradient const & GetGradientSetOrDefault(); OUString const & GetHatchingSetOrDefault(); OUString const & GetBitmapSetOrDefault(); OUString const & GetPatternSetOrDefault(); diff --git a/sw/source/uibase/uiview/viewtab.cxx b/sw/source/uibase/uiview/viewtab.cxx index 9f1bf5f9ce36..729405068a1a 100644 --- a/sw/source/uibase/uiview/viewtab.cxx +++ b/sw/source/uibase/uiview/viewtab.cxx @@ -2517,8 +2517,8 @@ void SwView::StateTabWin(SfxItemSet& rSet) case drawing::FillStyle_GRADIENT: { - const XGradient& xGradient = aSet.GetItem<XFillGradientItem>( XATTR_FILLGRADIENT )->GetGradientValue(); - XFillGradientItem aFillGradientItem( OUString(), xGradient, SID_ATTR_PAGE_GRADIENT ); + const basegfx::BGradient& aBGradient = aSet.GetItem<XFillGradientItem>( XATTR_FILLGRADIENT )->GetGradientValue(); + XFillGradientItem aFillGradientItem( OUString(), aBGradient, SID_ATTR_PAGE_GRADIENT ); rSet.Put( aFillGradientItem ); } break; |