提问:如何像winamp一样同时移动几个form?
我用WM_MOVE好像比较麻烦,而且不是像winamp同时移动,是移动了一个,另一个马上更过去
不想用timer,太浪费

解决方案 »

  1.   

    http://www.csdn.net/magazine/sourcecode/Topic/0/28.shtm
      

  2.   

    to:jiangsheng(蒋晟.MSMVP2004Jan)
    可惜是c的
    关键地方看不懂
      

  3.   

    可以自定义消息。比如有一个主窗体,多个从窗体,这些从窗体中都定义了一个WM_MYMOVE消息处理过程,过程内容就是判断主窗体的当前位置,并随知移动本窗体。
    当主窗体移动的时候,给各从窗体发送一个WM_MYMOVE即可。
      

  4.   

    几个form同时显示的问题 
    Form1.FormStyle:=fsNormal; 
    Form2.FormStyle:=fsNormal; 
    Form3.FormStyle:=fsNormal; 
    Form1.Show; 
    Form2.Show; 
    Form3.Show; 
    如何让它有粘性呢?
    winamp的用户都知道,winamp的播放列表或均衡器在被移动的时候,仿佛会受到一股磁力, 
    每当靠近主窗口时就一下子被“吸附”过去,自动沿边对齐。我想让我的winamp插件也具备 
    这种奇妙特性,于是琢磨出了一种“磁化”窗口的方法。该法适用于delphi的各个版本。为 
    了演示这种技术,请随我来制作一个会被winamp“吸引”的样板程序。 
      先新建一应用程序项目,把主窗口form1适当改小些,并将borderstyle设为bsnone。放 
    一个按钮元件,双击它并在onclick事件中写“close;”。待会儿就按它来结束程序。现在 
    切换到代码编辑区,定义几个全局变量 
    var 
      form1: tform1; //“磁性”窗口 
      lastx, lasty: integer; //记录前一次的坐标 
      winamprect:trect; //保存winamp窗口的矩形区域 
      hwnd_winamp:hwnd; //winamp窗口的控制句柄 
       
      接着编写form1的onmousedown和onmousemove事件。 
    procedure tform1.formmousedown(sender: tobject; button:tmousebutton; 
      shift: tshiftstate; x, y: integer); 
    const 
      classname = 'winamp v1.x'; //winamp主窗口的类名 
      //如果改成classname=‘tappbuilder’,你就会发现连delphi也有引力啦! 
    begin 
      //记录当前坐标 
      lastx := x; 
      lasty := y; 
      //查找winamp 
      hwnd_winamp := findwindow(classname,nil); 
      if hwnd_winamp>0 then //找到的话,记录其窗口区域 
        getwindowrect(hwnd_winamp, winamprect); 
    end; procedure tform1.formmousemove(sender: tobject; shift:  
      tshiftstate; x, y: integer); 
    var 
      nleft,ntop:integer; //记录新位置的临时变量 
    begin 
      //检查鼠标左键是否按下 
      if hiword(getasynckeystate(vk_lbutton)) > 0 then 
      begin 
        //计算新坐标 
        nleft := left + x - lastx; 
        ntop := top + y - lasty; 
        //如果找到winamp,就修正以上坐标,产生“磁化”效果 
        if hwnd_winamp>0 then 
          magnetize(nleft,ntop); 
          //重设窗口位置 
          setbounds(nleft,ntop,width,height); 
      end; 
    end; 
    别急着,看magnetize()过程,先来了解一下修正坐标的原理。根据对winamp实现效果的观 
    察,我斗胆给所谓“磁化”下一个简单的定义,就是“在原窗口与目标窗口接近到某种预定 
    程度,通过修正原窗口的坐标,使两窗口处于同一平面且具有公共边的过程”。依此定义, 
    我设计了以下的“磁化”步骤。第一步,判断目标窗口(即winamp)和我们的form1在水平及 
    垂直方向上的投影线是否重叠。“某方向投影线有重叠”是“需要进行坐标修正”的必要 
    非充分条件。判断依据是两投影线段最右与最左边界的差减去它们宽度和的值的正负。第 
    二步,判断两窗口对应边界是否靠得足够近了。肯定的话就让它们合拢。 
    好了,下面便是“神秘”的magnetize过程了…… procedure tform1.magnetize(var nl,nt:integer); 
      //内嵌两个比大小的函数 
      function min(a,b:integer):integer; 
      begin 
        if a > b then result:=b else result:=a; 
      end; 
      function max(a,b:integer):integer; 
      begin 
        if a < b then result:=b else result:=a;  
      end; 
    var 
      h_overlapped,v_overlapped:boolean; //记录投影线是否重叠 
      tw,ww,wh:integer; //临时变量 
    const 
      magneticforce:integer=50; //“磁力”的大小。 
      //准确的说,就是控制窗口边缘至多相距多少像素时需要修正坐标 
      //为了演示,这里用一个比较夸张的数字——50。 
      //一般可以用20左右,那样比较接近winamp的效果 
    begin 
      //判断水平方向是否有重叠投影 
      ww := winamprect.right - winamprect.left; 
      tw := max(winamprect.right,nl+width) - min(winamprect.left,nl); 
      h_overlapped := tw<=(width+ww); 
      //再判断垂直方向 
      wh := winamprect.bottom - winamprect.top; 
      tw := max(winamprect.bottom,nt + height) - min(winamprect.top,nt); 
      v_overlapped := tw<=(height + wh); 
      //足够接近的话就调整坐标 
      if h_overlapped then 
      begin 
        if abs(winamprect.bottom - nt)     
        else if abs(nt + height - winamprect.top)     
      end; 
      if v_overlapped then 
      begin 
        if abs(winamprect.right - nl)     
        else if abs(nl + width - winamprect.left)     
      end; 
    end; 
      

  5.   

    这段代码贴过很多了
    不过nl,nt等是什么啊
    还有好像是讲磁性,不是我问的同时移动多个form的问题吧
    我是菜鸟,问的问题比较没水平,不要见怪