mirror of
https://github.com/thorvg/thorvg.git
synced 2025-06-08 13:43:43 +00:00
renderer: code refactoring
- introduced RenderColor - internal name changes to avoid conflicts
This commit is contained in:
parent
a67f30de65
commit
d3d085de15
16 changed files with 154 additions and 167 deletions
|
@ -119,7 +119,7 @@ void GlRenderer::initShaders()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void GlRenderer::drawPrimitive(GlShape& sdata, uint8_t r, uint8_t g, uint8_t b, uint8_t a, RenderUpdateFlag flag, int32_t depth)
|
void GlRenderer::drawPrimitive(GlShape& sdata, const RenderColor& c, RenderUpdateFlag flag, int32_t depth)
|
||||||
{
|
{
|
||||||
auto vp = currentPass()->getViewport();
|
auto vp = currentPass()->getViewport();
|
||||||
auto bbox = sdata.geometry->getViewport();
|
auto bbox = sdata.geometry->getViewport();
|
||||||
|
@ -159,7 +159,7 @@ void GlRenderer::drawPrimitive(GlShape& sdata, uint8_t r, uint8_t g, uint8_t b,
|
||||||
stencilTask->setDrawDepth(depth);
|
stencilTask->setDrawDepth(depth);
|
||||||
}
|
}
|
||||||
|
|
||||||
a = MULTIPLY(a, sdata.opacity);
|
auto a = MULTIPLY(c.a, sdata.opacity);
|
||||||
|
|
||||||
if (flag & RenderUpdateFlag::Stroke) {
|
if (flag & RenderUpdateFlag::Stroke) {
|
||||||
float strokeWidth = sdata.rshape->strokeWidth() * sdata.geometry->getTransformMatrix().e11;
|
float strokeWidth = sdata.rshape->strokeWidth() * sdata.geometry->getTransformMatrix().e11;
|
||||||
|
@ -195,7 +195,7 @@ void GlRenderer::drawPrimitive(GlShape& sdata, uint8_t r, uint8_t g, uint8_t b,
|
||||||
}
|
}
|
||||||
|
|
||||||
// color
|
// color
|
||||||
float color[4] = {r / 255.f, g / 255.f, b / 255.f, a / 255.f};
|
float color[] = {c.r / 255.f, c.g / 255.f, c.b / 255.f, c.a / 255.f};
|
||||||
|
|
||||||
task->addBindResource(GlBindingResource{
|
task->addBindResource(GlBindingResource{
|
||||||
1,
|
1,
|
||||||
|
@ -1104,7 +1104,6 @@ bool GlRenderer::renderShape(RenderData data)
|
||||||
|
|
||||||
if (bbox.w <= 0 || bbox.h <= 0) return true;
|
if (bbox.w <= 0 || bbox.h <= 0) return true;
|
||||||
|
|
||||||
uint8_t r = 0, g = 0, b = 0, a = 0;
|
|
||||||
int32_t drawDepth1 = 0, drawDepth2 = 0;
|
int32_t drawDepth1 = 0, drawDepth2 = 0;
|
||||||
|
|
||||||
size_t flags = static_cast<size_t>(sdata->updateFlag);
|
size_t flags = static_cast<size_t>(sdata->updateFlag);
|
||||||
|
@ -1122,13 +1121,7 @@ bool GlRenderer::renderShape(RenderData data)
|
||||||
{
|
{
|
||||||
auto gradient = sdata->rshape->fill;
|
auto gradient = sdata->rshape->fill;
|
||||||
if (gradient) drawPrimitive(*sdata, gradient, RenderUpdateFlag::Gradient, drawDepth1);
|
if (gradient) drawPrimitive(*sdata, gradient, RenderUpdateFlag::Gradient, drawDepth1);
|
||||||
else {
|
else if (sdata->rshape->color.a > 0) drawPrimitive(*sdata, sdata->rshape->color, RenderUpdateFlag::Color, drawDepth1);
|
||||||
sdata->rshape->fillColor(&r, &g, &b, &a);
|
|
||||||
if (a > 0)
|
|
||||||
{
|
|
||||||
drawPrimitive(*sdata, r, g, b, a, RenderUpdateFlag::Color, drawDepth1);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (flags & (RenderUpdateFlag::Stroke | RenderUpdateFlag::GradientStroke))
|
if (flags & (RenderUpdateFlag::Stroke | RenderUpdateFlag::GradientStroke))
|
||||||
|
@ -1136,11 +1129,8 @@ bool GlRenderer::renderShape(RenderData data)
|
||||||
auto gradient = sdata->rshape->strokeFill();
|
auto gradient = sdata->rshape->strokeFill();
|
||||||
if (gradient) {
|
if (gradient) {
|
||||||
drawPrimitive(*sdata, gradient, RenderUpdateFlag::GradientStroke, drawDepth2);
|
drawPrimitive(*sdata, gradient, RenderUpdateFlag::GradientStroke, drawDepth2);
|
||||||
} else {
|
} else if (sdata->rshape->stroke && sdata->rshape->stroke->color.a > 0) {
|
||||||
if (sdata->rshape->strokeFill(&r, &g, &b, &a) && a > 0)
|
drawPrimitive(*sdata, sdata->rshape->stroke->color, RenderUpdateFlag::Stroke, drawDepth2);
|
||||||
{
|
|
||||||
drawPrimitive(*sdata, r, g, b, a, RenderUpdateFlag::Stroke, drawDepth2);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1236,9 +1226,8 @@ RenderData GlRenderer::prepare(const RenderShape& rshape, RenderData data, const
|
||||||
sdata->opacity = opacity;
|
sdata->opacity = opacity;
|
||||||
|
|
||||||
//invisible?
|
//invisible?
|
||||||
uint8_t alphaF = 0, alphaS = 0;
|
auto alphaF = rshape.color.a;
|
||||||
rshape.fillColor(nullptr, nullptr, nullptr, &alphaF);
|
auto alphaS = rshape.stroke ? rshape.stroke->color.a : 0;
|
||||||
rshape.strokeFill(nullptr, nullptr, nullptr, &alphaS);
|
|
||||||
|
|
||||||
if ( ((flags & RenderUpdateFlag::Gradient) == 0) &&
|
if ( ((flags & RenderUpdateFlag::Gradient) == 0) &&
|
||||||
((flags & RenderUpdateFlag::Color) && alphaF == 0) &&
|
((flags & RenderUpdateFlag::Color) && alphaF == 0) &&
|
||||||
|
|
|
@ -99,7 +99,7 @@ private:
|
||||||
~GlRenderer();
|
~GlRenderer();
|
||||||
|
|
||||||
void initShaders();
|
void initShaders();
|
||||||
void drawPrimitive(GlShape& sdata, uint8_t r, uint8_t g, uint8_t b, uint8_t a, RenderUpdateFlag flag, int32_t depth);
|
void drawPrimitive(GlShape& sdata, const RenderColor& c, RenderUpdateFlag flag, int32_t depth);
|
||||||
void drawPrimitive(GlShape& sdata, const Fill* fill, RenderUpdateFlag flag, int32_t depth);
|
void drawPrimitive(GlShape& sdata, const Fill* fill, RenderUpdateFlag flag, int32_t depth);
|
||||||
void drawClip(Array<RenderData>& clips);
|
void drawClip(Array<RenderData>& clips);
|
||||||
|
|
||||||
|
|
|
@ -558,9 +558,9 @@ void mpoolRetDashOutline(SwMpool* mpool, unsigned idx);
|
||||||
|
|
||||||
bool rasterCompositor(SwSurface* surface);
|
bool rasterCompositor(SwSurface* surface);
|
||||||
bool rasterGradientShape(SwSurface* surface, SwShape* shape, const Fill* fdata, uint8_t opacity);
|
bool rasterGradientShape(SwSurface* surface, SwShape* shape, const Fill* fdata, uint8_t opacity);
|
||||||
bool rasterShape(SwSurface* surface, SwShape* shape, uint8_t r, uint8_t g, uint8_t b, uint8_t a);
|
bool rasterShape(SwSurface* surface, SwShape* shape, RenderColor& c);
|
||||||
bool rasterImage(SwSurface* surface, SwImage* image, const Matrix& transform, const SwBBox& bbox, uint8_t opacity);
|
bool rasterImage(SwSurface* surface, SwImage* image, const Matrix& transform, const SwBBox& bbox, uint8_t opacity);
|
||||||
bool rasterStroke(SwSurface* surface, SwShape* shape, uint8_t r, uint8_t g, uint8_t b, uint8_t a);
|
bool rasterStroke(SwSurface* surface, SwShape* shape, RenderColor& c);
|
||||||
bool rasterGradientStroke(SwSurface* surface, SwShape* shape, const Fill* fdata, uint8_t opacity);
|
bool rasterGradientStroke(SwSurface* surface, SwShape* shape, const Fill* fdata, uint8_t opacity);
|
||||||
bool rasterClear(SwSurface* surface, uint32_t x, uint32_t y, uint32_t w, uint32_t h, pixel_t val = 0);
|
bool rasterClear(SwSurface* surface, uint32_t x, uint32_t y, uint32_t w, uint32_t h, pixel_t val = 0);
|
||||||
void rasterPixel32(uint32_t *dst, uint32_t val, uint32_t offset, int32_t len);
|
void rasterPixel32(uint32_t *dst, uint32_t val, uint32_t offset, int32_t len);
|
||||||
|
|
|
@ -324,7 +324,7 @@ static uint32_t _interpDownScaler(const uint32_t *img, uint32_t stride, uint32_t
|
||||||
/* Rect */
|
/* Rect */
|
||||||
/************************************************************************/
|
/************************************************************************/
|
||||||
|
|
||||||
static bool _rasterCompositeMaskedRect(SwSurface* surface, const SwBBox& region, SwMask maskOp, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool _rasterCompositeMaskedRect(SwSurface* surface, const SwBBox& region, SwMask maskOp, uint8_t a)
|
||||||
{
|
{
|
||||||
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
||||||
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
||||||
|
@ -343,7 +343,7 @@ static bool _rasterCompositeMaskedRect(SwSurface* surface, const SwBBox& region,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool _rasterDirectMaskedRect(SwSurface* surface, const SwBBox& region, SwMask maskOp, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool _rasterDirectMaskedRect(SwSurface* surface, const SwBBox& region, SwMask maskOp, uint8_t a)
|
||||||
{
|
{
|
||||||
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
||||||
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
||||||
|
@ -364,7 +364,7 @@ static bool _rasterDirectMaskedRect(SwSurface* surface, const SwBBox& region, Sw
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool _rasterMaskedRect(SwSurface* surface, const SwBBox& region, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool _rasterMaskedRect(SwSurface* surface, const SwBBox& region, const RenderColor& c)
|
||||||
{
|
{
|
||||||
//8bit masking channels composition
|
//8bit masking channels composition
|
||||||
if (surface->channelSize != sizeof(uint8_t)) return false;
|
if (surface->channelSize != sizeof(uint8_t)) return false;
|
||||||
|
@ -372,13 +372,13 @@ static bool _rasterMaskedRect(SwSurface* surface, const SwBBox& region, uint8_t
|
||||||
TVGLOG("SW_ENGINE", "Masked(%d) Rect [Region: %lu %lu %lu %lu]", (int)surface->compositor->method, region.min.x, region.min.y, region.max.x - region.min.x, region.max.y - region.min.y);
|
TVGLOG("SW_ENGINE", "Masked(%d) Rect [Region: %lu %lu %lu %lu]", (int)surface->compositor->method, region.min.x, region.min.y, region.max.x - region.min.x, region.max.y - region.min.y);
|
||||||
|
|
||||||
auto maskOp = _getMaskOp(surface->compositor->method);
|
auto maskOp = _getMaskOp(surface->compositor->method);
|
||||||
if (_direct(surface->compositor->method)) return _rasterDirectMaskedRect(surface, region, maskOp, r, g, b, a);
|
if (_direct(surface->compositor->method)) return _rasterDirectMaskedRect(surface, region, maskOp, c.a);
|
||||||
else return _rasterCompositeMaskedRect(surface, region, maskOp, r, g, b, a);
|
else return _rasterCompositeMaskedRect(surface, region, maskOp, c.a);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool _rasterMattedRect(SwSurface* surface, const SwBBox& region, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool _rasterMattedRect(SwSurface* surface, const SwBBox& region, const RenderColor& c)
|
||||||
{
|
{
|
||||||
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
||||||
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
||||||
|
@ -390,7 +390,7 @@ static bool _rasterMattedRect(SwSurface* surface, const SwBBox& region, uint8_t
|
||||||
|
|
||||||
//32bits channels
|
//32bits channels
|
||||||
if (surface->channelSize == sizeof(uint32_t)) {
|
if (surface->channelSize == sizeof(uint32_t)) {
|
||||||
auto color = surface->join(r, g, b, a);
|
auto color = surface->join(c.r, c.g, c.b, c.a);
|
||||||
auto buffer = surface->buf32 + (region.min.y * surface->stride) + region.min.x;
|
auto buffer = surface->buf32 + (region.min.y * surface->stride) + region.min.x;
|
||||||
for (uint32_t y = 0; y < h; ++y) {
|
for (uint32_t y = 0; y < h; ++y) {
|
||||||
auto dst = &buffer[y * surface->stride];
|
auto dst = &buffer[y * surface->stride];
|
||||||
|
@ -407,7 +407,7 @@ static bool _rasterMattedRect(SwSurface* surface, const SwBBox& region, uint8_t
|
||||||
auto dst = &buffer[y * surface->stride];
|
auto dst = &buffer[y * surface->stride];
|
||||||
auto cmp = &cbuffer[y * surface->compositor->image.stride * csize];
|
auto cmp = &cbuffer[y * surface->compositor->image.stride * csize];
|
||||||
for (uint32_t x = 0; x < w; ++x, ++dst, cmp += csize) {
|
for (uint32_t x = 0; x < w; ++x, ++dst, cmp += csize) {
|
||||||
*dst = INTERPOLATE8(a, *dst, alpha(cmp));
|
*dst = INTERPOLATE8(c.a, *dst, alpha(cmp));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -415,13 +415,13 @@ static bool _rasterMattedRect(SwSurface* surface, const SwBBox& region, uint8_t
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool _rasterBlendingRect(SwSurface* surface, const SwBBox& region, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool _rasterBlendingRect(SwSurface* surface, const SwBBox& region, const RenderColor& c)
|
||||||
{
|
{
|
||||||
if (surface->channelSize != sizeof(uint32_t)) return false;
|
if (surface->channelSize != sizeof(uint32_t)) return false;
|
||||||
|
|
||||||
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
||||||
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
||||||
auto color = surface->join(r, g, b, a);
|
auto color = surface->join(c.r, c.g, c.b, c.a);
|
||||||
auto buffer = surface->buf32 + (region.min.y * surface->stride) + region.min.x;
|
auto buffer = surface->buf32 + (region.min.y * surface->stride) + region.min.x;
|
||||||
|
|
||||||
for (uint32_t y = 0; y < h; ++y) {
|
for (uint32_t y = 0; y < h; ++y) {
|
||||||
|
@ -434,26 +434,26 @@ static bool _rasterBlendingRect(SwSurface* surface, const SwBBox& region, uint8_
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool _rasterTranslucentRect(SwSurface* surface, const SwBBox& region, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool _rasterTranslucentRect(SwSurface* surface, const SwBBox& region, const RenderColor& c)
|
||||||
{
|
{
|
||||||
#if defined(THORVG_AVX_VECTOR_SUPPORT)
|
#if defined(THORVG_AVX_VECTOR_SUPPORT)
|
||||||
return avxRasterTranslucentRect(surface, region, r, g, b, a);
|
return avxRasterTranslucentRect(surface, region, c);
|
||||||
#elif defined(THORVG_NEON_VECTOR_SUPPORT)
|
#elif defined(THORVG_NEON_VECTOR_SUPPORT)
|
||||||
return neonRasterTranslucentRect(surface, region, r, g, b, a);
|
return neonRasterTranslucentRect(surface, region, c);
|
||||||
#else
|
#else
|
||||||
return cRasterTranslucentRect(surface, region, r, g, b, a);
|
return cRasterTranslucentRect(surface, region, c);
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool _rasterSolidRect(SwSurface* surface, const SwBBox& region, uint8_t r, uint8_t g, uint8_t b)
|
static bool _rasterSolidRect(SwSurface* surface, const SwBBox& region, const RenderColor& c)
|
||||||
{
|
{
|
||||||
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
||||||
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
||||||
|
|
||||||
//32bits channels
|
//32bits channels
|
||||||
if (surface->channelSize == sizeof(uint32_t)) {
|
if (surface->channelSize == sizeof(uint32_t)) {
|
||||||
auto color = surface->join(r, g, b, 255);
|
auto color = surface->join(c.r, c.g, c.b, 255);
|
||||||
auto buffer = surface->buf32 + (region.min.y * surface->stride);
|
auto buffer = surface->buf32 + (region.min.y * surface->stride);
|
||||||
for (uint32_t y = 0; y < h; ++y) {
|
for (uint32_t y = 0; y < h; ++y) {
|
||||||
rasterPixel32(buffer + y * surface->stride, color, region.min.x, w);
|
rasterPixel32(buffer + y * surface->stride, color, region.min.x, w);
|
||||||
|
@ -471,16 +471,16 @@ static bool _rasterSolidRect(SwSurface* surface, const SwBBox& region, uint8_t r
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool _rasterRect(SwSurface* surface, const SwBBox& region, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool _rasterRect(SwSurface* surface, const SwBBox& region, const RenderColor& c)
|
||||||
{
|
{
|
||||||
if (_compositing(surface)) {
|
if (_compositing(surface)) {
|
||||||
if (_matting(surface)) return _rasterMattedRect(surface, region, r, g, b, a);
|
if (_matting(surface)) return _rasterMattedRect(surface, region, c);
|
||||||
else return _rasterMaskedRect(surface, region, r, g, b, a);
|
else return _rasterMaskedRect(surface, region, c);
|
||||||
} else if (_blending(surface)) {
|
} else if (_blending(surface)) {
|
||||||
return _rasterBlendingRect(surface, region, r, g, b, a);
|
return _rasterBlendingRect(surface, region, c);
|
||||||
} else {
|
} else {
|
||||||
if (a == 255) return _rasterSolidRect(surface, region, r, g, b);
|
if (c.a == 255) return _rasterSolidRect(surface, region, c);
|
||||||
else return _rasterTranslucentRect(surface, region, r, g, b, a);
|
else return _rasterTranslucentRect(surface, region, c);
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -490,7 +490,7 @@ static bool _rasterRect(SwSurface* surface, const SwBBox& region, uint8_t r, uin
|
||||||
/* Rle */
|
/* Rle */
|
||||||
/************************************************************************/
|
/************************************************************************/
|
||||||
|
|
||||||
static bool _rasterCompositeMaskedRle(SwSurface* surface, SwRle* rle, SwMask maskOp, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool _rasterCompositeMaskedRle(SwSurface* surface, SwRle* rle, SwMask maskOp, uint8_t a)
|
||||||
{
|
{
|
||||||
auto span = rle->spans;
|
auto span = rle->spans;
|
||||||
auto cbuffer = surface->compositor->image.buf8;
|
auto cbuffer = surface->compositor->image.buf8;
|
||||||
|
@ -510,7 +510,7 @@ static bool _rasterCompositeMaskedRle(SwSurface* surface, SwRle* rle, SwMask mas
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool _rasterDirectMaskedRle(SwSurface* surface, SwRle* rle, SwMask maskOp, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool _rasterDirectMaskedRle(SwSurface* surface, SwRle* rle, SwMask maskOp, uint8_t a)
|
||||||
{
|
{
|
||||||
auto span = rle->spans;
|
auto span = rle->spans;
|
||||||
auto cbuffer = surface->compositor->image.buf8;
|
auto cbuffer = surface->compositor->image.buf8;
|
||||||
|
@ -531,7 +531,7 @@ static bool _rasterDirectMaskedRle(SwSurface* surface, SwRle* rle, SwMask maskOp
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool _rasterMaskedRle(SwSurface* surface, SwRle* rle, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool _rasterMaskedRle(SwSurface* surface, SwRle* rle, const RenderColor& c)
|
||||||
{
|
{
|
||||||
TVGLOG("SW_ENGINE", "Masked(%d) Rle", (int)surface->compositor->method);
|
TVGLOG("SW_ENGINE", "Masked(%d) Rle", (int)surface->compositor->method);
|
||||||
|
|
||||||
|
@ -539,13 +539,13 @@ static bool _rasterMaskedRle(SwSurface* surface, SwRle* rle, uint8_t r, uint8_t
|
||||||
if (surface->channelSize != sizeof(uint8_t)) return false;
|
if (surface->channelSize != sizeof(uint8_t)) return false;
|
||||||
|
|
||||||
auto maskOp = _getMaskOp(surface->compositor->method);
|
auto maskOp = _getMaskOp(surface->compositor->method);
|
||||||
if (_direct(surface->compositor->method)) return _rasterDirectMaskedRle(surface, rle, maskOp, r, g, b, a);
|
if (_direct(surface->compositor->method)) return _rasterDirectMaskedRle(surface, rle, maskOp, c.a);
|
||||||
else return _rasterCompositeMaskedRle(surface, rle, maskOp, r, g, b, a);
|
else return _rasterCompositeMaskedRle(surface, rle, maskOp, c.a);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool _rasterMattedRle(SwSurface* surface, SwRle* rle, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool _rasterMattedRle(SwSurface* surface, SwRle* rle, const RenderColor& c)
|
||||||
{
|
{
|
||||||
TVGLOG("SW_ENGINE", "Matted(%d) Rle", (int)surface->compositor->method);
|
TVGLOG("SW_ENGINE", "Matted(%d) Rle", (int)surface->compositor->method);
|
||||||
|
|
||||||
|
@ -557,7 +557,7 @@ static bool _rasterMattedRle(SwSurface* surface, SwRle* rle, uint8_t r, uint8_t
|
||||||
//32bit channels
|
//32bit channels
|
||||||
if (surface->channelSize == sizeof(uint32_t)) {
|
if (surface->channelSize == sizeof(uint32_t)) {
|
||||||
uint32_t src;
|
uint32_t src;
|
||||||
auto color = surface->join(r, g, b, a);
|
auto color = surface->join(c.r, c.g, c.b, c.a);
|
||||||
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
||||||
auto dst = &surface->buf32[span->y * surface->stride + span->x];
|
auto dst = &surface->buf32[span->y * surface->stride + span->x];
|
||||||
auto cmp = &cbuffer[(span->y * surface->compositor->image.stride + span->x) * csize];
|
auto cmp = &cbuffer[(span->y * surface->compositor->image.stride + span->x) * csize];
|
||||||
|
@ -574,8 +574,8 @@ static bool _rasterMattedRle(SwSurface* surface, SwRle* rle, uint8_t r, uint8_t
|
||||||
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
||||||
auto dst = &surface->buf8[span->y * surface->stride + span->x];
|
auto dst = &surface->buf8[span->y * surface->stride + span->x];
|
||||||
auto cmp = &cbuffer[(span->y * surface->compositor->image.stride + span->x) * csize];
|
auto cmp = &cbuffer[(span->y * surface->compositor->image.stride + span->x) * csize];
|
||||||
if (span->coverage == 255) src = a;
|
if (span->coverage == 255) src = c.a;
|
||||||
else src = MULTIPLY(a, span->coverage);
|
else src = MULTIPLY(c.a, span->coverage);
|
||||||
for (uint32_t x = 0; x < span->len; ++x, ++dst, cmp += csize) {
|
for (uint32_t x = 0; x < span->len; ++x, ++dst, cmp += csize) {
|
||||||
*dst = INTERPOLATE8(src, *dst, alpha(cmp));
|
*dst = INTERPOLATE8(src, *dst, alpha(cmp));
|
||||||
}
|
}
|
||||||
|
@ -585,12 +585,12 @@ static bool _rasterMattedRle(SwSurface* surface, SwRle* rle, uint8_t r, uint8_t
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool _rasterBlendingRle(SwSurface* surface, const SwRle* rle, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool _rasterBlendingRle(SwSurface* surface, const SwRle* rle, const RenderColor& c)
|
||||||
{
|
{
|
||||||
if (surface->channelSize != sizeof(uint32_t)) return false;
|
if (surface->channelSize != sizeof(uint32_t)) return false;
|
||||||
|
|
||||||
auto span = rle->spans;
|
auto span = rle->spans;
|
||||||
auto color = surface->join(r, g, b, a);
|
auto color = surface->join(c.r, c.g, c.b, c.a);
|
||||||
|
|
||||||
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
||||||
auto dst = &surface->buf32[span->y * surface->stride + span->x];
|
auto dst = &surface->buf32[span->y * surface->stride + span->x];
|
||||||
|
@ -609,25 +609,25 @@ static bool _rasterBlendingRle(SwSurface* surface, const SwRle* rle, uint8_t r,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool _rasterTranslucentRle(SwSurface* surface, const SwRle* rle, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool _rasterTranslucentRle(SwSurface* surface, const SwRle* rle, const RenderColor& c)
|
||||||
{
|
{
|
||||||
#if defined(THORVG_AVX_VECTOR_SUPPORT)
|
#if defined(THORVG_AVX_VECTOR_SUPPORT)
|
||||||
return avxRasterTranslucentRle(surface, rle, r, g, b, a);
|
return avxRasterTranslucentRle(surface, rle, c);
|
||||||
#elif defined(THORVG_NEON_VECTOR_SUPPORT)
|
#elif defined(THORVG_NEON_VECTOR_SUPPORT)
|
||||||
return neonRasterTranslucentRle(surface, rle, r, g, b, a);
|
return neonRasterTranslucentRle(surface, rle, c);
|
||||||
#else
|
#else
|
||||||
return cRasterTranslucentRle(surface, rle, r, g, b, a);
|
return cRasterTranslucentRle(surface, rle, c);
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool _rasterSolidRle(SwSurface* surface, const SwRle* rle, uint8_t r, uint8_t g, uint8_t b)
|
static bool _rasterSolidRle(SwSurface* surface, const SwRle* rle, const RenderColor& c)
|
||||||
{
|
{
|
||||||
auto span = rle->spans;
|
auto span = rle->spans;
|
||||||
|
|
||||||
//32bit channels
|
//32bit channels
|
||||||
if (surface->channelSize == sizeof(uint32_t)) {
|
if (surface->channelSize == sizeof(uint32_t)) {
|
||||||
auto color = surface->join(r, g, b, 255);
|
auto color = surface->join(c.r, c.g, c.b, 255);
|
||||||
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
||||||
if (span->coverage == 255) {
|
if (span->coverage == 255) {
|
||||||
rasterPixel32(surface->buf32 + span->y * surface->stride, color, span->x, span->len);
|
rasterPixel32(surface->buf32 + span->y * surface->stride, color, span->x, span->len);
|
||||||
|
@ -658,18 +658,18 @@ static bool _rasterSolidRle(SwSurface* surface, const SwRle* rle, uint8_t r, uin
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool _rasterRle(SwSurface* surface, SwRle* rle, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool _rasterRle(SwSurface* surface, SwRle* rle, const RenderColor& c)
|
||||||
{
|
{
|
||||||
if (!rle) return false;
|
if (!rle) return false;
|
||||||
|
|
||||||
if (_compositing(surface)) {
|
if (_compositing(surface)) {
|
||||||
if (_matting(surface)) return _rasterMattedRle(surface, rle, r, g, b, a);
|
if (_matting(surface)) return _rasterMattedRle(surface, rle, c);
|
||||||
else return _rasterMaskedRle(surface, rle, r, g, b, a);
|
else return _rasterMaskedRle(surface, rle, c);
|
||||||
} else if (_blending(surface)) {
|
} else if (_blending(surface)) {
|
||||||
return _rasterBlendingRle(surface, rle, r, g, b, a);
|
return _rasterBlendingRle(surface, rle, c);
|
||||||
} else {
|
} else {
|
||||||
if (a == 255) return _rasterSolidRle(surface, rle, r, g, b);
|
if (c.a == 255) return _rasterSolidRle(surface, rle, c);
|
||||||
else return _rasterTranslucentRle(surface, rle, r, g, b, a);
|
else return _rasterTranslucentRle(surface, rle, c);
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -1724,7 +1724,8 @@ bool rasterGradientShape(SwSurface* surface, SwShape* shape, const Fill* fdata,
|
||||||
|
|
||||||
if (auto color = fillFetchSolid(shape->fill, fdata)) {
|
if (auto color = fillFetchSolid(shape->fill, fdata)) {
|
||||||
auto a = MULTIPLY(color->a, opacity);
|
auto a = MULTIPLY(color->a, opacity);
|
||||||
return a > 0 ? rasterShape(surface, shape, color->r, color->g, color->b, a) : true;
|
RenderColor c = {color->r, color->g, color->b, a};
|
||||||
|
return a > 0 ? rasterShape(surface, shape, c) : true;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto type = fdata->type();
|
auto type = fdata->type();
|
||||||
|
@ -1744,8 +1745,9 @@ bool rasterGradientStroke(SwSurface* surface, SwShape* shape, const Fill* fdata,
|
||||||
if (!shape->stroke || !shape->stroke->fill || !shape->strokeRle) return false;
|
if (!shape->stroke || !shape->stroke->fill || !shape->strokeRle) return false;
|
||||||
|
|
||||||
if (auto color = fillFetchSolid(shape->stroke->fill, fdata)) {
|
if (auto color = fillFetchSolid(shape->stroke->fill, fdata)) {
|
||||||
auto a = MULTIPLY(color->a, opacity);
|
RenderColor c = {color->r, color->g, color->b, color->a};
|
||||||
return a > 0 ? rasterStroke(surface, shape, color->r, color->g, color->b, a) : true;
|
c.a = MULTIPLY(c.a, opacity);
|
||||||
|
return c.a > 0 ? rasterStroke(surface, shape, c) : true;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto type = fdata->type();
|
auto type = fdata->type();
|
||||||
|
@ -1756,27 +1758,27 @@ bool rasterGradientStroke(SwSurface* surface, SwShape* shape, const Fill* fdata,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
bool rasterShape(SwSurface* surface, SwShape* shape, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
bool rasterShape(SwSurface* surface, SwShape* shape, RenderColor& c)
|
||||||
{
|
{
|
||||||
if (a < 255) {
|
if (c.a < 255) {
|
||||||
r = MULTIPLY(r, a);
|
c.r = MULTIPLY(c.r, c.a);
|
||||||
g = MULTIPLY(g, a);
|
c.g = MULTIPLY(c.g, c.a);
|
||||||
b = MULTIPLY(b, a);
|
c.b = MULTIPLY(c.b, c.a);
|
||||||
}
|
}
|
||||||
if (shape->fastTrack) return _rasterRect(surface, shape->bbox, r, g, b, a);
|
if (shape->fastTrack) return _rasterRect(surface, shape->bbox, c);
|
||||||
else return _rasterRle(surface, shape->rle, r, g, b, a);
|
else return _rasterRle(surface, shape->rle, c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
bool rasterStroke(SwSurface* surface, SwShape* shape, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
bool rasterStroke(SwSurface* surface, SwShape* shape, RenderColor& c)
|
||||||
{
|
{
|
||||||
if (a < 255) {
|
if (c.a < 255) {
|
||||||
r = MULTIPLY(r, a);
|
c.r = MULTIPLY(c.r, c.a);
|
||||||
g = MULTIPLY(g, a);
|
c.g = MULTIPLY(c.g, c.a);
|
||||||
b = MULTIPLY(b, a);
|
c.b = MULTIPLY(c.b, c.a);
|
||||||
}
|
}
|
||||||
|
|
||||||
return _rasterRle(surface, shape->strokeRle, r, g, b, a);
|
return _rasterRle(surface, shape->strokeRle, c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -99,17 +99,17 @@ static void avxRasterPixel32(uint32_t *dst, uint32_t val, uint32_t offset, int32
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool avxRasterTranslucentRect(SwSurface* surface, const SwBBox& region, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool avxRasterTranslucentRect(SwSurface* surface, const SwBBox& region, const RenderColor& c)
|
||||||
{
|
{
|
||||||
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
||||||
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
||||||
|
|
||||||
//32bits channels
|
//32bits channels
|
||||||
if (surface->channelSize == sizeof(uint32_t)) {
|
if (surface->channelSize == sizeof(uint32_t)) {
|
||||||
auto color = surface->join(r, g, b, a);
|
auto color = surface->join(c.r, c.g, c.b, c.a);
|
||||||
auto buffer = surface->buf32 + (region.min.y * surface->stride) + region.min.x;
|
auto buffer = surface->buf32 + (region.min.y * surface->stride) + region.min.x;
|
||||||
|
|
||||||
uint32_t ialpha = 255 - a;
|
uint32_t ialpha = 255 - c.a;
|
||||||
|
|
||||||
auto avxColor = _mm_set1_epi32(color);
|
auto avxColor = _mm_set1_epi32(color);
|
||||||
auto avxIalpha = _mm_set1_epi8(ialpha);
|
auto avxIalpha = _mm_set1_epi8(ialpha);
|
||||||
|
@ -146,11 +146,11 @@ static bool avxRasterTranslucentRect(SwSurface* surface, const SwBBox& region, u
|
||||||
} else if (surface->channelSize == sizeof(uint8_t)) {
|
} else if (surface->channelSize == sizeof(uint8_t)) {
|
||||||
TVGLOG("SW_ENGINE", "Require AVX Optimization, Channel Size = %d", surface->channelSize);
|
TVGLOG("SW_ENGINE", "Require AVX Optimization, Channel Size = %d", surface->channelSize);
|
||||||
auto buffer = surface->buf8 + (region.min.y * surface->stride) + region.min.x;
|
auto buffer = surface->buf8 + (region.min.y * surface->stride) + region.min.x;
|
||||||
auto ialpha = ~a;
|
auto ialpha = ~c.a;
|
||||||
for (uint32_t y = 0; y < h; ++y) {
|
for (uint32_t y = 0; y < h; ++y) {
|
||||||
auto dst = &buffer[y * surface->stride];
|
auto dst = &buffer[y * surface->stride];
|
||||||
for (uint32_t x = 0; x < w; ++x, ++dst) {
|
for (uint32_t x = 0; x < w; ++x, ++dst) {
|
||||||
*dst = a + MULTIPLY(*dst, ialpha);
|
*dst = c.a + MULTIPLY(*dst, ialpha);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -158,13 +158,13 @@ static bool avxRasterTranslucentRect(SwSurface* surface, const SwBBox& region, u
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool avxRasterTranslucentRle(SwSurface* surface, const SwRle* rle, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool avxRasterTranslucentRle(SwSurface* surface, const SwRle* rle, const RenderColor& c)
|
||||||
{
|
{
|
||||||
auto span = rle->spans;
|
auto span = rle->spans;
|
||||||
|
|
||||||
//32bit channels
|
//32bit channels
|
||||||
if (surface->channelSize == sizeof(uint32_t)) {
|
if (surface->channelSize == sizeof(uint32_t)) {
|
||||||
auto color = surface->join(r, g, b, a);
|
auto color = surface->join(c.r, c.g, c.b, c.a);
|
||||||
uint32_t src;
|
uint32_t src;
|
||||||
|
|
||||||
for (uint32_t i = 0; i < rle->size; ++i) {
|
for (uint32_t i = 0; i < rle->size; ++i) {
|
||||||
|
@ -215,9 +215,9 @@ static bool avxRasterTranslucentRle(SwSurface* surface, const SwRle* rle, uint8_
|
||||||
uint8_t src;
|
uint8_t src;
|
||||||
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
||||||
auto dst = &surface->buf8[span->y * surface->stride + span->x];
|
auto dst = &surface->buf8[span->y * surface->stride + span->x];
|
||||||
if (span->coverage < 255) src = MULTIPLY(span->coverage, a);
|
if (span->coverage < 255) src = MULTIPLY(span->coverage, c.a);
|
||||||
else src = a;
|
else src = c.a;
|
||||||
auto ialpha = ~a;
|
auto ialpha = ~c.a;
|
||||||
for (uint32_t x = 0; x < span->len; ++x, ++dst) {
|
for (uint32_t x = 0; x < span->len; ++x, ++dst) {
|
||||||
*dst = src + MULTIPLY(*dst, ialpha);
|
*dst = src + MULTIPLY(*dst, ialpha);
|
||||||
}
|
}
|
||||||
|
|
|
@ -92,13 +92,13 @@ static void inline cRasterPixels(PIXEL_T* dst, PIXEL_T val, uint32_t offset, int
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool inline cRasterTranslucentRle(SwSurface* surface, const SwRle* rle, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool inline cRasterTranslucentRle(SwSurface* surface, const SwRle* rle, const RenderColor& c)
|
||||||
{
|
{
|
||||||
auto span = rle->spans;
|
auto span = rle->spans;
|
||||||
|
|
||||||
//32bit channels
|
//32bit channels
|
||||||
if (surface->channelSize == sizeof(uint32_t)) {
|
if (surface->channelSize == sizeof(uint32_t)) {
|
||||||
auto color = surface->join(r, g, b, a);
|
auto color = surface->join(c.r, c.g, c.b, c.a);
|
||||||
uint32_t src;
|
uint32_t src;
|
||||||
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
||||||
auto dst = &surface->buf32[span->y * surface->stride + span->x];
|
auto dst = &surface->buf32[span->y * surface->stride + span->x];
|
||||||
|
@ -114,9 +114,9 @@ static bool inline cRasterTranslucentRle(SwSurface* surface, const SwRle* rle, u
|
||||||
uint8_t src;
|
uint8_t src;
|
||||||
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
||||||
auto dst = &surface->buf8[span->y * surface->stride + span->x];
|
auto dst = &surface->buf8[span->y * surface->stride + span->x];
|
||||||
if (span->coverage < 255) src = MULTIPLY(span->coverage, a);
|
if (span->coverage < 255) src = MULTIPLY(span->coverage, c.a);
|
||||||
else src = a;
|
else src = c.a;
|
||||||
auto ialpha = ~a;
|
auto ialpha = ~c.a;
|
||||||
for (uint32_t x = 0; x < span->len; ++x, ++dst) {
|
for (uint32_t x = 0; x < span->len; ++x, ++dst) {
|
||||||
*dst = src + MULTIPLY(*dst, ialpha);
|
*dst = src + MULTIPLY(*dst, ialpha);
|
||||||
}
|
}
|
||||||
|
@ -126,16 +126,16 @@ static bool inline cRasterTranslucentRle(SwSurface* surface, const SwRle* rle, u
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool inline cRasterTranslucentRect(SwSurface* surface, const SwBBox& region, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool inline cRasterTranslucentRect(SwSurface* surface, const SwBBox& region, const RenderColor& c)
|
||||||
{
|
{
|
||||||
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
||||||
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
||||||
|
|
||||||
//32bits channels
|
//32bits channels
|
||||||
if (surface->channelSize == sizeof(uint32_t)) {
|
if (surface->channelSize == sizeof(uint32_t)) {
|
||||||
auto color = surface->join(r, g, b, a);
|
auto color = surface->join(c.r, c.g, c.b, c.a);
|
||||||
auto buffer = surface->buf32 + (region.min.y * surface->stride) + region.min.x;
|
auto buffer = surface->buf32 + (region.min.y * surface->stride) + region.min.x;
|
||||||
auto ialpha = 255 - a;
|
auto ialpha = 255 - c.a;
|
||||||
for (uint32_t y = 0; y < h; ++y) {
|
for (uint32_t y = 0; y < h; ++y) {
|
||||||
auto dst = &buffer[y * surface->stride];
|
auto dst = &buffer[y * surface->stride];
|
||||||
for (uint32_t x = 0; x < w; ++x, ++dst) {
|
for (uint32_t x = 0; x < w; ++x, ++dst) {
|
||||||
|
@ -145,11 +145,11 @@ static bool inline cRasterTranslucentRect(SwSurface* surface, const SwBBox& regi
|
||||||
//8bit grayscale
|
//8bit grayscale
|
||||||
} else if (surface->channelSize == sizeof(uint8_t)) {
|
} else if (surface->channelSize == sizeof(uint8_t)) {
|
||||||
auto buffer = surface->buf8 + (region.min.y * surface->stride) + region.min.x;
|
auto buffer = surface->buf8 + (region.min.y * surface->stride) + region.min.x;
|
||||||
auto ialpha = ~a;
|
auto ialpha = ~c.a;
|
||||||
for (uint32_t y = 0; y < h; ++y) {
|
for (uint32_t y = 0; y < h; ++y) {
|
||||||
auto dst = &buffer[y * surface->stride];
|
auto dst = &buffer[y * surface->stride];
|
||||||
for (uint32_t x = 0; x < w; ++x, ++dst) {
|
for (uint32_t x = 0; x < w; ++x, ++dst) {
|
||||||
*dst = a + MULTIPLY(*dst, ialpha);
|
*dst = c.a + MULTIPLY(*dst, ialpha);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -89,13 +89,13 @@ static void neonRasterPixel32(uint32_t *dst, uint32_t val, uint32_t offset, int3
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool neonRasterTranslucentRle(SwSurface* surface, const SwRle* rle, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool neonRasterTranslucentRle(SwSurface* surface, const SwRle* rle, const RenderColor& c)
|
||||||
{
|
{
|
||||||
auto span = rle->spans;
|
auto span = rle->spans;
|
||||||
|
|
||||||
//32bit channels
|
//32bit channels
|
||||||
if (surface->channelSize == sizeof(uint32_t)) {
|
if (surface->channelSize == sizeof(uint32_t)) {
|
||||||
auto color = surface->join(r, g, b, a);
|
auto color = surface->join(c.r, c.g, c.b, c.a);
|
||||||
uint32_t src;
|
uint32_t src;
|
||||||
uint8x8_t *vDst = nullptr;
|
uint8x8_t *vDst = nullptr;
|
||||||
uint16_t align;
|
uint16_t align;
|
||||||
|
@ -134,9 +134,9 @@ static bool neonRasterTranslucentRle(SwSurface* surface, const SwRle* rle, uint8
|
||||||
uint8_t src;
|
uint8_t src;
|
||||||
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
for (uint32_t i = 0; i < rle->size; ++i, ++span) {
|
||||||
auto dst = &surface->buf8[span->y * surface->stride + span->x];
|
auto dst = &surface->buf8[span->y * surface->stride + span->x];
|
||||||
if (span->coverage < 255) src = MULTIPLY(span->coverage, a);
|
if (span->coverage < 255) src = MULTIPLY(span->coverage, c.a);
|
||||||
else src = a;
|
else src = c.a;
|
||||||
auto ialpha = ~a;
|
auto ialpha = ~c.a;
|
||||||
for (uint32_t x = 0; x < span->len; ++x, ++dst) {
|
for (uint32_t x = 0; x < span->len; ++x, ++dst) {
|
||||||
*dst = src + MULTIPLY(*dst, ialpha);
|
*dst = src + MULTIPLY(*dst, ialpha);
|
||||||
}
|
}
|
||||||
|
@ -146,16 +146,16 @@ static bool neonRasterTranslucentRle(SwSurface* surface, const SwRle* rle, uint8
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static bool neonRasterTranslucentRect(SwSurface* surface, const SwBBox& region, uint8_t r, uint8_t g, uint8_t b, uint8_t a)
|
static bool neonRasterTranslucentRect(SwSurface* surface, const SwBBox& region, const RenderColor& c)
|
||||||
{
|
{
|
||||||
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
auto h = static_cast<uint32_t>(region.max.y - region.min.y);
|
||||||
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
auto w = static_cast<uint32_t>(region.max.x - region.min.x);
|
||||||
|
|
||||||
//32bits channels
|
//32bits channels
|
||||||
if (surface->channelSize == sizeof(uint32_t)) {
|
if (surface->channelSize == sizeof(uint32_t)) {
|
||||||
auto color = surface->join(r, g, b, a);
|
auto color = surface->join(c.r, c.g, c.b, c.a);
|
||||||
auto buffer = surface->buf32 + (region.min.y * surface->stride) + region.min.x;
|
auto buffer = surface->buf32 + (region.min.y * surface->stride) + region.min.x;
|
||||||
auto ialpha = 255 - a;
|
auto ialpha = 255 - c.a;
|
||||||
|
|
||||||
auto vColor = vdup_n_u32(color);
|
auto vColor = vdup_n_u32(color);
|
||||||
auto vIalpha = vdup_n_u8((uint8_t) ialpha);
|
auto vIalpha = vdup_n_u8((uint8_t) ialpha);
|
||||||
|
@ -186,11 +186,11 @@ static bool neonRasterTranslucentRect(SwSurface* surface, const SwBBox& region,
|
||||||
} else if (surface->channelSize == sizeof(uint8_t)) {
|
} else if (surface->channelSize == sizeof(uint8_t)) {
|
||||||
TVGLOG("SW_ENGINE", "Require Neon Optimization, Channel Size = %d", surface->channelSize);
|
TVGLOG("SW_ENGINE", "Require Neon Optimization, Channel Size = %d", surface->channelSize);
|
||||||
auto buffer = surface->buf8 + (region.min.y * surface->stride) + region.min.x;
|
auto buffer = surface->buf8 + (region.min.y * surface->stride) + region.min.x;
|
||||||
auto ialpha = ~a;
|
auto ialpha = ~c.a;
|
||||||
for (uint32_t y = 0; y < h; ++y) {
|
for (uint32_t y = 0; y < h; ++y) {
|
||||||
auto dst = &buffer[y * surface->stride];
|
auto dst = &buffer[y * surface->stride];
|
||||||
for (uint32_t x = 0; x < w; ++x, ++dst) {
|
for (uint32_t x = 0; x < w; ++x, ++dst) {
|
||||||
*dst = a + MULTIPLY(*dst, ialpha);
|
*dst = c.a + MULTIPLY(*dst, ialpha);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -85,7 +85,7 @@ struct SwShapeTask : SwTask
|
||||||
Additionally, the stroke style should not be dashed. */
|
Additionally, the stroke style should not be dashed. */
|
||||||
bool antialiasing(float strokeWidth)
|
bool antialiasing(float strokeWidth)
|
||||||
{
|
{
|
||||||
return strokeWidth < 2.0f || rshape->stroke->dashCnt > 0 || rshape->stroke->strokeFirst || rshape->strokeTrim() || rshape->stroke->color[3] < 255;;
|
return strokeWidth < 2.0f || rshape->stroke->dashCnt > 0 || rshape->stroke->strokeFirst || rshape->strokeTrim() || rshape->stroke->color.a < 255;
|
||||||
}
|
}
|
||||||
|
|
||||||
float validStrokeWidth()
|
float validStrokeWidth()
|
||||||
|
@ -95,7 +95,7 @@ struct SwShapeTask : SwTask
|
||||||
auto width = rshape->stroke->width;
|
auto width = rshape->stroke->width;
|
||||||
if (tvg::zero(width)) return 0.0f;
|
if (tvg::zero(width)) return 0.0f;
|
||||||
|
|
||||||
if (!rshape->stroke->fill && (MULTIPLY(rshape->stroke->color[3], opacity) == 0)) return 0.0f;
|
if (!rshape->stroke->fill && (MULTIPLY(rshape->stroke->color.a, opacity) == 0)) return 0.0f;
|
||||||
if (tvg::zero(rshape->stroke->trim.begin - rshape->stroke->trim.end)) return 0.0f;
|
if (tvg::zero(rshape->stroke->trim.begin - rshape->stroke->trim.end)) return 0.0f;
|
||||||
|
|
||||||
return (width * sqrt(transform.e11 * transform.e11 + transform.e12 * transform.e12));
|
return (width * sqrt(transform.e11 * transform.e11 + transform.e12 * transform.e12));
|
||||||
|
@ -128,8 +128,7 @@ struct SwShapeTask : SwTask
|
||||||
|
|
||||||
//Shape
|
//Shape
|
||||||
if (flags & (RenderUpdateFlag::Path | RenderUpdateFlag::Transform) || prepareShape) {
|
if (flags & (RenderUpdateFlag::Path | RenderUpdateFlag::Transform) || prepareShape) {
|
||||||
uint8_t alpha = 0;
|
auto alpha = rshape->color.a;
|
||||||
rshape->fillColor(nullptr, nullptr, nullptr, &alpha);
|
|
||||||
alpha = MULTIPLY(alpha, opacity);
|
alpha = MULTIPLY(alpha, opacity);
|
||||||
visibleFill = (alpha > 0 || rshape->fill);
|
visibleFill = (alpha > 0 || rshape->fill);
|
||||||
shapeReset(&shape);
|
shapeReset(&shape);
|
||||||
|
@ -270,25 +269,25 @@ static void _termEngine()
|
||||||
|
|
||||||
static void _renderFill(SwShapeTask* task, SwSurface* surface, uint8_t opacity)
|
static void _renderFill(SwShapeTask* task, SwSurface* surface, uint8_t opacity)
|
||||||
{
|
{
|
||||||
uint8_t r, g, b, a;
|
|
||||||
if (auto fill = task->rshape->fill) {
|
if (auto fill = task->rshape->fill) {
|
||||||
rasterGradientShape(surface, &task->shape, fill, opacity);
|
rasterGradientShape(surface, &task->shape, fill, opacity);
|
||||||
} else {
|
} else {
|
||||||
task->rshape->fillColor(&r, &g, &b, &a);
|
RenderColor c;
|
||||||
a = MULTIPLY(opacity, a);
|
task->rshape->fillColor(&c.r, &c.g, &c.b, &c.a);
|
||||||
if (a > 0) rasterShape(surface, &task->shape, r, g, b, a);
|
c.a = MULTIPLY(opacity, c.a);
|
||||||
|
if (c.a > 0) rasterShape(surface, &task->shape, c);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void _renderStroke(SwShapeTask* task, SwSurface* surface, uint8_t opacity)
|
static void _renderStroke(SwShapeTask* task, SwSurface* surface, uint8_t opacity)
|
||||||
{
|
{
|
||||||
uint8_t r, g, b, a;
|
|
||||||
if (auto strokeFill = task->rshape->strokeFill()) {
|
if (auto strokeFill = task->rshape->strokeFill()) {
|
||||||
rasterGradientStroke(surface, &task->shape, strokeFill, opacity);
|
rasterGradientStroke(surface, &task->shape, strokeFill, opacity);
|
||||||
} else {
|
} else {
|
||||||
if (task->rshape->strokeFill(&r, &g, &b, &a)) {
|
RenderColor c;
|
||||||
a = MULTIPLY(opacity, a);
|
if (task->rshape->strokeFill(&c.r, &c.g, &c.b, &c.a)) {
|
||||||
if (a > 0) rasterStroke(surface, &task->shape, r, g, b, a);
|
c.a = MULTIPLY(opacity, c.a);
|
||||||
|
if (c.a > 0) rasterStroke(surface, &task->shape, c);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -67,6 +67,11 @@ struct RenderSurface
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct RenderColor
|
||||||
|
{
|
||||||
|
uint8_t r, g, b, a;
|
||||||
|
};
|
||||||
|
|
||||||
struct RenderCompositor
|
struct RenderCompositor
|
||||||
{
|
{
|
||||||
MaskMethod method;
|
MaskMethod method;
|
||||||
|
@ -90,7 +95,7 @@ struct RenderRegion
|
||||||
struct RenderStroke
|
struct RenderStroke
|
||||||
{
|
{
|
||||||
float width = 0.0f;
|
float width = 0.0f;
|
||||||
uint8_t color[4] = {0, 0, 0, 0};
|
RenderColor color{};
|
||||||
Fill *fill = nullptr;
|
Fill *fill = nullptr;
|
||||||
float* dashPattern = nullptr;
|
float* dashPattern = nullptr;
|
||||||
uint32_t dashCnt = 0;
|
uint32_t dashCnt = 0;
|
||||||
|
@ -109,8 +114,7 @@ struct RenderStroke
|
||||||
void operator=(const RenderStroke& rhs)
|
void operator=(const RenderStroke& rhs)
|
||||||
{
|
{
|
||||||
width = rhs.width;
|
width = rhs.width;
|
||||||
|
color = rhs.color;
|
||||||
memcpy(color, rhs.color, sizeof(color));
|
|
||||||
|
|
||||||
delete(fill);
|
delete(fill);
|
||||||
if (rhs.fill) fill = rhs.fill->duplicate();
|
if (rhs.fill) fill = rhs.fill->duplicate();
|
||||||
|
@ -173,7 +177,7 @@ struct RenderShape
|
||||||
} path;
|
} path;
|
||||||
|
|
||||||
Fill *fill = nullptr;
|
Fill *fill = nullptr;
|
||||||
uint8_t color[4] = {0, 0, 0, 0}; //r, g, b, a
|
RenderColor color{};
|
||||||
RenderStroke *stroke = nullptr;
|
RenderStroke *stroke = nullptr;
|
||||||
FillRule rule = FillRule::Winding;
|
FillRule rule = FillRule::Winding;
|
||||||
|
|
||||||
|
@ -185,10 +189,10 @@ struct RenderShape
|
||||||
|
|
||||||
void fillColor(uint8_t* r, uint8_t* g, uint8_t* b, uint8_t* a) const
|
void fillColor(uint8_t* r, uint8_t* g, uint8_t* b, uint8_t* a) const
|
||||||
{
|
{
|
||||||
if (r) *r = color[0];
|
if (r) *r = color.r;
|
||||||
if (g) *g = color[1];
|
if (g) *g = color.g;
|
||||||
if (b) *b = color[2];
|
if (b) *b = color.b;
|
||||||
if (a) *a = color[3];
|
if (a) *a = color.a;
|
||||||
}
|
}
|
||||||
|
|
||||||
float strokeWidth() const
|
float strokeWidth() const
|
||||||
|
@ -209,10 +213,10 @@ struct RenderShape
|
||||||
{
|
{
|
||||||
if (!stroke) return false;
|
if (!stroke) return false;
|
||||||
|
|
||||||
if (r) *r = stroke->color[0];
|
if (r) *r = stroke->color.r;
|
||||||
if (g) *g = stroke->color[1];
|
if (g) *g = stroke->color.g;
|
||||||
if (b) *b = stroke->color[2];
|
if (b) *b = stroke->color.b;
|
||||||
if (a) *a = stroke->color[3];
|
if (a) *a = stroke->color.a;
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
|
@ -198,12 +198,10 @@ Result Shape::fill(uint8_t r, uint8_t g, uint8_t b, uint8_t a) noexcept
|
||||||
pImpl->flag |= RenderUpdateFlag::Gradient;
|
pImpl->flag |= RenderUpdateFlag::Gradient;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (r == pImpl->rs.color[0] && g == pImpl->rs.color[1] && b == pImpl->rs.color[2] && a == pImpl->rs.color[3]) return Result::Success;
|
if (r == pImpl->rs.color.r && g == pImpl->rs.color.g && b == pImpl->rs.color.b && a == pImpl->rs.color.a) return Result::Success;
|
||||||
|
|
||||||
|
pImpl->rs.color = {r, g, b, a};
|
||||||
|
|
||||||
pImpl->rs.color[0] = r;
|
|
||||||
pImpl->rs.color[1] = g;
|
|
||||||
pImpl->rs.color[2] = b;
|
|
||||||
pImpl->rs.color[3] = a;
|
|
||||||
pImpl->flag |= RenderUpdateFlag::Color;
|
pImpl->flag |= RenderUpdateFlag::Color;
|
||||||
|
|
||||||
return Result::Success;
|
return Result::Success;
|
||||||
|
|
|
@ -72,8 +72,8 @@ struct Shape::Impl
|
||||||
if (opacity == 0) return false;
|
if (opacity == 0) return false;
|
||||||
|
|
||||||
//Shape composition is only necessary when stroking & fill are valid.
|
//Shape composition is only necessary when stroking & fill are valid.
|
||||||
if (!rs.stroke || rs.stroke->width < FLOAT_EPSILON || (!rs.stroke->fill && rs.stroke->color[3] == 0)) return false;
|
if (!rs.stroke || rs.stroke->width < FLOAT_EPSILON || (!rs.stroke->fill && rs.stroke->color.a == 0)) return false;
|
||||||
if (!rs.fill && rs.color[3] == 0) return false;
|
if (!rs.fill && rs.color.a == 0) return false;
|
||||||
|
|
||||||
//translucent fill & stroke
|
//translucent fill & stroke
|
||||||
if (opacity < 255) return true;
|
if (opacity < 255) return true;
|
||||||
|
@ -270,10 +270,7 @@ struct Shape::Impl
|
||||||
flag |= RenderUpdateFlag::GradientStroke;
|
flag |= RenderUpdateFlag::GradientStroke;
|
||||||
}
|
}
|
||||||
|
|
||||||
rs.stroke->color[0] = r;
|
rs.stroke->color = {r, g, b, a};
|
||||||
rs.stroke->color[1] = g;
|
|
||||||
rs.stroke->color[2] = b;
|
|
||||||
rs.stroke->color[3] = a;
|
|
||||||
|
|
||||||
flag |= RenderUpdateFlag::Stroke;
|
flag |= RenderUpdateFlag::Stroke;
|
||||||
}
|
}
|
||||||
|
@ -285,7 +282,7 @@ struct Shape::Impl
|
||||||
if (!rs.stroke) rs.stroke = new RenderStroke();
|
if (!rs.stroke) rs.stroke = new RenderStroke();
|
||||||
if (rs.stroke->fill && rs.stroke->fill != f) delete(rs.stroke->fill);
|
if (rs.stroke->fill && rs.stroke->fill != f) delete(rs.stroke->fill);
|
||||||
rs.stroke->fill = f;
|
rs.stroke->fill = f;
|
||||||
rs.stroke->color[3] = 0;
|
rs.stroke->color.a = 0;
|
||||||
|
|
||||||
flag |= RenderUpdateFlag::Stroke;
|
flag |= RenderUpdateFlag::Stroke;
|
||||||
flag |= RenderUpdateFlag::GradientStroke;
|
flag |= RenderUpdateFlag::GradientStroke;
|
||||||
|
@ -358,9 +355,7 @@ struct Shape::Impl
|
||||||
//Default Properties
|
//Default Properties
|
||||||
dup->flag = RenderUpdateFlag::All;
|
dup->flag = RenderUpdateFlag::All;
|
||||||
dup->rs.rule = rs.rule;
|
dup->rs.rule = rs.rule;
|
||||||
|
dup->rs.color = rs.color;
|
||||||
//Color
|
|
||||||
memcpy(dup->rs.color, rs.color, sizeof(rs.color));
|
|
||||||
|
|
||||||
//Path
|
//Path
|
||||||
dup->rs.path.cmds.push(rs.path.cmds);
|
dup->rs.path.cmds.push(rs.path.cmds);
|
||||||
|
@ -388,7 +383,7 @@ struct Shape::Impl
|
||||||
rs.path.cmds.clear();
|
rs.path.cmds.clear();
|
||||||
rs.path.pts.clear();
|
rs.path.pts.clear();
|
||||||
|
|
||||||
rs.color[3] = 0;
|
rs.color.a = 0;
|
||||||
rs.rule = FillRule::Winding;
|
rs.rule = FillRule::Winding;
|
||||||
|
|
||||||
delete(rs.stroke);
|
delete(rs.stroke);
|
||||||
|
|
|
@ -233,7 +233,7 @@ void WgImageData::release(WgContext& context)
|
||||||
// WgRenderSettings
|
// WgRenderSettings
|
||||||
//***********************************************************************
|
//***********************************************************************
|
||||||
|
|
||||||
void WgRenderSettings::update(WgContext& context, const Fill* fill, const uint8_t* color, const RenderUpdateFlag flags)
|
void WgRenderSettings::update(WgContext& context, const Fill* fill, const RenderColor& c, const RenderUpdateFlag flags)
|
||||||
{
|
{
|
||||||
// setup fill properties
|
// setup fill properties
|
||||||
if ((flags & (RenderUpdateFlag::Gradient)) && fill) {
|
if ((flags & (RenderUpdateFlag::Gradient)) && fill) {
|
||||||
|
@ -270,15 +270,15 @@ void WgRenderSettings::update(WgContext& context, const Fill* fill, const uint8_
|
||||||
sampler, texViewGradient, bufferGroupGradient, bufferGroupTransfromGrad);
|
sampler, texViewGradient, bufferGroupGradient, bufferGroupTransfromGrad);
|
||||||
}
|
}
|
||||||
skip = false;
|
skip = false;
|
||||||
} else if ((flags & (RenderUpdateFlag::Color)) && !fill) {
|
} else if ((flags & RenderUpdateFlag::Color) && !fill) {
|
||||||
rasterType = WgRenderRasterType::Solid;
|
rasterType = WgRenderRasterType::Solid;
|
||||||
WgShaderTypeSolidColor solidColor(color);
|
WgShaderTypeSolidColor solidColor(c);
|
||||||
if (context.allocateBufferUniform(bufferGroupSolid, &solidColor, sizeof(solidColor))) {
|
if (context.allocateBufferUniform(bufferGroupSolid, &solidColor, sizeof(solidColor))) {
|
||||||
context.pipelines->layouts.releaseBindGroup(bindGroupSolid);
|
context.pipelines->layouts.releaseBindGroup(bindGroupSolid);
|
||||||
bindGroupSolid = context.pipelines->layouts.createBindGroupBuffer1Un(bufferGroupSolid);
|
bindGroupSolid = context.pipelines->layouts.createBindGroupBuffer1Un(bufferGroupSolid);
|
||||||
}
|
}
|
||||||
fillType = WgRenderSettingsType::Solid;
|
fillType = WgRenderSettingsType::Solid;
|
||||||
skip = (color[3] == 0);
|
skip = (c.a == 0);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -90,7 +90,7 @@ struct WgRenderSettings
|
||||||
WgRenderRasterType rasterType{};
|
WgRenderRasterType rasterType{};
|
||||||
bool skip{};
|
bool skip{};
|
||||||
|
|
||||||
void update(WgContext& context, const Fill* fill, const uint8_t* color, const RenderUpdateFlag flags);
|
void update(WgContext& context, const Fill* fill, const RenderColor& c, const RenderUpdateFlag flags);
|
||||||
void release(WgContext& context);
|
void release(WgContext& context);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -369,7 +369,7 @@ bool WgRenderer::beginComposite(RenderCompositor* cmp, MaskMethod method, uint8_
|
||||||
mRenderStorageStack.push(storage);
|
mRenderStorageStack.push(storage);
|
||||||
// begin newly added render pass
|
// begin newly added render pass
|
||||||
WGPUColor color{};
|
WGPUColor color{};
|
||||||
if ((method == MaskMethod::None) && (opacity != 255)) color = { 1.0, 1.0, 1.0, 0.0 };
|
if ((method == MaskMethod::None) && (opacity != 255)) color = {1.0f, 1.0f, 1.0f, 0.0f};
|
||||||
mCompositor.beginRenderPass(mCommandEncoder, mRenderStorageStack.last(), true, color);
|
mCompositor.beginRenderPass(mCommandEncoder, mRenderStorageStack.last(), true, color);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
|
@ -99,18 +99,18 @@ void WgShaderTypeBlendSettings::update(const ColorSpace colorSpace, uint8_t o)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
WgShaderTypeSolidColor::WgShaderTypeSolidColor(const uint8_t* c)
|
WgShaderTypeSolidColor::WgShaderTypeSolidColor(const RenderColor& c)
|
||||||
{
|
{
|
||||||
update(c);
|
update(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void WgShaderTypeSolidColor::update(const uint8_t* c)
|
void WgShaderTypeSolidColor::update(const RenderColor& c)
|
||||||
{
|
{
|
||||||
color[0] = c[0] / 255.0f; // red
|
color[0] = c.r / 255.0f; // red
|
||||||
color[1] = c[1] / 255.0f; // green
|
color[1] = c.g / 255.0f; // green
|
||||||
color[2] = c[2] / 255.0f; // blue
|
color[2] = c.b / 255.0f; // blue
|
||||||
color[3] = c[3] / 255.0f; // alpha
|
color[3] = c.a / 255.0f; // alpha
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -57,8 +57,8 @@ struct WgShaderTypeSolidColor
|
||||||
{
|
{
|
||||||
float color[4]{};
|
float color[4]{};
|
||||||
|
|
||||||
WgShaderTypeSolidColor(const uint8_t* c);
|
WgShaderTypeSolidColor(const RenderColor& c);
|
||||||
void update(const uint8_t* c);
|
void update(const RenderColor& c);
|
||||||
};
|
};
|
||||||
|
|
||||||
// sampler, texture, vec4f
|
// sampler, texture, vec4f
|
||||||
|
|
Loading…
Add table
Reference in a new issue