diff --git a/crates/spirv-builder/src/test/basic.rs b/crates/spirv-builder/src/test/basic.rs index 3275de0aa9..76e8bd43fc 100644 --- a/crates/spirv-builder/src/test/basic.rs +++ b/crates/spirv-builder/src/test/basic.rs @@ -587,3 +587,14 @@ pub fn main(input: Input, image: UniformConstant) { } "#); } + +#[test] +fn image_fetch() { + val(r#" +#[spirv(fragment)] +pub fn main(image: UniformConstant, mut output: Output) { + let texel = image.fetch(glam::IVec2::new(0, 1)); + *output = texel; +} +"#); +} diff --git a/crates/spirv-std/src/textures.rs b/crates/spirv-std/src/textures.rs index 6d51deabbf..aaa881565e 100644 --- a/crates/spirv-std/src/textures.rs +++ b/crates/spirv-std/src/textures.rs @@ -42,6 +42,27 @@ impl Image2d { result } } + /// Fetch a single texel with a sampler set at compile time + #[spirv_std_macros::gpu_only] + pub fn fetch(&self, coordinate: impl Vector) -> Vec4 + where + I: Integer, + { + let mut result = Vec4::default(); + unsafe { + asm! { + "%image = OpLoad _ {this}", + "%coordinate = OpLoad _ {coordinate}", + "%result = OpImageFetch typeof*{result} %image %coordinate", + "OpStore {result} %result", + this = in(reg) self, + coordinate = in(reg) &coordinate, + result = in(reg) &mut result, + } + } + + result + } } #[spirv(image_type(