improve BGRA -> RGBA conversion
This commit is contained in:
parent
50288c5f18
commit
93f67a2bdf
@ -35,7 +35,7 @@
|
|||||||
#include <vips/vips.h>
|
#include <vips/vips.h>
|
||||||
#include <vips/internal.h>
|
#include <vips/internal.h>
|
||||||
|
|
||||||
/* Convert from ARGB to RGBA and undo premultiplication.
|
/* Convert from Cairo's BGRA to RGBA and undo premultiplication.
|
||||||
*
|
*
|
||||||
* See also openslide's argb2rgba().
|
* See also openslide's argb2rgba().
|
||||||
*/
|
*/
|
||||||
@ -45,22 +45,26 @@ vips__cairo2rgba( guint32 * restrict buf, int n )
|
|||||||
int i;
|
int i;
|
||||||
|
|
||||||
for( i = 0; i < n; i++ ) {
|
for( i = 0; i < n; i++ ) {
|
||||||
guint32 * restrict p = buf + i;
|
guint32 bgra = GUINT32_FROM_BE( buf[i] );
|
||||||
guint32 x = *p;
|
guint8 a = bgra & 0xff;
|
||||||
guint8 a = x >> 24;
|
|
||||||
VipsPel * restrict out = (VipsPel *) p;
|
|
||||||
|
|
||||||
if( a == 255 )
|
guint32 rgba;
|
||||||
*p = GUINT32_TO_BE( (x << 8) | 255 );
|
|
||||||
else if( a == 0 )
|
if( a == 0 ||
|
||||||
*p = GUINT32_TO_BE( x << 8 );
|
a == 255 )
|
||||||
else {
|
rgba =
|
||||||
/* Undo premultiplication.
|
(bgra & 0x00ff00ff) |
|
||||||
*/
|
(bgra & 0x0000ff00) << 16 |
|
||||||
out[0] = 255 * ((x >> 16) & 255) / a;
|
(bgra & 0xff000000) >> 16;
|
||||||
out[1] = 255 * ((x >> 8) & 255) / a;
|
else
|
||||||
out[2] = 255 * (x & 255) / a;
|
/* Undo premultiplication.
|
||||||
out[3] = a;
|
*/
|
||||||
}
|
rgba =
|
||||||
|
((255 * ((bgra >> 8) & 0xff) / a) << 24) |
|
||||||
|
((255 * ((bgra >> 16) & 0xff) / a) << 16) |
|
||||||
|
((255 * ((bgra >> 24) & 0xff) / a) << 8) |
|
||||||
|
a;
|
||||||
|
|
||||||
|
buf[i] = GUINT32_TO_BE( rgba );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -43,7 +43,6 @@
|
|||||||
|
|
||||||
/* TODO
|
/* TODO
|
||||||
*
|
*
|
||||||
* - speed up BRGA -> RGBA conversion
|
|
||||||
* - what about filename encodings?
|
* - what about filename encodings?
|
||||||
* - need to test on Windows
|
* - need to test on Windows
|
||||||
*/
|
*/
|
||||||
@ -569,19 +568,25 @@ vips_foreign_load_pdf_generate( VipsRegion *or,
|
|||||||
i += 1;
|
i += 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* PDFium writes BRGA, we must swap.
|
/* PDFium writes BGRA, we must swap.
|
||||||
*
|
|
||||||
* FIXME ... this is slow, try using vips__cairo2rgba()? Do we need to
|
|
||||||
* unpremultiply as well?
|
|
||||||
*/
|
*/
|
||||||
for( y = 0; y < r->height; y++ ) {
|
for( y = 0; y < r->height; y++ ) {
|
||||||
VipsPel *p;
|
guint32 * restrict p =
|
||||||
|
(guint32 *) VIPS_REGION_ADDR( or, r->left, r->top + y );
|
||||||
|
|
||||||
int x;
|
int x;
|
||||||
|
|
||||||
p = VIPS_REGION_ADDR( or, r->left, r->top + y );
|
|
||||||
for( x = 0; x < r->width; x++ ) {
|
for( x = 0; x < r->width; x++ ) {
|
||||||
VIPS_SWAP( VipsPel, p[0], p[2] );
|
guint32 bgra = GUINT32_FROM_BE( p[x] );
|
||||||
p += 4;
|
|
||||||
|
guint rgba;
|
||||||
|
|
||||||
|
rgba =
|
||||||
|
(bgra & 0x00ff00ff) |
|
||||||
|
(bgra & 0x0000ff00) << 16 |
|
||||||
|
(bgra & 0xff000000) >> 16;
|
||||||
|
|
||||||
|
p[x] = GUINT32_TO_BE( rgba );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user