1 /* $Id$ $Revision$ */ 2 /* vim:set shiftwidth=4 ts=8: */ 3 4 /************************************************************************* 5 * Copyright (c) 2011 AT&T Intellectual Property 6 * All rights reserved. This program and the accompanying materials 7 * are made available under the terms of the Eclipse Public License v1.0 8 * which accompanies this distribution, and is available at 9 * http://www.eclipse.org/legal/epl-v10.html 10 * 11 * Contributors: See CVS logs. Details at http://www.graphviz.org/ 12 *************************************************************************/ 13 14 using System; 15 using System.Drawing; 16 using System.Drawing.Drawing2D; 17 using System.Windows.Forms; 18 19 namespace Graphviz 20 { 21 public partial class ScrollableImageControl : ScrollableControl 22 { 23 public Image Image 24 { 25 get 26 { 27 return _image; 28 } 29 30 set 31 { 32 _image = value; 33 UpdateAutoScroll(); 34 } 35 } 36 37 public float Zoom 38 { 39 get 40 { 41 return _zoom; 42 } 43 44 set 45 { 46 _zoom = value; 47 UpdateAutoScroll(); 48 } 49 } 50 ScrollableImageControl()51 public ScrollableImageControl() 52 { 53 InitializeComponent(); 54 55 SetStyle(ControlStyles.AllPaintingInWmPaint | 56 ControlStyles.DoubleBuffer | 57 ControlStyles.ResizeRedraw | 58 ControlStyles.UserMouse | 59 ControlStyles.UserPaint, 60 true); 61 _image = null; 62 _zoom = 1.0f; 63 _lastScroll = new Point(0, 0); 64 } 65 ActualSize()66 public void ActualSize() 67 { 68 Zoom = 1.0f; 69 } 70 ZoomToFit()71 public void ZoomToFit() 72 { 73 Size imageSize = Image.Size; 74 Size controlSize = Size; 75 Zoom = Math.Min((float)controlSize.Width / (float)imageSize.Width, (float)controlSize.Height / (float)imageSize.Height); 76 } 77 ZoomIn()78 public void ZoomIn() 79 { 80 Zoom *= _squareRootOfTwo; 81 } 82 ZoomOut()83 public void ZoomOut() 84 { 85 Zoom /= _squareRootOfTwo; 86 } 87 OnMouseDown(MouseEventArgs e)88 protected override void OnMouseDown(MouseEventArgs e) 89 { 90 /* if potentially panning with the mouse, record last scroll position */ 91 /* NOTE: Autoscroll should be set to +ve values but always returns -ve values */ 92 if (e.Button == MouseButtons.Left) 93 _lastScroll = new Point( 94 e.X - AutoScrollPosition.X, 95 e.Y - AutoScrollPosition.Y); 96 base.OnMouseDown(e); 97 } 98 OnMouseMove(MouseEventArgs e)99 protected override void OnMouseMove(MouseEventArgs e) 100 { 101 /* if panning with the mouse, scroll to position */ 102 /* NOTE: Autoscroll should be set to +ve values but always returns -ve values */ 103 if (e.Button == MouseButtons.Left) 104 AutoScrollPosition = new Point( 105 _lastScroll.X - e.X, 106 _lastScroll.Y - e.Y); 107 base.OnMouseMove(e); 108 } 109 OnPaintBackground(PaintEventArgs e)110 protected override void OnPaintBackground(PaintEventArgs e) 111 { 112 /* fill clip rectangle with background color */ 113 e.Graphics.FillRectangle(new SolidBrush(BackColor), e.ClipRectangle); 114 } 115 OnPaint(PaintEventArgs pe)116 protected override void OnPaint(PaintEventArgs pe) 117 { 118 if (_image != null) { 119 Matrix oldMatrix = pe.Graphics.Transform; 120 121 /* if the zoomed image size is smaller than the control size, center the display */ 122 /* adjust by the scroll position, then scale by the zoom factor */ 123 pe.Graphics.TranslateTransform( 124 Math.Max((Width - _image.Width * _zoom) / 2.0f, 0.0f) + AutoScrollPosition.X, 125 Math.Max((Height - _image.Height * _zoom) / 2.0f, 0.0f) + AutoScrollPosition.Y); 126 pe.Graphics.ScaleTransform(_zoom, _zoom); 127 128 /* blit the image onto the graphics */ 129 pe.Graphics.DrawImage(_image, 0.0f, 0.0f); 130 131 pe.Graphics.Transform = oldMatrix; 132 } 133 base.OnPaint(pe); 134 135 } 136 UpdateAutoScroll()137 private void UpdateAutoScroll() 138 { 139 if (_image == null) 140 AutoScrollMinSize = Size; 141 else 142 AutoScrollMinSize = new Size( 143 (int)(_image.Width * _zoom + 0.5f), 144 (int)(_image.Height * _zoom + 0.5f)); 145 Invalidate(); 146 } 147 148 private readonly float _squareRootOfTwo = (float)Math.Sqrt(2.0); 149 private Image _image; 150 private float _zoom; 151 private Point _lastScroll; 152 } 153 } 154