获得随机的非重复颜色

时间:2019-03-08 12:20:41

标签: javascript

我有一个返回随机颜色的函数。我将这些颜色放入数组。我不想在数组中重复颜色。所以我这样做了:

 $scope.getRandomColor = function getRandomColor(arrayToCheckIfAlreadyContains) {
    var letters = '0123456789ABCDEF';
    var color = '#';
    for (var i = 0; i < 6; i++) {
      color += letters[Math.floor(Math.random() * 16)];
    }
  //check if array contains the generated color
    if(arrayToCheckIfAlreadyContains.indexOf(color) >= 0){
     let nonRepeatColor = $scope.getRandomColor(arrayToCheckIfAlreadyContains);
     console.log("color repeated", color, arrayToCheckIfAlreadyContains);
     return nonRepeatColor;
    }

    return color;
  }

但是我不知道这是否有效,甚至可以肯定地起作用。同样,如果颜色是可区分的,那就太好了。有时我得到几乎相同的颜色。我如何确保不会发生这种情况。

3 个答案:

答案 0 :(得分:1)

posts/:id可以帮助您产生可区分的颜色。试试这个。

hsl

答案 1 :(得分:1)

您可以考虑使用hsl而不是十六进制表示法-为初始颜色选择一个介于0到359之间的数字,然后选择其他等距的颜色。例如:

function getColors(num) {
  const initialColor = Math.floor(Math.random() * 360);
  const increment = 360 / num;
  const hsls = [];
  for (let i = 0; i < num; i++) {
    hsls.push(Math.round((initialColor + (i * increment)) % 360));
  }
  return hsls;
}
function displayNew() {
  container.innerHTML = '';
  const hsls = getColors(input.value);
  hsls.forEach((hsl) => {
    const div = container.appendChild(document.createElement('div'));
    div.style.backgroundColor = 'hsl(' + hsl + ', 100%, 50%)';
  });
}
#container > div {
  height: 30px;
}
<input id="input" onkeyup="displayNew()" type="number">
<div id="container"></div>

答案 2 :(得分:1)

从您的代码中,如果颜色已经在数组中,我不太了解您在做什么:您是否要选择另一种随机颜色,直到找到一种不在数组中的颜色?

无论如何,由于您的第二个目标(可区分的颜色),我想您需要做一些额外的工作:每次选择随机颜色时,都需要检查其与数组中所有颜色的相似性!

类似以下内容:

getRandomColor = function getRandomColor(arrayToCheckIfAlreadyContains) {
    let colorFound = true;        
    let letters = '0123456789ABCDEF';

    do {
        colorFound = true;
        var randomColor = '#';
        for (var i = 0; i < 6; i++) {
            randomColor += letters[Math.floor(Math.random() * 16)];
        }

        arrayToCheckIfAlreadyContains.some(color => {
            if (distanceBetweenColor(color, randomColor) < TRESHOLD) {
                /* Branch taken when randomColor is too similar
                 *  to an already existing color. */
                colorFound = false;
                return true;
            }

            return false;
        });
    } while (!colorFound);
}

现在,如何实现distanceBetweenColor()?您应该使用Delta-E算法:我建议您以SO https://stackoverflow.com/a/15189004/6070423

阅读此答案

编辑:请注意使用some而不是forEach:这样做,一旦发现颜色太相似,便停止迭代。