4

I am trying to write a Metal compute shader for converting from RGB to YUV, but am getting build errors.

typedef struct {
   float3x3 matrix;
   float3   offset;
} ColorConversion;

  // Compute kernel
 kernel void kernelRGBtoYUV(texture2d<half, access::sample> inputTexture [[ texture(0) ]],
                       texture2d<half, access::write> textureY [[ texture(1) ]],
                       texture2d<half, access::write> textureCbCr [[ texture(2) ]],
                       constant ColorConversion &colorConv [[ buffer(0) ]],
                       uint2 gid [[thread_position_in_grid]])
{
  // Make sure we don't read or write outside of the texture
  if ((gid.x >= inputTexture.get_width()) || (gid.y >= inputTexture.get_height())) {
      return;
  }



  float3 inputColor = float3(inputTexture.read(gid).rgb);

  float3 yuv = colorConv.matrix*inputColor + colorConv.offset;

  half2 uv = half2(yuv.gb);

  textureY.write(half(yuv.x), gid);

  if (gid.x % 2 == 0 && gid.y % 2 == 0) {
      textureCbCr.write(uv, uint2(gid.x / 2, gid.y / 2));
  }
} 

The last line, i.e. write to textureCbCr throws an error:

  no matching member function for call to 'write'

enter image description here What am I doing wrong?

Deepak Sharma
  • 5,577
  • 7
  • 55
  • 131

1 Answers1

4

According to the Metal Shading Language Specification, the first parameter of all overloads of write on texture2d<> are 4-element vectors. This is the case even if the texture you're writing to has fewer than 4 components. So you can fix this by replacing the erroneous line with:

textureCbCr.write(half4(yuv.xyzz), uint2(gid.x / 2, gid.y / 2));

And the superfluous components will be masked out when performing the write.

warrenm
  • 31,094
  • 6
  • 92
  • 116
  • Strangely, it works for 1 element vector but not 2, why? – Deepak Sharma Aug 04 '19 at 17:32
  • 1
    Perhaps because scalars can be [implicitly converted](https://en.cppreference.com/w/cpp/language/converting_constructor) to vectors in MSL, but I'm not certain. – warrenm Aug 04 '19 at 18:00
  • Could you also look please at this question - https://stackoverflow.com/questions/57834241/ciimage-display-mtkview-vs-glkview-performance – Deepak Sharma Sep 07 '19 at 18:57