【问题标题】:Get Color at position Webgl在 Webgl 位置获取颜色
【发布时间】:2017-05-19 21:08:51
【问题描述】:

我想在 Chrome 控制台中调试我的 html5 画布。我想获取位置 (445, 650) 的像素颜色。

我尝试使用此代码:

var example = document.getElementById('glcanvas');
var context = example.getContext('webgl');
var pixels = new Uint8Array(context.drawingBufferWidth * context.drawingBufferHeight * 4); 
var data = context.readPixels(445, 650, context.drawingBufferWidth, context.drawingBufferHeight, context.RGBA, context.UNSIGNED_BYTE, pixels);

当我逐行运行这些行时,我得到:

example
<canvas class="topleft" id="glcanvas" width="479" height="716" tabindex="1" contenteditable="true" style="cursor: default; width: 479px; height: 616px;"></canvas>

context
WebGLRenderingContext {vertexAttribDivisor: function, drawArraysInstanced: function, drawElementsInstanced: function, createVertexArray: function, deleteVertexArray: function…}

data
undefined

如何获取非未定义数据?我只是想在 (445, 650) 位置获取 HEX 中的像素颜色

第二次尝试:

var pixels = new Uint8Array(
    4 * context.drawingBufferWidth * context.drawingBufferHeight
);
var x = 445; 
var y = 650;
context.readPixels(
    0,
    0,
    context.drawingBufferWidth,
    context.drawingBufferHeight,
    context.RGBA,
    context.UNSIGNED_BYTE,
    pixels
);
var pixelR = pixels[4 * (y * context.drawingBufferWidth + x)];
var pixelG = pixels[4 * (y * context.drawingBufferWidth + x) + 1];
var pixelB = pixels[4 * (y * context.drawingBufferWidth + x) + 2];
var pixelA = pixels[4 * (y * context.drawingBufferWidth + x) + 3];

所有像素都返回0,包括:

pixels
Uint8Array(2268552) [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0…]

【问题讨论】:

    标签: javascript html debugging canvas webgl


    【解决方案1】:

    readPixels 函数确实没有返回任何有用的信息。你感兴趣的像素数据复制到pixels数组:

    var pixels = new Uint8Array(
        4 * context.drawingBufferWidth * context.drawingBufferHeight
    );
    context.readPixels(
        0,
        0,
        context.drawingBufferWidth,
        context.drawingBufferHeight,
        context.RGBA,
        context.UNSIGNED_BYTE,
        pixels
    );
    // And here's components of a pixel on (x, y):
    var pixelR = pixels[4 * (y * context.drawingBufferWidth + x)];
    var pixelG = pixels[4 * (y * context.drawingBufferWidth + x) + 1];
    var pixelB = pixels[4 * (y * context.drawingBufferWidth + x) + 2];
    var pixelA = pixels[4 * (y * context.drawingBufferWidth + x) + 3];
    

    这里的xy 是您要检查的像素的坐标。

    【讨论】:

    • 所有这 4 个新像素都返回 0 :(
    • @TSR 如果你没有画任何东西,那么这些值是正确的,画布中所有像素的所有组件都被初始化为 0。
    • @KirillDmitrenko 有点晚了,但是这个解决方案不是很慢吗?对于每个鼠标事件,我最多需要检查两个像素,所以我认为这将是非常糟糕的(或者可能不会那么糟糕?)什么是不强制同步的替代方案?
    • @synchronizer 是的,由于 readPixel 的同步特性以及浏览器实际获取该像素所需的大量工作,它可能会成为瓶颈。我在我的应用程序中所做的是读取帧缓冲区区域而不是单个像素并缓存读取数据。由于鼠标移动非常连续,因此下一次“查找”很有可能会进入该缓存区域。
    • @KirillDmitrenko 嗯...我明白了。就我而言,我刚刚意识到我只会在图像没有变化时检查像素。这是否意味着当没有绘制任何新内容并检查这些像素时,我可以从帧缓冲区缓存一些内容?始终保持 640 x 480 的缓存是“好的”(不是太多的内存)。
    【解决方案2】:

    它说,你的画布只有 616 的高度,所以像素在画布之外。

    【讨论】:

    • 这不是问题。在帧缓冲区之外读取像素是 WebGL 中定义的行为,所有像素都将设置为 (0, 0, 0, 0)。
    猜你喜欢
    • 2019-02-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-06-10
    • 1970-01-01
    相关资源
    最近更新 更多