0

我正在构建一个应用程序来创建可以在 DartFlash 中使用的 TextureAtlas。我的想法是使用输入标签加载许多文件,然后使用 FileReader API 将这些文件转换为图像,在画布上绘制它们并将画布转储为用户可以下载的图像,以及描述图像的 JSON 文件。但是,它有时无法完成任务并正确写入输出图像。我很确定这是一个同步问题,但我找不到问题所在。我已经在 Chrome 中对其进行了测试,它的成功率更高。在 Firefox 中,它的失败率更高。

这是代码:

 <html>
 <head>
 <script type="text/javascript">

 "use strict"

 var files=null;
 var img_list=[];
 var num_files=-1;
 var img_list_length=0;
 var output_json={}
 var output_canvas=null;
 var output_img=null;
 var download_png=null;

 function createOutputImg()
 {
    if(num_files != img_list_length)
    {
        return;
    }
    img_list.sort(function (a,b)
    {
        if(a.name > b.name)
        {
            return 1;
        }
        return -1;
    });
    output_canvas=document.createElement('canvas');
    var total_width=0;
    var highest_height=0;
    for (var i=0; i<img_list.length; i++)
    {
        total_width+=img_list[i].width;
        if(highest_height < img_list[i].height)
        {
            highest_height=img_list[i].height;
        }
    }
    console.log(total_width);
    output_canvas.width=total_width;
    output_canvas.height=highest_height;
    var context=output_canvas.getContext("2d");
    output_json["frames"]=[];
    var current_posx=0;
    for (var i=0; i<img_list.length; i++)
    {
        var img=img_list[i];
        context.drawImage(img, current_posx, 0);
        console.log(i.toString()+" - "+img.name);
        output_json["frames"].push(
        {
            "filename":img.name,
            "frame":
            {
                "x":current_posx,
                "y":0,
                "w":img.width,
                "h":img.height
            },
            "rotated":false,
            "trimmed":false,
            "spriteSourceSize":
            {
                "x":0,
                "y":0,
                "w":img.width,
                "h":img.height
            },
            "sourceSize":
            {
                "w":img.width,
                "h":img.height
            }
        });
        current_posx+=img.width;
    }
    output_img=document.createElement('img');
    output_img.src=output_canvas.toDataURL("image/png");

    if(output_img.width != total_width)
    {
        alert("Error happened somewhere, please, refresh and retry again");
        return;
    }

    var paragraph=document.createElement('p');
    paragraph.innerHTML="Type a name for this resource.";
    document.body.appendChild(paragraph);

    var input_name=document.createElement('input');
    input_name.type="text";
    document.body.appendChild(document.createElement('br'));
    document.body.appendChild(input_name);
    var go_button=document.createElement('button');
    go_button.innerHTML="Download";
    document.body.appendChild(go_button);
    document.body.appendChild(document.createElement('br'));
    go_button.inputElement=input_name;
    go_button.onclick=function (evt)
    {
        var resource_name=evt.target.inputElement.value;
        if(resource_name == "")
        {
            alert ("Please type a name for this resource.");
            return;
        }
        output_json["meta"]={}
        output_json["meta"]["app"]="HTML ImagePacker";
        output_json["meta"]["image"]=resource_name+".png";
        output_json["meta"]["format"]="RGBA8888";
        output_json["meta"]["size"]={};
        output_json["meta"]["size"]["w"]=output_img.width;
        output_json["meta"]["size"]["h"]=output_img.height;
        output_json["meta"]["scale"]="1";
        var json_data=new Blob([JSON.stringify(output_json)]);
        var download_json=document.createElement('a');
        download_json.innerHTML=resource_name+".json";
        download_json.download=download_json.innerHTML;
        download_json.href=window.URL.createObjectURL(json_data);
        var download_png=document.createElement('a');
        download_png.innerHTML=resource_name+".png";
        download_png.download=download_png.innerHTML;
        download_png.href=output_img.src;
        document.body.appendChild(document.createElement('br'));
        document.body.appendChild(download_json);
        document.body.appendChild(document.createElement('br'));
        document.body.appendChild(download_png);
        document.body.appendChild(document.createElement('br'));
        document.body.appendChild(output_img);
    };
 }

 function handleFileSelect()
 {
    var files=document.getElementById("files").files;
    num_files=files.length;
    console.log(files);
    var height=0;
    for(var i=0; i<files.length; i++)
    {
        (function (file)
        {
            var reader=new FileReader();
            reader.name=file.name;
            reader.readAsDataURL(file);
            reader.onload=(function (evt) 
            {
                //console.log(evt);
                if(evt.target.readyState == 2)
                {
                    var img=document.createElement('img');
                    img.name=evt.target.name;
                    img.src=evt.target.result;
                    img_list.push(img);
                    img_list_length+=1;
                    //document.body.appendChild(img, null);
                    if(num_files == img_list_length)
                    {
                        createOutputImg();
                    }
                }
            });
        })(files[i]);
    }
 }

 </script>
 </head>

 <body>
 <input type="file" id="files" name="files[]" onchange="handleFileSelect()"  multiple/><br>

 </body>
 </html>
4

0 回答 0