2012-07-23 101 views
6

可能重複:
Convert RGBA color to RGB轉換RGBA到RGB考慮背景考慮

我嘗試轉換RGBA顏色,具有阿爾法< 1成固體RGB表示服用考慮背景顏色。

使用提供的算法this question我設法得到正確的轉換爲固體RGB顏色 - 但只有當alpha = 0.5。

這裏是我的測試代碼:

<!DOCTYPE html> 
<html> 
<head></head> 
<body> 
    <script type="text/javascript"> 
    // Basic RGB(A) to CSS property value 
    function _toString(obj) { 
     var type = 'rgb', out = obj.red + ', ' + obj.green + ', ' + obj.blue; 

     if (obj.alpha !== undefined) { 
      type += 'a'; 
      out += ', ' + obj.alpha; 
     } 

     return type + '(' + out + ')'; 
    } 

    // Background color, assume this is always RGB 
    var bg = {red: 255, green: 51, blue: 0}; 
    // RGBA color 
    var RGBA = {red: 0, green: 102, blue: 204, alpha: 0}; 
    // Output RGB 
    var RGB = {red: null, green: null, blue: null}; 
    // Just a cache... 
    var alpha; 

    while (RGBA.alpha < 1) { 
     alpha = 1 - RGBA.alpha; 
     RGB.red = Math.round((alpha * (RGBA.red/255) + ((1 - RGBA.alpha) * (bg.red/255))) * 255); 
     RGB.green = Math.round((alpha * (RGBA.green/255) + ((1 - RGBA.alpha) * (bg.green/255))) * 255); 
     RGB.blue = Math.round((alpha * (RGBA.blue/255) + ((1 - RGBA.alpha) * (bg.blue/255))) * 255); 

     document.write('<div style="display: block; width: 150px; height: 100px; background-color: ' + _toString(bg) + '">\ 
      <div style="color: #fff; width: 50px; height: 50px; background-color: ' + _toString(RGBA) + '"><small>RGBA<br>' + RGBA.alpha + '</small></div>\ 
      <div style="color: #fff; width: 50px; height: 50px; background-color: ' + _toString(RGB) + '"><small>RGB<br>' + RGBA.alpha + '</small></div>\ 
     </div>'); 

     // Increment alpha 
     RGBA.alpha += 0.25; 
    } 
    </script> 
</body> 
</html> 

運行上面的兩個Chrome和Firefox結果成功RGBA-> RGB當α0.5,在不匹配的任何偏差0.5結果遠離,如果非常微妙偏差非常小(即當alpha爲0.55時可能會注意到問題)。

我已經多次重寫邏輯,將邏輯完全擴展到最基本的部分,但是我沒有成功。

回答

7

它看起來像你試圖使用普通的方法進行混合,但增量循環會把我扔掉。從OpenGL常見問題解答中抽取:

「上述[用於混合]的典型用法通過其相關的alpha值修改傳入顏色,然後將目標顏色修改一個減去傳入的alpha值,然後這兩種顏色的總和寫回幀緩衝區。「

因此,而不是一個while循環,使用:

alpha = 1 - RGBA.alpha; 
RGB.red = Math.round((RGBA.alpha * (RGBA.red/255) + (alpha * (bg.red/255))) * 255); 
RGB.green = Math.round((RGBA.alpha * (RGBA.green/255) + (alpha * (bg.green/255))) * 255); 
RGB.blue = Math.round((RGBA.alpha * (RGBA.blue/255) + (alpha * (bg.blue/255))) * 255); 
+0

完美!將邏輯更改爲您自己的(在背景上使用計算的alpha而不是前景),我可以得到由循環確定的變化alpha的正確值!好樣的! – seeSaw 2012-07-23 15:17:39