На данный вопрос уже ответили:
Мне нужно перевести черно-белое изображения в вектор, состоящий из 1 и 0 Написал функцию, которая принимает на вход путь к файлу и возвращает массив из 1 и 0.
function readImg(file) {
ctx.clearRect(0, 0, draw.width, draw.height);
var img = new Image(),
convert = [];
img.onload = function() {
ctx.drawImage(img, 0, 0);
var imgdata = ctx.getImageData(0, 0, draw.width, draw.height).data;
for (var i = 0; i < img.width * img.height; i++) {
if (imgdata[i*4] > 0)
convert.push(0);
else
convert.push(1);
}
}
img.src = file;
return convert;
}
Но вот проблема, если я пытаюсь дальше работать с этим массивом, то его как бы не существует. К примеру:
var temp = readImg("img.png");
console.log(temp.length) //Выведет "0"
Получается, что массив convert возвращается пустым и не успевает заполнится, т.к. функция img.onload еще не выполнилась.
UPD: Прочитал про Promise, попытался прикрутить его к моему коду
function readImg(file) {
return new Promise(function(resolve, reject) {
ctx.clearRect(0, 0, draw.width, draw.height);
var img = new Image(),
convert = [];
img.onload = function() {
ctx.drawImage(img, 0, 0);
var imgdata = ctx.getImageData(0, 0, draw.width, draw.height).data;
for (var i = 0; i < img.width * img.height; i++) {
if (imgdata[i*4] > 0)
convert.push(0);
else
convert.push(1);
}
resolve(convert);
}
img.src = file;
});
}
Теперь использую эту функцию так
readImg("img.png").then(function (result) {
console.log(result);
});
Результат выводит правильный, но как мне этот result присвоить другой переменной и использовать дальше? Я хочу использовать это так:
data = [];
for (var i = 0; i < 3; i++) {
data[i] = [];
readImg(i + 1 + ".png").then(function (result) {
data[i][0] = result; //ошибка Uncaught (in promise) TypeError: Cannot set property '0' of undefined
});
}
Проблема. Когда функция выполняется внутри Promise значение внешней переменной i будет другим и его напрямую использовать нельзя. Я передал его как параметр.
Только у меня здесь одна и та же картинка для примера.
var canvas = document.getElementById("canvas");
var ctx = canvas.getContext("2d");
var draw = new Object();
draw.width = ctx.canvas.clientWidth;
draw.height = ctx.canvas.clientHeight;
function readImg(file,num) {
return new Promise(function(resolve, reject) {
ctx.clearRect(0, 0, draw.width, draw.height);
var img = new Image(),
convert = [];
var myresult = new Object();
myresult.num=num;
img.crossOrigin = "Anonymous";
img.onload = function() {
ctx.drawImage(img, 0, 0);
var imgdata = ctx.getImageData(0, 0, draw.width, draw.height).data;
for (var i = 0; i < img.width * img.height; i++) {
if (imgdata[i*4] > 0)
convert.push(0);
else
convert.push(1);
}
myresult.convert=convert;
resolve(myresult);
}
img.src = file;
});
}
data = [];
for (var i = 0; i < 3; i++) {
readImg("https://i.imgur.com/K38QcUh.png",i).then(function (myresult) {
local_i=myresult.num;
data[local_i] = [];
data[local_i].push(myresult.convert);
// или data[local_i]=myresult.convert;
alert(data[local_i]);
});
}
<canvas id="canvas" width="5" height="5" class="playable-canvas"></canvas>
Ну тогда проще сделать так. Вызываем загрузку изображений одной функцией передавая ей список файлов для загрузки. После загрузки первого изображения вызывается загрузка второго и тд. После последнего запускается функция nextcode туда и пишите остальной код.
var canvas = document.getElementById("canvas");
var ctx = canvas.getContext("2d");
var data = [];
var draw = new Object();
draw.width = ctx.canvas.clientWidth;
draw.height = ctx.canvas.clientHeight;
function readImgList(imglist) {
ctx.clearRect(0, 0, draw.width, draw.height);
var img = new Image();
img.crossOrigin = "Anonymous"; //это нужно только для примера тк изображение загружается с другого домена
var k=0;
img.onload = function() {
ctx.drawImage(img, 0, 0);
var imgdata = ctx.getImageData(0, 0, draw.width, draw.height).data;
data[k]=[];
for (var i = 0; i < img.width * img.height; i++) {
if (imgdata[i*4] > 0)
data[k].push(0);
else
data[k].push(1);
}
if (k+1<imglist.length) {
k=k+1;
img.src=imglist[k];
} else {
nextcode();
}
}
img.src = imglist[0];
}
var imglist = [];
imglist[0] = "https://i.imgur.com/K38QcUh.png";
imglist[1] = "https://i.imgur.com/K38QcUh.png";
imglist[2] = "https://i.imgur.com/K38QcUh.png";
readImgList(imglist);
function nextcode() {
console.log(data);
//и сюда пишете весь ваш остальной код
}
<canvas id="canvas" width="5" height="5" class="playable-canvas"></canvas>
Сборка персонального компьютера от Artline: умный выбор для современных пользователей