Ensuring our Canvas Visuals Look Good on Retina/High-DPI Screens

This is a companion discussion topic for the original entry at https://www.kirupa.com/canvas/canvas_high_dpi_retina.htm

This is the way. But you will need to write a hack on drawImage not to copy and paste to the double every time.

Here is some sort of my code

    /********************************************************
	CANVAS.js ā€” microbians.com
	Create canvas and all the s**t
********************************************************/

// Create a new Layer (canvas)
layer = function(mainElementID, canvasWidth, canvasHeight, isBuffer, RETINA, FAKEAA) {
	if (document.getElementById(mainElementID)!=undefined) {
		this.main = document.getElementById(mainElementID); 			// Inside a DIV
	} else {
		this.main = document.body; 										// Directly on the body
	}


	this.canvas = document.createElement("canvas");						// Create de canvas
	this.canvas.id = "layer["+(layer.UID)+"]"; 							// Set a unique UID
	layer.UID++;

	this.canvas.style.position="absolute";
	this.canvas.display="block";
	this.canvas.width  = canvasWidth  * RETINA;							// Do a bigger canvas multiplied by REATINA value (1,2,3)
	this.canvas.height = canvasHeight * RETINA;
	this.canvas.style.zoom=( 100 / RETINA )+"%";						// Made the canvas zoom inveser to the size scaled by the RETINA parameter

//	this.hitCanvas = document.createElement("canvas");

	//this.canvas.style.filter="url(#turbnoise)"; 						// SVG Filters -> investigate...

	if (FAKEAA == undefined) { 											// If Not FAKEAA defined set it as half of RETINA paramater
        var FAKEAA = RETINA / 4;
	}
	if (FAKEAA > 0 ) this.canvas.style.filter="blur("+ FAKEAA +"px)"; 	// Add a subttle bur as a Fake blur

//	this.canvas.oncontextmenu = this.hitCanvas.oncontextmenu = function (e) { e.preventDefault(); };	// Prevent using secondary menu over canvas

	if (!isBuffer) this.main.appendChild(this.canvas); 					// If if set as buffer create it but not append (off screen canvas)

	this.ctx = this.canvas.getContext("2d");							// Set the canvas context
	this.ctx.scale(RETINA,RETINA);										// Set the scale of the contet as the RETINA

//	this.hitCanvas.getContext("2d").scale(RETINA,RETINA);				// Set the scale of the contet as the RETINA

	this.ctx._drawImage = this.ctx.drawImage; 													// Backup function
	this.ctx.drawImage = function(image, sx, sy, sWidth, sHeight, dx, dy, dWidth, dHeight) { 	// Overdrive the drawImage function, to take in consideratino the RETINA parameter, so it no ovrscale when copying from one canvas to another
		this.scale(1/RETINA,1/RETINA);
		sWidth = sWidth || this.canvas.width;
		sHeight = sHeight || this.canvas.height;
		dx = dx || 0;
		dy = dy || 0;
		dWidth = dWidth || this.canvas.width;
		dHeight = dHeight || this.canvas.height;
		this._drawImage(image, sx, sy, sWidth, sHeight, dx, dy, dWidth, dHeight);
		this.scale(RETINA,RETINA);
	}
	
	return this;
}
layer.UID = 0; 															// Unique ID for each layer

This code also had an option to add a fake antialiasing if needed by using a little little blur fx - but recently this fix I found works better for non retina displays and get smooth lines.

Enjoy
microbians.com

1 Like

Cool! Thanks for the tip. I will be sure to call this out when discussing drawImage :+1:

1 Like

Kirupa
I am new, just learning React. I am a Senior graduating in CyberSecurity from USF. My classmates and I chose react for our Redundant Servers Senior Project. I have a very good understanding of HTML, CSS, and JavaScript. I find your videos very good, I have watched the first 6 now and I think I have a good understanding of how React works and why it is chosen to be used. The sheer amount of styling that can be done at once with a few lines of code is mind boggling. It would take forever to do it the traditional way with CSS and JS. I had Website design last semester and I created a decent website, but had I known react, I would have made an outstanding website. I am going to purchase your book and add this language to my Resume. It is very interesting. Thanks for all the time you put into the videos to teach everyone.

Thomas

Hi @El_Rey! Welcome to the forums, and apologies for the delay in replying to you :slight_smile:

Iā€™m glad you are enjoying the videos. They are quite fun to make. If you ever have any questions about React or web development in general, feel free to ask here. You are in the company of some of the nicest and smartest web developers ever to hang out in one location. Of course, I am also a bit biased haha.

Cheers,
Kirupa