Skip to content

Add option to make explain cycle through colors of the rainbow (+ fix layering) #2913

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 2 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
76 changes: 69 additions & 7 deletions core/src/element.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ use crate::{
};

use std::borrow::Borrow;
use std::iter::Cycle;

/// A generic [`Widget`].
///
Expand Down Expand Up @@ -206,7 +207,7 @@ impl<'a, Message, Theme, Renderer> Element<'a, Message, Theme, Renderer> {
/// This can be very useful for debugging your layout!
///
/// [`Renderer`]: crate::Renderer
pub fn explain<C: Into<Color>>(
pub fn explain<C: Into<ExplainColor>>(
self,
color: C,
) -> Element<'a, Message, Theme, Renderer>
Expand Down Expand Up @@ -381,7 +382,7 @@ where

struct Explain<'a, Message, Theme, Renderer: crate::Renderer> {
element: Element<'a, Message, Theme, Renderer>,
color: Color,
color: ExplainColor,
}

impl<'a, Message, Theme, Renderer> Explain<'a, Message, Theme, Renderer>
Expand All @@ -390,7 +391,7 @@ where
{
fn new(
element: Element<'a, Message, Theme, Renderer>,
color: Color,
color: ExplainColor,
) -> Self {
Explain { element, color }
}
Expand Down Expand Up @@ -474,14 +475,14 @@ where
) {
fn explain_layout<Renderer: crate::Renderer>(
renderer: &mut Renderer,
color: Color,
mut color: ExplainIterator,
layout: Layout<'_>,
) {
renderer.fill_quad(
renderer::Quad {
bounds: layout.bounds(),
border: Border {
color,
color: color.next().unwrap(),
width: 1.0,
..Border::default()
},
Expand All @@ -491,15 +492,17 @@ where
);

for child in layout.children() {
explain_layout(renderer, color, child);
explain_layout(renderer, color.clone(), child);
}
}

self.element
.widget
.draw(state, renderer, theme, style, layout, cursor, viewport);

explain_layout(renderer, self.color, layout);
renderer.with_layer(Rectangle::INFINITE, |renderer| {
explain_layout(renderer, self.color.into_iter(), layout);
});
}

fn mouse_interaction(
Expand Down Expand Up @@ -532,3 +535,62 @@ where
)
}
}

#[derive(Debug, Clone, Copy)]
/// What color to use when explaining the layout of an [`Element`].
pub enum ExplainColor {
/// Use a single color for this element and its children
Color(Color),
/// Cycle through the colors of the rainbow for every child of this element
Rainbow,
}

impl<C> From<C> for ExplainColor
where
C: Into<Color>,
{
fn from(color: C) -> Self {
Self::Color(color.into())
}
}

impl IntoIterator for ExplainColor {
type Item = Color;
type IntoIter = ExplainIterator;

fn into_iter(self) -> Self::IntoIter {
const RAINBOW: [Color; 6] = [
Color::from_rgb8(235, 134, 149), // Red
Color::from_rgb8(243, 167, 126), // Orange
Color::from_rgb8(233, 207, 157), // Yellow
Color::from_rgb8(165, 217, 148), // Green
Color::from_rgb8(121, 189, 221), // Blue
Color::from_rgb8(193, 157, 241), // Purple
];
match self {
ExplainColor::Rainbow => {
ExplainIterator::Rainbow(RAINBOW.into_iter().cycle())
}
ExplainColor::Color(color) => ExplainIterator::Color(color),
}
}
}

#[derive(Debug, Clone)]
/// A never-ending iterator that either returns a single color every time
/// or cycles through the colors of the rainbow on each call to [`Iterator::next`].
pub enum ExplainIterator {
Rainbow(Cycle<std::array::IntoIter<Color, 6>>),
Color(Color),
}

impl Iterator for ExplainIterator {
type Item = Color;

fn next(&mut self) -> Option<Self::Item> {
match self {
ExplainIterator::Rainbow(rainbow) => rainbow.next(),
ExplainIterator::Color(color) => Some(*color),
}
}
}
2 changes: 1 addition & 1 deletion core/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,7 @@ pub use border::Border;
pub use clipboard::Clipboard;
pub use color::Color;
pub use content_fit::ContentFit;
pub use element::Element;
pub use element::{Element, ExplainColor};
pub use event::Event;
pub use font::Font;
pub use gradient::Gradient;
Expand Down
6 changes: 3 additions & 3 deletions examples/layout/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,8 @@ use iced::widget::{
text, vertical_rule,
};
use iced::{
Center, Element, Fill, Font, Length, Point, Rectangle, Renderer, Shrink,
Subscription, Theme, color,
Center, Element, ExplainColor, Fill, Font, Length, Point, Rectangle,
Renderer, Shrink, Subscription, Theme,
};

pub fn main() -> iced::Result {
Expand Down Expand Up @@ -80,7 +80,7 @@ impl Layout {
.align_y(Center);

let example = center(if self.explain {
self.example.view().explain(color!(0x0000ff))
self.example.view().explain(ExplainColor::Rainbow)
} else {
self.example.view()
})
Expand Down
5 changes: 3 additions & 2 deletions src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -522,8 +522,9 @@ pub use crate::core::padding;
pub use crate::core::theme;
pub use crate::core::{
Alignment, Animation, Background, Border, Color, ContentFit, Degrees,
Function, Gradient, Length, Padding, Pixels, Point, Radians, Rectangle,
Rotation, Settings, Shadow, Size, Theme, Transformation, Vector, never,
ExplainColor, Function, Gradient, Length, Padding, Pixels, Point, Radians,
Rectangle, Rotation, Settings, Shadow, Size, Theme, Transformation, Vector,
never,
};
pub use crate::runtime::exit;
pub use iced_futures::Subscription;
Expand Down