HTML Canvas - 将背景图像传递给Canvas,同时传递base64数据

时间:2017-09-04 13:06:25

标签: javascript html5 canvas sketchjs

我目前正尝试在Laserfiche表单中进行一些Javascript工作,这需要我将图像的base64数据保存在单独的文本区域中,并将该数据反馈到图像中以允许画布转动进入我可以保存到系统中的图像。

问题是我试图拥有一个用户可以在其上绘制的背景图像(在这种情况下,他们可以画一个圆圈以指示损坏的位置)。我正在使用sketch.js来完成任务的绘图部分。

从我读过的内容来看,后台CSS无法保存到画布中。这很好,但是当我已经抓住base64数据并将其传回画布时,如何传递背景图像?

saveimage类属于文本区域,imagefinish属于图像准备好时标记的复选框

html

<div class="demo" id="colors_demo">
  <div class="tools">
      <a href="#colors_sketch" data-tool="marker">Marker</a>         
      <a href="#colors_sketch" data-tool="eraser">Eraser</a>
      <a href="#colors_sketch" data-download="png" style="float: right; width: 100px;">Download</a>
  </div>
  <canvas id="colors_sketch" width="750" height="500" style="border:2px solid #000000 ; background: url(http://localhost/forms/img/vanImage.jpg"></canvas>
</div>
<input name="Field11" id="Field11-0" type="checkbox" value="isLocked" vo="e" data-parsley-class-handler="#Field11" data-parsley-errors-container="#Field11" data-parsley-multiple="Field11">
    <textarea id="Field13" name="Field13" aria-labelledby="Field13" class="cf-medium" rows="3" vo="e" data-parsley-id="28"></textarea>

Javascript

//submitted form
  if ($('[name=IsLocked]').val() == 'True') {
    var myCanvas = document.getElementById('colors_sketch');
    var ctx = myCanvas.getContext('2d');
    var img = new Image;
    img.onload = function() {
      ctx.drawImage(this, 0, 0, myCanvas.width, myCanvas.height);
    }
    img.src = $('.saveimage .cf-field').text();  
  }
  else {
  //fill form
  //$.getScript('http://localhost/Forms/js/sketch.js', function() {
     $.getScript('https://rawgit.com/intridea/sketch.js/gh-pages/lib/sketch.js', function() {
      //script is loaded and executed put your dependent JS here
      $.each(['#f00', '#ff0', '#0f0', '#0ff', '#00f', '#f0f', '#000', '#fff'], function() {
        $('#colors_demo .tools').append("<a href='#colors_sketch' data-color='" + this + "' style='width: 10px; background: " + this + ";'></a> ");
      });
      $.each([3, 5, 10, 15], function() {
        $('#colors_demo .tools').append("<a href='#colors_sketch' data-size='" + this + "' style='background: #ccc'>" + this + "</a> ");
      });
      //$('#colors_sketch').sketch();
      $('#colors_sketch').sketch({defaultColor: "#000"});
    });
    $('.imagefinish input').change(function(){
      if(this.checked) {
        var myCanvas = document.getElementById('colors_sketch');
        $('.saveimage textarea').val(myCanvas.toDataURL());
      }
    });
  }

我可以通过为图像路径添加变量来添加图像

 var image   = 'http://localhost/forms/img/vanImage.jpg'

我还为我的onload添加了两行代表&#34; myCanvas&#34;的风格。我觉得这个解决方案只会起作用,因为Laserfiches如何形成软件,但明确的答案也是正确的。

img.onload = function() {
      ctx.drawImage(this, 0, 0, myCanvas.width, myCanvas.height);
      myCanvas.style.backgroundRepeat = "no-repeat";
    myCanvas.style.backgroundImage = 'url('+image+')'
    }
    img.src = $('.saveimage .cf-field').text();  
  }

1 个答案:

答案 0 :(得分:1)

在页面加载时或适当的时间加载背景图像,当客户端准备就绪时,使用ctx.globalCompositeOperation = "destination-over";

将背景绘制到用户内容后面的画布上

创建一个图像来保存背景。

const backgroundImage = new Image();
backgroundImage.src = "http://localhost/forms/img/vanImage.jpg";

当客户端点击准备就绪时,您需要确保已加载图像,如果未加载,您可以设置一个回调函数,以便在需要时回调就绪函数。

var backgroundLoadedCallback = null;
backgroundImage.onload = function(){
     if( typeof backgroundLoadedCallback === "function"){
         backgroundLoadedCallback();
     }
}

然后创建画布 - &gt; textarea功能

function canvasToTextarea(){

    const myCanvas = document.getElementById('colors_sketch');
    const ctx = myCanvas.getContext("2d");
    ctx.globalCompositeOperation = "destination-over";  // make sure the background go under the drawn pixels
    // draw and fit background to the canvas
    ctx.drawImage(backgroundImage,0,0,ctx.canvas.width,ctx.canvas.height);
    // then convert to URL for textarea
    $('.saveimage textarea').val(myCanvas.toDataURL());

}

在已检查的功能

$('.imagefinish input').change(function(){
  if(this.checked) {
     if(backgroundImage.complete) { // image has loaded so all good
         canvasToTextarea(); // put canvas data URL to textarea
     } else { // background has not yet loaded (or could be an error you will have to deal with that as well
          // set the callback to the canvasToTextarea function
          backgroundLoadedCallback = canvasToTextarea;
          // when the background has loaded the canvas and background
          // will be moved to the textarea as a data URL
     } 
  }
});

或修改sketch.js

下面是sketch.js的绘图功能(它是非常古老的学校)

Sketch.prototype.redraw = function() {
  var sketch;
  this.el.width = this.canvas.width();
  this.context = this.el.getContext('2d');
  sketch = this;
  $.each(this.actions, function() {
    if (this.tool) {
      return $.sketch.tools[this.tool].draw.call(sketch, this);
    }
  });
  if (this.painting && this.action) {
    return $.sketch.tools[this.action.tool].draw.call(sketch, this.action);
  }
};

只需将其替换为以下内容即可。您不需要修改sketch.js文件,只需覆盖重绘原型

在您的代码中加载背景并设置新的重绘

const backgroundImage = new Image();
backgroundImage.src = "http://localhost/forms/img/vanImage.jpg";


// replace Sketch.js redraw function
Sketch.prototype.redraw = function(){
  var sketch;
  // dont need the next line use clear instead
  // this.el.width = this.canvas.width();

  const ctx = this.context = this.el.getContext('2d');
  // clear canvas
  this.context.clearRect(0, 0, ctx.canvas.width, ctx.canvas.height);
  // If backgroundimage complete draw it first
  if(backgroundImage && backgroundImage.complete){
      ctx.drawImage(backgroundImage,0,0,ctx.canvas.width,ctx.canvas.height);
  }

  // back to the original code. :P
  sketch = this;
  $.each(this.actions, function() {
    if (this.tool) {
      return $.sketch.tools[this.tool].draw.call(sketch, this);
    }
  });
  if (this.painting && this.action) {
    return $.sketch.tools[this.action.tool].draw.call(sketch, this.action);
  }
}