问题标签 [putimagedata]

For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.

0 投票
1 回答
309 浏览

javascript - PutImageData 出现黑屏

我有一个从 webgl 程序传递的像素数据数组。然后我处理像素数据以进行绿色筛选并将结果输出到 2d 画布中。考虑到我是 Canvas 2d 的新手,我的问题是,如何正确地将图像数据传递到画布。

0 投票
2 回答
54 浏览

javascript - 使用 putImageData 时我没有正确使用循环

我正在从文件中读取 rgb 值并尝试将它们放在画布上。

在此处输入图像描述

我尝试了许多不同的循环和增量值变体。

JavaScript:

数据格式示例:

我正在将 rgb 值添加到画布上,但它是我希望的大小的 1/4。我想要变量中 rgb 值的精确副本。

0 投票
1 回答
242 浏览

javascript - 为什么我的画布噪点功能总是只显示红色?

我正在尝试根据我看到的codepen对我的画布应用噪音效果,这又看起来与SO answer非常相似。

我想产生一个随机透明像素的“屏幕”,但我得到一个完全不透明的红色字段。我希望更熟悉画布或类型化数组的人可以告诉我我做错了什么,也许可以帮助我理解一些在起作用的技术。


我显着重构了 codepen 代码,因为(现在)我不关心动画噪声:

据我所知,正在发生的事情的核心是我们将ImageData的原始数据表示(一系列 8 位元素,它们依次反映每个像素的红色、绿色、蓝色和 alpha 值)在一个32 位数组,它允许我们将每个像素作为一个联合元组进行操作。我们得到一个每个像素一个元素而不是每个像素四个元素的数组。

然后,我们遍历该数组中的元素,根据我们的噪声逻辑将 RGBA 值写入每个元素(即每个像素)。这里的噪声逻辑非常简单:每个像素都有约 50% 的机会成为“噪声”像素。

噪声像素被分配了 32 位值0x00000088,这(感谢阵列提供的 32 位分块)相当于rgba(0, 0, 0, 0.5)50% 的不透明度,即黑色。

非噪声像素被分配32位值0x00000000,即黑色0%不透明度,即完全透明。

有趣的是,我们不会将 写到buffer32画布上。相反,我们编写了imageData用于构造 的Uint32Array,这让我相信我们正在通过某种传递引用来改变 imageData 对象;我不清楚这是为什么。我知道值和引用传递通常在 JS 中是如何工作的(标量通过值传递,对象通过引用传递),但是在非类型化数组世界中,传递给数组构造函数的值只决定了数组的长度。这显然不是这里发生的事情。


如前所述,我得到的不是一个 50% 或 100% 透明的黑色像素场,而是一个全实心像素场,全是红色。我不仅不希望看到红色,而且随机颜色分配的证据为零:每个像素都是纯红色。

通过使用两个十六进制值,我发现这会在黑色上产生红色的散射,具有正确的分布:

但它仍然是纯红色,纯黑色。没有任何底层画布数据通过应该不可见的像素显示。

令人困惑的是,除了红色或黑色之外,我找不到任何颜色。除了 100% 不透明,我也无法获得任何透明度。为了说明断开连接,我删除了随机元素并尝试将这九个值中的每一个写入每个像素,看看会发生什么:

这是怎么回事?


Uint32Array编辑:根据MDN 关于以下内容的文章,ImageData.data在消除了和诡异的突变后的类似(坏)结果:

0 投票
0 回答
131 浏览

canvas - 避免两个完整副本从 WebAssembly 更新画布?

在 JavaScript 中,我可以直接操作画布的像素并使用单个副本刷新它们:

但是在 wasm 中,我们必须TypedArray使用 wasm 内存分配我们自己的内存,然后我们可以使用imageData.data.set(myTypedArray)但是这似乎只是将新类型数组的全部内容复制到画布的类型数组中,它仍然必须跟随putImageData,复制整个内容 a第二次。

有什么方法可以将画布的 ImageData 重新分配给我们的新 ImageData,以便我们可以只使用一个副本更新画布ctx.putImageData()

如果不是这样,使用 wasm 操作图像的大部分好处似乎都会被低效的双重复制和双重内存表示所浪费,尤其是在处理大图像和/或不断更新画布时。

0 投票
1 回答
28 浏览

javascript - 从 ImageData 数组生成水平精灵图像

我正在尝试从 ImageData 数组构建一个水平透明图像,它将用作动画的精灵图像。您能否解释一下,如何将帧传递给更宽的画布(宽度 X countFrames)以及如何在迭代中移动 ImageData 宽度的偏移量?谢谢你。

0 投票
0 回答
69 浏览

javascript - 画布上下文 putImageData:由于浏览器优化导致的数据丢失

我正在研究涉及使用ImageData. 在MDN 文档的这个页面上,文章说:

由于与预乘 alpha 颜色值相互转换的有损特性,刚刚使用 putImageData() 设置的像素可能会作为不同的值返回给等效的 getImageData()。

并举了这样一个例子:

此示例中的输出是

这是违反直觉的,以至于我用我的代码解决了 2 天的搜索问题,并且没想到它实际上可以如此奇怪地工作。

所以,这篇文章没有说的是为什么会发生这种情况以及我该如何解决这个问题。我应该怎么做才能确保我的putImageData调用将导致之后返回完全相同的数据getImageData

在我看到这种方式之前,我一直在使用完全不透明的(每个第 4 个元素是 255 个)画布。这是确保在调用时不会以某种方式修改其余数据的唯一方法putImageData吗?

0 投票
0 回答
49 浏览

javascript - D3.js 性能问题,scaleDivergingSymlog 可以返回 RGB 值而不是字符串吗?

我正在使用 D3.js创建一个不同的规模:

然后我可以打电话scaleDiverging(0.05),我会得到'rgb(87, 175, 165)'. 这很好用,只是我需要canvas用 RGB 整数填充图像。所以我必须解析从返回的那些字符串scaleDiverging

简单的解决方案,但这是我的应用程序花费大部分时间的问题部分,也是我的交互式图形不流畅的原因。您移动一个滑块,2 秒后图像发生变化。如果我parseRgb用一个不准确地返回数字数组的简单函数替换,则图形是平滑的!我需要 CanvasputImageData函数的 RGB 值数组:

我可以scaleDivergingSymlog从不需要解析结果字符串的 D3.js 获得功能吗?我知道我可以自己查找代码并实现它,但是,除了避免这项工作之外,我还想知道将来如何正确使用 D3.js 来制作交互式图表。

stackoverflow 上的其他人也有类似的问题,唯一的答案是使用d3.color. 这与我上面的功能基本相同parseRgb,但性能更差:(。

0 投票
0 回答
38 浏览

javascript - 修改 ImageData 时画布看起来被拉伸

我正在尝试将我的一个处理项目(请参阅项目的 Github 页面)移植到 vanilla Javascript,但我遇到了将数据从一个 ImageData 对象“移植”到另一个 ImageData 对象的问题。我可以用一个颜色的矩形填充画布的一个区域就好了,但由于某种原因,同样不适用于图像。

这是我用来将 ImageData 的一个区域放入另一个图像数据区域的代码。

这是我用来从 x 和 y 值获取 ImageData 索引的函数

这是我用来将矩形放到画布上的函数。注意它与image()函数的相似程度

没有图像就无法真正显示问题,因此这里是带有 Godot 徽标图像的画布图像。(这就是我所说的拉伸)。 带有 Godot 徽标错误的 HTML5 画布图像 (这里是源图像外观的参考)。来自 Twitter 的 Godot 徽标

就函数执行的顺序而言,请参见下文。

0 投票
0 回答
64 浏览

html5-canvas - 如何使用画布 getImageData() 和 putImageData() 复制画布的一部分并将其粘贴到另一个位置?

它看起来很简单,但它让我很头疼。

我想要完成的是:

  • 从文件加载图像并将其放置在画布上的特定位置(不是 0,0)。这是正确完成的,没有任何问题。

  • 复制画布的那部分(画布上还有其他图纸,不需要复制),也放到另一个位置,这样画布上有相同图像数据的两个副本。这部分是我坚持的地方。

我当前的代码如下所示:

我在这里做错了什么?应该怎么做?

w3schools 网站上有一个非常简洁的 getImageData() 和 putImageData() 示例,在他们的尝试自己的页面上。当我尝试复制此过程以供自己使用时,一切都崩溃了。

我哪里错了?

0 投票
0 回答
98 浏览

javascript - javascript canvas如何“绘制”到ImageData数组

在画布上绘图时,我主要使用内置函数,如 fillText、drawCircle、DrawRect... 直接绘制到画布上。有没有这样的函数,而不是将这些形状绘制到画布上,而是直接将它们“绘制”(操纵数组可能是一个更好的词)到 imageData 数组中,这样你就可以只用 putImageData 将它放在画布上一次,当所有这些形状被“绘制”到数组中?

谢谢你。