From 1a3481f35bdd3bd26efbf31bbcdf32fc83513464 Mon Sep 17 00:00:00 2001 From: Mustafa Quraish Date: Thu, 26 Aug 2021 15:54:00 -0400 Subject: [PATCH] PixelPaint: Add ability to draw ellipse from center Like other common image editing applications, now if you press `alt` while drawing an ellipse, it uses the starting position as the center of the ellipse as opposed to one of the corners of the bounding rect. The EllipseTool class now keeps track of a `DrawMode`, which is either `DrawMode::FromCorner` (default), or `DrawMode::FromCenter` (the option added by this commit). The `draw_using()` function was modified to now take in the start and end positions and construct the `ellipse_intersecting_rect` itself, since we need to construct it differently based on the drawing mode. --- .../Applications/PixelPaint/EllipseTool.cpp | 17 ++++++++++++++--- Userland/Applications/PixelPaint/EllipseTool.h | 9 ++++++++- 2 files changed, 22 insertions(+), 4 deletions(-) diff --git a/Userland/Applications/PixelPaint/EllipseTool.cpp b/Userland/Applications/PixelPaint/EllipseTool.cpp index 50e1bbd2d91..5c5e4666c5c 100644 --- a/Userland/Applications/PixelPaint/EllipseTool.cpp +++ b/Userland/Applications/PixelPaint/EllipseTool.cpp @@ -1,5 +1,6 @@ /* * Copyright (c) 2018-2020, Andreas Kling + * Copyright (c) 2021, Mustafa Quraish * * SPDX-License-Identifier: BSD-2-Clause */ @@ -26,8 +27,16 @@ EllipseTool::~EllipseTool() { } -void EllipseTool::draw_using(GUI::Painter& painter, Gfx::IntRect const& ellipse_intersecting_rect) +void EllipseTool::draw_using(GUI::Painter& painter, Gfx::IntPoint const& start_position, Gfx::IntPoint const& end_position) { + Gfx::IntRect ellipse_intersecting_rect; + if (m_draw_mode == DrawMode::FromCenter) { + auto delta = end_position - start_position; + ellipse_intersecting_rect = Gfx::IntRect::from_two_points(start_position - delta, end_position); + } else { + ellipse_intersecting_rect = Gfx::IntRect::from_two_points(start_position, end_position); + } + switch (m_mode) { case Mode::Outline: painter.draw_ellipse_intersecting(ellipse_intersecting_rect, m_editor->color_for(m_drawing_button), m_thickness); @@ -65,7 +74,7 @@ void EllipseTool::on_mouseup(Layer* layer, MouseEvent& event) if (event.layer_event().button() == m_drawing_button) { GUI::Painter painter(layer->bitmap()); - draw_using(painter, Gfx::IntRect::from_two_points(m_ellipse_start_position, m_ellipse_end_position)); + draw_using(painter, m_ellipse_start_position, m_ellipse_end_position); m_drawing_button = GUI::MouseButton::None; m_editor->update(); m_editor->did_complete_action(); @@ -77,6 +86,8 @@ void EllipseTool::on_mousemove(Layer*, MouseEvent& event) if (m_drawing_button == GUI::MouseButton::None) return; + m_draw_mode = event.layer_event().alt() ? DrawMode::FromCenter : DrawMode::FromCorner; + m_ellipse_end_position = event.layer_event().position(); m_editor->update(); } @@ -90,7 +101,7 @@ void EllipseTool::on_second_paint(Layer const* layer, GUI::PaintEvent& event) painter.add_clip_rect(event.rect()); auto preview_start = m_editor->layer_position_to_editor_position(*layer, m_ellipse_start_position).to_type(); auto preview_end = m_editor->layer_position_to_editor_position(*layer, m_ellipse_end_position).to_type(); - draw_using(painter, Gfx::IntRect::from_two_points(preview_start, preview_end)); + draw_using(painter, preview_start, preview_end); } void EllipseTool::on_keydown(GUI::KeyEvent& event) diff --git a/Userland/Applications/PixelPaint/EllipseTool.h b/Userland/Applications/PixelPaint/EllipseTool.h index 08b22a245d9..9f85b95e738 100644 --- a/Userland/Applications/PixelPaint/EllipseTool.h +++ b/Userland/Applications/PixelPaint/EllipseTool.h @@ -1,5 +1,6 @@ /* * Copyright (c) 2018-2020, Andreas Kling + * Copyright (c) 2021, Mustafa Quraish * * SPDX-License-Identifier: BSD-2-Clause */ @@ -31,7 +32,12 @@ private: Fill, }; - void draw_using(GUI::Painter&, Gfx::IntRect const&); + enum class DrawMode { + FromCenter, + FromCorner, + }; + + void draw_using(GUI::Painter&, Gfx::IntPoint const& start_position, Gfx::IntPoint const& end_position); RefPtr m_properties_widget; GUI::MouseButton m_drawing_button { GUI::MouseButton::None }; @@ -39,6 +45,7 @@ private: Gfx::IntPoint m_ellipse_end_position; int m_thickness { 1 }; Mode m_mode { Mode::Outline }; + DrawMode m_draw_mode { DrawMode::FromCorner }; }; }