@@ -61,10 +61,44 @@ void VipsDecoder::decode(uint8_t* outPixels, const Rect outRect,
6161 VImage resized = image.resize (
6262 scale, VImage::option ()->set (" kernel" , VIPS_KERNEL_LANCZOS3 ));
6363
64- // convert image to sRGB. We could just pass the targetProfile here, but
65- // libvips only support loading it from a file. See:
66- // https://github.com/libvips/libvips/issues/4283
67- resized = resized.icc_transform (" srgb" );
64+ cmsHTRANSFORM transform = nullptr ;
65+ cmsHPROFILE profile;
66+ int bands = image.bands ();
67+
68+ if (resized.get_typeof (VIPS_META_ICC_NAME ) != 0 ) {
69+ size_t size;
70+ const void * data = resized.get_blob (VIPS_META_ICC_NAME , &size);
71+
72+ profile = cmsOpenProfileFromMem (data, size);
73+ if (profile) {
74+ cmsColorSpaceSignature colorspace = cmsGetColorSpace (profile);
75+
76+ if ((bands > 2 ) && (colorspace == cmsSigRgbData)) {
77+ LOGI (" RGB" );
78+ transform = cmsCreateTransform (
79+ profile, TYPE_RGBA_8 , targetProfile, TYPE_RGBA_8 ,
80+ cmsGetHeaderRenderingIntent (profile), cmsFLAGS_COPY_ALPHA);
81+ } else if ((bands == 4 ) && (colorspace == cmsSigCmykData)) {
82+ LOGI (" CMYK" );
83+ transform = cmsCreateTransform (
84+ profile, TYPE_CMYK_8 , targetProfile, TYPE_RGBA_8 ,
85+ cmsGetHeaderRenderingIntent (profile), cmsFLAGS_COPY_ALPHA);
86+ } else {
87+ LOGI (" n" );
88+ }
89+
90+ cmsCloseProfile (profile);
91+ }
92+ }
93+
94+ if (!transform) {
95+ resized = resized.icc_transform (" srgb" );
96+ cmsHPROFILE profile = cmsCreate_sRGBProfile ();
97+ transform = cmsCreateTransform (
98+ profile, TYPE_RGBA_8 , targetProfile, TYPE_RGBA_8 ,
99+ cmsGetHeaderRenderingIntent (profile), cmsFLAGS_COPY_ALPHA);
100+ cmsCloseProfile (profile);
101+ }
68102
69103 // convert to RGBA8888
70104 resized = resized.cast (VIPS_FORMAT_UCHAR );
@@ -79,7 +113,7 @@ void VipsDecoder::decode(uint8_t* outPixels, const Rect outRect,
79113 uint8_t * outline = outPixels;
80114 for (uint32_t y = outRect.y ; y < outRect.y + outRect.height ; y++) {
81115 const uint8_t * line = region.addr (outRect.x , y);
82- memcpy (outline , line, outRect.width * 4 );
116+ cmsDoTransform (transform , line, outline, outRect.width );
83117 outline += outRect.width * 4 ;
84118 }
85119 // ensure we didn't write past the end of the buffer
0 commit comments