如何将颜色在RGB格式转换为十六进制格式,反之亦然?

例如,将'#0080C0'转换为(0,128,192)。


当前回答

当你在3D环境中工作时(webGL, ThreeJS),你有时需要为网格的不同面创建3个值,基本的一个(主色),一个浅一点的和一个深一点的:

material.color.set( 0x660000, 0xff0000, 0xff6666 ); // red cube

我们可以从主RBG颜色创建这3个值:255,0,0

function rgbToHex(rgb) { 
  var hex = Number(rgb).toString(16);
  if (hex.length < 2) {
       hex = "0" + hex;
  }
  return hex;
};

function convertToHex(r,g,b) { 

    var fact = 100;  // contrast 
    var code = '0x';

    // main color
    var r_hexa = rgbToHex(r);
    var g_hexa = rgbToHex(g);
    var b_hexa = rgbToHex(b);

    // lighter
    var r_light = rgbToHex(Math.floor(r+((1-(r/255))*fact)));
    var g_light = rgbToHex(Math.floor(g+((1-(g/255))*fact)));
    var b_light = rgbToHex(Math.floor(b+((1-(b/255))*fact)));

    // darker
    var r_dark = rgbToHex(Math.floor(r-((r/255)*(fact*1.5)))); // increase contrast
    var g_dark = rgbToHex(Math.floor(g-((g/255)*(fact*1.5))));
    var b_dark = rgbToHex(Math.floor(b-((b/255)*(fact*1.5))));

    var hexa = code+r_hexa+g_hexa+b_hexa;
    var light = code+r_light+g_light+b_light;
    var dark = code+r_dark+g_dark+b_dark;

    console.log('HEXs -> '+dark+" + "+hexa+" + "+light)

    var colors = [dark, hexa, light]; 
    return colors;

}

在你的ThreeJS代码中简单地写:

var material = new THREE.MeshLambertMaterial();
var c = convertToHex(255,0,0); // red cube needed
material.color.set( Number(c[0]), Number(c[1]), Number(c[2]) );

结果:

//                                 dark      normal     light
convertToHex(255,255,255) HEXs -> 0x696969 + 0xffffff + 0xffffff
convertToHex(255,0,0) HEXs -> 0x690000 + 0xff0000 + 0xff6464
convertToHex(255,127,0) HEXs -> 0x690000 + 0xff0000 + 0xff6464
convertToHex(100,100,100) HEXs -> 0x292929 + 0x646464 + 0xa0a0a0
convertToHex(10,10,10) HEXs -> 0x040404 + 0x0a0a0a + 0x6a6a6a

其他回答

哇。这些答案都不能处理分数的边缘情况,等等。当r, g, b为零时,位移版本也不起作用。

这是一个可以处理r g b是小数的版本。它对颜色之间的插值很有用,所以我也包括了这段代码。但它仍然不能处理r, g, b在0-255范围之外的情况

/**
 * Operates with colors.
 * @class Q.Colors
 */
 Q.Color = {
    /**
     * Get a color somewhere between startColor and endColor
     * @method toHex
     * @static
     * @param {String|Number} startColor 
     * @param {String|Number} endColor 
     * @param {String|Number} fraction 
     * @returns {String} a color as a hex string without '#' in front
     */
    toHex: function (r, g, b) {
        return [r, g, b].map(x => {
            const hex = Math.round(x).toString(16)
            return hex.length === 1 ? '0' + hex : hex
          }).join('');
    },
    /**
     * Get a color somewhere between startColor and endColor
     * @method between
     * @static
     * @param {String|Number} startColor 
     * @param {String|Number} endColor 
     * @param {String|Number} fraction 
     * @returns {String} a color as a hex string without '#' in front
     */
    between: function(startColor, endColor, fraction) {
        if (typeof startColor === 'string') {
            startColor = parseInt(startColor.replace('#', '0x'), 16);
        }
        if (typeof endColor === 'string') {
            endColor = parseInt(endColor.replace('#', '0x'), 16);
        }
        var startRed = (startColor >> 16) & 0xFF;
        var startGreen = (startColor >> 8) & 0xFF;
        var startBlue = startColor & 0xFF;
        var endRed = (endColor >> 16) & 0xFF;
        var endGreen = (endColor >> 8) & 0xFF;
        var endBlue = endColor & 0xFF;
        var newRed = startRed + fraction * (endRed - startRed);
        var newGreen = startGreen + fraction * (endGreen - startGreen);
        var newBlue = startBlue + fraction * (endBlue - startBlue);
        return Q.Color.toHex(newRed, newGreen, newBlue);
    },
    /**
     * Sets a new theme-color on the window
     * @method setWindowTheme
     * @static
     * @param {String} color in any CSS format, such as "#aabbcc"
     * @return {String} the previous color
     */
    setWindowTheme: function (color) {
        var meta = document.querySelector('meta[name="theme-color"]');
        var prevColor = null;
        if (meta) {
            prevColor = meta.getAttribute('content');
        }
        if (color) {
            if (!meta) {
                meta = document.createElement('meta');
                meta.setAttribute('name', 'theme-color');
            }
            meta.setAttribute('content', color);
        }
        return prevColor;
    },
    /**
     * Gets the current window theme color
     * @method getWindowTheme
     * @static
     * @param {String} color in any CSS format, such as "#aabbcc"
     * @return {String} the previous color
     */
    getWindowTheme: function () {
        var meta = document.querySelector('meta[name="theme-color"]');
        return meta.getAttribute('content');
    }
}
function hex2rgb(hex) {
  return ['0x' + hex[1] + hex[2] | 0, '0x' + hex[3] + hex[4] | 0, '0x' + hex[5] + hex[6] | 0];
}

相当简单的一行。用逗号分隔rgb,忽略非数字,转换为十六进制,填充0,并以hashbang结束。

Var yellow = 'rgb(255,255,0)'; Var rgb2hex = STR => "#"+ STR .split(',')。map(s => (s.replace(/\D/g, ")|0). tostring(16))。Map (s => s.length < 2 ?"0"+s: s).join("); console.log (rgb2hex(黄色));

@ Tim,补充一下你的答案(把这个放进评论里有点尴尬)。

正如所写的,我发现rgbToHex函数返回一个包含元素的字符串,它要求r, g, b值落在0-255的范围内。

我相信这对大多数人来说是显而易见的,但我花了两个小时才弄明白,到那时,原来的方法已经膨胀到7行,直到我意识到我的问题在其他地方。因此,为了节省其他人的时间和麻烦,下面是我稍微修改过的代码,它检查了先决条件,并删除了字符串中无关的部分。

function rgbToHex(r, g, b) {
    if(r < 0 || r > 255) alert("r is out of bounds; "+r);
    if(g < 0 || g > 255) alert("g is out of bounds; "+g);
    if(b < 0 || b > 255) alert("b is out of bounds; "+b);
    return "#" + ((1 << 24) + (r << 16) + (g << 8) + b).toString(16).slice(1,7);
}

我发现了这个… http://jsfiddle.net/Mottie/xcqpF/1/light/

function rgb2hex(rgb){
    rgb = rgb.match(/^rgba?[\s+]?\([\s+]?(\d+)[\s+]?,[\s+]?(\d+)[\s+]?,[\s+]?(\d+)[\s+]?/i);
    return (rgb && rgb.length === 4) ? "#" +
        ("0" + parseInt(rgb[1],10).toString(16)).slice(-2) +
        ("0" + parseInt(rgb[2],10).toString(16)).slice(-2) +
        ("0" + parseInt(rgb[3],10).toString(16)).slice(-2) : '';
}