什么是 Apple 的 Metal(金属着色器语言)纹理坐标?
What are Apple's Metal (Metal Shader Language) texture coordinates?
在iOS或OS/X中Metal Shader Language内核函数使用了哪些纹理坐标?例如,给定一个 MTLTexture
and uint2 gid[[thread_position_in_grid]]
Is gid.x
and gid.y
between 0..1 (x and y are floats) or 0..inTexture.get_width()
( x 和 y 是整数)。
提前致谢
thread_position_in_grid
总是由无符号整数组成,并提供这些选项,但其中 none 与纹理坐标有关。问另一个相关问题可能会有所帮助,因为您似乎将纹理和内核函数的概念混为一谈。
- 16 或 -32 位
- 1D、2D 或 3D
thread_position_in_grid
是网格中的索引(整数),它采用您在 dispatchThreadgroups:threadsPerThreadgroup:
中指定的范围内的值。由您决定您想要多少个线程组,以及每个组有多少个线程。
在下面的sample code中你可以看到threadsPerGroup.width * numThreadgroups.width == inputImage.width
和threadsPerGroup.height * numThreadgroups.height == inputImage.height
。在这种情况下,网格中的位置将因此是 non-normalized(整数)像素坐标。
Metal 中计算着色器的每次启动都伴随着线程 ID 的密集矩形 3D 网格。调用 [MTLComputeCommandEncoder dispatchThreadGroups:threadsPerThreadgroup:]
时会设置网格的尺寸。例如,您可以将线程组大小设置为 {16,16,1}
(一个线程组中有 256 个线程,一个 16x16x1 正方形),线程组计数设置为 {1,2,1}
,这将导致启动两个线程组,总面积为 512 {16,32,1}
形状的线程。这些是在内核顶部显示为 [[thread_position_in_grid]]
的整数。线程位置是你告诉你是哪个线程的方式,就像通过 dispatch_apply()
.
传递给块的 threadID 参数一样
Metal 指定没有从 [[thread_position_in_grid]]
映射到纹理中的坐标。这是由您在计算着色器中的软件中完成的。如果你想在图像中的某个偏移处读取纹理区域中的每隔一个像素,那么你需要将 threadID 乘以 2 并在将新坐标传递给 texture2d.sample
之前在你的内核中添加一个偏移量。由于 Metal 无法启动部分线程组,因此您需要确保不执行不需要的线程组。例如,当应用于较小的纹理时,32x64 启动的全尺寸可能会导致您注销纹理的末端。在这种情况下,您必须检查线程 ID 以查看线程是否会注销结尾,然后 return 退出着色器或跳过该线程的纹理写入调用以避免问题。
在iOS或OS/X中Metal Shader Language内核函数使用了哪些纹理坐标?例如,给定一个 MTLTexture
and uint2 gid[[thread_position_in_grid]]
Is gid.x
and gid.y
between 0..1 (x and y are floats) or 0..inTexture.get_width()
( x 和 y 是整数)。
提前致谢
thread_position_in_grid
总是由无符号整数组成,并提供这些选项,但其中 none 与纹理坐标有关。问另一个相关问题可能会有所帮助,因为您似乎将纹理和内核函数的概念混为一谈。
- 16 或 -32 位
- 1D、2D 或 3D
thread_position_in_grid
是网格中的索引(整数),它采用您在 dispatchThreadgroups:threadsPerThreadgroup:
中指定的范围内的值。由您决定您想要多少个线程组,以及每个组有多少个线程。
在下面的sample code中你可以看到threadsPerGroup.width * numThreadgroups.width == inputImage.width
和threadsPerGroup.height * numThreadgroups.height == inputImage.height
。在这种情况下,网格中的位置将因此是 non-normalized(整数)像素坐标。
Metal 中计算着色器的每次启动都伴随着线程 ID 的密集矩形 3D 网格。调用 [MTLComputeCommandEncoder dispatchThreadGroups:threadsPerThreadgroup:]
时会设置网格的尺寸。例如,您可以将线程组大小设置为 {16,16,1}
(一个线程组中有 256 个线程,一个 16x16x1 正方形),线程组计数设置为 {1,2,1}
,这将导致启动两个线程组,总面积为 512 {16,32,1}
形状的线程。这些是在内核顶部显示为 [[thread_position_in_grid]]
的整数。线程位置是你告诉你是哪个线程的方式,就像通过 dispatch_apply()
.
Metal 指定没有从 [[thread_position_in_grid]]
映射到纹理中的坐标。这是由您在计算着色器中的软件中完成的。如果你想在图像中的某个偏移处读取纹理区域中的每隔一个像素,那么你需要将 threadID 乘以 2 并在将新坐标传递给 texture2d.sample
之前在你的内核中添加一个偏移量。由于 Metal 无法启动部分线程组,因此您需要确保不执行不需要的线程组。例如,当应用于较小的纹理时,32x64 启动的全尺寸可能会导致您注销纹理的末端。在这种情况下,您必须检查线程 ID 以查看线程是否会注销结尾,然后 return 退出着色器或跳过该线程的纹理写入调用以避免问题。