php - 将 Canvas 图像保存到服务器

标签 php jquery html html5-canvas

我已从数据库中提取数据来创建 HTML 表格,我希望能够将其保存为服务器上的 PNG 格式。

当我使用 PHP 将 PNG 保存到服务器时,它是空白的。

我创建了静态代码(即不是来自数据库)来说明我的示例。

如果我手动右键单击图像,然后“另存为”,则图像会正确保存,只有当我尝试自动执行时,图像才会显示为空白。我在 Chrome 和 Firefox 中都尝试过,结果相同。

如果有人能帮助我纠正我做错的事情,我将不胜感激。谢谢。

我正在使用:

  • PHP 7.3.4
  • jQuery 3.4.1
  • Chrome 76.0.3809.100
  • 火狐浏览器 68.01

index.php

<!DOCTYPE html>
<html>
<head>
    <meta charset="UTF-8">
    <script src="jquery-3.4.1.min.js" type="text/javascript"></script>
</head>

<body>
    <div id="invoicetable">
        <div xmlns="http://www.w3.org/1999/xhtml">
            <style>
        body        {font-family: courier new; font-size: 13px; }
        td      {padding: 2px 5px 2px 5px; }
        .headerTD   {font-weight: bold; }
        .w60        {width: 60px; }
        .w80        {width: 80px; }
        .w100       {width: 100px; }
        .w120       {width: 120px; }
        .w160       {width: 160px; }
            </style>

<table class='' border='01' style='border-collapse: collapse; font-size: 14px; font-family: trebuchet ms; '><tr><td class='headerTD w100'>Date</td><td class='headerTD w60'>Type</td><td class='headerTD w160'>Detail</td><td class='headerTD w120'>Username</td><td class='headerTD w100'>Line</td><td class='headerTD w100'>Start Date</td><td class='headerTD w100'>End Date</td><td class='headerTD w80'>Subtotal</td></tr><tr><td>23/07/2019</td><td>Credit</td><td>Business Fibre 1</td><td><a href="https://stackoverflow.com/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="83e2e1e0c3e7e6e5ade0ecee" rel="noreferrer noopener nofollow">[email protected]</a></td><td>011122223333</td><td>23/07/2019</td><td>21/08/2019</td><td>&pound; <div style='float: right'>-7.74</div></td></tr><tr><td>04/08/2019</td><td>Charge</td><td>Business Fibre 1</td><td><a href="https://stackoverflow.com/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="284f404168424344064b4745" rel="noreferrer noopener nofollow">[email protected]</a></td><td>01234567890</td><td>04/08/2019</td><td>03/09/2019</td><td>&pound; <div style='float: right'>22.50</div></td></tr><tr><td>04/08/2019</td><td>Charge</td><td>Line Rental</td><td></td><td>01234567890</td><td>04/08/2019</td><td>03/09/2019</td><td>&pound; <div style='float: right'>15.66</div></td></tr><tr><td>04/08/2019</td><td>Charge</td><td>Line Rental</td><td></td><td>01234567890</td><td>04/07/2019</td><td>03/08/2019</td><td>&pound; <div style='float: right'>0.00</div></td></tr><tr><td colspan='7'></td><td>&pound; <div style='float: right'>30.42</div></td></tr></table>

        </div>
    </div>
    <br>
    <br>

    <canvas id="canvas" width="930" height="150"></canvas>

    <script>
        $(function() {
            var canvas = document.getElementById("canvas");
            var ctx = canvas.getContext("2d");
            var imgW = 930;
            var imgH = 150;
            ctx.fillStyle = "white";
            ctx.fillRect(0, 0, imgW, imgH);

            var data = "<svg xmlns='http://www.w3.org/2000/svg' width='" + imgW + "' height='" + imgH + "'>" + "<foreignObject width='100%' height='100%'>" + $("#invoicetable").html() + "</foreignObject>" + "</svg>";
            var DOMURL = self.URL || self.webkitURL || self;
            var img = new Image();
            var svg = new Blob([data], {
                type: "image/svg+xml;charset=utf-8"
            });
            var url = DOMURL.createObjectURL(svg);
            img.onload = function() {
                ctx.drawImage(img, 0, 0);
                DOMURL.revokeObjectURL(url);
            };
            img.src = url;

            var canvas = document.getElementById("canvas");
            var pngData = canvas.toDataURL("image/png");
            $.post("savepng.php", {
                pngData: pngData
            }, function(data) {});

        });
    </script>
</body>

</html>


savepng.php

<?php
$aaa = explode(",", $_POST['pngData']);
file_put_contents("invoicedata.png", base64_decode($aaa[1]));
?>

这是预期的图像输出:
The expected image output

最佳答案

您的代码存在三个问题:

  1. 您正在尝试在将 SVG 图像绘制到 Canvas 上之前保存图像。
    将图像保存在 onload 回调中。

  2. 看来您从 this 获取了代码问题没有解决问题,因此当您调用 toDataURL 时,您会收到有关 Canvas 受污染的错误。

  3. 如果您使用上一个问题的修复,则呈现英镑符号似乎会出现问题。这似乎是编码问题,修复方法是 here .

要解决这些问题,请使用以下代码:

var img = new Image();
img.onload = function() {
    ctx.drawImage(img, 0, 0);

    var canvas = document.getElementById("canvas");
    var pngData = canvas.toDataURL("image/png");
    $.post("savepng.php", {
        pngData: pngData
    }, function(data) {});
};
function buildSvgImageUrl(svg) {
    var b64 = window.btoa(unescape(encodeURIComponent(svg)));
    return "data:image/svg+xml;base64," + b64;
}
img.src = buildSvgImageUrl(data);

关于php - 将 Canvas 图像保存到服务器,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57420608/

相关文章:

php - php中的对象持久化

php - 拒绝用户 '' @'localhost' 访问数据库 'finalproject'

php - SQL SELECT 和 GROUP BY Month 在 9 个多月前未返回任何结果

php - 使用 PDO 从多个字段进行高级搜索

html - 外部固定背景图像不显示

php - 如何在连续文本区域中打印结果?

jquery - HTML、CSS、JavaScript 弹出问题

javascript - 滚动到列表中的特定项目,然后滚动到列表中的下一个特定项目

javascript - 如何将标记添加到 MapBox GL JS map ?

html - 为什么这两个内联 block 不对齐?