Automattic / Automattic/node-canvas

Inaccurate RGB values due to a rounding error caused by premultiplication

Open
#1,933 0 comments 1 reaction 0 assignees View on GitHub
Bug Good first issue
Dominant language
JavaScript
Stars
10.7k
Forks
1.2k
Avg merge
4d 8h
Merged PRs (30d)
1

Description

## Issue or Feature
- [ ] If this is an issue with installation, I have read the [troubleshooting guide](https://github.com/Automattic/node-canvas/issues/1511).

When dealing with specific RGBA values, there's a chance that the RGB values will be incorrect. For example, with the RGBA values (252, 252, 252, 252), the RGB values are expected to be (252, 252, 252), but in practice, they're rounded down to (251, 251, 251) (with the alpha value remaining the same).

The root of the issue is somewhere within this area: https://github.com/Automattic/node-canvas/blob/198080580a0e3938c48daae357b88a1638a9ddcd/src/CanvasRenderingContext2d.cc#L1067
(Although I do not know where the premultiplication is done.)

## Steps to Reproduce

```js
const { createCanvas, createImageData } = require('canvas');

var canvas = createCanvas(1, 1);
var context = canvas.getContext('2d');

var data = createImageData(Uint8ClampedArray.from([252, 252, 252, 252]), 1);
context.putImageData(data, 0, 0);

var newData = context.getImageData(0, 0, 1, 1);
console.log(newData.data);
// expected to be Uint8ClampedArray[252, 252, 252, 252]
```

Minireprex of the issue in C++:
```cpp
#include
#include

int main()
{
uint32_t rgba = 4227858432u;
uint8_t a = rgba >> 24;

// premultiplied value: 252 * (252 / 255)
float r = 249.03529411764708f;

float alphaR = (float)255 / a;
uint8_t undone = (int)((float)r * alphaR);

assert(undone == 252);

return 0;
}
```

## Your Environment
* Version of node-canvas (output of `npm list canvas` or `yarn list canvas`): `-- canvas@2.6.1
* Environment (e.g. node 4.2.0 on Mac OS X 10.8): node v15.2.1 on Windows 10 Home v1909 (build 18363.1198)

Contributor guide

No contributing guide indexed for this repository

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.