Skip to content

Commit

Permalink
Merge pull request #72 from DerpDays/main
Browse files Browse the repository at this point in the history
feat: add highlighter tool
  • Loading branch information
gabm authored Apr 4, 2024
2 parents 591a920 + 8755f86 commit 1ba60d6
Show file tree
Hide file tree
Showing 6 changed files with 163 additions and 5 deletions.
3 changes: 2 additions & 1 deletion icons.toml
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ icons = [
"cursor-regular",
"number-circle-1-regular",
"drop-regular",
"highlight-regular",
"arrow-redo-filled",
"arrow-undo-filled",
"save-regular",
Expand All @@ -16,4 +17,4 @@ icons = [
"crop-filled",
"arrow-up-right-filled",
"rectangle-landscape-regular",
]
]
2 changes: 2 additions & 0 deletions src/command_line.rs
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,7 @@ pub enum Tools {
Text,
Marker,
Blur,
Highlight,
Brush,
}

Expand All @@ -79,6 +80,7 @@ impl std::fmt::Display for Tools {
Text => "text",
Marker => "marker",
Blur => "blur",
Highlight => "highlight",
Brush => "brush",
};
f.write_str(s)
Expand Down
8 changes: 8 additions & 0 deletions src/style.rs
Original file line number Diff line number Diff line change
Expand Up @@ -204,4 +204,12 @@ impl Size {
Size::Large => 30.0 * size_factor,
}
}

pub fn to_highlight_opacity(self) -> u8 {
match self {
Size::Small => 50,
Size::Medium => 100,
Size::Large => 150,
}
}
}
133 changes: 133 additions & 0 deletions src/tools/highlight.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,133 @@
use anyhow::Result;
use femtovg::{Paint, Path};

use relm4::gtk::gdk::Key;

use crate::{
math::{self, Vec2D},
sketch_board::{MouseEventMsg, MouseEventType},
style::{Size, Style},
};

use super::{Drawable, DrawableClone, Tool, ToolUpdateResult};

#[derive(Clone, Debug)]
pub struct Highlight {
top_left: Vec2D,
size: Option<Vec2D>,
style: Style,
editing: bool,
}

impl Drawable for Highlight {
fn draw(
&self,
canvas: &mut femtovg::Canvas<femtovg::renderer::OpenGl>,
_font: femtovg::FontId,
) -> Result<()> {
let size = match self.size {
Some(s) => s,
None => return Ok(()), // early exit if size is none
};

let (pos, size) = math::rect_ensure_positive_size(self.top_left, size);

if self.editing {
// include a border when selecting an area.
let border_paint =
Paint::color(self.style.color.into()).with_line_width(Size::Small.to_line_width());
let mut border_path = Path::new();
border_path.rect(pos.x, pos.y, size.x, size.y);
canvas.stroke_path(&border_path, &border_paint);
}

let mut shadow_path = Path::new();
shadow_path.rect(pos.x, pos.y, size.x, size.y);

let shadow_paint = Paint::color(femtovg::Color::rgba(
self.style.color.r,
self.style.color.g,
self.style.color.b,
self.style.size.to_highlight_opacity(),
));

canvas.fill_path(&shadow_path, &shadow_paint);
Ok(())
}
}

#[derive(Default)]
pub struct HighlightTool {
highlight: Option<Highlight>,
style: Style,
}

impl Tool for HighlightTool {
fn handle_mouse_event(&mut self, event: MouseEventMsg) -> ToolUpdateResult {
match event.type_ {
MouseEventType::BeginDrag => {
self.highlight = Some(Highlight {
top_left: event.pos,
size: None,
style: self.style,
editing: true,
});

ToolUpdateResult::Redraw
}
MouseEventType::EndDrag => {
if let Some(a) = &mut self.highlight {
if event.pos == Vec2D::zero() {
self.highlight = None;

ToolUpdateResult::Redraw
} else {
a.size = Some(event.pos);
a.editing = false;

let result = a.clone_box();
self.highlight = None;

ToolUpdateResult::Commit(result)
}
} else {
ToolUpdateResult::Unmodified
}
}
MouseEventType::UpdateDrag => {
if let Some(a) = &mut self.highlight {
if event.pos == Vec2D::zero() {
return ToolUpdateResult::Unmodified;
}
a.size = Some(event.pos);

ToolUpdateResult::Redraw
} else {
ToolUpdateResult::Unmodified
}
}
_ => ToolUpdateResult::Unmodified,
}
}

fn handle_key_event(&mut self, event: crate::sketch_board::KeyEventMsg) -> ToolUpdateResult {
if event.key == Key::Escape && self.highlight.is_some() {
self.highlight = None;
ToolUpdateResult::Redraw
} else {
ToolUpdateResult::Unmodified
}
}

fn handle_style_event(&mut self, style: Style) -> ToolUpdateResult {
self.style = style;
ToolUpdateResult::Unmodified
}

fn get_drawable(&self) -> Option<&dyn Drawable> {
match &self.highlight {
Some(d) => Some(d),
None => None,
}
}
}
13 changes: 11 additions & 2 deletions src/tools/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ mod arrow;
mod blur;
mod brush;
mod crop;
mod highlight;
mod line;
mod marker;
mod pointer;
Expand Down Expand Up @@ -125,6 +126,7 @@ pub enum ToolUpdateResult {
pub use arrow::ArrowTool;
pub use blur::BlurTool;
pub use crop::CropTool;
pub use highlight::HighlightTool;
pub use line::LineTool;
pub use rectangle::RectangleTool;
pub use text::TextTool;
Expand All @@ -142,7 +144,8 @@ pub enum Tools {
Text = 5,
Marker = 6,
Blur = 7,
Brush = 8,
Highlight = 8,
Brush = 9,
}

pub struct ToolsManager {
Expand All @@ -166,6 +169,10 @@ impl ToolsManager {
);
tools.insert(Tools::Text, Rc::new(RefCell::new(TextTool::default())));
tools.insert(Tools::Blur, Rc::new(RefCell::new(BlurTool::default())));
tools.insert(
Tools::Highlight,
Rc::new(RefCell::new(HighlightTool::default())),
);
tools.insert(Tools::Marker, Rc::new(RefCell::new(MarkerTool::default())));
tools.insert(Tools::Brush, Rc::new(RefCell::new(BrushTool::default())));

Expand Down Expand Up @@ -214,7 +221,8 @@ impl FromVariant for Tools {
5 => Some(Tools::Text),
6 => Some(Tools::Marker),
7 => Some(Tools::Blur),
8 => Some(Tools::Brush),
8 => Some(Tools::Highlight),
9 => Some(Tools::Brush),
_ => None,
})
}
Expand All @@ -231,6 +239,7 @@ impl From<command_line::Tools> for Tools {
command_line::Tools::Text => Self::Text,
command_line::Tools::Marker => Self::Marker,
command_line::Tools::Blur => Self::Blur,
command_line::Tools::Highlight => Self::Highlight,
command_line::Tools::Brush => Self::Brush,
}
}
Expand Down
9 changes: 7 additions & 2 deletions src/ui/toolbars.rs
Original file line number Diff line number Diff line change
Expand Up @@ -152,7 +152,6 @@ impl SimpleComponent for ToolsToolbar {
set_icon_name: "text-case-title-regular",
set_tooltip: "Text tool",
ActionablePlus::set_action::<ToolsAction>: Tools::Text,

},
gtk::ToggleButton {
set_focusable: false,
Expand All @@ -161,7 +160,6 @@ impl SimpleComponent for ToolsToolbar {
set_icon_name: "number-circle-1-regular",
set_tooltip: "Numbered Marker",
ActionablePlus::set_action::<ToolsAction>: Tools::Marker,

},
gtk::ToggleButton {
set_focusable: false,
Expand All @@ -170,7 +168,14 @@ impl SimpleComponent for ToolsToolbar {
set_icon_name: "drop-regular",
set_tooltip: "Blur",
ActionablePlus::set_action::<ToolsAction>: Tools::Blur,
},
gtk::ToggleButton {
set_focusable: false,
set_hexpand: false,

set_icon_name: "highlight-regular",
set_tooltip: "Highlight",
ActionablePlus::set_action::<ToolsAction>: Tools::Highlight,
},
gtk::Separator {},
gtk::Button {
Expand Down

0 comments on commit 1ba60d6

Please sign in to comment.