aboutsummaryrefslogtreecommitdiffstats
path: root/src/quickvectorimage
diff options
context:
space:
mode:
Diffstat (limited to 'src/quickvectorimage')
-rw-r--r--src/quickvectorimage/generator/qquickitemgenerator.cpp18
-rw-r--r--src/quickvectorimage/generator/qquicknodeinfo_p.h8
-rw-r--r--src/quickvectorimage/generator/qquickqmlgenerator.cpp23
-rw-r--r--src/quickvectorimage/generator/qsvgvisitorimpl.cpp126
-rw-r--r--src/quickvectorimage/generator/qsvgvisitorimpl_p.h1
5 files changed, 115 insertions, 61 deletions
diff --git a/src/quickvectorimage/generator/qquickitemgenerator.cpp b/src/quickvectorimage/generator/qquickitemgenerator.cpp
index c939ffccd7..1917c53013 100644
--- a/src/quickvectorimage/generator/qquickitemgenerator.cpp
+++ b/src/quickvectorimage/generator/qquickitemgenerator.cpp
@@ -123,12 +123,12 @@ void QQuickItemGenerator::outputShapePath(const PathNodeInfo &info, const QPaint
Q_UNUSED(pathSelector)
Q_ASSERT(painterPath || quadPath);
- QString penName = info.strokeColor;
- const bool noPen = penName.isEmpty() || penName == u"transparent";
+ const bool noPen = info.strokeColor == QColorConstants::Transparent;
if (pathSelector == QQuickVectorImageGenerator::StrokePath && noPen)
return;
- const bool noFill = info.grad.type() == QGradient::NoGradient && info.fillColor == u"transparent";
+ const bool noFill = info.grad.type() == QGradient::NoGradient && info.fillColor == QColorConstants::Transparent;
+
if (pathSelector == QQuickVectorImageGenerator::FillPath && noFill)
return;
@@ -145,7 +145,7 @@ void QQuickItemGenerator::outputShapePath(const PathNodeInfo &info, const QPaint
if (noPen || !(pathSelector & QQuickVectorImageGenerator::StrokePath)) {
shapePath->setStrokeColor(Qt::transparent);
} else {
- shapePath->setStrokeColor(QColor::fromString(penName));
+ shapePath->setStrokeColor(info.strokeColor);
shapePath->setStrokeWidth(info.strokeWidth);
}
@@ -156,7 +156,7 @@ void QQuickItemGenerator::outputShapePath(const PathNodeInfo &info, const QPaint
else if (info.grad.type() != QGradient::NoGradient)
generateGradient(&info.grad, shapePath, boundingRect);
else
- shapePath->setFillColor(QColor::fromString(info.fillColor));
+ shapePath->setFillColor(info.fillColor);
shapePath->setFillRule(fillRule);
@@ -179,7 +179,7 @@ void QQuickItemGenerator::generateGradient(const QGradient *grad, QQuickShapePat
if (!shapePath)
return;
- auto setStops = [](QQuickShapeGradient *quickGrad, const QGradientStops &stops) {
+ auto setStops = [=](QQuickShapeGradient *quickGrad, const QGradientStops &stops) {
auto stopsProp = quickGrad->stops();
for (auto &stop : stops) {
auto *stopObj = new QQuickGradientStop(quickGrad);
@@ -281,13 +281,13 @@ void QQuickItemGenerator::generateTextNode(const TextNodeInfo &info)
}
}
- textItem->setColor(QColor::fromString(info.color));
+ textItem->setColor(info.fillColor);
textItem->setTextFormat(info.needsRichText ? QQuickText::RichText : QQuickText::StyledText);
textItem->setText(info.text);
textItem->setFont(info.font);
- if (!info.strokeColor.isEmpty()) {
- textItem->setStyleColor(QColor::fromString(info.strokeColor));
+ if (info.strokeColor != QColorConstants::Transparent) {
+ textItem->setStyleColor(info.strokeColor);
textItem->setStyle(QQuickText::Outline);
}
diff --git a/src/quickvectorimage/generator/qquicknodeinfo_p.h b/src/quickvectorimage/generator/qquicknodeinfo_p.h
index 012e8f8c69..28629bf3e1 100644
--- a/src/quickvectorimage/generator/qquicknodeinfo_p.h
+++ b/src/quickvectorimage/generator/qquicknodeinfo_p.h
@@ -49,9 +49,9 @@ struct PathNodeInfo : NodeInfo
QPainterPath painterPath;
Qt::FillRule fillRule = Qt::FillRule::WindingFill;
Qt::PenCapStyle capStyle = Qt::SquareCap;
- QString strokeColor;
+ QColor strokeColor;
qreal strokeWidth;
- QString fillColor;
+ QColor fillColor;
QGradient grad;
};
@@ -64,8 +64,8 @@ struct TextNodeInfo : NodeInfo
QString text;
QFont font;
Qt::Alignment alignment;
- QString color;
- QString strokeColor;
+ QColor fillColor;
+ QColor strokeColor;
};
enum class StructureNodeStage
diff --git a/src/quickvectorimage/generator/qquickqmlgenerator.cpp b/src/quickvectorimage/generator/qquickqmlgenerator.cpp
index bdd3a29ed1..731d80f2da 100644
--- a/src/quickvectorimage/generator/qquickqmlgenerator.cpp
+++ b/src/quickvectorimage/generator/qquickqmlgenerator.cpp
@@ -220,9 +220,8 @@ void QQuickQmlGenerator::generateGradient(const QGradient *grad, const QRectF &b
stream() << "y1: " << logRect.top();
stream() << "x2: " << logRect.right();
stream() << "y2: " << logRect.bottom();
- for (auto &stop : linGrad->stops()) {
+ for (auto &stop : linGrad->stops())
stream() << "GradientStop { position: " << stop.first << "; color: \"" << stop.second.name(QColor::HexArgb) << "\" }";
- }
m_indentLevel--;
stream() << "}";
} else if (grad->type() == QGradient::RadialGradient) {
@@ -235,9 +234,8 @@ void QQuickQmlGenerator::generateGradient(const QGradient *grad, const QRectF &b
stream() << "centerRadius: " << radGrad->radius();
stream() << "focalX:" << radGrad->focalPoint().x();
stream() << "focalY:" << radGrad->focalPoint().y();
- for (auto &stop : radGrad->stops()) {
+ for (auto &stop : radGrad->stops())
stream() << "GradientStop { position: " << stop.first << "; color: \"" << stop.second.name(QColor::HexArgb) << "\" }";
- }
m_indentLevel--;
stream() << "}";
}
@@ -248,12 +246,12 @@ void QQuickQmlGenerator::outputShapePath(const PathNodeInfo &info, const QPainte
Q_UNUSED(pathSelector)
Q_ASSERT(painterPath || quadPath);
- QString penName = info.strokeColor;
- const bool noPen = penName.isEmpty() || penName == u"transparent";
+ const bool noPen = info.strokeColor == QColorConstants::Transparent;
if (pathSelector == QQuickVectorImageGenerator::StrokePath && noPen)
return;
- const bool noFill = info.grad.type() == QGradient::NoGradient && info.fillColor == u"transparent";
+ const bool noFill = info.grad.type() == QGradient::NoGradient && info.fillColor == QColorConstants::Transparent;
+
if (pathSelector == QQuickVectorImageGenerator::FillPath && noFill)
return;
@@ -277,7 +275,7 @@ void QQuickQmlGenerator::outputShapePath(const PathNodeInfo &info, const QPainte
if (noPen || !(pathSelector & QQuickVectorImageGenerator::StrokePath)) {
stream() << "strokeColor: \"transparent\"";
} else {
- stream() << "strokeColor: \"" << penName << "\"";
+ stream() << "strokeColor: \"" << info.strokeColor.name(QColor::HexArgb) << "\"";
stream() << "strokeWidth: " << info.strokeWidth;
}
if (info.capStyle == Qt::FlatCap)
@@ -288,8 +286,7 @@ void QQuickQmlGenerator::outputShapePath(const PathNodeInfo &info, const QPainte
} else if (info.grad.type() != QGradient::NoGradient) {
generateGradient(&info.grad, boundingRect);
} else {
- stream() << "fillColor: \"" << info.fillColor << "\"";
-
+ stream() << "fillColor: \"" << info.fillColor.name(QColor::HexArgb) << "\"";
}
if (fillRule == QQuickShapePath::WindingFill)
stream() << "fillRule: ShapePath.WindingFill";
@@ -368,7 +365,7 @@ void QQuickQmlGenerator::generateTextNode(const TextNodeInfo &info)
}
counter++;
- stream() << "color: \"" << info.color << "\"";
+ stream() << "color: \"" << info.fillColor.name(QColor::HexArgb) << "\"";
stream() << "textFormat:" << (info.needsRichText ? "Text.RichText" : "Text.StyledText");
QString s = info.text;
@@ -386,8 +383,8 @@ void QQuickQmlGenerator::generateTextNode(const TextNodeInfo &info)
if (info.font.italic())
stream() << "font.italic: true";
- if (!info.strokeColor.isEmpty()) {
- stream() << "styleColor: \"" << info.strokeColor << "\"";
+ if (info.strokeColor != QColorConstants::Transparent) {
+ stream() << "styleColor: \"" << info.strokeColor.name(QColor::HexArgb) << "\"";
stream() << "style: Text.Outline";
}
diff --git a/src/quickvectorimage/generator/qsvgvisitorimpl.cpp b/src/quickvectorimage/generator/qsvgvisitorimpl.cpp
index 6ccd51ee39..ce595f9a6b 100644
--- a/src/quickvectorimage/generator/qsvgvisitorimpl.cpp
+++ b/src/quickvectorimage/generator/qsvgvisitorimpl.cpp
@@ -87,9 +87,9 @@ public:
{
m_dummyImage = QImage(1, 1, QImage::Format_RGB32);
m_dummyPainter.begin(&m_dummyImage);
- QPen noPen(Qt::NoPen);
- noPen.setBrush(Qt::NoBrush);
- m_dummyPainter.setPen(noPen);
+ QPen defaultPen(Qt::NoBrush, 1, Qt::SolidLine, Qt::FlatCap, Qt::SvgMiterJoin);
+ defaultPen.setMiterLimit(4);
+ m_dummyPainter.setPen(defaultPen);
m_dummyPainter.setBrush(Qt::black);
}
@@ -101,16 +101,23 @@ public:
QPainter& painter() { return m_dummyPainter; }
QSvgExtraStates& states() { return m_svgState; }
- QString currentFillColor() const
+ QColor currentFillColor() const
{
- if (m_dummyPainter.brush().style() != Qt::NoBrush) {
- QColor c(m_dummyPainter.brush().color());
- c.setAlphaF(m_svgState.fillOpacity);
- //qCDebug(lcQuickVectorGraphics) << "FILL" << c << m_svgState.fillOpacity << c.name();
- return c.name(QColor::HexArgb);
- } else {
- return QStringLiteral("transparent");
+ if (m_dummyPainter.brush().style() == Qt::NoBrush ||
+ m_dummyPainter.brush().color() == QColorConstants::Transparent) {
+ return QColor(QColorConstants::Transparent);
}
+
+ QColor fillColor;
+ fillColor = m_dummyPainter.brush().color();
+ fillColor.setAlphaF(m_svgState.fillOpacity);
+
+ return fillColor;
+ }
+
+ qreal currentFillOpacity() const
+ {
+ return m_svgState.fillOpacity;
}
const QGradient *currentFillGradient() const
@@ -120,13 +127,23 @@ public:
return nullptr;
}
- QString currentStrokeColor() const
+ QColor currentStrokeColor() const
+ {
+ if (m_dummyPainter.pen().brush().style() == Qt::NoBrush ||
+ m_dummyPainter.pen().brush().color() == QColorConstants::Transparent) {
+ return QColor(QColorConstants::Transparent);
+ }
+
+ QColor strokeColor;
+ strokeColor = m_dummyPainter.pen().brush().color();
+ strokeColor.setAlphaF(m_svgState.strokeOpacity);
+
+ return strokeColor;
+ }
+
+ qreal currentStrokeOpacity() const
{
- if (m_dummyPainter.pen().style() != Qt::NoPen)
- return m_dummyPainter.pen().color().name();
- else if (m_dummyPainter.pen().brush().style() == Qt::SolidPattern)
- return m_dummyPainter.pen().brush().color().name();
- return {};
+ return m_svgState.strokeOpacity;
}
float currentStrokeWidth() const
@@ -135,6 +152,20 @@ public:
return penWidth ? penWidth : 1;
}
+ static QGradient applyOpacityToGradient(const QGradient &gradient, float opacity)
+ {
+ QGradient grad = gradient;
+ QGradientStops stops;
+ for (auto &stop : grad.stops()) {
+ stop.second.setAlphaF(stop.second.alphaF() * opacity);
+ stops.append(stop);
+ }
+
+ grad.setStops(stops);
+
+ return grad;
+ }
+
protected:
QPainter m_dummyPainter;
QImage m_dummyImage;
@@ -307,7 +338,7 @@ QString QSvgVisitorImpl::gradientCssDescription(const QGradient *gradient)
cssDescription += ",stop:"_L1;
cssDescription += QString::number(stop.first);
cssDescription += u' ';
- cssDescription += stop.second.name();
+ cssDescription += stop.second.name(QColor::HexArgb);
}
cssDescription += ");"_L1;
@@ -315,6 +346,18 @@ QString QSvgVisitorImpl::gradientCssDescription(const QGradient *gradient)
return cssDescription;
}
+QString QSvgVisitorImpl::colorCssDescription(QColor color)
+{
+ QString cssDescription;
+ cssDescription += QStringLiteral("rgba(");
+ cssDescription += QString::number(color.red()) + QStringLiteral(",");
+ cssDescription += QString::number(color.blue()) + QStringLiteral(",");
+ cssDescription += QString::number(color.green()) + QStringLiteral(",");
+ cssDescription += QString::number(color.alphaF()) + QStringLiteral(")");
+
+ return cssDescription;
+}
+
void QSvgVisitorImpl::visitTextNode(const QSvgText *node)
{
handleBaseNodeSetup(node);
@@ -361,11 +404,12 @@ void QSvgVisitorImpl::visitTextNode(const QSvgText *node)
if (styleResolver->currentFillGradient() != nullptr
&& styleResolver->currentFillGradient() != mainGradient) {
- styleTagContent += gradientCssDescription(styleResolver->currentFillGradient()) + u';';
+ const QGradient grad = styleResolver->applyOpacityToGradient(*styleResolver->currentFillGradient(), styleResolver->currentFillOpacity());
+ styleTagContent += gradientCssDescription(&grad) + u';';
needsPathNode = true;
}
- QString strokeColor = styleResolver->currentStrokeColor();
+ QString strokeColor = colorCssDescription(styleResolver->currentStrokeColor());
if (!strokeColor.isEmpty()) {
styleTagContent += QStringLiteral("-qt-stroke-color:%1;").arg(strokeColor);
styleTagContent += QStringLiteral("-qt-stroke-width:%1;").arg(styleResolver->currentStrokeWidth());
@@ -379,6 +423,26 @@ void QSvgVisitorImpl::visitTextNode(const QSvgText *node)
content.replace(QLatin1Char('\t'), QLatin1Char(' '));
content.replace(QLatin1Char('\n'), QLatin1Char(' '));
+ bool fontTag = false;
+ if (!tspan->style().fill.isDefault()) {
+ auto &b = tspan->style().fill->qbrush();
+ qCDebug(lcQuickVectorImage) << "tspan FILL:" << b;
+ if (b.style() != Qt::NoBrush)
+ {
+ if (qFuzzyCompare(b.color().alphaF() + 1.0, 2.0))
+ {
+ QString spanColor = b.color().name();
+ fontTag = !spanColor.isEmpty();
+ if (fontTag)
+ text += QStringLiteral("<font color=\"%1\">").arg(spanColor);
+ } else {
+ QString spanColor = colorCssDescription(b.color());
+ styleTagContent += QStringLiteral("color:%1").arg(spanColor);
+ }
+ }
+ }
+
+
needsRichText = needsRichText || !styleTagContent.isEmpty();
if (!styleTagContent.isEmpty())
text += QStringLiteral("<span style=\"%1\">").arg(styleTagContent);
@@ -389,16 +453,6 @@ void QSvgVisitorImpl::visitTextNode(const QSvgText *node)
if (font.resolveMask() & QFont::StyleResolved && font.italic())
text += QStringLiteral("<i>");
- QString spanColor;
- if (!tspan->style().fill.isDefault()) {
- auto &b = tspan->style().fill->qbrush();
- qCDebug(lcQuickVectorImage) << "tspan FILL:" << b;
- if (b.style() != Qt::NoBrush)
- spanColor = b.color().name();
- }
- bool fontTag = !spanColor.isEmpty();
- if (fontTag)
- text += QStringLiteral("<font color=\"%1\">").arg(spanColor);
if (font.resolveMask() & QFont::CapitalizationResolved) {
switch (font.capitalization()) {
@@ -462,7 +516,7 @@ void QSvgVisitorImpl::visitTextNode(const QSvgText *node)
info.fillRule = fillStyle->fillRule();
if (fmt.hasProperty(QTextCharFormat::ForegroundBrush)) {
- info.fillColor = fmt.foreground().color().name();
+ info.fillColor = fmt.foreground().color();
if (fmt.foreground().gradient() != nullptr && fmt.foreground().gradient()->type() != QGradient::NoGradient)
info.grad = *fmt.foreground().gradient();
} else {
@@ -470,15 +524,17 @@ void QSvgVisitorImpl::visitTextNode(const QSvgText *node)
}
info.painterPath = p;
+
if (fmt.hasProperty(QTextCharFormat::TextOutline)) {
info.strokeWidth = fmt.textOutline().widthF();
- info.strokeColor = fmt.textOutline().color().name();
+ info.strokeColor = fmt.textOutline().color();
} else {
info.strokeColor = styleResolver->currentStrokeColor();
info.strokeWidth = styleResolver->currentStrokeWidth();
}
+
if (info.grad.type() == QGradient::NoGradient && styleResolver->currentFillGradient() != nullptr)
- info.grad = *styleResolver->currentFillGradient();
+ info.grad = styleResolver->applyOpacityToGradient(*styleResolver->currentFillGradient(), styleResolver->currentFillOpacity());
m_generator->generatePath(info);
};
@@ -542,7 +598,7 @@ void QSvgVisitorImpl::visitTextNode(const QSvgText *node)
info.text = text;
info.isTextArea = isTextArea;
info.needsRichText = needsRichText;
- info.color = styleResolver->currentFillColor();
+ info.fillColor = styleResolver->currentFillColor();
info.alignment = styleResolver->states().textAnchor;
info.strokeColor = styleResolver->currentStrokeColor();
@@ -698,7 +754,7 @@ void QSvgVisitorImpl::handlePathNode(const QSvgNode *node, const QPainterPath &p
info.strokeColor = styleResolver->currentStrokeColor();
info.strokeWidth = styleResolver->currentStrokeWidth();
if (styleResolver->currentFillGradient() != nullptr)
- info.grad = *styleResolver->currentFillGradient();
+ info.grad = styleResolver->applyOpacityToGradient(*styleResolver->currentFillGradient(), styleResolver->currentFillOpacity());
m_generator->generatePath(info);
diff --git a/src/quickvectorimage/generator/qsvgvisitorimpl_p.h b/src/quickvectorimage/generator/qsvgvisitorimpl_p.h
index 12da4b68ca..d80c9ec992 100644
--- a/src/quickvectorimage/generator/qsvgvisitorimpl_p.h
+++ b/src/quickvectorimage/generator/qsvgvisitorimpl_p.h
@@ -57,6 +57,7 @@ private:
void handlePathNode(const QSvgNode *node, const QPainterPath &path, Qt::PenCapStyle capStyle = Qt::SquareCap);
void outputShapePath(QPainterPath pathCopy, const PathNodeInfo &info);
static QString gradientCssDescription(const QGradient *gradient);
+ static QString colorCssDescription(QColor color);
private:
QString m_svgFileName;