mirror of
https://github.com/gfx-rs/wgpu.git
synced 2026-04-22 03:02:01 -04:00
Merge #1007
1007: Improve cubemap validation r=kvark a=cwfitzgerald **Connections** Closes #952. **Description** We were missing depth-size and texture dimension validation when creating Cubemap and CubemapArray views. I split the depth-size errors so I can give a more helpful error message in both cases. **Testing** Tested on the skybox example when made intensionally incorrect. Co-authored-by: Connor Fitzgerald <connorwadefitzgerald@gmail.com>
This commit is contained in:
@@ -27,7 +27,9 @@ use hal::{
|
||||
};
|
||||
use parking_lot::{Mutex, MutexGuard};
|
||||
use thiserror::Error;
|
||||
use wgt::{BufferAddress, BufferSize, InputStepMode, TextureDimension, TextureFormat};
|
||||
use wgt::{
|
||||
BufferAddress, BufferSize, InputStepMode, TextureDimension, TextureFormat, TextureViewDimension,
|
||||
};
|
||||
|
||||
use std::{
|
||||
borrow::Cow,
|
||||
@@ -1477,16 +1479,50 @@ impl<G: GlobalIdentityHandlerFactory> Global<G> {
|
||||
.ok_or(resource::CreateTextureViewError::InvalidTexture)?;
|
||||
let device = &device_guard[texture.device_id.value];
|
||||
|
||||
let view_kind = match desc.dimension {
|
||||
Some(dim) => conv::map_texture_view_dimension(dim),
|
||||
None => match texture.kind {
|
||||
hal::image::Kind::D1(_, 1) => hal::image::ViewKind::D1,
|
||||
hal::image::Kind::D1(..) => hal::image::ViewKind::D1Array,
|
||||
hal::image::Kind::D2(_, _, 1, _) => hal::image::ViewKind::D2,
|
||||
hal::image::Kind::D2(..) => hal::image::ViewKind::D2Array,
|
||||
hal::image::Kind::D3(..) => hal::image::ViewKind::D3,
|
||||
},
|
||||
};
|
||||
let view_kind =
|
||||
match desc.dimension {
|
||||
Some(dim) => {
|
||||
use hal::image::Kind;
|
||||
|
||||
let required_tex_dim = dim.compatible_texture_dimension();
|
||||
|
||||
if required_tex_dim != texture.dimension {
|
||||
return Err(
|
||||
resource::CreateTextureViewError::InvalidTextureViewDimension {
|
||||
view: dim,
|
||||
image: texture.dimension,
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
if let Kind::D2(_, _, depth, _) = texture.kind {
|
||||
match dim {
|
||||
TextureViewDimension::Cube if depth != 6 => {
|
||||
return Err(
|
||||
resource::CreateTextureViewError::InvalidCubemapTextureDepth {
|
||||
depth,
|
||||
},
|
||||
)
|
||||
}
|
||||
TextureViewDimension::CubeArray if depth % 6 != 0 => return Err(
|
||||
resource::CreateTextureViewError::InvalidCubemapArrayTextureDepth {
|
||||
depth,
|
||||
},
|
||||
),
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
|
||||
conv::map_texture_view_dimension(dim)
|
||||
}
|
||||
None => match texture.kind {
|
||||
hal::image::Kind::D1(_, 1) => hal::image::ViewKind::D1,
|
||||
hal::image::Kind::D1(..) => hal::image::ViewKind::D1Array,
|
||||
hal::image::Kind::D2(_, _, 1, _) => hal::image::ViewKind::D2,
|
||||
hal::image::Kind::D2(..) => hal::image::ViewKind::D2Array,
|
||||
hal::image::Kind::D3(..) => hal::image::ViewKind::D3,
|
||||
},
|
||||
};
|
||||
let required_level_count =
|
||||
desc.base_mip_level + desc.level_count.map_or(1, |count| count.get());
|
||||
let required_layer_count =
|
||||
|
||||
@@ -317,6 +317,15 @@ pub enum CreateTextureViewError {
|
||||
InvalidTexture,
|
||||
#[error("not enough memory left")]
|
||||
OutOfMemory,
|
||||
#[error("Invalid texture view dimension `{view:?}` with texture of dimension `{image:?}`")]
|
||||
InvalidTextureViewDimension {
|
||||
view: wgt::TextureViewDimension,
|
||||
image: wgt::TextureDimension,
|
||||
},
|
||||
#[error("Invalid texture depth `{depth}` for texture view of dimension `Cubemap`. Cubemap views must use images of size 6.")]
|
||||
InvalidCubemapTextureDepth { depth: u16 },
|
||||
#[error("Invalid texture depth `{depth}` for texture view of dimension `CubemapArray`. Cubemap views must use images with sizes which are a multiple of 6.")]
|
||||
InvalidCubemapArrayTextureDepth { depth: u16 },
|
||||
#[error(
|
||||
"TextureView mip level count + base mip level {requested} must be <= Texture mip level count {total}"
|
||||
)]
|
||||
|
||||
@@ -434,6 +434,17 @@ pub enum TextureViewDimension {
|
||||
D3,
|
||||
}
|
||||
|
||||
impl TextureViewDimension {
|
||||
/// Get the texture dimension required fo this texture view dimension.
|
||||
pub fn compatible_texture_dimension(self) -> TextureDimension {
|
||||
match self {
|
||||
Self::D1 => TextureDimension::D1,
|
||||
Self::D2 | Self::D2Array | Self::Cube | Self::CubeArray => TextureDimension::D2,
|
||||
Self::D3 => TextureDimension::D3,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Alpha blend factor.
|
||||
///
|
||||
/// Alpha blending is very complicated: see the OpenGL or Vulkan spec for more information.
|
||||
|
||||
Reference in New Issue
Block a user