如何在Metal片段着色器中实现/使用原子计数器? [英] How to implement/use atomic counter in Metal fragment shader?

查看:139
本文介绍了如何在Metal片段着色器中实现/使用原子计数器?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想在我的Metal应用程序中实现A-Buffer算法,以实现顺序无关的透明度.该技术的描述提到了使用原子计数器.我从来没有使用过这些,甚至从未听说过.我只是在《金属着色语言规范》中阅读了有关原子变量的信息,但无法弄清楚如何实际实现或使用原子变量.

I want to implement an A-Buffer algorithm for order-independent-transparency in my Metal application. The description of the technique mentions using an atomic counter. I've never used one of these or even heard of them. I just read about atomic variables in the Metal Shading Language Specification, but I can't figure out how to actually implement or use one.

有人在金属领域有经验吗?您能指出一个如何设置和使用简单整数计数器的示例吗?基本上,每个渲染过程我都需要能够从片段着色器中增加一个从零开始的整数.这用于索引A缓冲区.

Does anyone have experience with these in Metal? Can you point me to an example of how to set up and use a simple integer counter? Basically each render pass I need to be able to increment an integer from within the fragment shader, starting from zero. This is used to index into the A-Buffer.

谢谢!

推荐答案

嗯,您的问题缺少足够的细节,无法提供比一般概述更多的信息.您可能会考虑使用不确定的伪代码添加不完整的着色器功能,在不确定如何实现某些功能的情况下.

Well, your question is lacking sufficient detail to provide much more than a general overview. You might consider adding an incomplete shader function, with pseudo-code where you're not sure how to implement something.

无论如何,原子计数器是类型为atomic_uint的变量(如果需要符号,则为atomic_int).为了有用,该变量需要在特定的地址空间中共享.您的示例听起来好像需要device地址空间.因此,您需要一个由缓冲区支持的device变量.您将其声明为:

Anyway, an atomic counter is a variable of type atomic_uint (or atomic_int if you need sign). To be useful, the variable needs to be shared across a particular address space. Your example sounds like it needs device address space. So, you would want a device variable backed by a buffer. You would declare it as:

fragment FragmentOut my_fragment_func(device atomic_uint &counter [[buffer(0)]], ...)
{
    ...
}

您还可以为参数使用结构类型,并将结构的字段作为您的atomic_uint变量.

You could also use a struct type for the parameter and have a field of the struct be your atomic_uint variable.

要将原子变量原子递增1并获得优先值,您可以这样做:

To atomically increment the atomic variable by 1 and obtain the prior value, you could do this:

    uint value = atomic_fetch_add_explicit(&counter, 1, memory_order_relaxed);

原子变量的初始值是在执行draw或dispatch命令之前从缓冲区的内容中获取的.它没有在规范中进行记录,但是原子类型的大小和位解释似乎与相应的非原子类型匹配.也就是说,您将uint(也称为unsigned intuint32_t)写入缓冲区以初始化atomic_uint.

The initial value of the atomic variable is taken from the contents of the buffer at a point before the draw or dispatch command is executed. It's not documented as such in the spec, but the size and bit-interpretation of an atomic type seems to match the corresponding non-atomic type. That is, you would write a uint (a.k.a. unsigned int or uint32_t) to the buffer to initialize an atomic_uint.

这篇关于如何在Metal片段着色器中实现/使用原子计数器?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆