rendering update
This commit is contained in:
parent
bc97c13a0b
commit
7fdab4f62b
4 changed files with 33 additions and 49 deletions
|
|
@ -115,5 +115,16 @@ export namespace Crafter {
|
||||||
redraw[i] = true;
|
redraw[i] = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
void CopyNearestNeighbor(Vector<std::uint8_t, 4>* dst, std::uint16_t dstSizeX, std::uint16_t dstScaledSizeX, std::uint16_t dstScaledSizeY, std::uint16_t offsetX, std::uint16_t offsetY) {
|
||||||
|
for (std::uint16_t y = 0; y < dstScaledSizeY; y++) {
|
||||||
|
std::uint16_t srcY = y * scaled.size.y / dstScaledSizeY;
|
||||||
|
std::uint16_t dstY = y + offsetY;
|
||||||
|
for (std::uint16_t x = 0; x < dstScaledSizeX; x++) {
|
||||||
|
std::uint16_t srcX = x * scaled.size.x / dstScaledSizeX;
|
||||||
|
std::uint16_t dstX = x + offsetX;
|
||||||
|
dst[dstY * dstSizeX + dstX] = buffer[srcY * this->scaled.size.x + srcX];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
@ -31,10 +31,10 @@ export namespace Crafter {
|
||||||
std::vector<std::tuple<const Transform*, std::uint32_t, std::uint32_t, std::chrono::nanoseconds>> renderTimings;
|
std::vector<std::tuple<const Transform*, std::uint32_t, std::uint32_t, std::chrono::nanoseconds>> renderTimings;
|
||||||
#endif
|
#endif
|
||||||
Transform2D transform;
|
Transform2D transform;
|
||||||
std::int32_t sizeX;
|
std::uint16_t sizeX;
|
||||||
std::int32_t sizeY;
|
std::uint16_t sizeY;
|
||||||
RendertargetBase() = default;
|
RendertargetBase() = default;
|
||||||
RendertargetBase(std::int16_t sizeX, std::int16_t sizeY) : sizeX(sizeX), sizeY(sizeY), transform({0, 0, 1, 1, 0, 0, 0}){
|
RendertargetBase(std::uint16_t sizeX, std::uint16_t sizeY) : sizeX(sizeX), sizeY(sizeY), transform({0, 0, 1, 1, 0, 0, 0}){
|
||||||
transform.scaled.size.x = sizeX;
|
transform.scaled.size.x = sizeX;
|
||||||
transform.scaled.size.y = sizeY;
|
transform.scaled.size.y = sizeY;
|
||||||
transform.scaled.position.x = 0;
|
transform.scaled.position.x = 0;
|
||||||
|
|
@ -71,56 +71,30 @@ export namespace Crafter {
|
||||||
std::int32_t src_height = element->scaled.size.y;
|
std::int32_t src_height = element->scaled.size.y;
|
||||||
|
|
||||||
switch (element->opaque) {
|
switch (element->opaque) {
|
||||||
case OpaqueType::FullyOpaque:
|
case OpaqueType::FullyOpaque: {
|
||||||
for (std::int32_t y = dirty.top; y < dirty.bottom; y++) {
|
for (std::int32_t y = dirty.top; y < dirty.bottom; y++) {
|
||||||
std::int32_t src_y = y - element->scaled.position.y;
|
std::int32_t src_y = y - element->scaled.position.y;
|
||||||
|
std::memcpy(&this->buffer[frame][y * this->sizeX], &src_buffer[src_y * src_width], dirty.right-dirty.left*sizeof(Vector<T, Channels, Alignment>));
|
||||||
for (std::int32_t x = dirty.left; x < dirty.right; x++) {
|
|
||||||
std::int32_t src_x = x - element->scaled.position.x;
|
|
||||||
|
|
||||||
this->buffer[frame][y * this->sizeX + x] = src_buffer[src_y * src_width + src_x];
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
case OpaqueType::SemiOpaque:
|
|
||||||
// For semi-opaque, we can avoid blending when alpha is 0 or 255
|
|
||||||
for (std::int32_t y = dirty.top; y < dirty.bottom; y++) {
|
|
||||||
std::int32_t src_y = y - element->scaled.position.y;
|
|
||||||
|
|
||||||
for (std::int32_t x = dirty.left; x < dirty.right; x++) {
|
|
||||||
std::int32_t src_x = x - element->scaled.position.x;
|
|
||||||
Vector<std::uint8_t, 4> src_pixel = src_buffer[src_y * src_width + src_x];
|
|
||||||
|
|
||||||
if (src_pixel.a == 0) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
this->buffer[frame][y * this->sizeX + x] = src_pixel;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
|
|
||||||
case OpaqueType::Transparent:
|
case OpaqueType::Transparent:
|
||||||
// For transparent, always perform blending
|
// For transparent, always perform blending
|
||||||
for (std::int32_t y = dirty.top; y < dirty.bottom; y++) {
|
for (std::uint16_t y = dirty.top; y < dirty.bottom; y++) {
|
||||||
std::int32_t src_y = y - element->scaled.position.y;
|
std::uint16_t src_y = y - element->scaled.position.y;
|
||||||
for (std::int32_t x = dirty.left; x < dirty.right; x++) {
|
for (std::uint16_t x = dirty.left; x < dirty.right; x++) {
|
||||||
std::int32_t src_x = x - element->scaled.position.x;
|
std::uint16_t src_x = x - element->scaled.position.x;
|
||||||
Vector<T, Channels, Alignment> src = src_buffer[src_y * src_width + src_x];
|
Vector<T, Channels, Alignment> src = src_buffer[src_y * src_width + src_x];
|
||||||
Vector<T, Channels, Alignment> dst = buffer[frame][y * this->sizeX + x];
|
Vector<T, Channels, Alignment> dst = buffer[frame][y * this->sizeX + x];
|
||||||
|
|
||||||
if(src.a == 0) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
float srcA = src.a / 255.0f;
|
float srcA = src.a / 255.0f;
|
||||||
float dstA = dst.a / 255.0f;
|
float dstA = dst.a / 255.0f;k
|
||||||
|
|
||||||
float outA = srcA + dstA * (1.0f - srcA);
|
float outA = srcA + dstA * (1.0f - srcA);
|
||||||
this->buffer[frame][y * this->sizeX + x] = Vector<T, Channels, Alignment>(
|
this->buffer[frame][y * this->sizeX + x] = Vector<T, Channels, Alignment>(
|
||||||
static_cast<T>((src.r * srcA + dst.r * dstA * (1.0f - srcA)) / outA),
|
static_cast<T>((src.r + dst.r * (1.0f - srcA)) / outA),
|
||||||
static_cast<T>((src.g * srcA + dst.g * dstA * (1.0f - srcA)) / outA),
|
static_cast<T>((src.g + dst.g * (1.0f - srcA)) / outA),
|
||||||
static_cast<T>((src.b * srcA + dst.b * dstA * (1.0f - srcA)) / outA),
|
static_cast<T>((src.b + dst.b * (1.0f - srcA)) / outA),
|
||||||
static_cast<T>(outA * 255)
|
static_cast<T>(outA * 255)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -30,10 +30,10 @@ export namespace Crafter {
|
||||||
float height;
|
float height;
|
||||||
float offsetX;
|
float offsetX;
|
||||||
float offsetY;
|
float offsetY;
|
||||||
std::int32_t z;
|
std::uint8_t z;
|
||||||
bool maintainAspectRatio;
|
bool maintainAspectRatio;
|
||||||
Anchor2D() = default;
|
Anchor2D() = default;
|
||||||
Anchor2D(float x, float y, float width, float height, float offsetX, float offsetY, std::int32_t z, bool maintainAspectRatio = false);
|
Anchor2D(float x, float y, float width, float height, float offsetX, float offsetY, std::uint8_t z, bool maintainAspectRatio = false);
|
||||||
};
|
};
|
||||||
|
|
||||||
struct Transform2D {
|
struct Transform2D {
|
||||||
|
|
@ -73,7 +73,6 @@ export namespace Crafter {
|
||||||
scaled.size.y = anchor.height * parent.scaled.size.x;
|
scaled.size.y = anchor.height * parent.scaled.size.x;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
|
||||||
scaled.size.x = anchor.width * parent.scaled.size.x;
|
scaled.size.x = anchor.width * parent.scaled.size.x;
|
||||||
scaled.size.y = anchor.height * parent.scaled.size.y;
|
scaled.size.y = anchor.height * parent.scaled.size.y;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -33,15 +33,15 @@ export namespace Crafter {
|
||||||
};
|
};
|
||||||
|
|
||||||
struct ScaleData2D {
|
struct ScaleData2D {
|
||||||
Vector<std::int32_t, 2> position;
|
Vector<std::uint16_t, 2> position;
|
||||||
Vector<std::int32_t, 2> size;
|
Vector<std::uint16_t, 2> size;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct ClipRect {
|
struct ClipRect {
|
||||||
std::int32_t left;
|
std::uint16_t left;
|
||||||
std::int32_t right;
|
std::uint16_t right;
|
||||||
std::int32_t top;
|
std::uint16_t top;
|
||||||
std::int32_t bottom;
|
std::uint16_t bottom;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct FrameTime {
|
struct FrameTime {
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue