//! Tool to create walls. For information about walls, see also //! [the wall module](crate::map::wall). use super::Tool; use crate::client::map::Map; use crate::client::transform::Transform; use crate::math::{LineSegment, Vec2}; use crate::net::{Cargo, Connection}; use crate::world::Wall; use raylib::core::drawing::{RaylibDraw, RaylibDrawHandle}; use raylib::ffi::{Color, Vector2}; /// The wall tool to create solid barriers a player usually cannot cross. pub struct WallTool { unfinished_wall: Option>, } impl WallTool { /// Create a new wall tool. There should only be one wall tool per program instance, which should /// be created inside of the editor. #[allow(clippy::new_without_default)] pub fn new() -> Self { Self { unfinished_wall: None, } } } impl Tool for WallTool { fn deactivate(&mut self) { self.unfinished_wall = None; } fn update(&mut self, _map: &Map, mouse_pos_m: &Vec2) { if let Some(ref mut wall) = &mut self.unfinished_wall { wall.end = *mouse_pos_m; } } fn draw(&self, rld: &mut RaylibDrawHandle, transform: &Transform) { if let Some(ref wall) = self.unfinished_wall { let start: Vector2 = transform.point_m_to_px(&wall.start).into(); let end: Vector2 = transform.point_m_to_px(&wall.end).into(); rld.draw_line_ex( start, end, transform.length_m_to_px(0.1) as f32, Color { r: 150, g: 200, b: 150, a: 255, }, ); } } fn place_single( &mut self, _map: &mut Map, server: &Connection, mouse_pos_m: &Vec2, ) { if let Some(wall) = self.unfinished_wall.take() { // Continue with the next wall straight away. self.unfinished_wall = Some(LineSegment::new(wall.end, wall.end)); server.send(Cargo::AddWall(Wall::new(wall))); } else { self.unfinished_wall = Some(LineSegment::new(*mouse_pos_m, *mouse_pos_m)); } } fn abort(&mut self) { self.unfinished_wall = None; } }