mirror of
https://github.com/ShareX/ShareX.git
synced 2024-10-06 05:05:42 +13:00
300 lines
No EOL
10 KiB
C#
300 lines
No EOL
10 KiB
C#
#region License Information (GPL v3)
|
|
|
|
/*
|
|
ShareX - A program that allows you to take screenshots and share any file type
|
|
Copyright © 2007-2015 ShareX Developers
|
|
|
|
This program is free software; you can redistribute it and/or
|
|
modify it under the terms of the GNU General Public License
|
|
as published by the Free Software Foundation; either version 2
|
|
of the License, or (at your option) any later version.
|
|
|
|
This program is distributed in the hope that it will be useful,
|
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
GNU General Public License for more details.
|
|
|
|
You should have received a copy of the GNU General Public License
|
|
along with this program; if not, write to the Free Software
|
|
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
|
|
|
Optionally you can also view the license at <http://www.gnu.org/licenses/>.
|
|
*/
|
|
|
|
#endregion License Information (GPL v3)
|
|
|
|
using ShareX.HelpersLib;
|
|
using System.Drawing;
|
|
using System.Linq;
|
|
using System.Windows.Forms;
|
|
|
|
namespace ShareX.ScreenCaptureLib
|
|
{
|
|
public class ResizeManager
|
|
{
|
|
private bool visible;
|
|
|
|
public bool Visible
|
|
{
|
|
get
|
|
{
|
|
return visible;
|
|
}
|
|
set
|
|
{
|
|
visible = value;
|
|
|
|
foreach (NodeObject node in nodes)
|
|
{
|
|
node.Visible = visible;
|
|
}
|
|
}
|
|
}
|
|
|
|
public bool IsResizing { get; private set; }
|
|
public int MaxMoveSpeed { get; set; }
|
|
public int MinMoveSpeed { get; set; }
|
|
public bool IsBottomRightResizing { get; set; }
|
|
|
|
private AreaManager areaManager;
|
|
private NodeObject[] nodes;
|
|
private Rectangle tempRect;
|
|
|
|
public ResizeManager(Surface surface, AreaManager areaManager)
|
|
{
|
|
this.areaManager = areaManager;
|
|
|
|
MinMoveSpeed = surface.Config.MinMoveSpeed;
|
|
MaxMoveSpeed = surface.Config.MaxMoveSpeed;
|
|
|
|
surface.KeyDown += surface_KeyDown;
|
|
|
|
nodes = new NodeObject[8];
|
|
|
|
for (int i = 0; i < 8; i++)
|
|
{
|
|
nodes[i] = surface.MakeNode();
|
|
}
|
|
|
|
nodes[(int)NodePosition.BottomRight].Order = 10;
|
|
}
|
|
|
|
public void Update()
|
|
{
|
|
if (Visible && nodes != null)
|
|
{
|
|
if (InputManager.IsMouseDown(MouseButtons.Left))
|
|
{
|
|
for (int i = 0; i < 8; i++)
|
|
{
|
|
if (nodes[i].IsDragging)
|
|
{
|
|
IsResizing = true;
|
|
|
|
if (!InputManager.IsBeforeMouseDown(MouseButtons.Left))
|
|
{
|
|
tempRect = areaManager.CurrentArea;
|
|
}
|
|
|
|
NodePosition nodePosition = (NodePosition)i;
|
|
|
|
int x = InputManager.MouseVelocity.X;
|
|
|
|
switch (nodePosition)
|
|
{
|
|
case NodePosition.TopLeft:
|
|
case NodePosition.Left:
|
|
case NodePosition.BottomLeft:
|
|
tempRect.X += x;
|
|
tempRect.Width -= x;
|
|
break;
|
|
case NodePosition.TopRight:
|
|
case NodePosition.Right:
|
|
case NodePosition.BottomRight:
|
|
tempRect.Width += x;
|
|
break;
|
|
}
|
|
|
|
int y = InputManager.MouseVelocity.Y;
|
|
|
|
switch (nodePosition)
|
|
{
|
|
case NodePosition.TopLeft:
|
|
case NodePosition.Top:
|
|
case NodePosition.TopRight:
|
|
tempRect.Y += y;
|
|
tempRect.Height -= y;
|
|
break;
|
|
case NodePosition.BottomLeft:
|
|
case NodePosition.Bottom:
|
|
case NodePosition.BottomRight:
|
|
tempRect.Height += y;
|
|
break;
|
|
}
|
|
|
|
areaManager.CurrentArea = CaptureHelpers.FixRectangle(tempRect);
|
|
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
IsResizing = false;
|
|
}
|
|
|
|
UpdateNodePositions();
|
|
}
|
|
}
|
|
|
|
private void surface_KeyDown(object sender, KeyEventArgs e)
|
|
{
|
|
int speed;
|
|
|
|
if (e.Control)
|
|
{
|
|
speed = MaxMoveSpeed;
|
|
}
|
|
else
|
|
{
|
|
speed = MinMoveSpeed;
|
|
}
|
|
|
|
switch (e.KeyCode)
|
|
{
|
|
case Keys.Left:
|
|
if (!areaManager.IsCurrentAreaValid || areaManager.IsCreating)
|
|
{
|
|
Cursor.Position = new Point(Cursor.Position.X - speed, Cursor.Position.Y);
|
|
}
|
|
else
|
|
{
|
|
if (e.Shift)
|
|
{
|
|
MoveCurrentArea(-speed, 0);
|
|
}
|
|
else
|
|
{
|
|
ResizeCurrentArea(-speed, 0, IsBottomRightResizing);
|
|
}
|
|
}
|
|
break;
|
|
case Keys.Right:
|
|
if (!areaManager.IsCurrentAreaValid || areaManager.IsCreating)
|
|
{
|
|
Cursor.Position = new Point(Cursor.Position.X + speed, Cursor.Position.Y);
|
|
}
|
|
else
|
|
{
|
|
if (e.Shift)
|
|
{
|
|
MoveCurrentArea(speed, 0);
|
|
}
|
|
else
|
|
{
|
|
ResizeCurrentArea(speed, 0, IsBottomRightResizing);
|
|
}
|
|
}
|
|
break;
|
|
case Keys.Up:
|
|
if (!areaManager.IsCurrentAreaValid || areaManager.IsCreating)
|
|
{
|
|
Cursor.Position = new Point(Cursor.Position.X, Cursor.Position.Y - speed);
|
|
}
|
|
else
|
|
{
|
|
if (e.Shift)
|
|
{
|
|
MoveCurrentArea(0, -speed);
|
|
}
|
|
else
|
|
{
|
|
ResizeCurrentArea(0, -speed, IsBottomRightResizing);
|
|
}
|
|
}
|
|
break;
|
|
case Keys.Down:
|
|
if (!areaManager.IsCurrentAreaValid || areaManager.IsCreating)
|
|
{
|
|
Cursor.Position = new Point(Cursor.Position.X, Cursor.Position.Y + speed);
|
|
}
|
|
else
|
|
{
|
|
if (e.Shift)
|
|
{
|
|
MoveCurrentArea(0, speed);
|
|
}
|
|
else
|
|
{
|
|
ResizeCurrentArea(0, speed, IsBottomRightResizing);
|
|
}
|
|
}
|
|
break;
|
|
case Keys.Tab:
|
|
IsBottomRightResizing = !IsBottomRightResizing;
|
|
break;
|
|
}
|
|
}
|
|
|
|
public bool IsCursorOnNode()
|
|
{
|
|
return Visible && nodes.Any(node => node.IsMouseHover);
|
|
}
|
|
|
|
public void Show()
|
|
{
|
|
UpdateNodePositions();
|
|
|
|
Visible = true;
|
|
}
|
|
|
|
public void Hide()
|
|
{
|
|
Visible = false;
|
|
}
|
|
|
|
public void UpdateNodePositions()
|
|
{
|
|
UpdateNodePositions(areaManager.CurrentArea);
|
|
}
|
|
|
|
private void UpdateNodePositions(Rectangle rect)
|
|
{
|
|
float xStart = rect.X;
|
|
float xMid = rect.X + rect.Width / 2;
|
|
float xEnd = rect.X + rect.Width - 1;
|
|
|
|
float yStart = rect.Y;
|
|
float yMid = rect.Y + rect.Height / 2;
|
|
float yEnd = rect.Y + rect.Height - 1;
|
|
|
|
nodes[(int)NodePosition.TopLeft].Position = new PointF(xStart, yStart);
|
|
nodes[(int)NodePosition.Top].Position = new PointF(xMid, yStart);
|
|
nodes[(int)NodePosition.TopRight].Position = new PointF(xEnd, yStart);
|
|
nodes[(int)NodePosition.Right].Position = new PointF(xEnd, yMid);
|
|
nodes[(int)NodePosition.BottomRight].Position = new PointF(xEnd, yEnd);
|
|
nodes[(int)NodePosition.Bottom].Position = new PointF(xMid, yEnd);
|
|
nodes[(int)NodePosition.BottomLeft].Position = new PointF(xStart, yEnd);
|
|
nodes[(int)NodePosition.Left].Position = new PointF(xStart, yMid);
|
|
}
|
|
|
|
public void MoveCurrentArea(int x, int y)
|
|
{
|
|
areaManager.CurrentArea = new Rectangle(new Point(areaManager.CurrentArea.X + x, areaManager.CurrentArea.Y + y), areaManager.CurrentArea.Size);
|
|
}
|
|
|
|
public void ResizeCurrentArea(int x, int y, bool isBottomRightMoving)
|
|
{
|
|
if (isBottomRightMoving)
|
|
{
|
|
areaManager.CurrentArea = new Rectangle(areaManager.CurrentArea.X, areaManager.CurrentArea.Y,
|
|
areaManager.CurrentArea.Width + x, areaManager.CurrentArea.Height + y);
|
|
}
|
|
else
|
|
{
|
|
areaManager.CurrentArea = new Rectangle(areaManager.CurrentArea.X + x, areaManager.CurrentArea.Y + y,
|
|
areaManager.CurrentArea.Width - x, areaManager.CurrentArea.Height - y);
|
|
}
|
|
}
|
|
}
|
|
} |