Getting RGB colors of selected area in an image

83 Views Asked by At

I have prepared a code that can give the average color of an image properly. But now I want users to select some area in that image and get average RGB values of that specific area.

For this purpose, I tried using the jCrop library and it also gave me the image x, y, width, and height values after selection. But when I apply these jCrop variables inside the getRGB function the function stops working.

<!DOCTYPE html>
<html>

<head>
  <meta charset="UTF-8">
  <title>Jcrop Example</title>
  <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/jquery-jcrop/0.9.15/css/jquery.Jcrop.css">
</head>

<body>
  <img id="img" src="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAGQAAABkCAIAAAD/gAIDAAABD0lEQVR4nOzSMQ0CYRgEUUJOAQUmMIEQapycA4IZbCEAA38z1ccl7ynYTHbb9+/p/zxe9+kJC+fpAUciViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFaw3a7v6Q0Ll+dnesKCZwViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgW/AAAA//+j+wYF8oSWtwAAAABJRU5ErkJggg=="
  />
  <div>
    <p class='inr'></p>
    <p class='ing'></p>
    <p class='inb'></p>
  </div>
  <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.8.2/jquery.min.js"></script>
  <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery-jcrop/0.9.15/js/jquery.Jcrop.js"></script>
  <script>
    $('#img').on('load change', function() {
      var rgb = getRGB(this);
      $('.inr').text(rgb.r);
      $('.ing').text(rgb.g);
      $('.inb').text(rgb.b);
    });

    function getRGB(img) {
      var dx, dy, dw, dh;
      $("#img").Jcrop({
        onSelect: function(c) {
          var dx = c.x,
            dy = c.y,
            dw = c.w,
            dh = c.h;
          console.log(dx, dy, dw, dh);
        }
      })
      var canvas = document.createElement('canvas'),
        context = canvas.getContext('2d'),
        rgb = {
          r: 0,
          g: 0,
          b: 0
        },
        i = -4,
        count = 0,
        height = canvas.height = img.naturalHeight,
        width = canvas.width = img.naturalWidth;
      context.drawImage(img, 0, 0);
      var data = context.getImageData(0, 0, width, height),
        length = data.data.length;
      while ((i += 4) < length) {
        ++count;
        rgb.r += data.data[i];
        rgb.g += data.data[i + 1];
        rgb.b += data.data[i + 2];
      }
      rgb.r = (rgb.r / count);
      rgb.g = (rgb.g / count);
      rgb.b = (rgb.b / count);
      return rgb;
    }
  </script>
</body>

</html>

1

There are 1 best solutions below

0
Paul WWJD On

Here's an example how to get the color of the clicked point.

  1. Event handler was changed to click (to actually process click event with its XY coordinates)
  2. Position can be managed by shifting an image width Y times and then shifting by X pixels from the left side.

You can try it and then extend processed point to selected area.

$('#img').on('click', function(e) {
    var rgb = getRGB(this);
    $('.inr').text(rgb.r);
    $('.ing').text(rgb.g);
    $('.inb').text(rgb.b);
});

function getRGB(img) {
    var dx, dy, dw, dh;
    $("#img").Jcrop({
        onSelect: function(c) {
            var dx = c.x,
                dy = c.y,
                dw = c.w,
                dh = c.h;
            console.log(dx, dy, dw, dh);
        }
    })
    var canvas = document.createElement('canvas'),
        context = canvas.getContext('2d'),
        rgb = {
            r: 0,
            g: 0,
            b: 0
        },
        height = canvas.height = img.naturalHeight,
        width = canvas.width = img.naturalWidth;
    context.drawImage(img, 0, 0);
    var data = context.getImageData(0, 0, width, height),
        length = data.data.length;
    var position = (width * event.offsetY + event.offsetX) * 4;
    rgb.r = data.data[position];
    rgb.g = data.data[++position];
    rgb.b = data.data[++position];
    return rgb;
}
<html>
  <head>
    <meta charset="UTF-8">
    <title>Jcrop Example</title>
    <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/jquery-jcrop/0.9.15/css/jquery.Jcrop.css">
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.8.2/jquery.min.js"></script>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery-jcrop/0.9.15/js/jquery.Jcrop.js"></script>
  </head>
  <body>
    <img id="img" src="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAGQAAABkCAIAAAD/gAIDAAABD0lEQVR4nOzSMQ0CYRgEUUJOAQUmMIEQapycA4IZbCEAA38z1ccl7ynYTHbb9+/p/zxe9+kJC+fpAUciViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFaw3a7v6Q0Ll+dnesKCZwViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgViBWIFYgW/AAAA//+j+wYF8oSWtwAAAABJRU5ErkJggg=="/>
    <div>
      <p class='inr'></p>
      <p class='ing'></p>
      <p class='inb'></p>
    </div>
    </body>
</html>