Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- use amethyst::{
- assets::{Loader, Handle},
- core::{
- transform::{TransformBundle, Transform},
- timing::Time,
- },
- ecs::{
- prelude::*,
- Join,
- },
- input::{Axis, Button, Bindings, InputBundle, InputHandler, StringBindings, VirtualKeyCode},
- controls::{FlyControlBundle, FlyControlTag},
- prelude::*,
- renderer::{
- Camera,
- camera::Projection,
- palette::rgb::Rgb,
- Material,
- MaterialDefaults,
- Mesh,
- light::{Light, DirectionalLight},
- pass::{
- DrawPbrDesc,
- DrawShadedDesc,
- },
- rendy::{
- factory::Factory,
- graph::{
- render::{RenderGroupDesc, SubpassBuilder},
- GraphBuilder,
- },
- hal::{format::Format, image},
- util::types::vertex::*,
- },
- shape::Shape,
- types::DefaultBackend,
- GraphCreator, RenderingSystem,
- },
- utils::application_root_dir,
- window::{ScreenDimensions, Window, WindowBundle},
- };
- struct Cube;
- impl Component for Cube {
- type Storage = DenseVecStorage<Cube>;
- }
- struct MyState;
- impl SimpleState for MyState {
- fn on_start(&mut self, data: StateData<'_, GameData<'_, '_>>) {
- let world = data.world;
- let (mesh, mat) = {
- let loader = world.read_resource::<Loader>();
- let cube = Shape::Cube.generate::<(
- Vec<Position>,
- Vec<Normal>,
- Vec<TexCoord>,
- Vec<Tangent>,
- )>(Some((0.25, 0.25, 0.25)));
- let mesh: Handle<Mesh> = loader.load_from_data(
- cube.into(),
- (),
- &world.read_resource(),
- );
- let mat_default = world.read_resource::<MaterialDefaults>();
- let mat: Handle<Material> = loader.load_from_data(
- Material {
- ..mat_default.0.clone()
- },
- (),
- &world.read_resource(),
- );
- (mesh, mat)
- };
- let mut transform = Transform::default();
- transform.set_translation_xyz(0.0, -0.15, -1.0);
- world.create_entity()
- .with(mesh)
- .with(mat)
- .with(transform)
- .with(Cube)
- .build();
- world.create_entity()
- .with(Light::from(DirectionalLight {
- color: Rgb::new(1.0, 1.0, 1.0),
- direction: [0.0, -1.0, 0.0].into(),
- intensity: 1.0,
- }))
- .build();
- let mut transform = Transform::default();
- transform.set_translation_xyz(0.0, 0.0, 0.0);
- let camera = Camera::from(Projection::perspective(
- 1.0,
- std::f32::consts::FRAC_PI_3,
- 0.1,
- 1000.0,
- ));
- world.create_entity()
- .with(transform)
- .with(camera)
- .with(FlyControlTag)
- .build();
- }
- }
- #[derive(Default)]
- struct MySystem {
- x_angle: f32,
- y_angle: f32,
- z_angle: f32,
- }
- impl<'a> System<'a> for MySystem {
- type SystemData = (
- Read<'a, InputHandler<StringBindings>>,
- Read<'a, Time>,
- ReadStorage<'a, Cube>,
- WriteStorage<'a, Transform>
- );
- fn run(&mut self, (input, time, cubes, mut transforms): Self::SystemData) {
- self.x_angle += input.axis_value("rotate_x").unwrap() as f32 * time.delta_seconds();
- self.y_angle += input.axis_value("rotate_y").unwrap() as f32 * time.delta_seconds();
- self.z_angle += input.axis_value("rotate_z").unwrap() as f32 * time.delta_seconds();
- for (_, transform) in (&cubes, &mut transforms).join() {
- transform.set_rotation_euler(self.x_angle, self.y_angle, self.z_angle);
- }
- }
- }
- fn main() -> amethyst::Result<()> {
- amethyst::start_logger(Default::default());
- let app_root = application_root_dir()?;
- let resources_dir = app_root.join("resources");
- let display_config_path = resources_dir.join("display_config.ron");
- let mut bindings = Bindings::new();
- // Camera controls
- bindings.insert_axis(
- "right",
- Axis::Emulated {
- neg: Button::Key(VirtualKeyCode::A),
- pos: Button::Key(VirtualKeyCode::D),
- },
- ).unwrap();
- bindings.insert_axis(
- "up",
- Axis::Emulated {
- neg: Button::Key(VirtualKeyCode::F),
- pos: Button::Key(VirtualKeyCode::R),
- },
- ).unwrap();
- bindings.insert_axis(
- "forward",
- Axis::Emulated {
- neg: Button::Key(VirtualKeyCode::W),
- pos: Button::Key(VirtualKeyCode::S),
- },
- ).unwrap();
- // Cube controls
- bindings.insert_axis(
- "rotate_x",
- Axis::Emulated {
- neg: Button::Key(VirtualKeyCode::T),
- pos: Button::Key(VirtualKeyCode::Y),
- },
- ).unwrap();
- bindings.insert_axis(
- "rotate_y",
- Axis::Emulated {
- neg: Button::Key(VirtualKeyCode::G),
- pos: Button::Key(VirtualKeyCode::H),
- },
- ).unwrap();
- bindings.insert_axis(
- "rotate_z",
- Axis::Emulated {
- neg: Button::Key(VirtualKeyCode::B),
- pos: Button::Key(VirtualKeyCode::N),
- },
- ).unwrap();
- let input_bundle = InputBundle::<StringBindings>::new()
- .with_bindings(bindings);
- let game_data = GameDataBuilder::default()
- .with_bundle(WindowBundle::from_config_path(display_config_path))?
- .with_bundle(TransformBundle::new())?
- .with_bundle(FlyControlBundle::<StringBindings>::new(
- Some(String::from("right")),
- Some(String::from("up")),
- Some(String::from("forward")),
- ))?
- .with_bundle(input_bundle)?
- .with(MySystem::default(), "my_system", &["input_system"])
- .with_thread_local(RenderingSystem::<DefaultBackend, _>::new(
- RenderingGraph::default(),
- ));
- let mut game = Application::new(resources_dir, MyState, game_data)?;
- game.run();
- Ok(())
- }
- #[derive(Default)]
- struct RenderingGraph {
- dimensions: Option<ScreenDimensions>,
- surface_format: Option<Format>,
- dirty: bool,
- }
- impl GraphCreator<DefaultBackend> for RenderingGraph {
- fn rebuild(&mut self, res: &Resources) -> bool {
- // Rebuild when dimensions change, but wait until at least two frames have the same.
- let new_dimensions = res.try_fetch::<ScreenDimensions>();
- use std::ops::Deref;
- if self.dimensions.as_ref() != new_dimensions.as_ref().map(|d| d.deref()) {
- self.dirty = true;
- self.dimensions = new_dimensions.map(|d| d.clone());
- return false;
- }
- self.dirty
- }
- fn builder(
- &mut self,
- factory: &mut Factory<DefaultBackend>,
- res: &Resources,
- ) -> GraphBuilder<DefaultBackend, Resources> {
- use amethyst::renderer::rendy::{
- graph::present::PresentNode,
- hal::command::{ClearDepthStencil, ClearValue},
- };
- self.dirty = false;
- let window = <ReadExpect<'_, Window>>::fetch(res);
- let surface = factory.create_surface(&window);
- // cache surface format to speed things up
- let surface_format = *self
- .surface_format
- .get_or_insert_with(|| factory.get_surface_format(&surface));
- let dimensions = self.dimensions.as_ref().unwrap();
- let window_kind =
- image::Kind::D2(dimensions.width() as u32, dimensions.height() as u32, 1, 1);
- let mut graph_builder = GraphBuilder::new();
- let color = graph_builder.create_image(
- window_kind,
- 1,
- surface_format,
- Some(ClearValue::Color([0.00, 0.01, 0.02, 1.0].into())),
- );
- let depth = graph_builder.create_image(
- window_kind,
- 1,
- Format::D32Sfloat,
- Some(ClearValue::DepthStencil(ClearDepthStencil(1.0, 0))),
- );
- let opaque = graph_builder.add_node(
- SubpassBuilder::new()
- //.with_group(DrawShadedDesc::new().builder())
- .with_group(DrawPbrDesc::new().builder())
- .with_color(color)
- .with_depth_stencil(depth)
- .into_pass(),
- );
- let _present = graph_builder
- .add_node(PresentNode::builder(factory, surface, color).with_dependency(opaque));
- graph_builder
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement