对 div 元素进行屏幕截图时,尺寸和边框不适合 SVG 屏幕截图

问题描述 投票:0回答:1

我想让自定义元素内部不需要div元素,使图像的大小与div的大小相同,并使div的底部边框出现。另外,style元素应该在div中才能起作用,最好解决一下。除了那些东西之外,这段代码工作得很好。简单来说,html2canvas 缺少一些元素,所以我用 SVG 重新制作了它。

<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <script>
        class CaptureElement extends HTMLElement {
            capture() {
                const div = this.querySelector("div");
                const br = document.createElement("br");
                div.appendChild(br);
                const canvas = document.createElement("canvas");
                const context = canvas.getContext("2d");
                const data = new XMLSerializer().serializeToString(div);
                const svg = `<svg xmlns="http://www.w3.org/2000/svg" width="${div.scrollWidth}" height="${div.scrollHeight}">
                                <foreignObject width="100%" height="100%">
                                    ${data}
                                </foreignObject>
                             </svg>`;
                const img = new Image();
                img.onload = () => {
                    canvas.width = div.scrollWidth;
                    canvas.height = div.scrollHeight;
                    context.drawImage(img, 0, 0);
                    const base64 = canvas.toDataURL("image/png");
                    console.log(base64);
                    div.removeChild(br);
                    if (this.hasAttribute("download")) {
                        var filename;
                        const download = this.getAttribute("download");
                        if (!download.endsWith(".png")) {
                            filename = download + ".png";
                        }
                        else {
                            filename = download;
                        }
                        const a = document.createElement('a');
                        a.href = base64;
                        a.download = filename;
                        a.click();
                    }
                };
                img.src = 'data:image/svg+xml;charset=utf-8,' + encodeURIComponent(svg);
            }
        }

        customElements.define("capture-element", CaptureElement);
        document.addEventListener("DOMContentLoaded", () => {
            document.querySelector("button").addEventListener("click", () => {
                document.querySelector("capture-element").capture();
            })
        });
    </script>
    <style>
        button {
            color: white;
            background-color: gray;
            border-radius: 5px;
        }

        div.button {
            text-align: center;
        }
    </style>
    <title>Custom element</title>
</head>

<body>
    <div class="button">
        <button>Download</button>
    </div>
    <br>
    <br>
    <capture-element download="Certification.png">
        <div id="certification">
            <style>
                * {
                    border: 0px;
                    background-color: white;
                    font-family: "Arial";
                }

                h1 {
                    background: linear-gradient(to right bottom, rgba(255, 188, 13, 1) 23%, rgba(0, 212, 255, 1));
                    font-weight: lighter;
                    color: transparent;
                    background-clip: text;
                    text-align: center;
                }

                p {
                    margin-left: 5px;
                }

                div#certification {
                    border-top: 1px solid black;
                    border-right: 1px solid black;
                    border-left: 1px solid black;
                    border-bottom: 2px solid black;
                    border-radius: 0px;
                    width: 50%;
                    min-width: 500px;
                    max-width: 1000px;
                    margin: auto;
                }

                .uname {
                    color: transparent;
                    font-weight: bolder;
                    font-size: xx-large;
                    text-align: center;
                    margin-top: 0px;
                    background: linear-gradient(to right bottom, rgb(132, 160, 68) 23%, rgb(66, 171, 192));
                    background-clip: text;
                }

                .fname {
                    font-weight: bold;
                    font-size: x-large;
                    text-align: center;
                    margin-right: 150px;
                    margin-top: 0px;
                }

                div:not(#certification) {
                    text-align: center;
                }
            </style>
            <h1>Digital certification</h1>
            <p>This certification is made for developers, from developers. This one is specially made for:</p>
            <p class="uname">Username</p>
            <p>From:</p>
            <p class="fname">HTML, CSS, JavaScript</p>
            <div>
                <ruby><meter style="font-size: xx-large;" min="0" max="100" low="33" high="66" optimum="80"></meter>
                    <rt style="font-size: larger;">0%</rt>
                </ruby>
            </div>
        </div>
    </capture-element>
</body>

</html>

javascript html css
1个回答
0
投票

几乎没有改进来简化 capture-element 自定义元素的 HTML 和 JavaScript,确保内部 div 不需要显式声明,调整图像大小以匹配 div 大小,使 div 的底部边框出现,并确保在 SVG 序列化中正确捕获样式。 使用这个修改后的代码片段。

© www.soinside.com 2019 - 2024. All rights reserved.