[Bug]: p5.Image.prototype.copy and blend do not scale destination coordinates for high pixel density
Nobody has claimed this yet.
- Dominant language
- JavaScript
- Stars
- 24k
- Forks
- 3.8k
- Avg merge
- 3d 16h
- Merged PRs (30d)
- 25
Description
Most appropriate component
Image (p5.Image, image, etc.)
Describe the bug
When calling copy() or blend() on a p5.Image instance that has pixelDensity > 1 (e.g., Retina / high-DPI displays), the destination coordinates (dx, dy, dw, dh) are not scaled by the destination image's pixel density.
In p5.Image.prototype._copyHelper (lines 920-960), the source coordinates are scaled by s = srcImage.canvas.width / srcImage.width, but the destination parameters are passed directly as raw logical values to dstImage.drawingContext.drawImage().
Because dstImage.drawingContext operates directly on the physical canvas of dstImage without an automated DPI transformation matrix, drawImage() draws into only [dx, dy, dw, dh] physical canvas pixels instead of [d*dx, d*dy, d*dw, d*dh].
For pixelDensity(2), this results in the copied image covering only 1/4th of the intended area in the top-left corner, leaving the remaining 75% of the intended target area completely untouched (transparent / blank). Because p5.Image.prototype.blend() delegates to copy(), it suffers from the identical issue.
Steps to reproduce
let src = createImage(50, 50);
src.loadPixels();
for (let i = 0; i < src.pixels.length; i += 4) {
src.pixels[i] = 255; // Red
src.pixels[i + 3] = 255; // Alpha
}
src.updatePixels();
let dst = createImage(100, 100);
dst.pixelDensity(2); // canvas backing store is 200x200
dst.copy(src, 0, 0, 50, 50, 0, 0, 50, 50);
// Sample a point in the bottom-right quadrant of the logical image
let col = dst.get(35, 35);
console.log(col); // [0, 0, 0, 0] instead of [255, 0, 0, 255]
Expected behavior
The destination coordinates should be scaled by d = dstImage.canvas.width / dstImage.width so that copy() and blend() properly fill the intended logical region on high-DPI images.
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start in p5.Image.prototype._copyHelper around lines 920-960 and reproduce the issue with the provided high-DPI copy() example. Check the destination values passed to dstImage.drawingContext.drawImage(), then verify both copy() and blend() cover the intended logical region when pixelDensity(2) is used.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- javascript
- Domain
- computer-graphics
- Issue type
- Bug
- Difficulty
- 2/5
- Estimated time
- 1-3 hours
- Activity status
- Active
- Clarity
- Clearly specified
- Newbie friendliness
- 78/100