Fabric.js changes my canvas size to 300x150 after initialization

in the latest version, you will have to do something like:

var canvas = new fabric.Canvas('myCanvas');
canvas.setHeight(500);
canvas.setWidth(800);

.... Your code ....

canvas.renderAll();

Works fine for me..

For dynamically changing size, this works too


When initializing canvas, Fabric reads width/height attributes on canvas element or takes width/height passed in options.

var myCanvas = new fabric.Canvas('myCanvas', { width: 900, height: 600 });

or:

<canvas width="900" height="600"></canvas>
...
var myCanvas = new fabric.Canvas('myCanvas');

A real answer to this question—not involving a new static size but actually permitting CSS to be effective—is one of the following options:

  1. In CSS, you can override individual properties and following them with !important; the downside to this is that any further definitions must also use !important or they will be ignored:
[width], [height], [style]
{
  width:      100vw!important;
  min-height: 100vh!important;
}
  1. Using JQuery you can set the inline property values to an empty string. You can presumably achieve this without JQuery, but I will leave that as an exercise to you.

Javascript (JQuery):

$('[style]').attr(  'style',  function(index, style){  return ''; });
$('[height]').attr( 'height', function(index, height){ return ''; });
$('[width]').attr(  'width',  function(index, height){ return ''; });

CSS:

*, *:before, *:after
{
  box-sizing: border-box;
}

body
{
  width:      100vw; 
  min-height: 100vh;
  padding:    0;
  margin:     0;
}

.canvas-container,
canvas
{
  width:      inherit; 
  min-height: inherit;
}

canvas.lower-canvas
{
  position: absolute;
  top:      0;
}

After that, CSS will be applied as expected.

It is apparently also necessary to tell Fabric about the change:

function sizeCanvas()
{
  var width  = Math.max(document.documentElement.clientWidth,  window.innerWidth  || 0);
  var height = Math.max(document.documentElement.clientHeight, window.innerHeight || 0);
  canvas.setHeight( height )
  canvas.setWidth( width )
}

window.addEventListener('resize', draw, false);

function initDraw()
{
  // setup
}

function draw()
{  
  canvas.renderAll();  
}

sizeCanvas();
initDraw();

This will configure Fabric to the viewport size and keep it sized accordingly if it resizes.

It's worth noting that this problem arises for two reasons:

  1. Someone thought it was a good idea to use inline styles and should be severely castigated, as there is no situation where this is ever an appropriate practice.

  2. Fabric changes the DOM arrangement and nests the original canvas in a new div with a second nested canvas, which may result in surprises.