我寫了一個從影像中提取像素顏色的網站。我通過在保存影像的畫布上使用getImageData來做到這一點。但是,我無法獲得此示例影像的正確值。
例如,當使用 Pillow 提取第一個像素顏色 (x=0, y=0) 時,它為 RGBA 顏色空間回傳 (49, 97, 172, 255)。
from PIL import Image
im = Image.open('image.png').convert('RGBA')
pix = im.load()
print(pix[0, 0])
Java 也給了我相同的結果:
BufferedImage bufferedImage = ImageIO.read(new File("image.png"));
int rawRGB = bufferedImage.getRGB(0, 0);
Color color = new Color(rawRGB);
但是,當我使用 HTML 畫布時,我通過 getImageData 獲得以下值:(27,98,178,255)。
let image = new Image();
const reader = new FileReader();
image.addEventListener('load', function () {
let canvas = document.createElement('canvas');
let ctx = canvas.getContext("2d");
canvas.width = this.width;
canvas.height = this.height;
ctx.drawImage(this, 0, 0);
let data = ctx.getImageData(0, 0, 1, 1).data;
document.getElementById('imageData').innerHTML = data;
});
image.addEventListener('load', function () {
let canvas = document.createElement('canvas');
let gl = canvas.getContext("webgl2");
gl.activeTexture(gl.TEXTURE0);
let texture = gl.createTexture();
gl.bindTexture(gl.TEXTURE_2D, texture);
const framebuffer = gl.createFramebuffer();
gl.bindFramebuffer(gl.FRAMEBUFFER, framebuffer);
gl.framebufferTexture2D(gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT0, gl.TEXTURE_2D, texture, 0);
gl.texImage2D(gl.TEXTURE_2D, 0, gl.RGBA, gl.RGBA, gl.UNSIGNED_BYTE, this);
gl.drawBuffers([gl.COLOR_ATTACHMENT0]);
let data = new Uint8Array(1 * 1 * 4);
gl.readPixels(0, 0, 1, 1, gl.RGBA, gl.UNSIGNED_BYTE, data);
document.getElementById('webGl').innerHTML = data;
});
reader.addEventListener('load', (event) => {
image.src = event.target.result;
});
var fileToRead = document.getElementById("yourFile");
fileToRead.addEventListener("change", function (event) {
var files = fileToRead.files;
if (files.length) {
reader.readAsDataURL(event.target.files[0]);
}
}, false);
<pre>Expected: 49,97,172,255<br>
ImageData: <span id="imageData"></span><br>
WebGL: <span id="webGl"></span><br></pre>
<input type="file" id="yourFile" name="file">
我不明白為什么會發生這種情況,或者瀏覽器是如何產生這些值的。我已經嘗試過 Chrome 和 Firefox,但它們顯示了相同的錯誤值。我已經閱讀了關于預乘 alpha 的內容,但我不知道這應該如何影響我的結果,因為圖片沒有使用 alpha 通道。任何幫助,將不勝感激!
uj5u.com熱心網友回復:
這是因為此影像的顏色組態檔設定為 P3,而 webGL 和 2D 背景關系的默認顏色空間是 sRGB,這意味著它們確實會轉換影像的顏色。
現在,有一個好訊息,canvas 2D API 最近得到了擴展以支持 P3 色彩空間,這在最新的 Chrome 和 Safari 瀏覽器中可用(Firefox 和 WebGL 應該很快就會跟進)。
要享受此功能,您需要使用以下colorSpace: "display-p3"選項創建背景關系:
const input = document.querySelector("input");
input.oninput = async(evt) => {
const canvas = document.createElement("canvas");
const ctx = canvas.getContext("2d", {
colorSpace: "display-p3"
});
if (!(ctx.getContextAttributes?.().colorSpace === "display-p3")) {
console.warn("your browser doesn't support the colorSpace setting");
}
const image = new Image();
image.src = URL.createObjectURL(input.files[0]);
await image.decode();
// not resizing the canvas to save memory since we're only interested in top-left pixel
ctx.drawImage(image, 0, 0);
const { data } = ctx.getImageData(0, 0, 1, 1);
console.log(data);
};
<input type="file">
轉載請註明出處,本文鏈接:https://www.uj5u.com/shujuku/393756.html
標籤:javascript html 图片 帆布 html5-canvas
下一篇:在影像懸停時顯示兩個按鈕
