diff options
author | Allan Sandfeld Jensen <allan.jensen@digia.com> | 2014-05-26 12:07:18 +0200 |
---|---|---|
committer | Allan Sandfeld Jensen <allan.jensen@digia.com> | 2014-07-04 14:03:46 +0200 |
commit | 3acd4b546ded7523f65d60cee6f3809113a91a16 (patch) | |
tree | ac526a90c4b39229ea5ec4c80b779ca8a4b66c24 /src/gui/painting/qdrawhelper_p.h | |
parent | 715b41ce48c9dd78eec3223606e9ca5193cf5bad (diff) |
QImage support for RGB30 formats
Adds basic support for 10-bit per color channel formats to QImage
and the XCB plugin. This will make it possible to paint to and from
these formats, but only at 8-bit per color channel accuracy.
This also fixes Qt5 applications on X11 with native 30bit depth.
[ChangeLog][QtGui][QImage] Added support for 10-bit per color channel image formats.
Task-number: QTBUG-25998
Change-Id: I93ccd3c74bfbb0bd94b352476e5fe58a94119e1f
Reviewed-by: Gunnar Sletta <gunnar.sletta@jollamobile.com>
Diffstat (limited to 'src/gui/painting/qdrawhelper_p.h')
-rw-r--r-- | src/gui/painting/qdrawhelper_p.h | 117 |
1 files changed, 108 insertions, 9 deletions
diff --git a/src/gui/painting/qdrawhelper_p.h b/src/gui/painting/qdrawhelper_p.h index 1c05fc305a..d6b557af01 100644 --- a/src/gui/painting/qdrawhelper_p.h +++ b/src/gui/painting/qdrawhelper_p.h @@ -672,6 +672,36 @@ static Q_ALWAYS_INLINE uint BYTE_MUL_RGB16_32(uint x, uint a) { return t; } +#if defined(Q_CC_RVCT) +# pragma push +# pragma arm +#endif +static Q_ALWAYS_INLINE int qt_div_255(int x) { return (x + (x>>8) + 0x80) >> 8; } +#if defined(Q_CC_RVCT) +# pragma pop +#endif + +static Q_ALWAYS_INLINE uint BYTE_MUL_RGB30(uint x, uint a) { + uint xa = x >> 30; + uint xr = (x >> 20) & 0x3ff; + uint xg = (x >> 10) & 0x3ff; + uint xb = x & 0x3ff; + xa = qt_div_255(xa * a); + xr = qt_div_255(xr * a); + xg = qt_div_255(xg * a); + xb = qt_div_255(xb * a); + return (xa << 30) | (xr << 20) | (xg << 10) | xb; +} + +static Q_ALWAYS_INLINE uint qAlphaRgb30(uint c) +{ + uint a = c >> 30; + a |= a << 2; + a |= a << 4; + return a; +} + + // FIXME: Remove when all Qt modules have stopped using PREMUL and INV_PREMUL #define PREMUL(x) qPremultiply(x) #define INV_PREMUL(p) qUnpremultiply(p) @@ -795,15 +825,6 @@ do { \ } \ } while (0) -#if defined(Q_CC_RVCT) -# pragma push -# pragma arm -#endif -static Q_ALWAYS_INLINE int qt_div_255(int x) { return (x + (x>>8) + 0x80) >> 8; } -#if defined(Q_CC_RVCT) -# pragma pop -#endif - inline ushort qConvertRgb32To16(uint c) { return (((c) >> 3) & 0x001f) @@ -819,6 +840,84 @@ inline QRgb qConvertRgb16To32(uint c) | ((((c) << 8) & 0xf80000) | (((c) << 3) & 0x70000)); } +enum QtPixelOrder { + PixelOrderRGB, + PixelOrderBGR +}; + +template<enum QtPixelOrder> inline uint qConvertArgb32ToA2rgb30(QRgb); + +template<enum QtPixelOrder> inline uint qConvertRgb32ToRgb30(QRgb); + +template<enum QtPixelOrder> inline QRgb qConvertA2rgb30ToArgb32(uint c); + +template<> +inline uint qConvertArgb32ToA2rgb30<PixelOrderBGR>(QRgb c) +{ + return (c & 0xc0000000) + | (((c << 22) & 0x3fc00000) | ((c << 14) & 0x00300000)) + | (((c << 4) & 0x000ff000) | ((c >> 4) & 0x00000c00)) + | (((c >> 14) & 0x000003fc) | ((c >> 22) & 0x00000003)); +} + +template<> +inline uint qConvertArgb32ToA2rgb30<PixelOrderRGB>(QRgb c) +{ + return (c & 0xc0000000) + | (((c << 6) & 0x3fc00000) | ((c >> 2) & 0x00300000)) + | (((c << 4) & 0x000ff000) | ((c >> 4) & 0x00000c00)) + | (((c << 2) & 0x000003fc) | ((c >> 6) & 0x00000003)); +} + +template<> +inline uint qConvertRgb32ToRgb30<PixelOrderBGR>(QRgb c) +{ + return 0xc0000000 + | (((c << 22) & 0x3fc00000) | ((c << 14) & 0x00300000)) + | (((c << 4) & 0x000ff000) | ((c >> 4) & 0x00000c00)) + | (((c >> 14) & 0x000003fc) | ((c >> 22) & 0x00000003)); +} + +template<> +inline uint qConvertRgb32ToRgb30<PixelOrderRGB>(QRgb c) +{ + return 0xc0000000 + | (((c << 6) & 0x3fc00000) | ((c >> 2) & 0x00300000)) + | (((c << 4) & 0x000ff000) | ((c >> 4) & 0x00000c00)) + | (((c << 2) & 0x000003fc) | ((c >> 6) & 0x00000003)); +} + +template<> +inline QRgb qConvertA2rgb30ToArgb32<PixelOrderBGR>(uint c) +{ + uint a = c >> 30; + a |= a << 2; + a |= a << 4; + return (a << 24) + | ((c << 14) & 0x00ff0000) + | ((c >> 4) & 0x0000ff00) + | ((c >> 22) & 0x000000ff); +} + +template<> +inline QRgb qConvertA2rgb30ToArgb32<PixelOrderRGB>(uint c) +{ + uint a = c >> 30; + a |= a << 2; + a |= a << 4; + return (a << 24) + | ((c >> 6) & 0x00ff0000) + | ((c >> 4) & 0x0000ff00) + | ((c >> 2) & 0x000000ff); +} + +inline uint qRgbSwapRgb30(uint c) +{ + const uint ag = c & 0xc00ffc00; + const uint rb = c & 0x3ff003ff; + return ag | (rb << 20) | (rb >> 20); +} + inline int qRed565(quint16 rgb) { const int r = (rgb & 0xf800); return (r >> 8) | (r >> 13); |