Adapt to new iced version, show events in month view
Signed-off-by: Fabrizio Iannetti <fabrizio.iannetti@gmail.com>
This commit is contained in:
parent
c805cc94d3
commit
ae13e98388
File diff suppressed because it is too large
Load Diff
|
@ -9,8 +9,7 @@ tracing = ["dep:lttng-ust"]
|
|||
[dependencies]
|
||||
#iced = "0.4.2"
|
||||
#iced_native = "0.5.1"
|
||||
iced = { path = "../iced" }
|
||||
iced_native = { path = "../iced/native" }
|
||||
iced = { path = "../iced", features = ["advanced"] }
|
||||
chrono = "0.4"
|
||||
lttng-ust = { version = "0.1.0", optional = true }
|
||||
|
||||
|
|
|
@ -9,6 +9,7 @@ use chrono::{Datelike, NaiveDate, Months, Utc};
|
|||
use calendar::{CalendarMonthView, CalendarYearView, CalendarParams };
|
||||
|
||||
use iced::{
|
||||
alignment,
|
||||
executor,
|
||||
Alignment, Application, Command,
|
||||
Element, Length, Settings,
|
||||
|
@ -100,13 +101,13 @@ impl Controls {
|
|||
.push(
|
||||
Text::new(month_name)
|
||||
.width(Length::Fill)
|
||||
.horizontal_alignment(iced_native::alignment::Horizontal::Left)
|
||||
.horizontal_alignment(alignment::Horizontal::Left)
|
||||
.size(40),
|
||||
)
|
||||
.push(
|
||||
Text::new(year.to_string())
|
||||
.width(Length::Fill)
|
||||
.horizontal_alignment(iced_native::alignment::Horizontal::Right)
|
||||
.horizontal_alignment(alignment::Horizontal::Right)
|
||||
.size(40),
|
||||
)
|
||||
.into()
|
||||
|
@ -169,7 +170,7 @@ impl Application for CalendarApp {
|
|||
|
||||
match self.controls.mode {
|
||||
Some(ViewMode::Year) => content = content.push(CalendarYearView::new(&CalendarParams::new(), self.month, &self.events)),
|
||||
Some(ViewMode::Month) | None => content = content.push(CalendarMonthView::new(&CalendarParams::new(), self.month)),
|
||||
Some(ViewMode::Month) | None => content = content.push(CalendarMonthView::new(&CalendarParams::new(), self.month, &self.events)),
|
||||
};
|
||||
|
||||
Container::new(content)
|
||||
|
|
|
@ -36,14 +36,14 @@ impl EventsCollection {
|
|||
// TODO: hard-coded events
|
||||
events: vec![
|
||||
Event {
|
||||
text: String::from("ev_1"),
|
||||
begin: NaiveDate::from_ymd_opt(2023, 01, 15).unwrap(),
|
||||
end: NaiveDate::from_ymd_opt(2023, 01, 16).unwrap(),
|
||||
text: String::from("pentecoste"),
|
||||
begin: NaiveDate::from_ymd_opt(2023, 05, 30).unwrap(),
|
||||
end: NaiveDate::from_ymd_opt(2023, 06, 09).unwrap(),
|
||||
},
|
||||
Event {
|
||||
text: String::from("ev_2"),
|
||||
begin: NaiveDate::from_ymd_opt(2023, 01, 16).unwrap(),
|
||||
end: NaiveDate::from_ymd_opt(2023, 01, 17).unwrap(),
|
||||
text: String::from("estate"),
|
||||
begin: NaiveDate::from_ymd_opt(2023, 07, 31).unwrap(),
|
||||
end: NaiveDate::from_ymd_opt(2023, 09, 11).unwrap(),
|
||||
},
|
||||
],
|
||||
}
|
||||
|
@ -57,6 +57,16 @@ impl EventsCollection {
|
|||
}
|
||||
None
|
||||
}
|
||||
|
||||
pub fn for_day(&self, day: NaiveDate) -> Vec<Event> {
|
||||
let mut events_in_day = Vec::new();
|
||||
for ev_day in &self.events {
|
||||
if ev_day.is_in_day(day) {
|
||||
events_in_day.push(ev_day.clone());
|
||||
}
|
||||
}
|
||||
events_in_day
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for EventsCollection {
|
||||
|
|
|
@ -19,7 +19,7 @@ pub struct CellGrid {
|
|||
width: f32,
|
||||
height: f32,
|
||||
|
||||
// size fo the grid, in number of cells
|
||||
// size of the grid, in number of cells
|
||||
num_x: u32,
|
||||
num_y: u32,
|
||||
|
||||
|
@ -46,6 +46,10 @@ impl CellGrid {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn rows(&self) -> Self {
|
||||
CellGrid::new(self.x, self.y, self.width, self.height, 1, self.num_y)
|
||||
}
|
||||
|
||||
fn compute_cell(&mut self) -> () {
|
||||
self.curr.pos_x = self.pos_x;
|
||||
self.curr.pos_y = self.pos_y;
|
||||
|
|
|
@ -8,12 +8,10 @@
|
|||
// if you wish to, by creating your own `Renderer` trait, which could be
|
||||
// implemented by `iced_wgpu` and other renderers.
|
||||
|
||||
use iced_native::layout::{self, Layout};
|
||||
use iced_native::renderer;
|
||||
use iced_native::{Color, Element, Length, Point, Rectangle, Widget};
|
||||
use iced_native::text;
|
||||
use iced_native::alignment;
|
||||
use iced_native::widget::Tree;
|
||||
use iced::advanced::{layout, renderer};
|
||||
use iced::advanced::widget::{Tree, Widget};
|
||||
use iced::{Color, Element, Length, Point, Rectangle, alignment};
|
||||
use iced::advanced::text::{self, Text, LineHeight, Shaping};
|
||||
use chrono::{NaiveDate, Datelike, Duration, Local};
|
||||
use super::basics::CellGrid;
|
||||
use crate::model::events::EventsCollection;
|
||||
|
@ -85,21 +83,102 @@ impl CalendarParams {
|
|||
|
||||
//-------------------------------------------------------------------------
|
||||
|
||||
pub struct CalendarMonthView {
|
||||
fn render_events_in_day(
|
||||
params: &CalendarParams,
|
||||
renderer: &mut impl text::Renderer,
|
||||
current_day: NaiveDate,
|
||||
day_bounds: Rectangle,
|
||||
font_size: f32,
|
||||
fg: Color,
|
||||
content: &str,
|
||||
events: &EventsCollection
|
||||
) {
|
||||
// render events, if enough space
|
||||
let day_text_size = renderer.measure(
|
||||
content,
|
||||
font_size,
|
||||
LineHeight::default(),
|
||||
renderer.default_font(),
|
||||
day_bounds.size(),
|
||||
Shaping::default());
|
||||
let ev_height = params.ev_height;
|
||||
let mut ev_y: f32 = 0.0;
|
||||
let y = day_bounds.y + params.day_text_margin;
|
||||
for ev_day in events.for_day(current_day) {
|
||||
if day_bounds.height - day_text_size.1 > ev_y + ev_height {
|
||||
let ev_bounds = Rectangle {
|
||||
y: y + ev_y + day_text_size.1,
|
||||
height: ev_height,
|
||||
..day_bounds
|
||||
};
|
||||
renderer.fill_quad(renderer::Quad {
|
||||
bounds: ev_bounds,
|
||||
border_radius: 0.0.into(),
|
||||
border_width: 1.0,
|
||||
border_color: params.day_other_month_fg,
|
||||
},
|
||||
params.ev_bg);
|
||||
renderer.fill_text(Text {
|
||||
content: ev_day.text.as_str(),
|
||||
bounds: ev_bounds,
|
||||
size: params.ev_fontsize,
|
||||
line_height: LineHeight::default(),
|
||||
color: fg,
|
||||
font: renderer.default_font(),
|
||||
horizontal_alignment: alignment::Horizontal::Left,
|
||||
vertical_alignment: alignment::Vertical::Top,
|
||||
shaping: Shaping::default(),
|
||||
});
|
||||
ev_y += ev_height
|
||||
}
|
||||
}
|
||||
if day_bounds.height - day_text_size.1 > ev_height {
|
||||
if let Some(ev_day) = events.is_any_in_day(current_day) {
|
||||
let ev_bounds = Rectangle {
|
||||
y: y + day_text_size.1,
|
||||
height: ev_height,
|
||||
..day_bounds
|
||||
};
|
||||
renderer.fill_quad(renderer::Quad {
|
||||
bounds: ev_bounds,
|
||||
border_radius: 0.0.into(),
|
||||
border_width: 1.0,
|
||||
border_color: params.day_other_month_fg,
|
||||
},
|
||||
params.ev_bg);
|
||||
renderer.fill_text(Text {
|
||||
content: ev_day.text.as_str(),
|
||||
bounds: ev_bounds,
|
||||
size: params.ev_fontsize,
|
||||
line_height: LineHeight::default(),
|
||||
color: fg,
|
||||
font: renderer.default_font(),
|
||||
horizontal_alignment: alignment::Horizontal::Left,
|
||||
vertical_alignment: alignment::Vertical::Top,
|
||||
shaping: Shaping::default(),
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//-------------------------------------------------------------------------
|
||||
|
||||
pub struct CalendarMonthView<'a> {
|
||||
first_day: NaiveDate,
|
||||
first_day_in_view: NaiveDate,
|
||||
params: CalendarParams,
|
||||
week_column_width: f32,
|
||||
week_column_font_size: f32,
|
||||
events: &'a EventsCollection,
|
||||
}
|
||||
|
||||
impl CalendarMonthView {
|
||||
pub fn new(params: &CalendarParams, day: NaiveDate) -> Self {
|
||||
impl<'a> CalendarMonthView<'a> {
|
||||
pub fn new(params: &CalendarParams, day: NaiveDate, events: &'a EventsCollection) -> Self {
|
||||
// first day of the month
|
||||
let first_day = if day.day() == 1 {
|
||||
day
|
||||
} else {
|
||||
NaiveDate::from_ymd(day.year(), day.month(), 1)
|
||||
NaiveDate::from_ymd_opt(day.year(), day.month(), 1).unwrap()
|
||||
};
|
||||
|
||||
// weekday on first day of the month
|
||||
|
@ -114,6 +193,7 @@ impl CalendarMonthView {
|
|||
params: params.clone(),
|
||||
week_column_width: 30.0,
|
||||
week_column_font_size: 18.0,
|
||||
events,
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -122,7 +202,7 @@ impl CalendarMonthView {
|
|||
let first_day = if day.day() == 1 {
|
||||
day
|
||||
} else {
|
||||
NaiveDate::from_ymd(day.year(), day.month(), 1)
|
||||
NaiveDate::from_ymd_opt(day.year(), day.month(), 1).unwrap()
|
||||
};
|
||||
|
||||
// weekday on first day of the month
|
||||
|
@ -178,14 +258,16 @@ impl CalendarMonthView {
|
|||
// color of text
|
||||
let fg = self.params.header_fg;
|
||||
|
||||
renderer.fill_text(text::Text {
|
||||
renderer.fill_text(Text {
|
||||
content : t,
|
||||
size: font_size,
|
||||
bounds,
|
||||
size: font_size,
|
||||
line_height: LineHeight::default(),
|
||||
color: fg,
|
||||
font: Default::default(),
|
||||
horizontal_alignment: alignment::Horizontal::Left,
|
||||
font: renderer.default_font(),
|
||||
horizontal_alignment: alignment::Horizontal::Right,
|
||||
vertical_alignment: alignment::Vertical::Center,
|
||||
shaping: Shaping::default(),
|
||||
});
|
||||
}
|
||||
}
|
||||
|
@ -211,18 +293,20 @@ impl CalendarMonthView {
|
|||
day += Duration::weeks(1);
|
||||
|
||||
// render week cell text
|
||||
renderer.fill_text(text::Text {
|
||||
renderer.fill_text(Text {
|
||||
content : &(week_of_first_day_of_month).to_string(),
|
||||
size: self.week_column_font_size,
|
||||
bounds: Rectangle {
|
||||
x: day_bounds.center_x(),
|
||||
y: day_bounds.y,
|
||||
..day_bounds
|
||||
},
|
||||
size: self.week_column_font_size,
|
||||
line_height: LineHeight::default(),
|
||||
color: self.params.day_fg,
|
||||
font: Default::default(),
|
||||
font: renderer.default_font(),
|
||||
horizontal_alignment: alignment::Horizontal::Center,
|
||||
vertical_alignment: alignment::Vertical::Top,
|
||||
shaping: Shaping::default(),
|
||||
});
|
||||
}
|
||||
}
|
||||
|
@ -258,7 +342,7 @@ impl CalendarMonthView {
|
|||
};
|
||||
|
||||
// background color of the day cell
|
||||
let bg_color = if current_day == Local::today().naive_local() {
|
||||
let bg_color = if current_day == Local::now().date_naive() {
|
||||
self.params.day_today_bg
|
||||
} else if current_day.weekday().num_days_from_monday() > 4 {
|
||||
self.params.day_weekend_bg
|
||||
|
@ -279,22 +363,36 @@ impl CalendarMonthView {
|
|||
bg_color);
|
||||
|
||||
// render day cell text
|
||||
renderer.fill_text(text::Text {
|
||||
renderer.fill_text(Text {
|
||||
content,
|
||||
size: font_size,
|
||||
bounds: Rectangle {x, y, ..day_bounds},
|
||||
size: font_size,
|
||||
line_height: LineHeight::default(),
|
||||
color: fg,
|
||||
font: Default::default(),
|
||||
font: renderer.default_font(),
|
||||
horizontal_alignment: alignment::Horizontal::Left,
|
||||
vertical_alignment: alignment::Vertical::Top,
|
||||
shaping: Shaping::default()
|
||||
});
|
||||
current_day = current_day.succ();
|
||||
|
||||
render_events_in_day(
|
||||
&self.params,
|
||||
renderer,
|
||||
current_day,
|
||||
day_bounds,
|
||||
font_size,
|
||||
fg,
|
||||
content,
|
||||
self.events
|
||||
);
|
||||
|
||||
current_day = current_day.succ_opt().unwrap();
|
||||
}
|
||||
}
|
||||
|
||||
} // CalendarMonthView
|
||||
|
||||
impl<Message, Renderer> Widget<Message, Renderer> for CalendarMonthView
|
||||
impl<Message, Renderer> Widget<Message, Renderer> for CalendarMonthView<'_>
|
||||
where
|
||||
Renderer: text::Renderer,
|
||||
{
|
||||
|
@ -320,7 +418,7 @@ where
|
|||
renderer: &mut Renderer,
|
||||
_theme: &Renderer::Theme,
|
||||
_style: &renderer::Style,
|
||||
layout: Layout<'_>,
|
||||
layout: layout::Layout<'_>,
|
||||
_cursor_position: Point,
|
||||
_viewport: &Rectangle,
|
||||
) {
|
||||
|
@ -359,11 +457,11 @@ where
|
|||
}
|
||||
}
|
||||
|
||||
impl<'a, Message, Renderer> From<CalendarMonthView> for Element<'a, Message, Renderer>
|
||||
impl<'a, Message, Renderer> From<CalendarMonthView<'a>> for Element<'a, Message, Renderer>
|
||||
where
|
||||
Renderer: text::Renderer,
|
||||
{
|
||||
fn from(month_view: CalendarMonthView) -> Self {
|
||||
fn from(month_view: CalendarMonthView<'a>) -> Self {
|
||||
Self::new(month_view)
|
||||
}
|
||||
}
|
||||
|
@ -382,7 +480,7 @@ pub struct CalendarYearView<'a> {
|
|||
impl<'a> CalendarYearView<'a> {
|
||||
pub fn new(params: &CalendarParams, day: NaiveDate, events: &'a EventsCollection) -> Self {
|
||||
// first day of the year
|
||||
let first_day = NaiveDate::from_ymd(day.year(), 1, 1);
|
||||
let first_day = NaiveDate::from_ymd_opt(day.year(), 1, 1).unwrap();
|
||||
|
||||
// weekday on first day of the year
|
||||
let weekday_on_first = first_day.weekday();
|
||||
|
@ -402,7 +500,7 @@ impl<'a> CalendarYearView<'a> {
|
|||
|
||||
pub fn set_year(&mut self, day: NaiveDate) {
|
||||
// first day of the year
|
||||
self.first_day = NaiveDate::from_ymd(day.year(), 1, 1);
|
||||
self.first_day = NaiveDate::from_ymd_opt(day.year(), 1, 1).unwrap();
|
||||
|
||||
// weekday on first day of the year
|
||||
let weekday_on_first = self.first_day.weekday();
|
||||
|
@ -474,14 +572,16 @@ impl<'a> CalendarYearView<'a> {
|
|||
|
||||
let x = bounds.x + self.params.day_text_margin;
|
||||
let y = bounds.center_y();
|
||||
renderer.fill_text(text::Text {
|
||||
renderer.fill_text(Text {
|
||||
content : t,
|
||||
size: font_size,
|
||||
bounds: Rectangle {x, y, ..bounds},
|
||||
size: font_size,
|
||||
line_height: LineHeight::default(),
|
||||
color: fg,
|
||||
font: Default::default(),
|
||||
font: renderer.default_font(),
|
||||
horizontal_alignment: alignment::Horizontal::Left,
|
||||
vertical_alignment: alignment::Vertical::Center,
|
||||
shaping: Shaping::default(),
|
||||
});
|
||||
}
|
||||
}
|
||||
|
@ -504,18 +604,20 @@ impl<'a> CalendarYearView<'a> {
|
|||
};
|
||||
|
||||
// render month name
|
||||
renderer.fill_text(text::Text {
|
||||
renderer.fill_text(Text {
|
||||
content : MONTH_NAMES[month],
|
||||
size: self.month_column_font_size,
|
||||
bounds: Rectangle {
|
||||
x: month_name_bounds.x + self.margin,
|
||||
y: month_name_bounds.center_y(),
|
||||
..month_name_bounds
|
||||
},
|
||||
size: self.month_column_font_size,
|
||||
line_height: LineHeight::default(),
|
||||
color: self.params.day_fg,
|
||||
font: Default::default(),
|
||||
font: renderer.default_font(),
|
||||
horizontal_alignment: alignment::Horizontal::Left,
|
||||
vertical_alignment: alignment::Vertical::Center,
|
||||
shaping: Shaping::default(),
|
||||
});
|
||||
}
|
||||
}
|
||||
|
@ -555,7 +657,7 @@ impl<'a> CalendarYearView<'a> {
|
|||
let fg = self.params.day_fg;
|
||||
|
||||
// background color of the day cell
|
||||
let bg_color = if current_day == Local::today().naive_local() {
|
||||
let bg_color = if current_day == Local::now().date_naive() {
|
||||
self.params.day_today_bg
|
||||
} else if weekday > 4 {
|
||||
self.params.day_weekend_bg
|
||||
|
@ -576,44 +678,28 @@ impl<'a> CalendarYearView<'a> {
|
|||
bg_color);
|
||||
|
||||
// render day cell text
|
||||
renderer.fill_text(text::Text {
|
||||
renderer.fill_text(Text {
|
||||
content,
|
||||
size: font_size,
|
||||
bounds: Rectangle {x, y, ..day_bounds},
|
||||
size: font_size,
|
||||
line_height: LineHeight::default(),
|
||||
color: fg,
|
||||
font: Default::default(),
|
||||
font: renderer.default_font(),
|
||||
horizontal_alignment: alignment::Horizontal::Left,
|
||||
vertical_alignment: alignment::Vertical::Top,
|
||||
shaping: Shaping::default(),
|
||||
});
|
||||
|
||||
// render events, if enough space
|
||||
let day_text_size = renderer.measure(content, font_size, Default::default(), day_bounds.size());
|
||||
let ev_height = self.params.ev_height;
|
||||
if day_bounds.height - day_text_size.1 > ev_height {
|
||||
if let Some(ev_day) = self.events.is_any_in_day(current_day) {
|
||||
let ev_bounds = Rectangle {
|
||||
y: y + day_text_size.1,
|
||||
height: ev_height,
|
||||
..day_bounds
|
||||
};
|
||||
renderer.fill_quad(renderer::Quad {
|
||||
bounds: ev_bounds,
|
||||
border_radius: 0.0.into(),
|
||||
border_width: 1.0,
|
||||
border_color: self.params.day_other_month_fg,
|
||||
},
|
||||
self.params.ev_bg);
|
||||
renderer.fill_text(text::Text {
|
||||
content: ev_day.text.as_str(),
|
||||
size: self.params.ev_fontsize,
|
||||
bounds: ev_bounds,
|
||||
color: fg,
|
||||
font: Default::default(),
|
||||
horizontal_alignment: alignment::Horizontal::Left,
|
||||
vertical_alignment: alignment::Vertical::Top,
|
||||
});
|
||||
}
|
||||
}
|
||||
render_events_in_day(
|
||||
&self.params,
|
||||
renderer,
|
||||
current_day,
|
||||
day_bounds,
|
||||
font_size,
|
||||
fg,
|
||||
content,
|
||||
self.events
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -621,7 +707,11 @@ impl<'a> CalendarYearView<'a> {
|
|||
fn compute_month_col_width(&self, renderer: &mut impl text::Renderer) -> f32 {
|
||||
let mut max_max_font_width = 0.0;
|
||||
for month_name in MONTH_NAMES {
|
||||
let month_width = renderer.measure_width(month_name, self.month_column_font_size, Default::default());
|
||||
let month_width = renderer.measure_width(
|
||||
month_name,
|
||||
self.month_column_font_size,
|
||||
renderer.default_font(),
|
||||
Shaping::default());
|
||||
if month_width > max_max_font_width {
|
||||
max_max_font_width = month_width;
|
||||
}
|
||||
|
@ -657,7 +747,7 @@ where
|
|||
renderer: &mut Renderer,
|
||||
_theme: &Renderer::Theme,
|
||||
_style: &renderer::Style,
|
||||
layout: Layout<'_>,
|
||||
layout: layout::Layout<'_>,
|
||||
_cursor_position: Point,
|
||||
_viewport: &Rectangle,
|
||||
) {
|
||||
|
|
Loading…
Reference in New Issue