From 5144609b6a894c78f090d989d3da5cb8d27c40b4 Mon Sep 17 00:00:00 2001 From: WindrunnerMax <651525974@qq.com> Date: Fri, 11 Aug 2023 21:30:29 +0800 Subject: [PATCH] 23/08/11 --- CATALOG.md | 6 + ...6foreignObject\345\205\203\347\264\240.md" | 180 +++++++++++++++++- README.md | 1 + 3 files changed, 186 insertions(+), 1 deletion(-) diff --git a/CATALOG.md b/CATALOG.md index 2bd70411..cf17a7d3 100644 --- a/CATALOG.md +++ b/CATALOG.md @@ -1,5 +1,11 @@ # Catalog +**2023-08-11** +> 第403题:[SVG与foreignObject元素](HTML/SVG与foreignObject元素.md) + +
+ + **2023-07-16** > 第402题:[从零实现的Chrome扩展](Plugin/从零实现的Chrome扩展.md) diff --git "a/HTML/SVG\344\270\216foreignObject\345\205\203\347\264\240.md" "b/HTML/SVG\344\270\216foreignObject\345\205\203\347\264\240.md" index 00deddc9..a3cd2547 100644 --- "a/HTML/SVG\344\270\216foreignObject\345\205\203\347\264\240.md" +++ "b/HTML/SVG\344\270\216foreignObject\345\205\203\347\264\240.md" @@ -84,7 +84,71 @@ ``` ```xml -
This is a long text that will automatically wrap within the rectangle.
This is a long text that will automatically...
Viewer does not support full SVG 1.1
+ + + + + + + +
+
+
+
+ + This is a long text that will automatically wrap within the rectangle. + +
+
+
+
+
+ + This is a long text that will automatically... + +
+
+
+ + + + + Viewer does not support full SVG 1.1 + + + +
``` 看起来一切都很完美,我们既能够借助`SVG`绘制矢量图形,又能够在比较复杂的情况下借助`HTML`的能力完成需求,但是事情总有两面性,当我们在某一方面享受到便利的时候,就可能在另一处带来意想不到的麻烦。设想一个场景,假设此时我们需要在后端将`SVG`绘制出来,然后将其转换为`PNG`格式的图片给予用户下载,在前端做一些批量的操作是不太现实的,再假设我们需要将这个`SVG`绘制出来拼接到`Word`或者`Excel`中,那么这些操作都要求我们需要在后端完整地将整个图片绘制出来,那么此时我们可能会想到`node-canvas`在后端创建和操作图形,但是当我们真的使用`node-canvas`绘制我们的`SVG`图形时例如上边的`DrawIO`的例子,会发现所有的图形形状是可以被绘制出来的,但是所有的文本都丢失了,那么既然`node-canvas`做不到,那么我们可能会想到`sharp`来完成图像处理的相关功能,例如先将`SVG`转换为`PNG`,但是很遗憾的是`sharp`也做不到这一点,最终效果与`node-canvas`是一致的。 @@ -138,8 +202,121 @@ return buffer; ``` ## DOM TO IMAGE +让我们想一想,`foreignObject`元素看起来是个非常神奇的设计,通过`foreignObject`元素我们可以把`HTML`绘制到`SVG`当中,那么我们是不是可以有一个非常神奇的点子,如果我们此时需要将浏览器当中的`DOM`绘制出来,实现于类似于截图的效果,那么我我们是不是就可以借助`foreignObject`元素来实现呢。这当然是可行的,而且是一件非常有意思的事情,我们可以将`DOM + CSS`绘制到`SVG`当中,紧接着将其转换为`DATA URL`,借助`canvas`将其绘制出来,最终我们就可以将`DOM`生成图像以及导出了。 +下面就是个这个能力的实现,当然在这里的实现还是比较简单的,主要处理的部分就是将`DOM`进行`clone`以及样式全部内联,由此来生成完整的`SVG`图像。实际上这其中还有很多需要注意的地方,例如生成伪元素、`@font-face`字体的声明、`BASE64`编码的内容、`img`元素到`CSS background`属性的转换等等,想要比较完整地实现整个功能还是需要考虑到很多`case`的,在这里就不涉及具体的实现了,可以参考`dom-to-image-more`。 +```html + + + + + + DOM IMAGE + + + + + +
+

Title

+
+
Content
+
+
+ label + value +
+
+ label + value +
+
+
+ + + + + +``` ## 每日一题 @@ -153,6 +330,7 @@ https://github.com/WindrunnerMax/EveryDay https://github.com/jgraph/drawio https://github.com/pbakaus/domvas https://github.com/puppeteer/puppeteer +https://www.npmjs.com/package/dom-to-image-more https://developer.mozilla.org/zh-CN/docs/Web/SVG https://zzerd.com/blog/2021/04/10/linux/debian_install_puppeteer https://developer.mozilla.org/zh-CN/docs/Web/SVG/Element/foreignObject diff --git a/README.md b/README.md index 909f7a23..75d8aa46 100644 --- a/README.md +++ b/README.md @@ -35,6 +35,7 @@ * [Shadow DOM的理解](HTML/Shadow%20DOM的理解.md) * [Service Worker的应用](HTML/Service%20Worker的应用.md) * [蒙层禁止页面滚动的方案](HTML/蒙层禁止页面滚动的方案.md) +* [SVG与foreignObject元素](HTML/SVG与foreignObject元素.md) ## CSS * [布局垂直居中](CSS/布局垂直居中.md)