如何从画布前的变量中写入文本?

Posted

技术标签:

【中文标题】如何从画布前的变量中写入文本?【英文标题】:How can I write text from variables in front of a canvas? 【发布时间】:2020-07-02 11:34:55 【问题描述】:

我正在开发卡片制作应用。其背后的想法是为每张卡片创建一个包含数据的 CSV 文件,一个包含图像的文件夹,并在上传 CSV 文件后为我拥有的每个角色创建一张卡片。到目前为止一切顺利,但我被困在画布前写文字。

画布是通过重叠许多不同的图像创建的,但文本出现在背景上,最终被其他图像完全覆盖。我希望文本在它前面!

我在加载包含数据的 CSV 文件时触发所有内容,我实际上使用了“context.fillText”,但没有按我希望的那样工作。

如何将变量中的文本放在画布前面的最后 3 个“context.fillText”中? 最后的范围是拥有一个可以保存为图像的画布。

这是我的代码

$( document ).ready(function() 

  function loadImages(sources, callback) 
      var images = ;
      var loadedImages = 0;
      var numImages = 0;
      // get num of sources
      for(var src in sources) 
        numImages++;
      
      for(var src in sources) 
        images[src] = new Image();
        images[src].onload = function() 
          if(++loadedImages >= numImages) 
            callback(images);
          
        ;
        images[src].src = sources[src];
      

    

    var canvas = document.getElementById('myCanvas');
    var context = canvas.getContext('2d');


  document.getElementById('txtFileUpload').addEventListener('change', upload, false);
  
  function upload(evt) 
      var file = evt.target.files[0];
      var reader = new FileReader();
      reader.readAsText(file);
      reader.onload = function (event) 
          var csvData = event.target.result;
          Papa.parse(csvData, 
              complete: function (results) 
                  console.log(results.data);
              
                  var imgStelle;
                  var imgClan;
                  var immagine;

                  var numeroCarte=(results.data.length);
                  for(var i=0; i<numeroCarte; i++)
                    
                      var clan=(results.data[i][0]);
                      var nome =(results.data[i][1]); 
                      var rarita =(results.data[i][2]);
                      var stelle =(results.data[i][3]);
                      var potenza =(results.data[i][4]);
                      var danno =(results.data[i][5]);
                      var potere =(results.data[i][6]);
                      var bonus=(results.data[i][7]);
                      var nomeintero=(results.data[i][8]);

                      imgStelle = "Immagini/LivelloCarte/livello"+ stelle +".png";
                      imgClan= "Immagini/IconeClan/"+ clan +"_42.png";
                      if (rarita=="Non comune")
                          imgRarita = "Immagini/RaritaCarta/raritanoncomune.png";
                       else 
                          imgRarita = "Immagini/RaritaCarta/rarita"+rarita+".png";
                      
                  
                      immagine ="Immagini/ImmaginiChar/"+clan+"_"+nomeintero+"_N"+stelle+"_HD_673.png"
                  
                      var sources = 
                          image1: 'Immagini/SfondoCarte/base.png',
                          image2:'Immagini/SfondoCarte/riquadro.png',
                          image3: immagine,
                          image4:'Immagini/SfondoCarte/poteri.png',
                          image5: imgRarita,
                          image6: imgStelle,
                          image7: 'Immagini/SfondoCarte/riquadrobis.png',
                          image8: imgClan,
                          image9: 'Immagini/Numeri/'+potenza+'.png',
                          image10:'Immagini/Numeri/'+danno+'.png',
                        ;

                        loadImages(sources, function(images) 
                          context.drawImage(images.image1, 0, 0,  2220 , 3240);  //SFONDO *   x - y
                          context.drawImage(images.image2, 80, 80,  2040 ,1900);//RIQUADRO
                          context.drawImage(images.image3, 0, 0,  2220 ,3150);  //IMMAGINE *
                          context.drawImage(images.image4, 80, 2000,  2050 ,1150);  //LAYOUT POTERI *
                          context.drawImage(images.image5, 520, 80,  1610 ,200);   //RARITA *
                          context.drawImage(images.image6, 600, 2000,  1240 ,260);  //STELLE *
                          context.drawImage(images.image7, 100, 70,  360 ,360);  //RIQUADRO CLAN *
                          context.drawImage(images.image8, 120, 80,  320 ,320);  //CLAN *
                          context.drawImage(images.image9, 170, 2350,  130 ,170);  //FORZA *
                          context.drawImage(images.image10, 170, 2950,  130 ,170);  //DANNO *
                        );

                        context.font = "40pt Calibri";
                        context.fillText(nome, 20, 20);
                        context.fillText(potere, 20, 20);
                        context.fillText(bonus, 20, 20);

                  
                  
              
          );
      ;
  
      

);
<html>

  <head>
    <meta charset="UTF-8" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <meta http-equiv="X-UA-Compatible" content="ie=edge" />

    <link href="https://fonts.googleapis.com/css?family=Roboto" rel="stylesheet"type="text/css" />

    <link rel="stylesheet" href="Pagina.css" />
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
    <script src="https://files.codepedia.info/files/uploads/iScripts/html2canvas.js"></script>
    <script src="Pagina.js"></script> 
    <script src="papaparse.js"></script> 
    <script src="papaparse.min.js"></script> 

    <title>Card maker</title>                             
  
  </head>


  <body>

    <input type="file" name="File Upload" id="txtFileUpload" accept=".csv" />

    <div class="cartaSingola">
        <div class="contenitoreCarte">
            <canvas id="myCanvas"  ></canvas>
        </div>
    </div>

  </body>

</html>

【问题讨论】:

您能否提供一个示例 CSV,以便我们试用您的代码?或者也许修改代码以使用一些预定义的值运行。 CSV 结构很简单,只有大量具有相同模式但值不同的行:ClanName,CardName,1,1,1,CardPower,CardBonus,FullName 如何将文本放入一个新的 html &lt;div&gt; 并使用 CSS 将其放置在画布前面? @Papooch 但随后您将失去“另存为图像”功能。 @OP 我收到了"Uncaught ReferenceError: Papa is not defined",你能正确地包括这个吗? @Stratubas Papa 是一个名为 papaparse 的外部库的 js :) 【参考方案1】:

我认为您的问题是您正在“所有图像已加载”回调中绘制图像,但在此回调运行之前绘制了文本。

试试这个:

loadImages(sources, function(images) 
    context.drawImage(images.image1, 0, 0,  2220 , 3240);
    // context.drawImage image2, 3, ...9,
    context.drawImage(images.image10, 170, 2950,  130 ,170);

    // Draw text here
    context.font = "40pt Calibri";
    context.fillText(nome, 20, 20);
    context.fillText(potere, 20, 20);
    context.fillText(bonus, 20, 20);
);

并在此处将var 替换为const

const nome = results.data[i][1]; 
const potere = results.data[i][6];
const bonus = results.data[i][7];

【讨论】:

@GianlucaFontana 在“不绘制任何东西”中不起作用或仍然在图像后面绘制? @GianlucaFontana 如果它画错了文字我也不会感到惊讶... @GianlucaFontana 尝试用const 替换var,正如我在回答中添加的那样。 先生,您破案了。非常感谢,真的! :)【参考方案2】:

我认为您可以使用 .append() 并在 .contenitoreCarte 甚至您的画布中创建文本

用法太简单了, 这里的文件: https://api.jquery.com/append/

如果您给我一个 CSV 示例,我可以通过完成您的代码来提交更好的答案

【讨论】:

这样我就无法保存为图片了。

以上是关于如何从画布前的变量中写入文本?的主要内容,如果未能解决你的问题,请参考以下文章

从 MFC 中的编辑控件写入文本 [重复]

如何使用python 2.7通过变量写入文本文件[重复]

我如何获得按键并将其写入变量?

如何用python将变量及其值写入文本文件?

从文本文件中读取和写入字符串

如何从文件中写入/读取变量并使用 Makefile 进行解析?