mirror of
https://git.libcamera.org/libcamera/libcamera.git
synced 2025-07-17 01:15:06 +03:00
qcam: viewfinder_gl: Add support for RAW12 packed formats
All the four Bayer orders are supported. The 4 LS bits of the 12-bit colour values are dropped as the RGBA format we convert into has only 8 bits per colour. Signed-off-by: Andrey Konovalov <andrey.konovalov@linaro.org> Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com> Reviewed-by: Paul Elder <paul.elder@ideasonboard.com> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
This commit is contained in:
parent
c4259493dc
commit
6424e86407
2 changed files with 80 additions and 11 deletions
|
@ -23,6 +23,40 @@
|
||||||
precision mediump float;
|
precision mediump float;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
/*
|
||||||
|
* These constants are used to select the bytes containing the HS part of
|
||||||
|
* the pixel value:
|
||||||
|
* BPP - bytes per pixel,
|
||||||
|
* THRESHOLD_L = fract(BPP) * 0.5 + 0.02
|
||||||
|
* THRESHOLD_H = 1.0 - fract(BPP) * 1.5 + 0.02
|
||||||
|
* Let X is the x coordinate in the texture measured in bytes (so that the
|
||||||
|
* range is from 0 to (stride_-1)) aligned on the nearest pixel.
|
||||||
|
* E.g. for RAW10P:
|
||||||
|
* -------------+-------------------+-------------------+--
|
||||||
|
* pixel No | 0 1 2 3 | 4 5 6 7 | ...
|
||||||
|
* -------------+-------------------+-------------------+--
|
||||||
|
* byte offset | 0 1 2 3 4 | 5 6 7 8 9 | ...
|
||||||
|
* -------------+-------------------+-------------------+--
|
||||||
|
* X | 0.0 1.25 2.5 3.75 | 5.0 6.25 7.5 8.75 | ...
|
||||||
|
* -------------+-------------------+-------------------+--
|
||||||
|
* If fract(X) < THRESHOLD_L then the previous byte contains the LS
|
||||||
|
* bits of the pixel values and needs to be skipped.
|
||||||
|
* If fract(X) > THRESHOLD_H then the next byte contains the LS bits
|
||||||
|
* of the pixel values and needs to be skipped.
|
||||||
|
*/
|
||||||
|
#if defined(RAW10P)
|
||||||
|
#define BPP 1.25
|
||||||
|
#define THRESHOLD_L 0.14
|
||||||
|
#define THRESHOLD_H 0.64
|
||||||
|
#elif defined(RAW12P)
|
||||||
|
#define BPP 1.5
|
||||||
|
#define THRESHOLD_L 0.27
|
||||||
|
#define THRESHOLD_H 0.27
|
||||||
|
#else
|
||||||
|
#error Invalid raw format
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
varying vec2 textureOut;
|
varying vec2 textureOut;
|
||||||
|
|
||||||
/* the texture size in pixels */
|
/* the texture size in pixels */
|
||||||
|
@ -66,10 +100,7 @@ void main(void)
|
||||||
* Add a small number (a few mantissa's LSBs) to avoid float
|
* Add a small number (a few mantissa's LSBs) to avoid float
|
||||||
* representation issues. Maybe paranoic.
|
* representation issues. Maybe paranoic.
|
||||||
*/
|
*/
|
||||||
center_bytes.x = BPP_X * center_pixel.x + 0.02;
|
center_bytes.x = BPP * center_pixel.x + 0.02;
|
||||||
|
|
||||||
const float threshold_l = 0.127 /* fract(BPP_X) * 0.5 + 0.02 */;
|
|
||||||
const float threshold_h = 0.625 /* 1.0 - fract(BPP_X) * 1.5 */;
|
|
||||||
|
|
||||||
float fract_x = fract(center_bytes.x);
|
float fract_x = fract(center_bytes.x);
|
||||||
|
|
||||||
|
@ -90,14 +121,14 @@ void main(void)
|
||||||
* of the previous group of the pixels, move xcoords[0] one
|
* of the previous group of the pixels, move xcoords[0] one
|
||||||
* byte back.
|
* byte back.
|
||||||
*/
|
*/
|
||||||
xcoords[0] += (fract_x < threshold_l) ? -tex_step.x : 0.0;
|
xcoords[0] += (fract_x < THRESHOLD_L) ? -tex_step.x : 0.0;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* If xcoords[1] points at the byte containing the LS bits
|
* If xcoords[1] points at the byte containing the LS bits
|
||||||
* of the current group of the pixels, move xcoords[1] one
|
* of the current group of the pixels, move xcoords[1] one
|
||||||
* byte forward.
|
* byte forward.
|
||||||
*/
|
*/
|
||||||
xcoords[1] += (fract_x > threshold_h) ? tex_step.x : 0.0;
|
xcoords[1] += (fract_x > THRESHOLD_H) ? tex_step.x : 0.0;
|
||||||
|
|
||||||
vec2 alternate = mod(center_pixel.xy + tex_bayer_first_red, 2.0);
|
vec2 alternate = mod(center_pixel.xy + tex_bayer_first_red, 2.0);
|
||||||
bool even_col = alternate.x < 1.0;
|
bool even_col = alternate.x < 1.0;
|
||||||
|
|
|
@ -41,6 +41,11 @@ static const QList<libcamera::PixelFormat> supportedFormats{
|
||||||
libcamera::formats::SGBRG10_CSI2P,
|
libcamera::formats::SGBRG10_CSI2P,
|
||||||
libcamera::formats::SGRBG10_CSI2P,
|
libcamera::formats::SGRBG10_CSI2P,
|
||||||
libcamera::formats::SRGGB10_CSI2P,
|
libcamera::formats::SRGGB10_CSI2P,
|
||||||
|
/* Raw Bayer 12-bit packed */
|
||||||
|
libcamera::formats::SBGGR12_CSI2P,
|
||||||
|
libcamera::formats::SGBRG12_CSI2P,
|
||||||
|
libcamera::formats::SGRBG12_CSI2P,
|
||||||
|
libcamera::formats::SRGGB12_CSI2P,
|
||||||
};
|
};
|
||||||
|
|
||||||
ViewFinderGL::ViewFinderGL(QWidget *parent)
|
ViewFinderGL::ViewFinderGL(QWidget *parent)
|
||||||
|
@ -218,28 +223,56 @@ bool ViewFinderGL::selectFormat(const libcamera::PixelFormat &format)
|
||||||
case libcamera::formats::SBGGR10_CSI2P:
|
case libcamera::formats::SBGGR10_CSI2P:
|
||||||
firstRed_.setX(1.0);
|
firstRed_.setX(1.0);
|
||||||
firstRed_.setY(1.0);
|
firstRed_.setY(1.0);
|
||||||
fragmentShaderDefines_.append("#define BPP_X 1.25");
|
fragmentShaderDefines_.append("#define RAW10P");
|
||||||
fragmentShaderFile_ = ":bayer_1x_packed.frag";
|
fragmentShaderFile_ = ":bayer_1x_packed.frag";
|
||||||
textureMinMagFilters_ = GL_NEAREST;
|
textureMinMagFilters_ = GL_NEAREST;
|
||||||
break;
|
break;
|
||||||
case libcamera::formats::SGBRG10_CSI2P:
|
case libcamera::formats::SGBRG10_CSI2P:
|
||||||
firstRed_.setX(0.0);
|
firstRed_.setX(0.0);
|
||||||
firstRed_.setY(1.0);
|
firstRed_.setY(1.0);
|
||||||
fragmentShaderDefines_.append("#define BPP_X 1.25");
|
fragmentShaderDefines_.append("#define RAW10P");
|
||||||
fragmentShaderFile_ = ":bayer_1x_packed.frag";
|
fragmentShaderFile_ = ":bayer_1x_packed.frag";
|
||||||
textureMinMagFilters_ = GL_NEAREST;
|
textureMinMagFilters_ = GL_NEAREST;
|
||||||
break;
|
break;
|
||||||
case libcamera::formats::SGRBG10_CSI2P:
|
case libcamera::formats::SGRBG10_CSI2P:
|
||||||
firstRed_.setX(1.0);
|
firstRed_.setX(1.0);
|
||||||
firstRed_.setY(0.0);
|
firstRed_.setY(0.0);
|
||||||
fragmentShaderDefines_.append("#define BPP_X 1.25");
|
fragmentShaderDefines_.append("#define RAW10P");
|
||||||
fragmentShaderFile_ = ":bayer_1x_packed.frag";
|
fragmentShaderFile_ = ":bayer_1x_packed.frag";
|
||||||
textureMinMagFilters_ = GL_NEAREST;
|
textureMinMagFilters_ = GL_NEAREST;
|
||||||
break;
|
break;
|
||||||
case libcamera::formats::SRGGB10_CSI2P:
|
case libcamera::formats::SRGGB10_CSI2P:
|
||||||
firstRed_.setX(0.0);
|
firstRed_.setX(0.0);
|
||||||
firstRed_.setY(0.0);
|
firstRed_.setY(0.0);
|
||||||
fragmentShaderDefines_.append("#define BPP_X 1.25");
|
fragmentShaderDefines_.append("#define RAW10P");
|
||||||
|
fragmentShaderFile_ = ":bayer_1x_packed.frag";
|
||||||
|
textureMinMagFilters_ = GL_NEAREST;
|
||||||
|
break;
|
||||||
|
case libcamera::formats::SBGGR12_CSI2P:
|
||||||
|
firstRed_.setX(1.0);
|
||||||
|
firstRed_.setY(1.0);
|
||||||
|
fragmentShaderDefines_.append("#define RAW12P");
|
||||||
|
fragmentShaderFile_ = ":bayer_1x_packed.frag";
|
||||||
|
textureMinMagFilters_ = GL_NEAREST;
|
||||||
|
break;
|
||||||
|
case libcamera::formats::SGBRG12_CSI2P:
|
||||||
|
firstRed_.setX(0.0);
|
||||||
|
firstRed_.setY(1.0);
|
||||||
|
fragmentShaderDefines_.append("#define RAW12P");
|
||||||
|
fragmentShaderFile_ = ":bayer_1x_packed.frag";
|
||||||
|
textureMinMagFilters_ = GL_NEAREST;
|
||||||
|
break;
|
||||||
|
case libcamera::formats::SGRBG12_CSI2P:
|
||||||
|
firstRed_.setX(1.0);
|
||||||
|
firstRed_.setY(0.0);
|
||||||
|
fragmentShaderDefines_.append("#define RAW12P");
|
||||||
|
fragmentShaderFile_ = ":bayer_1x_packed.frag";
|
||||||
|
textureMinMagFilters_ = GL_NEAREST;
|
||||||
|
break;
|
||||||
|
case libcamera::formats::SRGGB12_CSI2P:
|
||||||
|
firstRed_.setX(0.0);
|
||||||
|
firstRed_.setY(0.0);
|
||||||
|
fragmentShaderDefines_.append("#define RAW12P");
|
||||||
fragmentShaderFile_ = ":bayer_1x_packed.frag";
|
fragmentShaderFile_ = ":bayer_1x_packed.frag";
|
||||||
textureMinMagFilters_ = GL_NEAREST;
|
textureMinMagFilters_ = GL_NEAREST;
|
||||||
break;
|
break;
|
||||||
|
@ -595,8 +628,13 @@ void ViewFinderGL::doRender()
|
||||||
case libcamera::formats::SGBRG10_CSI2P:
|
case libcamera::formats::SGBRG10_CSI2P:
|
||||||
case libcamera::formats::SGRBG10_CSI2P:
|
case libcamera::formats::SGRBG10_CSI2P:
|
||||||
case libcamera::formats::SRGGB10_CSI2P:
|
case libcamera::formats::SRGGB10_CSI2P:
|
||||||
|
case libcamera::formats::SBGGR12_CSI2P:
|
||||||
|
case libcamera::formats::SGBRG12_CSI2P:
|
||||||
|
case libcamera::formats::SGRBG12_CSI2P:
|
||||||
|
case libcamera::formats::SRGGB12_CSI2P:
|
||||||
/*
|
/*
|
||||||
* Packed raw Bayer 10-bit formats are stored in GL_RED texture.
|
* Packed raw Bayer 10-bit and 12-bit formats are stored in
|
||||||
|
* GL_RED texture.
|
||||||
* The texture width is equal to the stride.
|
* The texture width is equal to the stride.
|
||||||
*/
|
*/
|
||||||
glActiveTexture(GL_TEXTURE0);
|
glActiveTexture(GL_TEXTURE0);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue