mirror of
https://github.com/JakubMelka/PDF4QT.git
synced 2025-02-28 09:27:42 +01:00
Sampler bugfixing
This commit is contained in:
parent
f0b1707d12
commit
3f7ddacdc0
@ -727,7 +727,8 @@ void PDFTransparencyRenderer::performPathPainting(const QPainterPath& path, bool
|
|||||||
{
|
{
|
||||||
Q_UNUSED(fillRule);
|
Q_UNUSED(fillRule);
|
||||||
|
|
||||||
PDFPainterPathSampler clipSampler(m_painterStateStack.top().clipPath, m_settings.samplesCount, 1.0f);
|
PDFPainterPathSampler clipSampler(m_painterStateStack.top().clipPath, m_settings.samplesCount, 1.0f,
|
||||||
|
m_settings.flags.testFlag(PDFTransparencyRendererSettings::PrecisePathSampler));
|
||||||
|
|
||||||
QMatrix worldMatrix = getCurrentWorldMatrix();
|
QMatrix worldMatrix = getCurrentWorldMatrix();
|
||||||
|
|
||||||
@ -754,7 +755,7 @@ void PDFTransparencyRenderer::performPathPainting(const QPainterPath& path, bool
|
|||||||
// and world matrix. Path can be translated outside of the paint area.
|
// and world matrix. Path can be translated outside of the paint area.
|
||||||
if (fillRect.isValid())
|
if (fillRect.isValid())
|
||||||
{
|
{
|
||||||
PDFPainterPathSampler pathSampler(worldPath, m_settings.samplesCount, 0.0f);
|
PDFPainterPathSampler pathSampler(worldPath, m_settings.samplesCount, 0.0f, m_settings.flags.testFlag(PDFTransparencyRendererSettings::PrecisePathSampler));
|
||||||
const PDFMappedColor& fillColor = getMappedFillColor();
|
const PDFMappedColor& fillColor = getMappedFillColor();
|
||||||
|
|
||||||
for (int x = fillRect.left(); x < fillRect.right(); ++x)
|
for (int x = fillRect.left(); x < fillRect.right(); ++x)
|
||||||
@ -812,7 +813,7 @@ void PDFTransparencyRenderer::performPathPainting(const QPainterPath& path, bool
|
|||||||
// and world matrix. Path can be translated outside of the paint area.
|
// and world matrix. Path can be translated outside of the paint area.
|
||||||
if (strokeRect.isValid())
|
if (strokeRect.isValid())
|
||||||
{
|
{
|
||||||
PDFPainterPathSampler pathSampler(worldPath, m_settings.samplesCount, 0.0f);
|
PDFPainterPathSampler pathSampler(worldPath, m_settings.samplesCount, 0.0f, m_settings.flags.testFlag(PDFTransparencyRendererSettings::PrecisePathSampler));
|
||||||
const PDFMappedColor& strokeColor = getMappedStrokeColor();
|
const PDFMappedColor& strokeColor = getMappedStrokeColor();
|
||||||
|
|
||||||
for (int x = strokeRect.left(); x < strokeRect.right(); ++x)
|
for (int x = strokeRect.left(); x < strokeRect.right(); ++x)
|
||||||
@ -821,7 +822,7 @@ void PDFTransparencyRenderer::performPathPainting(const QPainterPath& path, bool
|
|||||||
{
|
{
|
||||||
const PDFColorComponent clipValue = clipSampler.sample(QPoint(x, y));
|
const PDFColorComponent clipValue = clipSampler.sample(QPoint(x, y));
|
||||||
const PDFColorComponent objectShapeValue = pathSampler.sample(QPoint(x, y));
|
const PDFColorComponent objectShapeValue = pathSampler.sample(QPoint(x, y));
|
||||||
const PDFColorComponent shapeValue = objectShapeValue * clipValue * shapeFilling;
|
const PDFColorComponent shapeValue = objectShapeValue * clipValue * shapeStroking;
|
||||||
|
|
||||||
if (shapeValue > 0.0f)
|
if (shapeValue > 0.0f)
|
||||||
{
|
{
|
||||||
@ -830,7 +831,7 @@ void PDFTransparencyRenderer::performPathPainting(const QPainterPath& path, bool
|
|||||||
|
|
||||||
PDFColorBuffer pixel = m_drawBuffer.getPixel(x, y);
|
PDFColorBuffer pixel = m_drawBuffer.getPixel(x, y);
|
||||||
pixel[shapeChannel] = PDFBlendFunction::blend_Union(shapeValue, pixel[shapeChannel]);
|
pixel[shapeChannel] = PDFBlendFunction::blend_Union(shapeValue, pixel[shapeChannel]);
|
||||||
pixel[opacityChannel] = pixel[shapeChannel] * opacityFilling;
|
pixel[opacityChannel] = pixel[shapeChannel] * opacityStroking;
|
||||||
|
|
||||||
// Copy color
|
// Copy color
|
||||||
for (uint8_t colorChannelIndex = colorChannelStart; colorChannelIndex < colorChannelEnd; ++colorChannelIndex)
|
for (uint8_t colorChannelIndex = colorChannelStart; colorChannelIndex < colorChannelEnd; ++colorChannelIndex)
|
||||||
@ -1497,12 +1498,16 @@ PDFInkMapping PDFInkMapper::createMapping(const PDFAbstractColorSpace* sourceCol
|
|||||||
return mapping;
|
return mapping;
|
||||||
}
|
}
|
||||||
|
|
||||||
PDFPainterPathSampler::PDFPainterPathSampler(QPainterPath path, int samplesCount, PDFColorComponent defaultShape) :
|
PDFPainterPathSampler::PDFPainterPathSampler(QPainterPath path, int samplesCount, PDFColorComponent defaultShape, bool precise) :
|
||||||
m_defaultShape(defaultShape),
|
m_defaultShape(defaultShape),
|
||||||
m_samplesCount(samplesCount),
|
m_samplesCount(samplesCount),
|
||||||
|
m_precise(precise),
|
||||||
m_path(qMove(path))
|
m_path(qMove(path))
|
||||||
{
|
{
|
||||||
|
if (!precise)
|
||||||
|
{
|
||||||
|
m_fillPolygon = m_path.toFillPolygon();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
PDFColorComponent PDFPainterPathSampler::sample(QPoint point) const
|
PDFColorComponent PDFPainterPathSampler::sample(QPoint point) const
|
||||||
@ -1528,15 +1533,33 @@ PDFColorComponent PDFPainterPathSampler::sample(QPoint point) const
|
|||||||
if (m_samplesCount <= 1)
|
if (m_samplesCount <= 1)
|
||||||
{
|
{
|
||||||
// Jakub Melka: Just one sample
|
// Jakub Melka: Just one sample
|
||||||
|
if (m_precise)
|
||||||
|
{
|
||||||
return m_path.contains(QPointF(centerX, centerY)) ? 1.0f : 0.0f;
|
return m_path.contains(QPointF(centerX, centerY)) ? 1.0f : 0.0f;
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return m_fillPolygon.contains(QPointF(centerX, centerY)) ? 1.0f : 0.0f;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int cornerHits = 0;
|
int cornerHits = 0;
|
||||||
|
Qt::FillRule fillRule = m_path.fillRule();
|
||||||
|
|
||||||
|
if (m_precise)
|
||||||
|
{
|
||||||
cornerHits += m_path.contains(topLeft) ? 1 : 0;
|
cornerHits += m_path.contains(topLeft) ? 1 : 0;
|
||||||
cornerHits += m_path.contains(topRight) ? 1 : 0;
|
cornerHits += m_path.contains(topRight) ? 1 : 0;
|
||||||
cornerHits += m_path.contains(bottomLeft) ? 1 : 0;
|
cornerHits += m_path.contains(bottomLeft) ? 1 : 0;
|
||||||
cornerHits += m_path.contains(bottomRight) ? 1 : 0;
|
cornerHits += m_path.contains(bottomRight) ? 1 : 0;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
cornerHits += m_fillPolygon.containsPoint(topLeft, fillRule) ? 1 : 0;
|
||||||
|
cornerHits += m_fillPolygon.containsPoint(topRight, fillRule) ? 1 : 0;
|
||||||
|
cornerHits += m_fillPolygon.containsPoint(bottomLeft, fillRule) ? 1 : 0;
|
||||||
|
cornerHits += m_fillPolygon.containsPoint(bottomRight, fillRule) ? 1 : 0;
|
||||||
|
}
|
||||||
|
|
||||||
if (cornerHits == 4)
|
if (cornerHits == 4)
|
||||||
{
|
{
|
||||||
@ -1562,11 +1585,21 @@ PDFColorComponent PDFPainterPathSampler::sample(QPoint point) const
|
|||||||
{
|
{
|
||||||
const qreal y = offset * (iy + 1) + coordY1;
|
const qreal y = offset * (iy + 1) + coordY1;
|
||||||
|
|
||||||
|
if (m_precise)
|
||||||
|
{
|
||||||
if (m_path.contains(QPointF(x, y)))
|
if (m_path.contains(QPointF(x, y)))
|
||||||
{
|
{
|
||||||
sampleValue += sampleGain;
|
sampleValue += sampleGain;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (m_fillPolygon.containsPoint(QPointF(x, y), fillRule))
|
||||||
|
{
|
||||||
|
sampleValue += sampleGain;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return sampleValue;
|
return sampleValue;
|
||||||
|
@ -332,15 +332,18 @@ public:
|
|||||||
/// \param path Sampled path
|
/// \param path Sampled path
|
||||||
/// \param samplesCount Samples count in one direction
|
/// \param samplesCount Samples count in one direction
|
||||||
/// \param defaultShape Default shape returned, if path is empty
|
/// \param defaultShape Default shape returned, if path is empty
|
||||||
PDFPainterPathSampler(QPainterPath path, int samplesCount, PDFColorComponent defaultShape);
|
/// \param precise Use precise sampling (using spline curves), or fill polygon (fast, but not too precise)
|
||||||
|
PDFPainterPathSampler(QPainterPath path, int samplesCount, PDFColorComponent defaultShape, bool precise);
|
||||||
|
|
||||||
/// Return sample value for a given pixel
|
/// Return sample value for a given pixel
|
||||||
PDFColorComponent sample(QPoint point) const;
|
PDFColorComponent sample(QPoint point) const;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
PDFColorComponent m_defaultShape = 0.0;
|
PDFColorComponent m_defaultShape = 0.0;
|
||||||
int m_samplesCount; ///< Samples count in one direction
|
int m_samplesCount = 0; ///< Samples count in one direction
|
||||||
|
bool m_precise = false;
|
||||||
QPainterPath m_path;
|
QPainterPath m_path;
|
||||||
|
QPolygonF m_fillPolygon;
|
||||||
};
|
};
|
||||||
|
|
||||||
/// Represents draw buffer, into which is current graphics drawn
|
/// Represents draw buffer, into which is current graphics drawn
|
||||||
@ -381,6 +384,20 @@ struct PDFTransparencyRendererSettings
|
|||||||
{
|
{
|
||||||
/// Sample count for MSAA antialiasing
|
/// Sample count for MSAA antialiasing
|
||||||
int samplesCount = 16;
|
int samplesCount = 16;
|
||||||
|
|
||||||
|
enum Flag
|
||||||
|
{
|
||||||
|
None = 0x0000,
|
||||||
|
|
||||||
|
/// Use precise path sampler, which uses paths instead
|
||||||
|
/// of filling polygon.
|
||||||
|
PrecisePathSampler = 0x0001
|
||||||
|
};
|
||||||
|
|
||||||
|
Q_DECLARE_FLAGS(Flags, Flag)
|
||||||
|
|
||||||
|
/// Flags
|
||||||
|
Flags flags = None;
|
||||||
};
|
};
|
||||||
|
|
||||||
/// Renders PDF pages with transparency, using 32-bit floating point precision.
|
/// Renders PDF pages with transparency, using 32-bit floating point precision.
|
||||||
|
Loading…
x
Reference in New Issue
Block a user