mirror of https://github.com/JakubMelka/PDF4QT.git
Pixel format descriptor
This commit is contained in:
parent
a169a8c06b
commit
ccb84401db
|
@ -20,10 +20,53 @@
|
|||
namespace pdf
|
||||
{
|
||||
|
||||
PDFFloatBitmap::PDFFloatBitmap() :
|
||||
m_width(0),
|
||||
m_height(0),
|
||||
m_pixelSize(0)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
PDFFloatBitmap::PDFFloatBitmap(size_t width, size_t height, PDFPixelFormat format) :
|
||||
m_format(format),
|
||||
m_width(width),
|
||||
m_height(height),
|
||||
m_pixelSize(format.getChannelCount())
|
||||
{
|
||||
Q_ASSERT(format.isValid());
|
||||
|
||||
m_data.resize(format.calculateBitmapDataLength(width, height), static_cast<PDFColorComponent>(0.0));
|
||||
}
|
||||
|
||||
PDFColorBuffer PDFFloatBitmap::getPixel(size_t x, size_t y)
|
||||
{
|
||||
s
|
||||
}
|
||||
|
||||
const PDFColorComponent* PDFFloatBitmap::begin() const
|
||||
{
|
||||
return m_data.data();
|
||||
}
|
||||
|
||||
const PDFColorComponent* PDFFloatBitmap::end() const
|
||||
{
|
||||
return m_data.data() + m_data.size();
|
||||
}
|
||||
|
||||
PDFColorComponent* PDFFloatBitmap::begin()
|
||||
{
|
||||
return m_data.data();
|
||||
}
|
||||
|
||||
PDFColorComponent* PDFFloatBitmap::end()
|
||||
{
|
||||
return m_data.data() + m_data.size();
|
||||
}
|
||||
|
||||
PDFTransparencyRenderer::PDFTransparencyRenderer()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
|
||||
} // namespace pdf
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
// Copyright (C) 2020 Jakub Melka
|
||||
// Copyright (C) 2021 Jakub Melka
|
||||
//
|
||||
// This file is part of Pdf4Qt.
|
||||
//
|
||||
|
@ -18,9 +18,123 @@
|
|||
#ifndef PDFTRANSPARENCYRENDERER_H
|
||||
#define PDFTRANSPARENCYRENDERER_H
|
||||
|
||||
#include "pdfglobal.h"
|
||||
#include "pdfcolorspaces.h"
|
||||
|
||||
namespace pdf
|
||||
{
|
||||
|
||||
/// Pixel format, describes color channels, both process colors (for example,
|
||||
/// R, G, B, Gray, C, M, Y, K) or spot colors. Also, describes, if pixel
|
||||
/// has shape channel and opacity channel. Two auxiliary channels are possible,
|
||||
/// shape channel and opacity channel. Shape channel defines the shape (so, for
|
||||
/// example, if we draw a rectangle onto the bitmap, shape value is 1.0 inside the
|
||||
/// rectangle and 0.0 outside the rectangle). PDF transparency processing requires
|
||||
/// shape and opacity values separated.
|
||||
class PDFPixelFormat
|
||||
{
|
||||
public:
|
||||
inline explicit constexpr PDFPixelFormat() = default;
|
||||
|
||||
constexpr uint8_t INVALID_CHANNEL_INDEX = 0xFF;
|
||||
|
||||
constexpr bool hasProcessColors() const { return m_processColors > 0; }
|
||||
constexpr bool hasSpotColors() const { return m_spotColors > 0; }
|
||||
constexpr bool hasShapeChannel() const { return m_flags & FLAG_HAS_SHAPE_CHANNEL; }
|
||||
constexpr bool hasOpacityChannel() const { return m_flags & FLAG_HAS_OPACITY_CHANNEL; }
|
||||
constexpr bool hasProcessColorsSubtractive() const { return m_flags & FLAG_PROCESS_COLORS_SUBTRACTIVE; }
|
||||
constexpr bool hasSpotColorsSubtractive() const { return true; }
|
||||
|
||||
constexpr uint8_t getFlags() const { return m_flags; }
|
||||
constexpr uint8_t getMaximalColorChannelCount() const { return 32; }
|
||||
constexpr uint8_t getProcessColorChannelCount() const { return m_processColors; }
|
||||
constexpr uint8_t getSpotColorChannelCount() const { return m_spotColors; }
|
||||
constexpr uint8_t getColorChannelCount() const { return getProcessColorChannelCount() + getSpotColorChannelCount(); }
|
||||
constexpr uint8_t getShapeChannelCount() const { return hasShapeChannel() ? 1 : 0; }
|
||||
constexpr uint8_t getOpacityChannelCount() const { return hasOpacityChannel() ? 1 : 0; }
|
||||
constexpr uint8_t getAuxiliaryChannelCount() const { return getShapeChannelCount() + getOpacityChannelCount(); }
|
||||
constexpr uint8_t getChannelCount() const { return getColorChannelCount() + getAuxiliaryChannelCount(); }
|
||||
|
||||
constexpr uint8_t getProcessColorChannelIndexStart() const { return hasProcessColors() ? 0 : INVALID_CHANNEL_INDEX; }
|
||||
constexpr uint8_t getProcessColorChannelIndexEnd() const { return hasProcessColors() ? getProcessColorChannelCount() : INVALID_CHANNEL_INDEX; }
|
||||
constexpr uint8_t getSpotColorChannelIndexStart() const { return hasSpotColors() ? getProcessColorChannelCount() : INVALID_CHANNEL_INDEX; }
|
||||
constexpr uint8_t getSpotColorChannelIndexEnd() const { return hasSpotColors() ? getSpotColorChannelIndexStart() + getSpotColorChannelCount() : INVALID_CHANNEL_INDEX; }
|
||||
constexpr uint8_t getShapeChannelIndex() const { return hasShapeChannel() ? getProcessColorChannelCount() + getSpotColorChannelCount() : INVALID_CHANNEL_INDEX; }
|
||||
constexpr uint8_t getOpacityChannelIndex() const { return hasShapeChannel() ? getProcessColorChannelCount() + getSpotColorChannelCount() + getShapeChannelCount() : INVALID_CHANNEL_INDEX; }
|
||||
|
||||
/// Pixel format is valid, if we have at least one color channel
|
||||
/// (it doesn't matter, if it is process color, or spot color)
|
||||
constexpr bool isValid() const { return getColorChannelCount() > 0; }
|
||||
|
||||
inline void setProcessColors(const uint8_t& processColors) { m_processColors = processColors; }
|
||||
inline void setSpotColors(const uint8_t& spotColors) { m_spotColors = spotColors; }
|
||||
|
||||
static constexpr PDFPixelFormat createFormatDefaultGray(uint8_t spotColors) { return createFormat(1, spotColors, true, false); }
|
||||
static constexpr PDFPixelFormat createFormatDefaultRGB(uint8_t spotColors) { return createFormat(3, spotColors, true, false); }
|
||||
static constexpr PDFPixelFormat createFormatDefaultCMYK(uint8_t spotColors) { return createFormat(4, spotColors, true, true); }
|
||||
|
||||
static constexpr PDFPixelFormat removeProcessColors(PDFPixelFormat format) { return PDFPixelFormat(0, format.getSpotColorChannelCount(), format.getFlags()); }
|
||||
static constexpr PDFPixelFormat removeSpotColors(PDFPixelFormat format) { return PDFPixelFormat(format.getProcessColorChannelCount(), 0, format.getFlags()); }
|
||||
static constexpr PDFPixelFormat removeShapeAndOpacity(PDFPixelFormat format) { return PDFPixelFormat(format.getProcessColorChannelCount(), format.getSpotColorChannelCount(), format.hasProcessColorsSubtractive() ? FLAG_PROCESS_COLORS_SUBTRACTIVE : 0); }
|
||||
|
||||
static constexpr PDFPixelFormat createFormat(uint8_t processColors, uint8_t spotColors, bool withShapeAndOpacity, bool processColorSubtractive)
|
||||
{
|
||||
return PDFPixelFormat(processColors, spotColors, (withShapeAndOpacity ? FLAG_HAS_SHAPE_CHANNEL + FLAG_HAS_OPACITY_CHANNEL : 0) + (processColorSubtractive ? FLAG_PROCESS_COLORS_SUBTRACTIVE : 0));
|
||||
}
|
||||
|
||||
/// Calculates bitmap data length required to store bitmapt with given pixel format.
|
||||
/// \param width Bitmap width
|
||||
/// \param height Bitmap height
|
||||
size_t calculateBitmapDataLength(size_t width, size_t height) const { return width * height * size_t(getChannelCount()); }
|
||||
|
||||
private:
|
||||
inline explicit constexpr PDFPixelFormat(uint8_t processColors, uint8_t spotColors, uint8_t flags) :
|
||||
m_processColors(processColors),
|
||||
m_spotColors(spotColors),
|
||||
m_flags(flags)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
constexpr uint8_t FLAG_HAS_SHAPE_CHANNEL = 0x01;
|
||||
constexpr uint8_t FLAG_HAS_OPACITY_CHANNEL = 0x02;
|
||||
constexpr uint8_t FLAG_PROCESS_COLORS_SUBTRACTIVE = 0x04;
|
||||
|
||||
uint8_t m_processColors = 0;
|
||||
uint8_t m_spotColors = 0;
|
||||
uint8_t m_flags = 0;
|
||||
};
|
||||
|
||||
/// Represents float bitmap with arbitrary color channel count. Bitmap can also
|
||||
/// have auxiliary channels, such as shape and opacity channels.
|
||||
class PDFFloatBitmap
|
||||
{
|
||||
public:
|
||||
explicit PDFFloatBitmap();
|
||||
explicit PDFFloatBitmap(size_t width, size_t height, PDFPixelFormat format);
|
||||
|
||||
/// Returns buffer with pixel
|
||||
PDFColorBuffer getPixel(size_t x, size_t y);
|
||||
|
||||
const PDFColorComponent* begin() const;
|
||||
const PDFColorComponent* end() const;
|
||||
|
||||
PDFColorComponent* begin();
|
||||
PDFColorComponent* end();
|
||||
|
||||
/// Returns index where given pixel starts in the data block
|
||||
/// \param x Horizontal coordinate of the pixel
|
||||
/// \param y Vertical coordinate of the pixel
|
||||
size_t getPixelIndex(size_t x, size_t y) const;
|
||||
|
||||
private:
|
||||
PDFPixelFormat m_format;
|
||||
std::size_t m_width;
|
||||
std::size_t m_height;
|
||||
std::size_t m_pixelSize;
|
||||
std::vector<PDFColorComponent> m_data;
|
||||
};
|
||||
|
||||
class PDFTransparencyRenderer
|
||||
{
|
||||
public:
|
||||
|
|
Loading…
Reference in New Issue