国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁(yè) > 學(xué)院 > 開發(fā)設(shè)計(jì) > 正文

“磁性”窗口

2019-11-18 18:54:07
字體:
供稿:網(wǎng)友

Winamp的用戶都知道,Winamp的播放列表或均衡器在被移動(dòng)的時(shí)候,仿佛會(huì)受到一股磁力,每當(dāng)靠近主窗口時(shí)就一下子被“吸附”過去,自動(dòng)沿邊對(duì)齊。我想讓我的Winamp插件也具備這種奇妙特性,于是琢磨出了一種“磁化”窗口的方法。該法適用于Delphi的各個(gè)版本。為了演示這種技術(shù),請(qǐng)隨我來制作一個(gè)會(huì)被Winamp“吸引”的樣板程序。
  先新建一應(yīng)用程序項(xiàng)目,把主窗口Form1適當(dāng)改小些,并將BorderStyle設(shè)為bsNone。放一個(gè)按鈕元件,雙擊它并在OnClick事件中寫“Close;”。待會(huì)兒就按它來結(jié)束程序。現(xiàn)在切換到代碼編輯區(qū),定義幾個(gè)全局變量。
  var
   Form1: TForm1; //“磁性”窗口
   LastX, LastY: Integer; //記錄前一次的坐標(biāo)
   WinamPRect:Trect; //保存Winamp窗口的矩形區(qū)域
   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’,你就會(huì)發(fā)現(xiàn)連Delphi也有引力啦!
  begin
  //記錄當(dāng)前坐標(biāo)
  LastX := X;
  LastY := Y;
  //查找Winamp
  hwnd_Winamp := FindWindow(ClassName,nil);
  if hwnd_Winamp>0 then //找到的話,記錄其窗口區(qū)域
  GetWindowRect(hwnd_Winamp, WinampRect);
  end;
  procedure TForm1.FormMouseMove(Sender: Tobject; Shift: TShiftState; X,
   Y: Integer);
  var
   nLeft,nTop:integer; //記錄新位置的臨時(shí)變量
  begin
  //檢查鼠標(biāo)左鍵是否按下
   if HiWord(GetAsyncKeyState(VK_LBUTTON)) > 0 then
   begin
   //計(jì)算新坐標(biāo)
   nleft := Left + X - LastX;
   nTop := Top + Y - LastY;
   //如果找到Winamp,就修正以上坐標(biāo),產(chǎn)生“磁化”效果
   if hwnd_Winamp>0 then
   Magnetize(nleft,ntop);
   //重設(shè)窗口位置
   SetBounds(nLeft,nTop,width,height);
   end;
  end;
  別急著,看Magnetize()過程,先來了解一下修正坐標(biāo)的原理。根據(jù)對(duì)Winamp實(shí)現(xiàn)效果的觀察,我斗膽給所謂“磁化”下一個(gè)簡(jiǎn)單的定義,就是“在原窗口與目標(biāo)窗口接近到某種預(yù)定程度,通過修正原窗口的坐標(biāo),使兩窗口處于同一平面且具有公共邊的過程”。依此定義,我設(shè)計(jì)了以下的“磁化”步驟。第一步,判斷目標(biāo)窗口(即Winamp)和我們的Form1在水平及垂直方向上的投影線是否重疊。“某方向投影線有重疊”是“需要進(jìn)行坐標(biāo)修正”的必要非充分條件。判斷依據(jù)是兩投影線段最右與最左邊界的差減去它們寬度和的值的正負(fù)。第二步,判斷兩窗口對(duì)應(yīng)邊界是否靠得足夠近了。肯定的話就讓它們合攏。
  好了,下面便是“神秘”的Magnetize過程了……
  procedure TForm1.Magnetize(var nl,nt:integer);
   //內(nèi)嵌兩個(gè)比大小的函數(shù)
   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    end;
  var
   H_Overlapped,V_Overlapped:boolean; //記錄投影線是否重疊
   tw,ww,wh:integer; //臨時(shí)變量
  const
   MagneticForce:integer=50; //“磁力”的大小。
   //準(zhǔn)確的說,就是控制窗口邊緣至多相距多少像素時(shí)需要修正坐標(biāo)
   //為了演示,這里用一個(gè)比較夸張的數(shù)字——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);
  //足夠接近的話就調(diào)整坐標(biāo)
  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;
  怎么樣?運(yùn)行后效果不錯(cuò)吧!


上一篇:動(dòng)態(tài)更新DBGrid的顏色

下一篇:代替showmodal其他兩種方法

發(fā)表評(píng)論 共有條評(píng)論
用戶名: 密碼:
驗(yàn)證碼: 匿名發(fā)表
學(xué)習(xí)交流
熱門圖片

新聞熱點(diǎn)

疑難解答

圖片精選

網(wǎng)友關(guān)注

主站蜘蛛池模板: 遂宁市| 固安县| 新营市| 平塘县| 新和县| 金华市| 岢岚县| 土默特左旗| 赤峰市| 老河口市| 沽源县| 夏邑县| 长乐市| 于都县| 武安市| 且末县| 团风县| 新沂市| 安陆市| 庐江县| 淮阳县| 玛纳斯县| 永川市| 改则县| 富裕县| 乐陵市| 福建省| 肥东县| 嘉祥县| 桑植县| 建昌县| 西宁市| 康定县| 安远县| 通州区| 云梦县| 开化县| 顺平县| 兴义市| 祥云县| 永胜县|