2017-07-16 76 views
0

我想检测下图中图标的宽度(右手指) 。如何使用javascript检测图像内图标的宽度?

enter image description here

我假设可能的解决方案可能涉及color removal illustrated in this approach,其可以被用于去除在这种情况下,lightblue背景颜色。但是我不确定去除颜色后的下一步。

+0

我想我发现[A溶液](https://stackoverflow.com/a/12178531/1091014)。我将尝试使用该解决方案来实现它,但欢迎任何更好的解决方案。 –

回答

1

我想出了一些东西!

我是这样做的:

  1. 使用<img>标记的图像添加到文档(无论是通过普通的OLE-HTML或JS)
  2. 创建2D canvas元素,使它的尺寸相同大小的IMG
  3. 绘制图像投影到使用context.drawImage
  4. 使用context.getImageData获得的像素的颜色在画布
  5. TRANSFO画布RM此原始数的阵列,以十六进制字符串颜色
  6. 组的颜色由图像
  7. 抓取的图像的第一颜色作为colorToFilter
  8. 的行到行创建minXminYmaxX,和maxY变量保持不属于colorToFilter
  9. 迭代穿过pixelMatrix每个像素检查是否当前rowcolumn或比色小于或大于不属于colorToFilter
  10. 像素的轨道
  11. maxX - minXmaxY - minY的差值,这就是您的尺寸!

仅供参考:由于交叉来源问题,我使用图像src的数据uri。

让我知道你是否需要更多的解释。这个解决方案可能不是最有效的,但它的工作原理!

/** 
 
* converts a number from 0-255 to a hex number padded with a zero if necessary 
 
* @param {number} number 
 
*/ 
 
function toHex(number) { 
 
    const numberAsString = Number(number).toString(16); 
 
    return numberAsString.length === 1 ? '0' + numberAsString : numberAsString; 
 
} 
 

 
/** 
 
* Grabs the pixel colors from an image and stores it in a matrix 
 
* @param {HTMLImageElement} img 
 
*/ 
 
function convertImageToPixelData(img) { 
 
    // credit for getting the color of pixel comes from here: 
 
    // https://stackoverflow.com/questions/8751020/how-to-get-a-pixels-x-y-coordinate-color-from-an-image 
 
    const canvas = document.createElement('canvas'); 
 
    const imgWidth = img.clientWidth; 
 
    const imgHeight = img.clientHeight; 
 
    canvas.width = imgWidth; 
 
    canvas.height = imgHeight; 
 
    const context = canvas.getContext('2d'); 
 
    context.drawImage(img, 0, 0, imgWidth, imgHeight); 
 

 
    const rawPixelData = context.getImageData(0, 0, imgWidth, imgHeight).data; 
 

 
    // convert to hex string 
 
    const pixelColors = rawPixelData.reduce((groups, pixelColor, index) => { 
 
    if (index % 4 === 3) { // skip the alpha channel 
 
     return groups; 
 
    } 
 
    if (groups[groups.length - 1].length === 6) { 
 
     groups.push(''); 
 
    } 
 
    groups[groups.length - 1] += toHex(pixelColor); 
 
    return groups; 
 
    }, ['']); 
 

 
    // convert to matrix 
 
    /** 
 
    * @type {string[][]} 
 
    */ 
 
    const pixelMatrix = pixelColors.reduce((matrix, pixel) => { 
 
    const currentRow = matrix[matrix.length - 1]; 
 
    if (currentRow.length < imgWidth) { 
 
     currentRow.push(pixel); 
 
    } else { 
 
     matrix.push([pixel]); 
 
    } 
 
    return matrix; 
 
    }, [[]]); 
 
    return pixelMatrix; 
 
} 
 

 
/** 
 
* finds the dimensions of an icon inside a single colored image 
 
* @param {HTMLImageElement} img 
 
*/ 
 
function findBox(img) { 
 
    const pixelMatrix = convertImageToPixelData(img); 
 
    const colorToFilter = pixelMatrix[0][0]; 
 

 
    const imgWidth = img.clientWidth; 
 
    const imgHeight = img.clientHeight; 
 

 
    let maxX = 0; 
 
    let minX = imgWidth; 
 
    let maxY = 0; 
 
    let minY = imgHeight; 
 

 
    // for each pixel calculate if the index of the pixel is greater than the current max or min 
 
    for (let row = 0; row < imgHeight; row += 1) { 
 
    for (let column = 0; column < imgWidth; column += 1) { 
 
     const pixel = pixelMatrix[row][column]; 
 
     if (pixel !== colorToFilter) { 
 
     if (column < minX) { 
 
      minX = column; 
 
     } 
 
     if (column > maxX) { 
 
      maxX = column; 
 
     } 
 
     if (row < minY) { 
 
      minY = row; 
 
     } 
 
     if (row > maxY) { 
 
      maxY = row; 
 
     } 
 
     } 
 
    } 
 
    } 
 

 
    const width = maxX - minX + 1; 
 
    const height = maxY - minY + 1; 
 

 
    return { width, height }; 
 
} 
 

 
const img = document.querySelector('#my-image'); 
 

 
const box = findBox(img); 
 
console.log(box);
<img id="my-image" src="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAJYAAABkCAIAAADrOV6nAAAFUklEQVR42u3caVPaXByG8X7/D+AuakXBBQVFgiRhJyAgCpElICSAJkFQcFdQLKCt6/NYW8LWe+Z6pTOO429O+J+TxG+6hIj6um/4E4AQgRCBEIT4K4AQgRCBEIQIhAiECIQgRCBEIEQgBCECIQIhAiEIEQgRCBEIQYhA2DvlyQglOqclSiV5LKE4CPuntVggtbUkUyMiMSSaJ4u+leskUdv3JTgQ9nLxfVfYnvcuyNRoU44Yke3q8o7xTqAfsk9VMwkQ9thSC5hEz4LsmJbJR7YhyTJ55NJUwut3/LPcc/weCHskjvPOSubGRXJUts+WGO1pSHcRJWpp6gO2F92kQNgLRd2ifay55kj1WfITs1cJ+mIgDsIuT5juHZ3cWHzEsOxcvhXor/gZK475HItxppvTSjTjUUnNCXOiFDLVs1/wqyd0JXpY8mytYlPRtcklapXo1g6Bnjv/ysXznls7dasan5qS3ezDvrBbF89AUNu6eI4UmNXq71w8+c0bVldmZgqPY6p5QmR8loH262HC+HbeOd5imDqJmP//4lkXTJd+TdE2JrV2Fw1yyarJMh579AAHbN3JtLsuk8PNrZ5Nc/m7F0/yLrpSdk1KxHjOG1mNZcyRpDkSdfo9ga1WXjLmWE+04pyGDD2VJ191QKoOP+rAsZx3PabPBax8nHVxhyD8bNvXXEljRz5D7SuTy9NHIG+5SxHVpOUyYihvr75rpbGPPPu8pTKjLrmbFe2TMjUubw6LT0u8saWZKYV3LCD8aHJxSrbW5GKZLrObD1/3UzbBUkuuXwS1ReuoaFYV2QwIX/uFjbKldU5mX7zm6Z7ze7PWo4ulLZsVhC+GF3vLb7jA/MnFsyvVUsw2CH+141U1159L1y9+rfwsCH/mlajGEpyqcH3k1/hoDLlB+FSMkBsjjGP5rp+WIH2b4TDO/CyibxAWfMY+8qsLARabiq4QVlndOWu+4R1V4VfWL/4Q2zUf8XDY2r9sz6g04T2nr7i+N+9yJFbLzgmJ1PBs/r9+Hz0nWJP8y/z7bCrdaC+UFEw4YPsoSilCfvM6vHhsG5cd2hcHddRt8LtE63dwRtq+giI9JLpW2rxviy6duNUlRnseJ999l7rwzIosCNt3U0lwDon2xWonRxLOUNgDYfsKN7b25PxVR6dKl5gCYRsPSIPzIjFzmv4Xz1YG5Yx0RycR48dsB084+ZgehG0/oCkGLR3xs1b5XR/u2rc7j0QOycyaAvuKjXPf/LFfX8vS19tzJe/6/sA9jdEjhKmco83HpPW08YyZkqmZ8vOjN1Q1ojmyzGR3QahAMc9424bStPHUqy6558rba++fe6vHtAUXvQbCtkf51Z0aSqmr4EYYhMoMpaPH4Y5MpPveXRAqNJQeBYhOEPIRAoQK5BfpIcmj78Cm4jSdwzijSBnXsGhduFXWz1lJp/XYVCg50cyeCcps5wW/mE7YB/GN+156mpvdkNs00bTu8aoKTu0FRz4IpnPfbIGalgKRtQQIlS2es/3VGc39/vpFaKn5ZgU9W3nzMo1gPnNNS7sgVPqFmKBGojRXf/XMPFFNbt5//F1DJZwGodLt5unRUphSaJyppA9BqHirYYNs1d7gNm9fv19oDy4UfMa6As9fMxhnOpYltHEUIdtK6DlMDeBVtLfftY/nHKmwzDM3gqOatf75Xaes8yLTWw/v/jv/LuFNh6bmg7mJeJrlM4ET3n/28ePY1lrr6zeCr5hhQ8mcPjGweH1HiEAIQgRCBEIEQhAiECIQIhCCEIEQgRCBEIQIhAiECIQgRCBEIEQgBCECIQIhAiEIUe/0A1MOqyYF+UAcAAAAAElFTkSuQmCC">

+0

看起来很棒!你的方法更清洁,更有组织。非常感谢! –

相关问题