Why doesn't fillRect cover whole canvas? [duplicate] - javascript

This question already has answers here:
Canvas is stretched when using CSS but normal with "width" / "height" properties
(10 answers)
Closed 5 years ago.
I have a canvas tag without width and height attributes. The canvas has inline width and height. Now when I apply linearGradient over it, it doesn't cover whole canvas. Demo:
var c = document.getElementById("canvas");
var ctx = c.getContext("2d");
var gradient1 = ctx.createLinearGradient(0, 0, 150, 0);
gradient1.addColorStop(0, "#123456");
gradient1.addColorStop(1, "#654321");
ctx.fillStyle = gradient1;
ctx.fillRect(0, 0, 150, 100);
canvas {
border: 1px dotted red;
}
<canvas id="canvas" style="width: 150px; height: 100px;"></canvas>
Question1: Why doesn't whole 150px of canvas get covered? And if I add width="150" and height="100" attributes on canvas tag, why does it then fill whole canvas?
Question 2: In below script c.width returns 300px not 150px, why?
var c = document.getElementById("canvas");
var ctx = c.getContext("2d");
console.log(c.width);
console.log(c.height);
canvas {
border: 1px dotted red;
}
<canvas id="canvas" style="width: 150px; height: 100px;"></canvas>
Question3: Is this behavior due to something similar to svg viewBox?

I'm not sure why the inline styling isn't working, but if you change your canvas element to this:
<canvas id="canvas" width="150px" height= "100px;"></canvas>
Then the console logs the correct value and the gradient fills the canvas. :) I don't know why you can't use the other method, but I do know that everywhere I've seen I think everyone who uses the html canvas specifies the width and height in this way. (unless they specify it in the javascript)
Here's a pen of your working code: https://codepen.io/Awesomennjawarrior/pen/zwmmPY

Related

Pixel not the right size on canvas [duplicate]

This question already has answers here:
Canvas is stretched when using CSS but normal with "width" / "height" properties
(10 answers)
Closed 3 years ago.
So my rectangle i want to draw on a canvas are, i think scaled to the size of the canvas. I i want them to be 8x8 they dont come out as 8x8.
Here's my code:
function draw() {
var canvas = document.getElementById('karte');
var ctx = canvas.getContext("2d");
Stuttgart = ctx.fillRect(10,10,8,8);
}
.map {
height: 799px;
width: 591px;
margin: auto;
margin-top: 50px;
background-image: url('../img/Karte_Deutschland.svg');
background-repeat: no-repeat;
background-size: contain;
background-position: center;
}
.map canvas {
height: 799px;
width: 591px;
}
<canvas id="karte">
</canvas>
Here's a screenshot how it looks like in the end: https://prnt.sc/r58bvl
For now you set the canvas width and height on the screen different then the canvas actual width and height (which is 300/150 by default) it is why anything scaled for you. so :
Eather add the height and width to the canvas:
<canvas id="karte" height="799" width="591"><canvas>
Or add it manually in the js:
canvas.width = canvas.offsetWidth;
canvas.height = canvas.offsetHeight

Can anyone tell me why this isn't creating a square? [duplicate]

This question already has answers here:
Canvas is stretched when using CSS but normal with "width" / "height" properties
(10 answers)
Closed 3 years ago.
I'm following a tutorial to learn about canvas, and I'm unstuck pretty early on.
Here is the code:
var canvas = document.getElementById("canvas");
var context = canvas.getContext("2d");
context.lineWidth = 3;
context.strokeStyle = "blue";
context.lineJoin = "square";
context.strokeRect(10,10,200,200);
#canvas{
border: 1px solid black;
display: block;
width: 900px;
height: 600px;
margin: 0 auto;
}
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>HTML Canvas</title>
<link rel="stylesheet" href="stylesheet.css" type="text/css">
</head>
<body>
<canvas id="canvas"></canvas>
<script src="script.js" type="text/javascript"></script>
</body>
</html>
It seems like it should be pretty straight-forward, but it's not doing what I expect. Can anyone advise?
The height and width of the canvas should initially be set in HTML or via DOM properties, not CSS to avoid resizing.
From MDN:
Indeed, the element has only two attributes, width and
height. These are both optional and can also be set using DOM
properties. When no width and height attributes are specified, the
canvas will initially be 300 pixels wide and 150 pixels high. The
element can be sized arbitrarily by CSS, but during rendering the
image is scaled to fit its layout size: if the CSS sizing doesn't
respect the ratio of the initial canvas, it will appear distorted.
Because of this, your square was also being resized to the same size of the canvas and could no longer fit completely within it.
var canvas = document.getElementById("canvas");
var context = canvas.getContext("2d");
context.lineWidth = 3;
context.strokeStyle = "blue";
context.lineJoin = "square";
context.strokeRect(10,10,200,200);
#canvas{
border: 1px solid black;
display: block;
margin: 0 auto;
}
<canvas id="canvas" height="600" width="900"></canvas>

How to make canvas full width and height of body while not stretching or blurring drawings?

I want to make a canvas that occupies the full width and height of the body (with no scrolling), and has non stretched and non blurred drawings. Whenever I make a canvas 100vw and 100vh, the drawings get blurred and stretched image, with incorrect sizings.
Example:
<html>
<body>
<canvas id="c" style="border: 2px solid black;"></canvas>
<style> body, html {padding: 0; margin: 0; overflow: hidden;} </style>
<script>
var c = document.getElementById("c");
var ctx = c.getContext("2d");
function draw() {
ctx.fillRect(100, 50, 100, 75);
c.style.width = document.body.clientWidth;
c.style.height = document.body.clientHeight;
}
draw();
</script>
This code produces a black rectangle, but very blurry and a much larger size then I would like and expect (considering the width and height of the canvas is the whole body, and the width and height of the rectangle is only 100 and 75). Are there any fixes to this issue?
Thanks.
The reason why it gets stretched etc. is because of several reasons:
The rectangle must be drawn after the size of the canvas is set
When setting the canvas size, you don't actually set the style height and width, since the element canvas already has those attributes itself.
Also note that you will want your body/html css height to be 100% since it begins as auto, when canvas' height is set to the height of the body, it only fills up the little space body initially gives it compared to the whole screen.
Your new draw() function should look like this
function draw() {
c.width = document.body.clientWidth; // Remove .style from both
c.height = document.body.clientHeight;
ctx.fillRect(100, 50, 100, 75); // fillRect post setting size
}
and css
<style> body, html {padding: 0; margin: 0; overflow: hidden; height:100%;} </style>

Does using percentages instead of pixels change an html 5 canvas change its properties?

I am practicing javascript and I am trying to make a game. I want the canvas element to be fullscreen, so I used percentages for the height and width attribute, but when I do, it doesn't behave like it normally does. When I run my debug code, it is supposed to make a box that is 50px by 50px, but the graphics look bigger than normal.
I've tried getting the canvas height and width in pixels, but that did not work. It does not report any error messages, but it is still too big.
<!DOCTYPE html>
<html>
<head></head>
<body>
<canvas id="canvas" style="height: 100%; width:100%;"></canvas>
</body>
<style>
html, body {width: 100%;
margin: 0;
height: 100%;
overflow: hidden;
position:fixed;}
</style>
<script>
var canvas = document.getElementById("canvas")
var c = canvas.getContext("2d")
c.fillStyle = "#FFFF00"
c.fillRect(50,50,50,50)
</script>
There are no error messages none appearing, but it is not sized correctly, and I can't figure out why it's not working.
It makes a difference if canvas size is set in CSS or using element attributes.
The canvas element size is set by its width and height attributes (as numbers). This sets the number of addressable pixels used to store the canvas drawing in memory. In the absence of width and height attributes, canvas element dimensions are set to 300 by 150 (pixels) by default.
CSS applied to the canvas can scale its dimensions using software interpolation of the canvas treated as an image. Just as a small image looks bigger when scaled to full screen, both the 300 by 150 pixel canvas and objects drawn within it (using canvas pixel coordinates) appear larger when blown up.
To make canvas coordinates match the screen size in pixels, set its width and height attributes to pixel number values. E.G.
var canvas = document.getElementById("canvas")
var c = canvas.getContext("2d")
c.fillStyle = "#FFFF00"
c.fillRect(50,50,50,50)
console.log( canvas.width, canvas.height);
alert( "fix?" )
canvas.style=""; // remove CSS scaling
canvas.width = document.body.clientWidth;
canvas.height = document.body.clientHeight;
c.fillStyle = "#FFFF00"
c.fillRect(50,50,50,50)
body {
width: 100%;
margin: 0;
height: 100%;
background-color: honeydew;
overflow: hidden;
position:fixed;
}
canvas {
background-color: silver;
}
<canvas id="canvas" style="height: 100%; width:100%;"></canvas>

Draw circle canvas and print canvas

I wanted to draw the circular canvas and wanted to download the canvas with same format. Following is css which i am using
canvas {
width: 20em;
height: 20em;
border-radius: 50%;
background-color: red;
border: 4px solid #fff;
box-shadow: 0 0 0 5px red;
}
At present i have just apply the css to canvas to look a like it will not print same in fabric js.
Is there any possible way? Because i am trying to create circular canvas and add text and wanted to print same canvas with text and styling.
Edit:
Is it possible to draw the circle with same styling in fabric.js
You cannot really have a circular canvas in fabricjs, but you can clip a canvas to look like a circle.
i did a circle that has radius half of the canvas, and is positioned in the center.
Effect is same as your example.
Look the fiddle:
var canvas = new fabric.Canvas('c');
canvas.clipTo = function(ctx) {
ctx.beginPath();
ctx.arc(200,200,200,0,2*Math.PI);
}
canvas.backgroundColor = 'blue';
var rect = new fabric.Rect({width: 100, height:100, fill:'red', top:30, left:30});
canvas.add(rect);
canvas.renderAll();
<script src="http://www.fabricjs.com/lib/fabric.js"></script>
<canvas id="c" width="400" height="400" ></canvas>

Categories

Resources