How to Draw an Inline Svg (In Dom) to a Canvas

How to draw an inline svg (in DOM) to a canvas?

For inline SVG you'll need to:

  • Convert the SVG string to a Blob
  • Get an URL for the Blob
  • Create an image element and set the URL as src
  • When loaded (onload) you can draw the SVG as an image on canvas
  • Use toDataURL() to get the PNG file from canvas.

For example:

function drawInlineSVG(ctx, rawSVG, callback) {

var svg = new Blob([rawSVG], {type:"image/svg+xml;charset=utf-8"}),
domURL = self.URL || self.webkitURL || self,
url = domURL.createObjectURL(svg),
img = new Image;

img.onload = function () {
ctx.drawImage(this, 0, 0);
domURL.revokeObjectURL(url);
callback(this);
};

img.src = url;
}

// usage:
drawInlineSVG(ctxt, svgText, function() {
console.log(canvas.toDataURL()); // -> PNG data-uri
});

Of course, console.log here is just for example. Store/transfer the string instead here. (I would also recommend adding an onerror handler inside the method).

Also remember to set canvas size using either the width and height attributes, or from JavaScript using properties.

How to draw a SVG on Canvas using Javascript?

Try to use image to draw (so snippet not works - but when you edit it - it works)

let xml = new XMLSerializer().serializeToString(circSvg);   // get svg datalet svg64 = btoa(xml);                         // make it base64let b64Start = 'data:image/svg+xml;base64,';let image64 = b64Start + svg64;                // prepend a "header"
circImg.src = image64; // image sourcecircImg.onload = x=> { can.getContext('2d').drawImage(circImg, 0, 0); // draw}
svg<br><svg id="circSvg" width="100" height="100">   <circle cx="50" cy="50" r="40" stroke="green" stroke-width="4" fill="yellow" />   Sorry, your browser does not support inline SVG.</svg> 
<br>canvas<br> <canvas id="can"></canvas>
<img id="circImg" style="display:none">

Drawing an SVG file on a HTML5 canvas

EDIT: Dec 2019

The Path2D() constructor is supported by all major browsers now, "allowing path objects to be declared on 2D canvas surfaces".



EDIT: Nov 2014

You can now use ctx.drawImage to draw HTMLImageElements that have a .svg source in some but not all browsers (75% coverage: Chrome, IE11, and Safari work, Firefox works with some bugs, but nightly has fixed them).

var img = new Image();
img.onload = function() {
ctx.drawImage(img, 0, 0);
}
img.src = "http://upload.wikimedia.org/wikipedia/commons/d/d2/Svg_example_square.svg";

Live example here. You should see a green square in the canvas. The second green square on the page is the same <svg> element inserted into the DOM for reference.

You can also use the new Path2D objects to draw SVG (string) paths. In other words, you can write:

var path = new Path2D('M 100,100 h 50 v 50 h 50');
ctx.stroke(path);

Live example of that here.



Original 2010 answer:

There's nothing native that allows you to natively use SVG paths in canvas. You must convert yourself or use a library to do it for you.

I'd suggest looking in to canvg: (check homepage & demos)

canvg takes the URL to an SVG file, or the text of the SVG file, parses it in JavaScript and renders the result on Canvas.

How to draw a SVG in string format in a canvas html element?

Here you have two examples. In both examples I added the SVG namespace to the string, be cause it is a separate XML/SVG document and not haft of the HTML.

In the first example I just create a data URL and insert that as the source of an image object. Here you need to set the width and the height.

In the second example I used Blob and the function URL.createObjectURL().

var canvas = document.getElementById('canvas');
var ctx = canvas.getContext('2d');

const svgString = (color) => `<svg xmlns="http://www.w3.org/2000/svg" height="150" width="500">
<ellipse cx="240" cy="100" rx="220" ry="30" style="fill:${color}" />
<ellipse cx="220" cy="70" rx="190" ry="20" style="fill:lime" />
<ellipse cx="210" cy="45" rx="170" ry="15" style="fill:yellow" />
</svg>`;

var img = new Image();
img.width = 500;
img.height = 150;

img.addEventListener('load', e => {
ctx.drawImage(e.target, 0, 0);
});

img.src = `data:image/svg+xml,${svgString('red')}`;
<canvas width="500" height="150" id="canvas"></canvas>

Drawing SVG into Canvas and manipulating drawn elements using their IDs

Here's how to do this with Fabric:

fabric.loadSVGFromURL('/assets/72.svg', function(objects, options){

var group = fabric.util.groupSVGElements(objects, options);

group
.set({ left: 300, top: 200 })
.scaleToWidth(500)
.setCoords();

canvas.add(group);
}, reviver);

function reviver(element, object) {
object.id = element.getAttribute('id');
}

The code should be pretty self-explanatory. We load SVG; Fabric parses it internally, spitting out set of objects representing each element. We then group those elements and add them onto canvas in one chunk. Reviver is responsible for reading id off of each SVG element and assigning it to a corresponding fabric instance.

Run this snippet in http://fabricjs.com/kitchensink/ and you get:

loaded svg

Let's inspect this grouped object:

canvas.item(0) + ''; "#<fabric.PathGroup (29303): { top: 200, left: 300 }>"

And its children:

canvas.item(0).getObjects(); // Array[2287]

Let's retrieve one by id:

var greenland = canvas.item(0).getObjects().filter(function(obj) {
return obj.id === 'path4206';
})[0];

This is all plain old Javascript, as you can see. Let's change color of that particular object/shape now:

greenland.fill = 'red';

greenland in red

Trying to draw SVG to canvas, but it's being cut short

Change the SVG so its size matches the canvas and it works on Firefox for me e.g.

<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" version="1.1" class="layer" id="layer_text" width="778" height="544">



Related Topics



Leave a reply



Submit