如何将SVG字符串渲染到画布(并导出为PNG或JPEG)

了解如何轻松地将 SVG 字符串渲染到画布中,然后将其导出为具有所需大小的 PNG 或 JPEG,而不会降低质量,包括具体的SVG字符串渲染到画布实例。

如何将SVG字符串渲染到画布(并导出为PNG或JPEG)

文章图片
SVG字符串渲染到画布实例
图像的操作总是有点棘手,尤其是当你想使用 JavaScript 等语言进行操作时,如果还不够,可以直接在浏览器中操作。在过去的几天里,我一直在使用一个非常特殊的库,即dom-to-image,该库允许你使用纯 JavaScript 将任意 DOM 节点转换为矢量(SVG)或光栅(PNG 或 JPEG)图像.  我使用这个库来简单地在浏览器中捕获一个 DOM 元素,以允许用户下载图像,就是这样。
从理论上讲,它非常简单,因为 DOM 只是一组带有表情符号的按钮集合,它看起来像这样:
如何将SVG字符串渲染到画布(并导出为PNG或JPEG)

文章图片
【如何将SVG字符串渲染到画布(并导出为PNG或JPEG)】请注意,上图是使用外部工具制作的屏幕截图,并保持原始大小。现在,如果我决定使用 JPEG 或 PNG 中提到的库导出 DOM 元素,它将大大降低质量:
如何将SVG字符串渲染到画布(并导出为PNG或JPEG)

文章图片
这当然不是库的错,因为它将 DOM 元素光栅化为 PNG 格式的图像,但是,它看起来很糟糕,因为我的屏幕上的按钮确实很小。因此,解决方案是要么使按钮更大,要么使用 SVG 而不是 DOM 元素的光栅化版本。如何将SVG字符串渲染到画布?你可能知道,你可以将 SVG 放大和缩小到你想要的任何尺寸,而不会降低质量。如果将 DOM 元素导出为 SVG,你可以将其调整为你想要的大小,例如,以下代码会将选定的 DOM 元素呈现为 SVG 并将其显示到新的浏览器选项卡中:
let domNode = document.getElementById("myDiv"); // 1. Render the selected node to SVG domtoimage.toSvg(domNode).then(function(SVG){// 2. Load the SVG string (it looks something like this: // data:image/svg+xml; charset=utf-8,< svg xmlns="http://www.w3.org/2000/svg" width="1623" height="64">< foreignObject x="0" y="0" width="100%" height="100%">< div id="myDiv" .... let image = new Image(); image.src = https://www.lsbin.com/SVG; // 3. Launch a new tab in the browser and load the image to see the preview let newWindow = window.open(""); newWindow.document.write(image.outerHTML); });

然后,在新选项卡中,你将看到图像看起来非常清晰,你可以将图像调整到你想要的大小而不会降低质量(我们将其调整为3500 像素的图片,与原始大小相比,这是非常大的)纽扣):
如何将SVG字符串渲染到画布(并导出为PNG或JPEG)

文章图片
SVG字符串如何渲染到画布?你可以稍后将其光栅化为流行的格式,如 PNG 或 JPEG,但质量不错!在本教程中,我将向你展示如何轻松使用 JavaScript 将 SVG 字符串或 SVG 文件渲染为图像,并将其调整为你想要保持其原始质量的大小。
1. 创建/获取 SVG 数据 URLSVG字符串渲染到画布实例:数据 URL(以data:方案为前缀的 URL)允许内容创建者在文档中嵌入小文件。在我们的例子中,我们的 SVG 文件数据方案将是:
重要提示:如果你对纯 SVG 数据进行 URL 编码以编码不应出现在 URL 中的字符会更好。
data:image/svg+xml; charset=utf-8,[ The URL Encoded Plain Data of SVG should be here]

请注意,与使用 Base64 编码的其他格式不同,我们将需要数据 URL 中的纯数据。对于此示例,我们将使用来自 Wikipedia的广为人知的SVG Tiger。SVG 字符串可以来自任何地方,可以从 Web 资源下载,在浏览器中创建或作为 dom-to-image 库的输出,这一步的重点是你知道它需要在数据 URL 格式。
2.测试是否可以在Image中渲染SVGSVG字符串如何渲染到画布?要测试你创建的 SVG 数据 URL 是否有效,你可以轻松地将其用作 HTML 中图像元素的来源。在这个例子中,我们将使用 Wikipedia 中提到的 SVG Tiger,我们将手动创建它,将 SVG 存储到一个字符串变量中,然后将数据 URL 方案添加到 URL 编码的 SVG 中:
< !-- An image element where the DataURL will be displayed --> < img src="" id="test" /> < script> // 1. Prepare SVG String let SVGString = ` < svg id="svg2" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 900 900" version="1.1"> < g id="g4" fill="none" transform="matrix(1.7656463,0,0,1.7656463,324.90716,255.00942)"> < g id="g6" stroke-width="0.17200001" stroke="#000" fill="#FFF"> < path id="path8" d="m-122.3,84.285s0.1,1.894-0.73,1.875c-0.82-0.019-17.27-48.094-37.8-45.851,0,0,17.78-7.353,38.53,43.976z"/> < /g>........ (rest of the SVG String, note that we remove the following string from the SVG: < ?xml version="1.0" encoding="UTF-8" standalone="no"?>).... < /svg> `; // 2. Convert to Data URL let dataURL = "data:image/svg+xml; charset=utf-8," + encodeURIComponent(SVGString); // 3. Set the DataURL as source of the test image document.getElementById("test").src = https://www.lsbin.com/dataURL; < /script>

你可以在以下小提琴中看到这一点,它应该在 Image 元素中显示 SVG 老虎:
现在知道 SVG 数据 URL 是有效的(只要你期望从给定 SVG 获得的图像出现在 img 元素中),你就可以继续下一步。
3. 在 Canvas 中渲染 SVG 并将其导出为任意大小的图像如何将SVG字符串渲染到画布?现在是时候实现你正在寻找的内容,将 SVG 渲染到画布中以将其调整为你想要的任何大小。实现的逻辑如下。你需要一个空画布,你应该在其中渲染具有自定义大小的 SVG,然后你可以将其导出为 PNG 或 JPEG:
< canvas id="myOutputCanvas">< /canvas>< script> // 1. Obtain the canvas element and access its context let canvas = document.getElementById('myOutputCanvas'); let ctx = canvas.getContext("2d"); // 2. Declare the new width of the image that you want to generate in pixels // e.g create an image of 1000 pixels of width from the given SVG // note: the height is automatically calculated to preserve aspect ratio let newWidth = 1000; // 3. Create an image element to load the SVG let img = new Image(); // 4. Once the SVGDataURL is rendered in the Image element // proceed to render it in the empty canvas that will contain // the same image, but in the size that you want preserving the // sharpness of the SVG string img.onload = function() { // Declare initial dimensions of the image let originalWidth = img.width; let originalHeight = img.height; // Declare the new width of the image // And calculate the new height to preserve the aspect ratio img.width = newWidth; img.height = (originalHeight / originalWidth) * newWidth; // Set the dimensions of the canvas to the new dimensions of the image canvas.width = img.width; canvas.height = img.height; // Render image in Canvas ctx.drawImage(img, 0, 0, img.width, img.height); // That's it! If your canvas is visible, you may now see // the image of the new size! // Export the canvas to blob // You may export this now as a base64 data URL or blob // canvas.toBlob(function(blob){ //do something with the blob //}, "image/png", 1); }; // Load the DataURL of the SVG img.src = "data:image/svg+xml; charset=utf-8,[ The URL Encoded Plain Data of SVG should be here, replace this with the data from step #1]"; < /script>

你可以在以下小提琴中看到此实现的实时示例,你可以在其中简单地将 SVG 字符串提供到 textarea 中,设置输出图像的新宽度,然后将其导出为你想要的图像格式:
快乐编码??!

    推荐阅读