I'm trying to set up some compute kernels that require interpolating some radial profiles of Fourier coefficients. Essentially I need to be discreet in one index but interpolating in the other. I figured that implementing these a 1D texture array would allow me to use the built in interpolation functions of my GPU. Looking through the Metal docs, it seems like a MTLTextureType1DArray
with a MTLPixelFormatR32Float
would be the right setup for this.
I'm setting up my texture description as
MTLTextureDescriptor *textureDescriptor = [[MTLTextureDescriptor alloc] init];
textureDescriptor.pixelFormat = MTLPixelFormatR32Float;
textureDescriptor.textureType = MTLTextureType1DArray;
textureDescriptor.width = numRadialPoints;
textureDescriptor.height = 1;
textureDescriptor.depth = 1;
textureDescriptor.arrayLength = numArrays;
textureDescriptor.mipmapLevelCount = 1;
textureDescriptor.sampleCount = 1;
textureDescriptor.resourceOptions = MTLResourceCPUCacheModeWriteCombined | MTLResourceStorageModeManaged;
textureDescriptor.cpuCacheMode = MTLCPUCacheModeWriteCombined;
textureDescriptor.storageMode = MTLStorageModeManaged;
textureDescriptor.usage = MTLTextureUsageShaderRead;
What I can't figure out is how to now load the texture data. My first attempt was to
_texture = [device newTextureWithDescriptor:textureDescriptor];
[_texture replaceRegion:MTLRegionMake2D(0, 0, numRadialPoints, numArrays) mipmapLevel:0 withBytes:floatbuffer bytesPerRow:4*numRadialPoints];
But this results in an error since heights don't match.
_validateReplaceRegion:144: failed assertion `(origin.y + size.height)(163) must be <= height(1).'
How do I load data into a MTLTextureType1DArray?
You need to use multiple calls to -replaceRegion:mipmapLevel:slice:withBytes:bytesPerRow:bytesPerImage:
, once for each element of the array. You specify the array index with the slice
parameter.
The region parameter needs to be 1-dimensional.