mirror of
https://github.com/mozilla/pdf.js.git
synced 2025-04-26 10:08:06 +02:00
Add a new parameter to JpegImage.getData
to indicate the source of the image data (issue 9513)
The purpose of this patch is to provide a better default behaviour when `JpegImage` is used to parse standalone JPEG images with CMYK colour spaces. Since the issue that the patch concerns is somewhat of a special-case, the implementation utilizes the already existing decode support in an attempt to minimize the impact w.r.t. code size. *Please note:* It's always possible for the user of `JpegImage` to control image inversion, and thus override the new behaviour, by simply passing a custom `decodeTransform` array upon initialization.
This commit is contained in:
parent
47bf12cbac
commit
663922f93f
3 changed files with 36 additions and 11 deletions
|
@ -975,7 +975,7 @@ var JpegImage = (function JpegImageClosure() {
|
|||
this.numComponents = this.components.length;
|
||||
},
|
||||
|
||||
_getLinearizedBlockData: function getLinearizedBlockData(width, height) {
|
||||
_getLinearizedBlockData(width, height, isSourcePDF = false) {
|
||||
var scaleX = this.width / width, scaleY = this.height / height;
|
||||
|
||||
var component, componentScaleX, componentScaleY, blocksPerScanline;
|
||||
|
@ -1013,7 +1013,24 @@ var JpegImage = (function JpegImageClosure() {
|
|||
}
|
||||
|
||||
// decodeTransform contains pairs of multiplier (-256..256) and additive
|
||||
const transform = this._decodeTransform;
|
||||
let transform = this._decodeTransform;
|
||||
|
||||
// In PDF files, JPEG images with CMYK colour spaces are usually inverted
|
||||
// (this can be observed by extracting the raw image data).
|
||||
// Since the conversion algorithms (see below) were written primarily for
|
||||
// the PDF use-cases, attempting to use `JpegImage` to parse standalone
|
||||
// JPEG (CMYK) images may thus result in inverted images (see issue 9513).
|
||||
//
|
||||
// Unfortunately it's not (always) possible to tell, from the image data
|
||||
// alone, if it needs to be inverted. Thus in an attempt to provide better
|
||||
// out-of-box behaviour when `JpegImage` is used standalone, default to
|
||||
// inverting JPEG (CMYK) images if and only if the image data does *not*
|
||||
// come from a PDF file and no `decodeTransform` was passed by the user.
|
||||
if (!transform && numComponents === 4 && !isSourcePDF) {
|
||||
transform = new Int32Array([
|
||||
-256, 255, -256, 255, -256, 255, -256, 255]);
|
||||
}
|
||||
|
||||
if (transform) {
|
||||
for (i = 0; i < dataLength;) {
|
||||
for (j = 0, k = 0; j < numComponents; j++, i++, k += 2) {
|
||||
|
@ -1162,14 +1179,14 @@ var JpegImage = (function JpegImageClosure() {
|
|||
return data.subarray(0, offset);
|
||||
},
|
||||
|
||||
getData: function getData(width, height, forceRGBoutput) {
|
||||
getData({ width, height, forceRGB = false, isSourcePDF = false, }) {
|
||||
if (this.numComponents > 4) {
|
||||
throw new JpegError('Unsupported color mode');
|
||||
}
|
||||
// type of data: Uint8Array(width * height * numComponents)
|
||||
var data = this._getLinearizedBlockData(width, height);
|
||||
// Type of data: Uint8ClampedArray(width * height * numComponents)
|
||||
var data = this._getLinearizedBlockData(width, height, isSourcePDF);
|
||||
|
||||
if (this.numComponents === 1 && forceRGBoutput) {
|
||||
if (this.numComponents === 1 && forceRGB) {
|
||||
var dataLength = data.length;
|
||||
var rgbData = new Uint8ClampedArray(dataLength * 3);
|
||||
var offset = 0;
|
||||
|
@ -1184,11 +1201,11 @@ var JpegImage = (function JpegImageClosure() {
|
|||
return this._convertYccToRgb(data);
|
||||
} else if (this.numComponents === 4) {
|
||||
if (this._isColorConversionNeeded) {
|
||||
if (forceRGBoutput) {
|
||||
if (forceRGB) {
|
||||
return this._convertYcckToRgb(data);
|
||||
}
|
||||
return this._convertYcckToCmyk(data);
|
||||
} else if (forceRGBoutput) {
|
||||
} else if (forceRGB) {
|
||||
return this._convertCmykToRgb(data);
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue