Reputation: 403
I have a drawing application that I use Graphic
object to draw a rectangle and circles and some lines. The app has the capability of zooming, but I'm trying to get Panning working but couldn't find the best solution.
public partial class Form1 : Form
{
protected Point clickPosition;
protected Point scrollPosition;
protected Point lastPosition;
public Form1()
{
InitializeComponent();
SetStyle(ControlStyles.AllPaintingInWmPaint | ControlStyles.OptimizedDoubleBuffer, true);
AutoScroll = true;
AutoScrollMinSize = new Size(0, 0);
}
float zoom = 100f;
private void panel1_Paint(object sender, PaintEventArgs e)
{
Graphics g = e.Graphics;
g.ScaleTransform(zoom, zoom);
g.SmoothingMode = SmoothingMode.AntiAlias;
// some demo drawing:
Rectangle rect = panel1.ClientRectangle;
g.DrawEllipse(Pens.Firebrick, rect);
using (Pen pen = new Pen(Color.DarkBlue, 4f))
g.DrawLine(pen, 22, 22, 88, 88);
}
private void trackBar1_Scroll(object sender, EventArgs e)
{
zoom = trackBar1.Value / 10f;
panel1.Invalidate();
}
protected override void OnMouseDown(MouseEventArgs e)
{
clickPosition.X = e.X;
clickPosition.Y = e.Y;
}
protected override void OnMouseUp(MouseEventArgs e)
{
Cursor = Cursors.Default;
lastPosition.X = AutoScrollPosition.X;
lastPosition.Y = AutoScrollPosition.Y;
}
protected override void OnMouseMove(MouseEventArgs e)
{
if (e.Button == MouseButtons.Left)
{
Cursor = Cursors.Hand;
scrollPosition.X = clickPosition.X - e.X - lastPosition.X;
scrollPosition.Y = clickPosition.Y - e.Y - lastPosition.Y;
AutoScrollPosition = scrollPosition;
panel1.Invalidate();
}
}
private void Viewer_MouseDown(object sender, MouseEventArgs e)
{
OnMouseDown(e);
}
private void Viewer_MouseMove(object sender, MouseEventArgs e)
{
OnMouseMove(e);
}
private void Viewer_MouseUp(object sender, MouseEventArgs e)
{
OnMouseUp(e);
}
}
this what I have so far, the code missing 2 things one is Using AutoScrollMinSize
to update the min size and AutoScrollPosition
to get the latest position, the problem is both can be used with DrawImage
and Images
and I'm not sure in my case how to get it work with line drawing and circles. Also for some reason my AutoScrollPosition
always 0 for x
and y
.
Any Ideas, or is there another way to create the pan effect
Upvotes: 0
Views: 2545
Reputation: 54433
You can use the very same trick for panning as for zooming: Pan the Graphics
object used for drawing!
Simply add one (or for vertical panning as well two) numbers, say offSetX and offsetY
to your application. You may controls it with a Trackbar
or a NumericUpDown
or in any other way..
Now add this line that translates (pans) everything the Graphics
object draws, before the ScaleTransform
:
g.TranslateTransform(offSetX , offSetY);
This will move everything for so many pixels to the right or left and up or down..
Note that this includes everything the Graphics object draws, including all images it draws.
But this will not move a BackgroundImage
if you have one.. To move those as well you should use two Panels
: A panelFrame
with AutoSize
on and a larger panelCanvas
which is nested in the frame panel and gets moved around inside it by using the scrollbars..
Upvotes: 3