Skip to content

Commit

Permalink
updated Tabs to latest Iced. Also fixed #81
Browse files Browse the repository at this point in the history
  • Loading branch information
genusistimelord committed Jul 26, 2023
1 parent 2f03a33 commit e9dc6b9
Show file tree
Hide file tree
Showing 8 changed files with 214 additions and 162 deletions.
10 changes: 6 additions & 4 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -46,14 +46,16 @@ default = [
"grid",
"modal",
"tab_bar",
#"tabs",
"tabs",
"time_picker",
"wrap",
"selection_list",
"split",
#"menu",
"quad",
#"context_menu"
"context_menu",
#"spinner",
#"cupertino",
]

[dependencies]
Expand Down Expand Up @@ -99,7 +101,7 @@ members = [
"examples/modal",
"examples/modal_component",
"examples/tab_bar",
#"examples/tabs",
"examples/tabs",
"examples/time_picker",
"examples/wrap",
"examples/number_input",
Expand All @@ -108,7 +110,7 @@ members = [
"examples/split_scroller",
#"examples/menu",
#"examples/spinner",
#"examples/context_menu"
"examples/context_menu"
]

[workspace.dependencies.iced]
Expand Down
172 changes: 107 additions & 65 deletions examples/tabs/src/main.rs
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
mod login;
use iced::{
alignment::{Horizontal, Vertical},
widget::{Column, Container, Text},
Element, Font, Length, Sandbox, Settings,
alignment::{self, Horizontal, Vertical},
font,
widget::{container, text, Column, Container, Text},
Application, Command, Element, Font, Length, Settings, Theme,
};
use iced_aw::{TabLabel, Tabs};
use login::{LoginMessage, LoginTab};
Expand All @@ -18,11 +19,8 @@ use settings::{SettingsMessage, SettingsTab, TabBarPosition};

const HEADER_SIZE: u16 = 32;
const TAB_PADDING: u16 = 16;

const ICON_FONT: Font = iced::Font::External {
name: "Icons",
bytes: include_bytes!("../fonts/icons.ttf"),
};
const ICON_FONT_BYTES: &[u8] = include_bytes!("../fonts/icons.ttf");
const ICON_FONT: Font = Font::with_name("icons");

enum Icon {
User,
Expand All @@ -46,7 +44,12 @@ fn main() -> iced::Result {
TabBarExample::run(Settings::default())
}

struct TabBarExample {
enum TabBarExample {
Loading,
Loaded(State),
}

struct State {
active_tab: TabId,
login_tab: LoginTab,
ferris_tab: FerrisTab,
Expand All @@ -68,76 +71,115 @@ enum Message {
Ferris(FerrisMessage),
Counter(CounterMessage),
Settings(SettingsMessage),
Loaded(Result<(), String>),
FontLoaded(Result<(), font::Error>),
}

impl Sandbox for TabBarExample {
type Message = Message;
async fn load() -> Result<(), String> {
Ok(())
}

fn new() -> Self {
TabBarExample {
active_tab: TabId::Login,
login_tab: LoginTab::new(),
ferris_tab: FerrisTab::new(),
counter_tab: CounterTab::new(),
settings_tab: SettingsTab::new(),
}
impl Application for TabBarExample {
type Message = Message;
type Theme = Theme;
type Executor = iced::executor::Default;
type Flags = ();

fn new(_flags: ()) -> (TabBarExample, Command<Message>) {
(
TabBarExample::Loading,
Command::batch(vec![
font::load(ICON_FONT_BYTES).map(Message::FontLoaded),
Command::perform(load(), Message::Loaded),
]),
)
}

fn title(&self) -> String {
String::from("TabBar Example")
}

fn update(&mut self, message: Self::Message) {
match message {
Message::TabSelected(selected) => self.active_tab = selected,
Message::Login(message) => self.login_tab.update(message),
Message::Ferris(message) => self.ferris_tab.update(message),
Message::Counter(message) => self.counter_tab.update(message),
Message::Settings(message) => self.settings_tab.update(message),
fn update(&mut self, message: Self::Message) -> Command<Message> {
match self {
TabBarExample::Loading => {
if let Message::Loaded(_) = message {
*self = TabBarExample::Loaded(State {
active_tab: TabId::Login,
login_tab: LoginTab::new(),
ferris_tab: FerrisTab::new(),
counter_tab: CounterTab::new(),
settings_tab: SettingsTab::new(),
})
}
}
TabBarExample::Loaded(state) => match message {
Message::TabSelected(selected) => state.active_tab = selected,
Message::Login(message) => state.login_tab.update(message),
Message::Ferris(message) => state.ferris_tab.update(message),
Message::Counter(message) => state.counter_tab.update(message),
Message::Settings(message) => state.settings_tab.update(message),
_ => {}
},
}

Command::none()
}

fn view(&self) -> Element<'_, Self::Message> {
let position = self
.settings_tab
.settings()
.tab_bar_position
.unwrap_or_default();
let theme = self
.settings_tab
.settings()
.tab_bar_theme
.unwrap_or_default();

Tabs::new(Message::TabSelected)
.push(
TabId::Login,
self.login_tab.tab_label(),
self.login_tab.view(),
)
.push(
TabId::Ferris,
self.ferris_tab.tab_label(),
self.ferris_tab.view(),
)
.push(
TabId::Counter,
self.counter_tab.tab_label(),
self.counter_tab.view(),
)
.push(
TabId::Settings,
self.settings_tab.tab_label(),
self.settings_tab.view(),
match self {
TabBarExample::Loading => container(
text("Loading...")
.horizontal_alignment(alignment::Horizontal::Center)
.size(50),
)
.set_active_tab(&self.active_tab)
.tab_bar_style(theme)
.icon_font(ICON_FONT)
.tab_bar_position(match position {
TabBarPosition::Top => iced_aw::TabBarPosition::Top,
TabBarPosition::Bottom => iced_aw::TabBarPosition::Bottom,
})
.into()
.width(Length::Fill)
.height(Length::Fill)
.center_y()
.center_x()
.into(),
TabBarExample::Loaded(state) => {
let position = state
.settings_tab
.settings()
.tab_bar_position
.unwrap_or_default();
let theme = state
.settings_tab
.settings()
.tab_bar_theme
.unwrap_or_default();

Tabs::new(Message::TabSelected)
.push(
TabId::Login,
state.login_tab.tab_label(),
state.login_tab.view(),
)
.push(
TabId::Ferris,
state.ferris_tab.tab_label(),
state.ferris_tab.view(),
)
.push(
TabId::Counter,
state.counter_tab.tab_label(),
state.counter_tab.view(),
)
.push(
TabId::Settings,
state.settings_tab.tab_label(),
state.settings_tab.view(),
)
.set_active_tab(&state.active_tab)
.tab_bar_style(theme)
.icon_font(ICON_FONT)
.tab_bar_position(match position {
TabBarPosition::Top => iced_aw::TabBarPosition::Top,
TabBarPosition::Bottom => iced_aw::TabBarPosition::Bottom,
})
.into()
}
}
}
}

Expand Down
46 changes: 23 additions & 23 deletions src/native/context_menu.rs
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
//! A context menu for showing actions on right click.
//!
use iced_native::{
event,
mouse::{self, Button},
use iced_widget::core::{
self, event,
layout::{Limits, Node},
mouse::{self, Button, Cursor},
overlay, renderer,
widget::{tree, Operation, Tree},
Clipboard, Element, Event, Layout, Length, Point, Rectangle, Shell, Widget,
};
Expand Down Expand Up @@ -35,11 +37,11 @@ pub use crate::style::context_menu::StyleSheet;
/// );
/// ```
#[allow(missing_debug_implementations)]
pub struct ContextMenu<'a, Overlay, Message, Renderer>
pub struct ContextMenu<'a, Overlay, Message, Renderer = crate::Renderer>
where
Overlay: Fn() -> Element<'a, Message, Renderer>,
Message: Clone,
Renderer: iced_native::Renderer,
Renderer: core::Renderer,
Renderer::Theme: StyleSheet,
{
/// The underlying element.
Expand All @@ -54,7 +56,7 @@ impl<'a, Overlay, Message, Renderer> ContextMenu<'a, Overlay, Message, Renderer>
where
Overlay: Fn() -> Element<'a, Message, Renderer>,
Message: Clone,
Renderer: iced_native::Renderer,
Renderer: core::Renderer,
Renderer::Theme: StyleSheet,
{
/// Creates a new [`ContextMenu`](ContextMenu)
Expand Down Expand Up @@ -86,7 +88,7 @@ impl<'a, Content, Message, Renderer> Widget<Message, Renderer>
where
Content: 'a + Fn() -> Element<'a, Message, Renderer>,
Message: 'a + Clone,
Renderer: 'a + iced_native::Renderer,
Renderer: 'a + core::Renderer,
Renderer::Theme: StyleSheet,
{
fn width(&self) -> Length {
Expand All @@ -97,11 +99,7 @@ where
self.underlay.as_widget().height()
}

fn layout(
&self,
renderer: &Renderer,
limits: &iced_native::layout::Limits,
) -> iced_native::layout::Node {
fn layout(&self, renderer: &Renderer, limits: &Limits) -> Node {
self.underlay.as_widget().layout(renderer, limits)
}

Expand All @@ -110,9 +108,9 @@ where
state: &Tree,
renderer: &mut Renderer,
theme: &Renderer::Theme,
style: &iced_native::renderer::Style,
style: &renderer::Style,
layout: Layout<'_>,
cursor_position: Point,
cursor: Cursor,
viewport: &Rectangle,
) {
self.underlay.as_widget().draw(
Expand All @@ -121,7 +119,7 @@ where
theme,
style,
layout,
cursor_position,
cursor,
viewport,
);
}
Expand Down Expand Up @@ -170,17 +168,18 @@ where
state: &mut Tree,
event: Event,
layout: Layout<'_>,
cursor_position: Point,
cursor: Cursor,
renderer: &Renderer,
clipboard: &mut dyn Clipboard,
shell: &mut Shell<'_, Message>,
viewport: &Rectangle,
) -> event::Status {
if event == Event::Mouse(mouse::Event::ButtonPressed(Button::Right)) {
let bounds = layout.bounds();

if bounds.contains(cursor_position) {
if cursor.is_over(bounds) {
let s: &mut State = state.state.downcast_mut();
s.cursor_position = cursor_position;
s.cursor_position = cursor.position().unwrap_or_default();
s.show = !s.show;
return event::Status::Captured;
}
Expand All @@ -190,25 +189,26 @@ where
&mut state.children[0],
event,
layout,
cursor_position,
cursor,
renderer,
clipboard,
shell,
viewport,
)
}

fn mouse_interaction(
&self,
state: &Tree,
layout: Layout<'_>,
cursor_position: Point,
cursor: Cursor,
viewport: &Rectangle,
renderer: &Renderer,
) -> mouse::Interaction {
self.underlay.as_widget().mouse_interaction(
&state.children[0],
layout,
cursor_position,
cursor,
viewport,
renderer,
)
Expand All @@ -219,7 +219,7 @@ where
state: &'b mut Tree,
layout: Layout<'_>,
renderer: &Renderer,
) -> Option<iced_native::overlay::Element<'b, Message, Renderer>> {
) -> Option<overlay::Element<'b, Message, Renderer>> {
let s: &mut State = state.state.downcast_mut();

if !s.show {
Expand All @@ -245,7 +245,7 @@ impl<'a, Content, Message, Renderer> From<ContextMenu<'a, Content, Message, Rend
where
Content: 'a + Fn() -> Element<'a, Message, Renderer>,
Message: 'a + Clone,
Renderer: 'a + iced_native::Renderer,
Renderer: 'a + core::Renderer,
Renderer::Theme: StyleSheet,
{
fn from(modal: ContextMenu<'a, Content, Message, Renderer>) -> Self {
Expand Down
Loading

0 comments on commit e9dc6b9

Please sign in to comment.