Skip to content

Commit af998a8

Browse files
committed
try to fix the yuv420 conversion
1 parent eafecfd commit af998a8

1 file changed

Lines changed: 25 additions & 18 deletions

File tree

src/libcameracamera.cpp

Lines changed: 25 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -543,30 +543,37 @@ QImage LibCameraWorker::convertBufferToImage(
543543
// YUV420 planar format (I420)
544544
unsigned int width = cfg.size.width;
545545
unsigned int height = cfg.size.height;
546+
unsigned int stride = cfg.stride;
547+
unsigned int uvStride = stride / 2;
548+
546549
image = QImage(width, height, QImage::Format_RGB888);
547550

548-
const uint8_t *src = static_cast<const uint8_t *>(memory);
549-
const uint8_t *yPlane = src;
550-
const uint8_t *uPlane = src + width * height;
551-
const uint8_t *vPlane = uPlane + (width * height / 4);
551+
const uint8_t *yPlane = static_cast<const uint8_t *>(memory);
552+
const uint8_t *uPlane = yPlane + stride * height;
553+
const uint8_t *vPlane = uPlane + uvStride * (height / 2);
552554

553-
for (unsigned int y = 0; y < height; y++) {
554-
for (unsigned int x = 0; x < width; x++) {
555-
int yVal = yPlane[y * width + x];
556-
int uVal = uPlane[(y / 2) * (width / 2) + (x / 2)];
557-
int vVal = vPlane[(y / 2) * (width / 2) + (x / 2)];
558-
559-
auto clamp = [](int val) { return std::max(0, std::min(255, val)); };
555+
qDebug() << "[DEBUG] YUV420: width=" << width << "height=" << height
556+
<< "stride=" << stride << "uvStride=" << uvStride;
557+
558+
for (unsigned int j = 0; j < height; ++j) {
559+
uint8_t *rgbRow = image.scanLine(j);
560+
for (unsigned int i = 0; i < width; ++i) {
561+
int Y = yPlane[j * stride + i];
562+
int U = uPlane[(j / 2) * uvStride + (i / 2)] - 128;
563+
int V = vPlane[(j / 2) * uvStride + (i / 2)] - 128;
560564

561-
int c = yVal - 16;
562-
int d = uVal - 128;
563-
int e = vVal - 128;
565+
// BT.601 / sYCC conversion (full range)
566+
int R = Y + static_cast<int>(1.402 * V);
567+
int G = Y - static_cast<int>(0.344136 * U) - static_cast<int>(0.714136 * V);
568+
int B = Y + static_cast<int>(1.772 * U);
564569

565-
int r = clamp((298 * c + 409 * e + 128) >> 8);
566-
int g = clamp((298 * c - 100 * d - 208 * e + 128) >> 8);
567-
int b = clamp((298 * c + 516 * d + 128) >> 8);
570+
R = std::clamp(R, 0, 255);
571+
G = std::clamp(G, 0, 255);
572+
B = std::clamp(B, 0, 255);
568573

569-
image.setPixel(x, y, qRgb(r, g, b));
574+
rgbRow[i * 3 + 0] = static_cast<uint8_t>(R);
575+
rgbRow[i * 3 + 1] = static_cast<uint8_t>(G);
576+
rgbRow[i * 3 + 2] = static_cast<uint8_t>(B);
570577
}
571578
}
572579

0 commit comments

Comments
 (0)