This is an automated email from the git hooks/post-receive script. thansen pushed a commit to branch master in repository aseprite.
commit 8a5de088e2f222fea69526aca28b70772090901d Author: David Capello <[email protected]> Date: Fri Apr 8 11:55:40 2016 -0300 Add scaling from center/pivot (fix #576) and with flipping (fix #579) --- data/gui.xml | 4 + src/app/ui/editor/moving_pixels_state.cpp | 5 +- src/app/ui/editor/pixels_movement.cpp | 184 +++++++++++++----------------- src/app/ui/editor/pixels_movement.h | 5 +- src/app/ui/keyboard_shortcuts.cpp | 2 + src/app/ui/keyboard_shortcuts.h | 1 + 6 files changed, 94 insertions(+), 107 deletions(-) diff --git a/data/gui.xml b/data/gui.xml index 1d1cb01..a0d4d4a 100644 --- a/data/gui.xml +++ b/data/gui.xml @@ -473,6 +473,10 @@ keyboard shortcut you maintain aspect ratio --> <key action="MaintainAspectRatio" shortcut="Shift" /> + <!-- When you scale the selection, pressing this key the + selectino will be scaled from the pivot point --> + <key action="ScaleFromCenter" shortcut="Alt" /> + <!-- Modifiers for selection tool --> <key action="AddSelection" shortcut="Shift" /> <key action="SubtractSelection" shortcut="Shift+Alt" /> diff --git a/src/app/ui/editor/moving_pixels_state.cpp b/src/app/ui/editor/moving_pixels_state.cpp index 9f3e03f..0be8360 100644 --- a/src/app/ui/editor/moving_pixels_state.cpp +++ b/src/app/ui/editor/moving_pixels_state.cpp @@ -1,5 +1,5 @@ // Aseprite -// Copyright (C) 2001-2015 David Capello +// Copyright (C) 2001-2016 David Capello // // This program is free software; you can redistribute it and/or modify // it under the terms of the GNU General Public License version 2 as @@ -355,6 +355,9 @@ bool MovingPixelsState::onMouseMove(Editor* editor, MouseMessage* msg) if (int(action & KeyAction::MaintainAspectRatio)) moveModifier |= PixelsMovement::MaintainAspectRatioMovement; + if (int(action & KeyAction::ScaleFromCenter)) + moveModifier |= PixelsMovement::ScaleFromPivot; + if (int(action & KeyAction::LockAxis)) moveModifier |= PixelsMovement::LockAxisMovement; diff --git a/src/app/ui/editor/pixels_movement.cpp b/src/app/ui/editor/pixels_movement.cpp index 81afc82..e21a1fa 100644 --- a/src/app/ui/editor/pixels_movement.cpp +++ b/src/app/ui/editor/pixels_movement.cpp @@ -228,147 +228,123 @@ void PixelsMovement::moveImage(const gfx::Point& pos, MoveModifier moveModifier) m_currentData.transformBox(oldCorners); ContextWriter writer(m_reader, 1000); - int x1, y1, x2, y2; - - x1 = m_initialData.bounds().x; - y1 = m_initialData.bounds().y; - x2 = m_initialData.bounds().x + m_initialData.bounds().w; - y2 = m_initialData.bounds().y + m_initialData.bounds().h; - + gfx::Rect bounds = m_initialData.bounds(); bool updateBounds = false; - int dx, dy; + double dx, dy; - dx = int((pos.x - m_catchPos.x) * cos(m_currentData.angle()) + - (pos.y - m_catchPos.y) * -sin(m_currentData.angle())); - dy = int((pos.x - m_catchPos.x) * sin(m_currentData.angle()) + - (pos.y - m_catchPos.y) * cos(m_currentData.angle())); + dx = ((pos.x - m_catchPos.x) * cos(m_currentData.angle()) + + (pos.y - m_catchPos.y) * -sin(m_currentData.angle())); + dy = ((pos.x - m_catchPos.x) * sin(m_currentData.angle()) + + (pos.y - m_catchPos.y) * cos(m_currentData.angle())); switch (m_handle) { case MoveHandle: - x1 += dx; - y1 += dy; - x2 += dx; - y2 += dy; - updateBounds = true; - if ((moveModifier & LockAxisMovement) == LockAxisMovement) { - if (ABS(dx) < ABS(dy)) { - x1 -= dx; - x2 -= dx; - } - else { - y1 -= dy; - y2 -= dy; - } + if (ABS(dx) < ABS(dy)) + dx = 0.0; + else + dy = 0.0; } + bounds.offset(int(dx), int(dy)); + updateBounds = true; + if ((moveModifier & SnapToGridMovement) == SnapToGridMovement) { // Snap the x1,y1 point to the grid. gfx::Rect gridBounds = App::instance() ->preferences().document(m_document).grid.bounds(); - gfx::Point gridOffset(x1, y1); + gfx::Point gridOffset(bounds.origin()); gridOffset = snap_to_grid(gridBounds, gridOffset, PreferSnapTo::ClosestGridVertex); // Now we calculate the difference from x1,y1 point and we can // use it to adjust all coordinates (x1, y1, x2, y2). - gridOffset -= gfx::Point(x1, y1); - - x1 += gridOffset.x; - y1 += gridOffset.y; - x2 += gridOffset.x; - y2 += gridOffset.y; + gridOffset -= bounds.origin(); + bounds.offset(gridOffset); } break; case ScaleNWHandle: - x1 = MIN(x1+dx, x2-1); - y1 = MIN(y1+dy, y2-1); - - if ((moveModifier & MaintainAspectRatioMovement) == MaintainAspectRatioMovement) { - if (1000 * (x2-x1) / getInitialImageSize().w > - 1000 * (y2-y1) / getInitialImageSize().h) { - y1 = y2 - getInitialImageSize().h * (x2-x1) / getInitialImageSize().w; - } - else { - x1 = x2 - getInitialImageSize().w * (y2-y1) / getInitialImageSize().h; - } - } - - updateBounds = true; - break; - case ScaleNHandle: - y1 = MIN(y1+dy, y2-1); - updateBounds = true; - break; - case ScaleNEHandle: - x2 = MAX(x2+dx, x1+1); - y1 = MIN(y1+dy, y2-1); - - if ((moveModifier & MaintainAspectRatioMovement) == MaintainAspectRatioMovement) { - if (1000 * (x2-x1) / getInitialImageSize().w > - 1000 * (y2-y1) / getInitialImageSize().h) { - y1 = y2 - getInitialImageSize().h * (x2-x1) / getInitialImageSize().w; - } - else { - x2 = x1 + getInitialImageSize().w * (y2-y1) / getInitialImageSize().h; - } - } - - updateBounds = true; - break; - case ScaleWHandle: - x1 = MIN(x1+dx, x2-1); - updateBounds = true; - break; - case ScaleEHandle: - x2 = MAX(x2+dx, x1+1); - updateBounds = true; - break; - case ScaleSWHandle: - x1 = MIN(x1+dx, x2-1); - y2 = MAX(y2+dy, y1+1); - - if ((moveModifier & MaintainAspectRatioMovement) == MaintainAspectRatioMovement) { - if (1000 * (x2-x1) / getInitialImageSize().w > - 1000 * (y2-y1) / getInitialImageSize().h) { - y2 = y1 + getInitialImageSize().h * (x2-x1) / getInitialImageSize().w; - } - else { - x1 = x2 - getInitialImageSize().w * (y2-y1) / getInitialImageSize().h; - } + case ScaleSHandle: + case ScaleSEHandle: { + static double handles[][2] = { + { 0.0, 0.0 }, { 0.5, 0.0 }, { 1.0, 0.0 }, + { 0.0, 0.5 }, { 1.0, 0.5 }, + { 0.0, 1.0 }, { 0.5, 1.0 }, { 1.0, 1.0 } + }; + gfx::PointT<double> pivot; + gfx::PointT<double> handle( + handles[m_handle-ScaleNWHandle][0], + handles[m_handle-ScaleNWHandle][1]); + + if ((moveModifier & ScaleFromPivot) == ScaleFromPivot) { + pivot.x = m_currentData.pivot().x; + pivot.y = m_currentData.pivot().y; + } + else { + pivot.x = 1.0 - handle.x; + pivot.y = 1.0 - handle.y; + pivot.x = bounds.x + bounds.w*pivot.x; + pivot.y = bounds.y + bounds.h*pivot.y; } - updateBounds = true; - break; + gfx::Point a = bounds.origin(); + gfx::Point b = bounds.point2(); - case ScaleSHandle: - y2 = MAX(y2+dy, y1+1); - updateBounds = true; - break; + if ((moveModifier & MaintainAspectRatioMovement) == MaintainAspectRatioMovement) { + auto u = point2Vector(gfx::PointT<double>(m_catchPos) - pivot); + auto v = point2Vector(gfx::PointT<double>(pos) - pivot); + auto w = v.projectOn(u); + double scale = u.magnitude(); + if (scale != 0.0) + scale = (std::fabs(w.angle()-u.angle()) < PI/2.0 ? 1.0: -1.0) * w.magnitude() / scale; + else + scale = 1.0; + + a.x = int((a.x-pivot.x)*scale + pivot.x); + a.y = int((a.y-pivot.y)*scale + pivot.y); + b.x = int((b.x-pivot.x)*scale + pivot.x); + b.y = int((b.y-pivot.y)*scale + pivot.y); + } + else { + handle.x = bounds.x + bounds.w*handle.x; + handle.y = bounds.y + bounds.h*handle.y; - case ScaleSEHandle: - x2 = MAX(x2+dx, x1+1); - y2 = MAX(y2+dy, y1+1); + double w = (handle.x-pivot.x); + double h = (handle.y-pivot.y); - if ((moveModifier & MaintainAspectRatioMovement) == MaintainAspectRatioMovement) { - if (1000 * (x2-x1) / getInitialImageSize().w > - 1000 * (y2-y1) / getInitialImageSize().h) { - y2 = y1 + getInitialImageSize().h * (x2-x1) / getInitialImageSize().w; + if (m_handle == ScaleNHandle || m_handle == ScaleSHandle) { + dx = 0.0; + w = 1.0; // Any value != 0.0 to avoid div by zero } - else { - x2 = x1 + getInitialImageSize().w * (y2-y1) / getInitialImageSize().h; + else if (m_handle == ScaleWHandle || m_handle == ScaleEHandle) { + dy = 0.0; + h = 1.0; } + + a.x = (a.x-pivot.x)*(1.0+dx/w) + pivot.x; + a.y = (a.y-pivot.y)*(1.0+dy/h) + pivot.y; + b.x = (b.x-pivot.x)*(1.0+dx/w) + pivot.x; + b.y = (b.y-pivot.y)*(1.0+dy/h) + pivot.y; } + // Do not use "gfx::Rect(a, b)" here because if a > b we want to + // keep a rectangle with negative width or height (to know that + // it was flipped). + bounds.x = a.x; + bounds.y = a.y; + bounds.w = b.x - a.x; + bounds.h = b.y - a.y; + updateBounds = true; break; + } case RotateNWHandle: case RotateNHandle: @@ -432,7 +408,7 @@ void PixelsMovement::moveImage(const gfx::Point& pos, MoveModifier moveModifier) } if (updateBounds) { - m_currentData.bounds(gfx::Rect(x1, y1, x2 - x1, y2 - y1)); + m_currentData.bounds(bounds); m_adjustPivot = true; } diff --git a/src/app/ui/editor/pixels_movement.h b/src/app/ui/editor/pixels_movement.h index 7490ac7..84c74f4 100644 --- a/src/app/ui/editor/pixels_movement.h +++ b/src/app/ui/editor/pixels_movement.h @@ -1,5 +1,5 @@ // Aseprite -// Copyright (C) 2001-2015 David Capello +// Copyright (C) 2001-2016 David Capello // // This program is free software; you can redistribute it and/or modify // it under the terms of the GNU General Public License version 2 as @@ -44,7 +44,8 @@ namespace app { SnapToGridMovement = 2, AngleSnapMovement = 4, MaintainAspectRatioMovement = 8, - LockAxisMovement = 16 + LockAxisMovement = 16, + ScaleFromPivot = 32, }; PixelsMovement(Context* context, diff --git a/src/app/ui/keyboard_shortcuts.cpp b/src/app/ui/keyboard_shortcuts.cpp index d9f895c..53c6f77 100644 --- a/src/app/ui/keyboard_shortcuts.cpp +++ b/src/app/ui/keyboard_shortcuts.cpp @@ -39,6 +39,7 @@ namespace { { "SnapToGrid" , "Snap To Grid" , app::KeyAction::SnapToGrid }, { "AngleSnap" , "Angle Snap" , app::KeyAction::AngleSnap }, { "MaintainAspectRatio" , "Maintain Aspect Ratio", app::KeyAction::MaintainAspectRatio }, + { "ScaleFromCenter" , "Scale From Center" , app::KeyAction::ScaleFromCenter }, { "LockAxis" , "Lock Axis" , app::KeyAction::LockAxis }, { "AddSelection" , "Add Selection" , app::KeyAction::AddSelection }, { "SubtractSelection" , "Subtract Selection" , app::KeyAction::SubtractSelection }, @@ -147,6 +148,7 @@ Key::Key(KeyAction action) m_keycontext = KeyContext::RotatingSelection; break; case KeyAction::MaintainAspectRatio: + case KeyAction::ScaleFromCenter: m_keycontext = KeyContext::ScalingSelection; break; case KeyAction::AddSelection: diff --git a/src/app/ui/keyboard_shortcuts.h b/src/app/ui/keyboard_shortcuts.h index bd53a4c..ed6cd49 100644 --- a/src/app/ui/keyboard_shortcuts.h +++ b/src/app/ui/keyboard_shortcuts.h @@ -71,6 +71,7 @@ namespace app { MoveOrigin = 0x00000800, SquareAspect = 0x00001000, DrawFromCenter = 0x00002000, + ScaleFromCenter = 0x00004000, }; inline KeyAction operator&(KeyAction a, KeyAction b) { -- Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-games/aseprite.git _______________________________________________ Pkg-games-commits mailing list [email protected] http://lists.alioth.debian.org/cgi-bin/mailman/listinfo/pkg-games-commits

