use crate::{
core::{
color::Color,
math::aabb::AxisAlignedBoundingBox,
pool::Handle,
reflect::prelude::*,
type_traits::prelude::*,
uuid::{uuid, Uuid},
variable::InheritableVariable,
visitor::prelude::*,
},
resource::texture::TextureResource,
scene::node::constructor::NodeConstructor,
scene::{
base::{Base, BaseBuilder},
graph::Graph,
node::{Node, NodeTrait},
},
};
use fyrox_graph::constructor::ConstructorProvider;
use fyrox_graph::SceneGraph;
use std::ops::{Deref, DerefMut};
#[derive(Debug, Visit, Default, Clone, Reflect, ComponentProvider)]
#[reflect(derived_type = "Node")]
pub struct Decal {
base: Base,
#[reflect(setter = "set_diffuse_texture")]
diffuse_texture: InheritableVariable<Option<TextureResource>>,
#[reflect(setter = "set_normal_texture")]
normal_texture: InheritableVariable<Option<TextureResource>>,
#[reflect(setter = "set_color")]
color: InheritableVariable<Color>,
#[reflect(min_value = 0.0)]
#[reflect(setter = "set_layer")]
layer: InheritableVariable<u8>,
}
impl Deref for Decal {
type Target = Base;
fn deref(&self) -> &Self::Target {
&self.base
}
}
impl DerefMut for Decal {
fn deref_mut(&mut self) -> &mut Self::Target {
&mut self.base
}
}
impl TypeUuidProvider for Decal {
fn type_uuid() -> Uuid {
uuid!("c4d24e48-edd1-4fb2-ad82-4b3d3ea985d8")
}
}
impl Decal {
pub fn set_diffuse_texture(
&mut self,
diffuse_texture: Option<TextureResource>,
) -> Option<TextureResource> {
std::mem::replace(
self.diffuse_texture.get_value_mut_and_mark_modified(),
diffuse_texture,
)
}
pub fn diffuse_texture(&self) -> Option<&TextureResource> {
self.diffuse_texture.as_ref()
}
pub fn diffuse_texture_value(&self) -> Option<TextureResource> {
(*self.diffuse_texture).clone()
}
pub fn set_normal_texture(
&mut self,
normal_texture: Option<TextureResource>,
) -> Option<TextureResource> {
std::mem::replace(
self.normal_texture.get_value_mut_and_mark_modified(),
normal_texture,
)
}
pub fn normal_texture(&self) -> Option<&TextureResource> {
self.normal_texture.as_ref()
}
pub fn normal_texture_value(&self) -> Option<TextureResource> {
(*self.normal_texture).clone()
}
pub fn set_color(&mut self, color: Color) -> Color {
self.color.set_value_and_mark_modified(color)
}
pub fn color(&self) -> Color {
*self.color
}
pub fn set_layer(&mut self, layer: u8) -> u8 {
self.layer.set_value_and_mark_modified(layer)
}
pub fn layer(&self) -> u8 {
*self.layer
}
}
impl ConstructorProvider<Node, Graph> for Decal {
fn constructor() -> NodeConstructor {
NodeConstructor::new::<Self>().with_variant("Decal", |_| {
DecalBuilder::new(BaseBuilder::new().with_name("Decal"))
.build_node()
.into()
})
}
}
impl NodeTrait for Decal {
#[inline]
fn local_bounding_box(&self) -> AxisAlignedBoundingBox {
self.base.local_bounding_box()
}
fn world_bounding_box(&self) -> AxisAlignedBoundingBox {
self.base.world_bounding_box()
}
fn id(&self) -> Uuid {
Self::type_uuid()
}
}
pub struct DecalBuilder {
base_builder: BaseBuilder,
diffuse_texture: Option<TextureResource>,
normal_texture: Option<TextureResource>,
color: Color,
layer: u8,
}
impl DecalBuilder {
pub fn new(base_builder: BaseBuilder) -> Self {
Self {
base_builder,
diffuse_texture: None,
normal_texture: None,
color: Color::opaque(255, 255, 255),
layer: 0,
}
}
pub fn with_diffuse_texture(mut self, diffuse_texture: TextureResource) -> Self {
self.diffuse_texture = Some(diffuse_texture);
self
}
pub fn with_normal_texture(mut self, normal_texture: TextureResource) -> Self {
self.normal_texture = Some(normal_texture);
self
}
pub fn with_color(mut self, color: Color) -> Self {
self.color = color;
self
}
pub fn with_layer(mut self, layer: u8) -> Self {
self.layer = layer;
self
}
pub fn build_decal(self) -> Decal {
Decal {
base: self.base_builder.build_base(),
diffuse_texture: self.diffuse_texture.into(),
normal_texture: self.normal_texture.into(),
color: self.color.into(),
layer: self.layer.into(),
}
}
pub fn build_node(self) -> Node {
Node::new(self.build_decal())
}
pub fn build(self, graph: &mut Graph) -> Handle<Decal> {
graph.add_node(self.build_node()).to_variant()
}
}