Javascript 在p5js中获取图像的像素值

Javascript 在p5js中获取图像的像素值,javascript,p5.js,Javascript,P5.js,我一直在写一些代码,应该在每个黑色像素上画一个点椭圆。我不熟悉get函数,并且怀疑我可能在使用它时犯了错误。有人知道为什么我的代码不能成功地在印度地图上打上点吗 功能设置{ CreateCanvas400400; } window.onload=函数{ var c=document.getElementByIdmyCanvas; var ctx=c.getContext2d; var img=document.getElementByIdmap; ctx.IMG,10,10,150000,18

我一直在写一些代码,应该在每个黑色像素上画一个点椭圆。我不熟悉get函数,并且怀疑我可能在使用它时犯了错误。有人知道为什么我的代码不能成功地在印度地图上打上点吗

功能设置{ CreateCanvas400400; } window.onload=函数{ var c=document.getElementByIdmyCanvas; var ctx=c.getContext2d; var img=document.getElementByIdmap; ctx.IMG,10,10,150000,1800000; } 函数图{ 对于变量x=0;x<100;x++{ 对于变量y=0;y<100;y++{ 如果blackgetx,y==255{ ellipsex,y,10100; } } } } p{ 位置:绝对位置; z指数:3; } img{ 位置:绝对位置; z指数:-1; } 正文{填充:0;边距:0;}


因为您使用的是p5js,所以应该使用它提供的方法和函数。没有必要像使用p5js那样获得画布。p5js在您键入canvas时提供对它的引用

此时,您正在使用图像标记显示图像。相反,您希望在画布上显示图像。您可以使用p5的预加载方法来加载图像。然后,一旦加载了它,就可以在绘制方法中引用它

您的绘制方法将持续在循环上运行。但是,您不需要循环,因为您只需要进行一次计算。因此,您可以使用p5的方法noLoop来阻止draw循环

最后,要获得特定像素的颜色,需要使用getx,y。这将为您提供一个红色、绿色和蓝色值的数组。黑色像素表示这三个值均为0。但是,您的图像的像素不是严格意义上的黑色。例如,如果您的r g b红色、绿色和蓝色的颜色值为1、1、1,则您的颜色仍然看起来是黑色。因此,要检查给定颜色是否为黑色,您需要检查所有这些值是否小于特定数字,例如80

如果您将所有这些想法合并到您的代码中,您应该得到如下结果:

let img;

function preload() {
  img = loadImage('india-map.gif');
}

function setup() {
  createCanvas(400, 400);
}

function draw() {
  background(220);
  image(img, 0, 0, width, height);
  for(let x = 0; x < width; x++) {
    for(let y = 0; y < height; y++) {
      const [r, g, b] = get(x, y); // get colors
      if(r <= 80 && b <= 80 && g <= 80) { // if r g b all less than 80 then color will appear black
        noStroke(); // remove black outline from thing we are about to draw (the ellipse)
        fill(255, 0, 0); // make the ellipse red
        ellipse(x, y, 1); // draw the ellipse at the pixle
      }
    }
  }
  noLoop();
}

你可以找到一个有效的例子。但请注意,这是为了演示。请花点时间理解代码。另外,当我们使用get查看画布上每个像素的颜色时,一旦运行,计算将花费很长时间。考虑一下每第二个像素,把椭圆画得稍微大一些

,因为你使用P5JS,你应该使用它提供的方法和功能。没有必要像使用p5js那样获得画布。p5js在您键入canvas时提供对它的引用

此时,您正在使用图像标记显示图像。相反,您希望在画布上显示图像。您可以使用p5的预加载方法来加载图像。然后,一旦加载了它,就可以在绘制方法中引用它

您的绘制方法将持续在循环上运行。但是,您不需要循环,因为您只需要进行一次计算。因此,您可以使用p5的方法noLoop来阻止draw循环

最后,要获得特定像素的颜色,需要使用getx,y。这将为您提供一个红色、绿色和蓝色值的数组。黑色像素表示这三个值均为0。但是,您的图像的像素不是严格意义上的黑色。例如,如果您的r g b红色、绿色和蓝色的颜色值为1、1、1,则您的颜色仍然看起来是黑色。因此,要检查给定颜色是否为黑色,您需要检查所有这些值是否小于特定数字,例如80

如果您将所有这些想法合并到您的代码中,您应该得到如下结果:

let img;

function preload() {
  img = loadImage('india-map.gif');
}

function setup() {
  createCanvas(400, 400);
}

function draw() {
  background(220);
  image(img, 0, 0, width, height);
  for(let x = 0; x < width; x++) {
    for(let y = 0; y < height; y++) {
      const [r, g, b] = get(x, y); // get colors
      if(r <= 80 && b <= 80 && g <= 80) { // if r g b all less than 80 then color will appear black
        noStroke(); // remove black outline from thing we are about to draw (the ellipse)
        fill(255, 0, 0); // make the ellipse red
        ellipse(x, y, 1); // draw the ellipse at the pixle
      }
    }
  }
  noLoop();
}

你可以找到一个有效的例子。但请注意,这是为了演示。请花点时间理解代码。另外,当我们使用get查看画布上每个像素的颜色时,一旦运行,计算将花费很长时间。考虑一下每第二个像素,把椭圆画得稍微大一点,

是Nick Parson优秀答案的一个微小的调整,但它是一个使用而不是得到的答案。这表明get是罪魁祸首

//tweak of Code from Nick Parsons

let img;

function preload() {
  img = loadImage('india-map.gif');
}

function setup() {
  createCanvas(400, 400);
}

function draw() {
  background(220);
  image(img, 0, 0, width, height);
  loadPixels();
  const d = pixelDensity();

  for (let x = 0; x < width; x++) {
    for (let y = 0; y < height; y++) {
      const i = 4 * d*(y * d*width + x);
      const [r, g, b] = [pixels[i], pixels[i + 1], pixels[i + 2]]; // get colors
      if (r <= 80 && b <= 80 && g <= 80) { // if r g b all less than 80 then color will appear black
        noStroke();
        fill(255, 0, 0);
        ellipse(x, y, 1);
      }
    }
  }
  noLoop();
}

尼克·帕森(Nick Parson)的优秀答案有点小的改动,但它使用而不是获取。这表明get是罪魁祸首

//tweak of Code from Nick Parsons

let img;

function preload() {
  img = loadImage('india-map.gif');
}

function setup() {
  createCanvas(400, 400);
}

function draw() {
  background(220);
  image(img, 0, 0, width, height);
  loadPixels();
  const d = pixelDensity();

  for (let x = 0; x < width; x++) {
    for (let y = 0; y < height; y++) {
      const i = 4 * d*(y * d*width + x);
      const [r, g, b] = [pixels[i], pixels[i + 1], pixels[i + 2]]; // get colors
      if (r <= 80 && b <= 80 && g <= 80) { // if r g b all less than 80 then color will appear black
        noStroke();
        fill(255, 0, 0);
        ellipse(x, y, 1);
      }
    }
  }
  noLoop();
}

您没有id为myCanvas的元素,因此document.getElementByIdmyCanvas;返回nullIn p5js您不需要获取画布,您可以使用Canvast引用它这是一种奇怪的混合p5.js和非p5.js图形编程方法。我对javascript和p5js不熟悉,并使用了一些来自互联网的代码片段。还有-什么是黑色?这不是p5.js函数。就学习p5.js而言,我强烈推荐Dan Shiffman在编码列车频道上的YouTube视频您没有id为myCanvas的元素,因此document.getElementByIdmyCanvas;在p5js中返回null,您不需要获取画布,可以参考
ence it using canvasThis是p5.js和non-p5.js图形编程方法的奇怪结合。我不熟悉javascript和p5js,并使用了一些来自互联网的代码片段。还有-什么是黑色?这不是p5.js函数。就学习p5.js而言,我强烈推荐Dan Shiffman在编码列车频道上的YouTube视频谢谢你的代码,但是当我运行它时,我会收到一条错误消息。它说,SyntaxError:jdk.nashoen.internal.ir.ForNode不能强制转换为jdk.nashorn.internal.ir.Block。这意味着什么?@BobTimmon该错误与此代码无关,但与您如何在网页中使用p5.js有关。在第一次学习时,像Nick在链接中所做的那样使用p5.js web编辑器可能是一个好主意,因为它可以为您处理一些HTML模板。@BobTimmon嗨Bob,正如John所说,您似乎试图以一种奇怪的方式使用p5。也许你可以试着玩一下网页编辑器。400^2只有16000。如果需要那么长的时间,那么一定是瓶颈。结果发现买东西有点贵。如果首先加载像素并直接使用像素,代码几乎立即运行。我修改了代码。评论太长了,所以我把它作为答案发布,但这是你的想法+1。谢谢你的代码,但当我运行它时,我收到一条错误消息。它说,SyntaxError:jdk.nashoen.internal.ir.ForNode不能强制转换为jdk.nashorn.internal.ir.Block。这意味着什么?@BobTimmon该错误与此代码无关,但与您如何在网页中使用p5.js有关。在第一次学习时,像Nick在链接中所做的那样使用p5.js web编辑器可能是一个好主意,因为它可以为您处理一些HTML模板。@BobTimmon嗨Bob,正如John所说,您似乎试图以一种奇怪的方式使用p5。也许你可以试着玩一下网页编辑器。400^2只有16000。如果需要那么长的时间,那么一定是瓶颈。结果发现买东西有点贵。如果首先加载像素并直接使用像素,代码几乎立即运行。我修改了代码。评论太长了,所以我把它作为答案发布,但这是你的想法+1。很好的修复,我没有想到使用loadPixels:DNice修复,我没有想到使用loadPixels:D