Game rules screen functional
This commit is contained in:
		@@ -8,6 +8,7 @@ use crossterm::event;
 | 
				
			|||||||
use crossterm::event::{Event, KeyCode};
 | 
					use crossterm::event::{Event, KeyCode};
 | 
				
			||||||
use tui::backend::Backend;
 | 
					use tui::backend::Backend;
 | 
				
			||||||
use tui::layout::{Constraint, Direction, Layout, Margin};
 | 
					use tui::layout::{Constraint, Direction, Layout, Margin};
 | 
				
			||||||
 | 
					use tui::style::{Color, Style};
 | 
				
			||||||
use tui::widgets::*;
 | 
					use tui::widgets::*;
 | 
				
			||||||
use tui::{Frame, Terminal};
 | 
					use tui::{Frame, Terminal};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@@ -159,7 +160,9 @@ fn ui<B: Backend>(f: &mut Frame<B>, model: &mut GameRulesConfigurationScreen) {
 | 
				
			|||||||
            Constraint::Length(3),
 | 
					            Constraint::Length(3),
 | 
				
			||||||
            Constraint::Length(1),
 | 
					            Constraint::Length(1),
 | 
				
			||||||
            Constraint::Length(1),
 | 
					            Constraint::Length(1),
 | 
				
			||||||
            Constraint::Length(3),
 | 
					            Constraint::Length(1),
 | 
				
			||||||
 | 
					            Constraint::Length(1), // Buttons
 | 
				
			||||||
 | 
					            Constraint::Length(1), // Error message (if any)
 | 
				
			||||||
        ])
 | 
					        ])
 | 
				
			||||||
        .split(area.inner(&Margin {
 | 
					        .split(area.inner(&Margin {
 | 
				
			||||||
            horizontal: 2,
 | 
					            horizontal: 2,
 | 
				
			||||||
@@ -207,14 +210,23 @@ fn ui<B: Backend>(f: &mut Frame<B>, model: &mut GameRulesConfigurationScreen) {
 | 
				
			|||||||
    );
 | 
					    );
 | 
				
			||||||
    f.render_widget(editor, chunks[EditingField::PlayerContinueOnHit as usize]);
 | 
					    f.render_widget(editor, chunks[EditingField::PlayerContinueOnHit as usize]);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    // Buttons
 | 
				
			||||||
    let buttons_chunk = Layout::default()
 | 
					    let buttons_chunk = Layout::default()
 | 
				
			||||||
        .direction(Direction::Horizontal)
 | 
					        .direction(Direction::Horizontal)
 | 
				
			||||||
        .constraints([Constraint::Percentage(50), Constraint::Percentage(50)])
 | 
					        .constraints([Constraint::Percentage(50), Constraint::Percentage(50)])
 | 
				
			||||||
        .split(*chunks.last().unwrap());
 | 
					        .split(chunks[EditingField::OK as usize]);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    let button = ButtonWidget::new("Cancel", model.curr_field == EditingField::Cancel);
 | 
					    let button = ButtonWidget::new("Cancel", model.curr_field == EditingField::Cancel);
 | 
				
			||||||
    f.render_widget(button, buttons_chunk[0]);
 | 
					    f.render_widget(button, buttons_chunk[0]);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    let button = ButtonWidget::new("OK", model.curr_field == EditingField::OK);
 | 
					    let button = ButtonWidget::new("OK", model.curr_field == EditingField::OK)
 | 
				
			||||||
 | 
					        .set_disabled(!model.rules.is_valid());
 | 
				
			||||||
    f.render_widget(button, buttons_chunk[1]);
 | 
					    f.render_widget(button, buttons_chunk[1]);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    // Error message (if any)
 | 
				
			||||||
 | 
					    if let Some(msg) = model.rules.get_errors().first() {
 | 
				
			||||||
 | 
					        let area = centered_rect_size(msg.len() as u16, 1, *chunks.last().unwrap());
 | 
				
			||||||
 | 
					        let err = Paragraph::new(*msg).style(Style::default().fg(Color::Red));
 | 
				
			||||||
 | 
					        f.render_widget(err, area);
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -1,13 +1,16 @@
 | 
				
			|||||||
use crate::ui_screens::utils::centered_rect_size;
 | 
					 | 
				
			||||||
use std::fmt::Display;
 | 
					use std::fmt::Display;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
use tui::buffer::Buffer;
 | 
					use tui::buffer::Buffer;
 | 
				
			||||||
use tui::layout::Rect;
 | 
					use tui::layout::Rect;
 | 
				
			||||||
use tui::style::{Color, Style};
 | 
					use tui::style::{Color, Style};
 | 
				
			||||||
use tui::widgets::*;
 | 
					use tui::widgets::*;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					use crate::ui_screens::utils::centered_rect_size;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
pub struct ButtonWidget {
 | 
					pub struct ButtonWidget {
 | 
				
			||||||
    is_hovered: bool,
 | 
					    is_hovered: bool,
 | 
				
			||||||
    label: String,
 | 
					    label: String,
 | 
				
			||||||
 | 
					    disabled: bool,
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
impl ButtonWidget {
 | 
					impl ButtonWidget {
 | 
				
			||||||
@@ -15,8 +18,14 @@ impl ButtonWidget {
 | 
				
			|||||||
        Self {
 | 
					        Self {
 | 
				
			||||||
            label: label.to_string(),
 | 
					            label: label.to_string(),
 | 
				
			||||||
            is_hovered,
 | 
					            is_hovered,
 | 
				
			||||||
 | 
					            disabled: false,
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    pub fn set_disabled(mut self, disabled: bool) -> Self {
 | 
				
			||||||
 | 
					        self.disabled = disabled;
 | 
				
			||||||
 | 
					        self
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
impl Widget for ButtonWidget {
 | 
					impl Widget for ButtonWidget {
 | 
				
			||||||
@@ -25,9 +34,10 @@ impl Widget for ButtonWidget {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
        let area = centered_rect_size(label.len() as u16, 1, area);
 | 
					        let area = centered_rect_size(label.len() as u16, 1, area);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        let input = Paragraph::new(label.as_ref()).style(match &self.is_hovered {
 | 
					        let input = Paragraph::new(label.as_ref()).style(match (self.disabled, self.is_hovered) {
 | 
				
			||||||
            false => Style::default().bg(Color::DarkGray),
 | 
					            (true, _) => Style::default(),
 | 
				
			||||||
            true => Style::default().fg(Color::White).bg(Color::Yellow),
 | 
					            (_, false) => Style::default().bg(Color::DarkGray),
 | 
				
			||||||
 | 
					            (_, true) => Style::default().fg(Color::White).bg(Color::Yellow),
 | 
				
			||||||
        });
 | 
					        });
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        input.render(area, buf);
 | 
					        input.render(area, buf);
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -102,7 +102,7 @@ impl GameRules {
 | 
				
			|||||||
        if self.boats_list().len() < config.min_boats_number
 | 
					        if self.boats_list().len() < config.min_boats_number
 | 
				
			||||||
            || self.boats_list().len() > config.max_boats_number
 | 
					            || self.boats_list().len() > config.max_boats_number
 | 
				
			||||||
        {
 | 
					        {
 | 
				
			||||||
            errors.push("Number of boats is invalid!");
 | 
					            errors.push("The number of boats is invalid!");
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        for boat in self.boats_list() {
 | 
					        for boat in self.boats_list() {
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user