Got it working using two separate canvas elements, but in the browsers I've tested I need a magic number.
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>Raster</title>
<link rel="stylesheet" href="../css/style.css">
<script type="text/javascript" src="../../dist/paper.js"></script>
<script type="text/javascript">
paper.install(window);
setTimeout(function() {
// Prepare ImageData in separate canvas
var imageX = 0;
var imageY = 0;
var imageWidth = 256;
var imageHeight = 256;
var rasterCanvas = document.getElementById('rasterCanvas');
/*
rasterCanvas.style.width = imageWidth + 'px';
rasterCanvas.style.height = imageHeight + 'px';
rasterCanvas.style.top = '300px';
rasterCanvas.style.left = '0px';
rasterCanvas.style.position = 'absolute';
*/
var rasterContext = rasterCanvas.getContext('2d');
// Draw something (RGBA) into the ImageData
var magicNumber = 50; // Why do i need this to draw a square in Paper.js?
var imageData = rasterContext.getImageData(imageX, imageY, imageWidth + magicNumber, imageHeight);
var data = imageData.data;
for(var i = 0, n = data.length; i < n; i += 4) {
var red = data[i] = 255;
var green = data[i + 1] = 0;
var blue = data[i + 2] = 0;
var alpha = data[i + 3] = 255;
}
rasterContext.putImageData(imageData, imageX, imageY);
// Prepare canvas for paper to draw in
var paperCanvas = document.getElementById('paperCanvas');
paper.setup(paperCanvas);
// Draw the ImageData from the other canvas into a Raster in the paper instance
var raster = new paper.Raster(rasterCanvas);
raster.position = new paper.Point(imageWidth/2 , imageHeight/2);
raster.size = new paper.Point(imageWidth, imageHeight);
// Draw a path on top
var path = new paper.Path();
path.strokeColor = 'black';
var start = new paper.Point(0, 0);
path.moveTo(start);
path.lineTo(start.add([ 256, 256 ]));
}, 0);
</script>
</head>
<body>
<canvas id="paperCanvas" resize></canvas>
<canvas id="rasterCanvas" resize></canvas>
</body>
</html>
In Node.js no magic numbers are needed
function renderJpg(z, x, y, decompressed, newerPaths, callback) {
var xOffset = x * tileSize,
yOffset = y * tileSize;
var can = new paper.Canvas(tileSize, tileSize);
var background = new paper.Canvas(tileSize, tileSize);
var context = background.getContext('2d');
var imageX = 0;
var imageY = 0;
var imageWidth = tileSize;
var imageHeight = tileSize;
var imageData = context.getImageData(imageX, imageY, imageWidth, imageHeight);
paper.setup(can);
var layer = paper.project.activeLayer;
var white = new paper.Path.Rectangle(paper.view.bounds);
white.fillColor = 'white';
layer.addChild(white);
layer = new paper.Layer();
if (decompressed) {
var data = imageData.data, d = decompressed;
for (var i = 0, n = data.length; i < n; i += 4) {
var red = data[i] = d[i];
var green = data[i + 1] = d[i + 1];
var blue = data[i + 2] = d[i + 2];
var alpha = data[i + 3] = d[i + 3];
}
// Draw the modified image data into background canvas
context.putImageData(imageData, imageX, imageY, imageX, imageY, imageWidth, imageHeight);
// Draw into paper instance
var raster = new paper.Raster(background);
raster.position = new paper.Point(xOffset + imageWidth/2, yOffset + imageHeight/2);
}
// Draw paths on top
for (var j = 0, jl = newerPaths.length; j < jl; j++) {
layer.addChild(makePath(newerPaths[j], z));
}
layer.translate(new paper.Point(-xOffset, -yOffset))
paper.view.draw();
// Create JPG stream
....
}