Move Painting demo to own window (and file)

This commit is contained in:
Emil Ernerfeldt 2020-12-19 17:02:42 +01:00
parent f9b1e88fe6
commit 8e9bce459f
4 changed files with 88 additions and 73 deletions

View File

@ -11,7 +11,6 @@ pub struct DemoWindow {
layout: LayoutDemo,
tree: Tree,
box_painting: BoxPainting,
painting: Painting,
}
impl Default for DemoWindow {
@ -24,7 +23,6 @@ impl Default for DemoWindow {
layout: Default::default(),
tree: Tree::demo(),
box_painting: Default::default(),
painting: Default::default(),
}
}
}
@ -75,10 +73,6 @@ impl DemoWindow {
});
});
CollapsingHeader::new("Paint with your mouse")
.default_open(false)
.show(ui, |ui| self.painting.ui(ui));
CollapsingHeader::new("Resize")
.default_open(false)
.show(ui, |ui| {
@ -232,72 +226,6 @@ impl BoxPainting {
// ----------------------------------------------------------------------------
#[cfg_attr(feature = "serde", derive(serde::Deserialize, serde::Serialize))]
#[cfg_attr(feature = "serde", serde(default))]
struct Painting {
lines: Vec<Vec<Vec2>>,
stroke: Stroke,
}
impl Default for Painting {
fn default() -> Self {
Self {
lines: Default::default(),
stroke: Stroke::new(1.0, LIGHT_BLUE),
}
}
}
impl Painting {
pub fn ui(&mut self, ui: &mut Ui) {
ui.label("Draw with your mouse to paint");
ui.horizontal(|ui| {
self.stroke.ui(ui, "Stroke");
if ui.button("Clear").clicked {
self.lines.clear();
}
});
Resize::default()
.default_size([200.0, 200.0])
.show(ui, |ui| self.content(ui));
}
fn content(&mut self, ui: &mut Ui) {
let painter = ui.allocate_painter(ui.available_size_before_wrap_finite());
let rect = painter.clip_rect();
let id = ui.make_position_id();
let response = ui.interact(rect, id, Sense::drag());
if self.lines.is_empty() {
self.lines.push(vec![]);
}
let current_line = self.lines.last_mut().unwrap();
if response.active {
if let Some(mouse_pos) = ui.input().mouse.pos {
let canvas_pos = mouse_pos - rect.min;
if current_line.last() != Some(&canvas_pos) {
current_line.push(canvas_pos);
}
}
} else if !current_line.is_empty() {
self.lines.push(vec![]);
}
for line in &self.lines {
if line.len() >= 2 {
let points: Vec<Pos2> = line.iter().map(|p| rect.min + *p).collect();
painter.add(paint::PaintCmd::line(points, self.stroke));
}
}
}
}
// ----------------------------------------------------------------------------
use crate::layout::*;
#[cfg_attr(feature = "serde", derive(serde::Deserialize, serde::Serialize))]

View File

@ -36,6 +36,7 @@ impl Default for Demos {
Self {
demos: vec![
(false, Box::new(crate::demos::FontBook::default())),
(false, Box::new(crate::demos::Painting::default())),
(false, Box::new(crate::demos::DancingStrings::default())),
(false, Box::new(crate::demos::DragAndDropDemo::default())),
(false, Box::new(crate::demos::Tests::default())),

View File

@ -11,6 +11,7 @@ mod font_book;
pub mod font_contents_emoji;
pub mod font_contents_ubuntu;
mod fractal_clock;
mod painting;
mod sliders;
mod tests;
pub mod toggle_switch;
@ -19,7 +20,7 @@ mod widgets;
pub use {
app::*, color_test::ColorTest, dancing_strings::DancingStrings, demo_window::DemoWindow,
demo_windows::*, drag_and_drop::*, font_book::FontBook, fractal_clock::FractalClock,
sliders::Sliders, tests::Tests, widgets::Widgets,
painting::Painting, sliders::Sliders, tests::Tests, widgets::Widgets,
};
pub const LOREM_IPSUM: &str = "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.";

View File

@ -0,0 +1,85 @@
use crate::{demos::*, *};
#[cfg_attr(feature = "serde", derive(serde::Deserialize, serde::Serialize))]
#[cfg_attr(feature = "serde", serde(default))]
pub struct Painting {
lines: Vec<Vec<Vec2>>,
stroke: Stroke,
}
impl Default for Painting {
fn default() -> Self {
Self {
lines: Default::default(),
stroke: Stroke::new(1.0, color::LIGHT_BLUE),
}
}
}
impl Painting {
pub fn ui_control(&mut self, ui: &mut Ui) {
ui.horizontal(|ui| {
self.stroke.ui(ui, "Stroke");
ui.separator();
if ui.button("Clear Painting").clicked {
self.lines.clear();
}
});
}
pub fn ui_content(&mut self, ui: &mut Ui) {
let painter = ui.allocate_painter(ui.available_size_before_wrap_finite());
let rect = painter.clip_rect();
let id = ui.make_position_id();
let response = ui.interact(rect, id, Sense::drag());
if self.lines.is_empty() {
self.lines.push(vec![]);
}
let current_line = self.lines.last_mut().unwrap();
if response.active {
if let Some(mouse_pos) = ui.input().mouse.pos {
let canvas_pos = mouse_pos - rect.min;
if current_line.last() != Some(&canvas_pos) {
current_line.push(canvas_pos);
}
}
} else if !current_line.is_empty() {
self.lines.push(vec![]);
}
for line in &self.lines {
if line.len() >= 2 {
let points: Vec<Pos2> = line.iter().map(|p| rect.min + *p).collect();
painter.add(PaintCmd::line(points, self.stroke));
}
}
}
}
impl demos::Demo for Painting {
fn name(&self) -> &str {
"🖊 Painting"
}
fn show(&mut self, ctx: &CtxRef, open: &mut bool) {
Window::new(self.name())
.open(open)
.default_size(vec2(512.0, 512.0))
.scroll(false)
.show(ctx, |ui| self.ui(ui));
}
}
impl demos::View for Painting {
fn ui(&mut self, ui: &mut Ui) {
ui.add(__egui_github_link_file!("(source code)"));
self.ui_control(ui);
ui.label("Paint with your mouse/touch!");
Frame::dark_canvas(ui.style()).show(ui, |ui| {
self.ui_content(ui);
});
}
}