独书先生 Menu

js颜色改变深浅 判断浅色自动加深

需求

工作中的需求,动态获取页面中的一个颜色值,应用到另一个元素的背景上,这样保持页面元素的颜色搭配比较统一。

难点

颜色值可以用户任意定义的,但是应用元素的文字字体颜色是固定白色的,这样如果用户定义的是浅色,那么应用元素的背景设置为浅色这个元素的文字就会看不清楚,如下

文字内容

方案

为了白色文字可以看清楚,考虑把浅色背景统一加深处理,已是深色不处理

效果如下(点击开始可随机显示浅色加深):

浅色区域
深色区域

 

代码

复制以下代码粘贴进html文件可以直接运行

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>change color</title>
    <style>
        .colordivContainer{overflow: hidden;}
        #colordiv{float:left;width:200px;height:100px;text-align:center;line-height:100px;font-size: 24px;font-weight: 700;color:#fff;background: #FFFF66; margin-right:10px;}
        #changediv{float:left;width:200px;height:100px;text-align:center;line-height:100px;font-size: 24px;font-weight: 700;color:#fff;background: #d7d73e}
        #isChange{float: left;}
        .colorbtn{margin:5px;border-radius: 5px;}
    </style>
</head>
<body>
    <div id="changeColorContainer">
            <div class="colordivContainer">
                    <div id="colordiv">浅色区域</div>
                    <div id="changediv">深色区域</div>
            </div>
            <button id="startColor" class="colorbtn">开始</button><button id="pauseColor" class="colorbtn">暂停</button>
    </div>

<script>
      //RGB颜色转化为16进制颜色
      function colorHex(str) {
            var reg = /^#([0-9a-fA-f]{3}|[0-9a-fA-f]{6})$/;
            var that = str;
            if (/^(rgb|RGB)/.test(that)) {
              var aColor = that.replace(/(?:\(|\)|rgb|RGB)*/g, "").split(",");
              var strHex = "#";
              for (var i = 0; i < aColor.length; i++) {
                var hex = Number(aColor[i]).toString(16);
                if (hex === "0") {
                  hex += hex;
                }
                strHex += hex;
              }
              if (strHex.length !== 7) {
                strHex = that;
              }
              return strHex;
            } else if (reg.test(that)) {
              var aNum = that.replace(/#/, "").split("");
              if (aNum.length === 6) {
                return that;
              } else if (aNum.length === 3) {
                var numHex = "#";
                for (var i = 0; i < aNum.length; i += 1) {
                  numHex += (aNum[i] + aNum[i]);
                }
                return numHex;
              }
            } else {
              return that;
            }   
      }
      //16进制颜色转化为RGB颜色
      function colorRgb(str) {
            var reg = /^#([0-9a-fA-f]{3}|[0-9a-fA-f]{6})$/;
            var sColor = str.toLowerCase();
            if (sColor && reg.test(sColor)) {
              if (sColor.length === 4) {
                var sColorNew = "#";
                for (var i = 1; i < 4; i += 1) {
                  sColorNew += sColor.slice(i, i + 1).concat(sColor.slice(i, i + 1));
                }
                sColor = sColorNew;
              }
              //处理六位的颜色值
              var sColorChange = [];
              for (var i = 1; i < 7; i += 2) {
                sColorChange.push(parseInt("0x" + sColor.slice(i, i + 2)));
              }
              return "rgb(" + sColorChange.join(",") + ")";
            } else {
              return sColor;
            }                   
      }
      //变暗变亮主方法
      function LightenDarkenColor (col, amt) {
            var usePound = false;

            if (col[0] == "#") {
              col = col.slice(1);
              usePound = true;
            }

            var num = parseInt(col, 16);

            var r = (num >> 16) + amt;

            if (r > 255) r = 255;
            else if (r < 0) r = 0;

            var b = ((num >> 8) & 0x00FF) + amt;

            if (b > 255) b = 255;
            else if (b < 0) b = 0;

            var g = (num & 0x0000FF) + amt;

            if (g > 255) g = 255;
            else if (g < 0) g = 0;


            return (usePound ? "#" : "") + String("000000" + (g | (b << 8) | (r << 16)).toString(16)).slice(-6);
      }
      //判断是否为亮色
      function getContrastYIQ(hexcolor) {
            var colorrgb = colorRgb(hexcolor);
            var colors = colorrgb.match(/^rgb\((\d+),\s*(\d+),\s*(\d+)\)$/);
            var red = colors[1];
            var green = colors[2];
            var blue = colors[3];
            var brightness;
            brightness = (red * 299) + (green * 587) + (blue * 114);
            brightness = brightness / 255000;
            if (brightness >= 0.5) {
              return "light";
            } else {
              return "dark";
            }
      }

      var startBtn = document.querySelector("#startColor"),
          pauseBtn = document.querySelector("#pauseColor");
      window.intervalSetColor = null;
      startBtn.addEventListener("click",function(e){
            if(intervalSetColor != null){
                clearInterval(intervalSetColor);
            }
        intervalSetColor = setInterval(function(){
                //获取随机颜色
                var color = "",findColor = true;
                while(findColor){
                    color = '#' +'0123456789abcdef'.split('').map(function(v,i,a){
                return i>5 ? null : a[Math.floor(Math.random()*16)] }).join('');
                    if(getContrastYIQ(color) == "light"){
                        findColor = false;
                    }
                }
            //自定义变暗参数,< 0为变暗,>0为变亮
                var amt = -40;

                document.querySelector("#colordiv").style.backgroundColor = color;
                document.querySelector("#changediv").style.backgroundColor = LightenDarkenColor(colorHex(color),amt); //调用核心方法处理浅色

        },1000)
      })
      pauseBtn.addEventListener("click",function(e){
            if(intervalSetColor != null){
                clearInterval(intervalSetColor);
            }

      })


</script>
</body>
</html>


https://appsoftea.com/zh/js-color-change-darken-and-shallow/