辅导:开发自己的窗体设计器
来源:优易学  2011-11-4 12:46:20   【优易学:中国教育考试门户网】   资料下载   IT书店
  控件移动的关键点就是需要设计一个独立于任何控件的类(UIMoveKnob)来控制控件的移动。我这里实现的方法只针对一个控件,如果需要同时选择多个控件,然后同时移动的话,你需要修改这个类,这里是有点难于控制,我使用的方法严重耦合,所以只在这里给出移动一个控件的办法,具体移动过个控件的方法请各位讨论。
  要移动某个选定的控件,我们需要实现控件的:
  MouseDown
  MouseMove
  MouseUp
  这3个事件。
  在MouseDown的时候,记录鼠标点击的开始位置,并设置开始移动标志为True;
  在MouseMove的时候,把控件移动相应的距离(当前鼠标位置 – 鼠标点击的开始位置);
  在MouseUp的时候,释放移动标志为false。
  有了控件移动控制类(UIMoveKnob)以后,我们怎么实现UIMoveKnob和具体控件的关联呢?同样,我们需要在Form中增加一个变量private Hashtable _HashUIMoveKnob用于缓存每个控件对应的UIMoveKnob对象。
  同时在Form.ControlAdded事件中,通过this._HashUIMoveKnob.Add(e.Control, new UIMoveKnob(e.Control));设置其关联性。
  UIMoveKnob的代码如下:
  public class UIMoveKnob
  {
  private System.Windows.Forms.Control _Owner;
  private int _MouseClickAtX;
  private int _MouseClickAtY;
  private bool _BeginDrag;
  public UIMoveKnob(System.Windows.Forms.Control Owner)
  {
  this._Owner = Owner;
  this._Owner.MouseDown += new System.Windows.Forms.MouseEventHandler(this.Owner_MouseDown);
  this._Owner.MouseMove += new System.Windows.Forms.MouseEventHandler(this.Owner_MouseMove);
  this._Owner.MouseUp += new System.Windows.Forms.MouseEventHandler(this.Owner_MouseUp);
  }
  void Owner_MouseDown(object sender, System.Windows.Forms.MouseEventArgs e)
  {
  this._Owner.Cursor = System.Windows.Forms.Cursors.Default;
  this._MouseClickAtX = e.X;
  this._MouseClickAtY = e.Y;
  this._BeginDrag = true;
  }
  void Owner_MouseMove(object sender, System.Windows.Forms.MouseEventArgs e)
  {
  try
  {
  if (this._BeginDrag)
  {
  Rectangle rect;
  /*
  * 对于下列控件,是不能拖动的,所以这里也不绘制拖动边框
  * TabPage,
  */
  if (this._Owner is System.Windows.Forms.TabPage)
  {
  //
  }
  else
  {
  this._Owner.Location = new Point(this._Owner.Left + e.X - this._MouseClickAtX, this._Owner.Top + e.Y - this._MouseClickAtY);
  }
  }
  }
  catch { }
  }
  void Owner_MouseUp(object sender, System.Windows.Forms.MouseEventArgs e)
  {
  this._BeginDrag = false;
  this._Owner.Parent.Refresh();
  }
  }
  修改后的Form代码前半部分如下:
  private MouseHook _MouseHook;
  //我们将所有的已经与具体控件关联了的UISizeKnob缓存在这个HashTable中
  private Hashtable _HashUISizeKnob;
  //负责控件移动的类
  private Hashtable _HashUIMoveKnob;
  public Form1()
  {
  InitializeComponent();
  this._MouseHook = new MouseHook(this);
  this._HashUISizeKnob = new Hashtable();
  this._HashUIMoveKnob = new Hashtable();
  //为了简洁明了,我们在ControlAdded中来设置具体控件和UISizeKnob的关联
  this.ControlAdded += new ControlEventHandler(Form1_ControlAdded);
  }
  void Form1_ControlAdded(object sender, ControlEventArgs e)
  {
  if (!(e.Control is UISizeDot))
  {
  this._HashUISizeKnob.Add(e.Control, new UISizeKnob(e.Control));
  this._HashUIMoveKnob.Add(e.Control, new UIMoveKnob(e.Control));
  //点击控件的时候,显示控件的选择
  e.Control.Click += new EventHandler(Control_Click);
  }
  }
  void Control_Click(object sender, EventArgs e)
  {
  //寿险清除已经选择的控件
  foreach (UISizeKnob knob in this._HashUISizeKnob.Values)
  {
  knob.ShowUISizeDots(false);
  }
  try
  {
  ((UISizeKnob)this._HashUISizeKnob[sender]).ShowUISizeDots(true);
  }
  catch { }
  }
  相对来说实现单个控件的拖动比较简单,而实现多个控件的拖动,我们需要首先使用一个全局的变量来缓存我们所选择的控件,然后在此类中。拖动的时候,通过遍历此全局变量,一个个改变所选择控件的位置。

责任编辑:小草

文章搜索:
 相关文章
热点资讯
资讯快报
热门课程培训