Как увеличить изображение под курсором мыши
Создайте новое приложение. На форму поместите компонент TImage (Image1). Его свойство Align выставите в alClient, а свойство Visible в False. Затем TPanel (Panel1), на которой будут находится остальные компоненты. Это сделано для того, чтобы можно было легко скрывать/отображать компоненты управления и настройки. Свойству Caption присвойте пустую строку. На Panel1 поместите компонент TGroupBox (GroupBox1). Свойство Caption этого компонента установите в Кратность увеличения. Внутрь его поместите TTrackBar (Slider). Свойства Max = 4, Min = 1, PageSize = 1, ShowSelRange = True. Под ним поместите компоненты TLabel с надписями 2х, 4х, 6х и 8х, как показано на рисунке.
Ниже поместите TCheckBox (cbShowCross). Свойство Checked установите в True. А также TTimer (Timer1), свойство Interval равен 25.
Вся идея состоит в том, чтобы отслеживать положение курсора мыши и увеличивать изображение вокруг него в несколько раз (от 2-х до 8-ми).
Теперь запишем некоторый код. В событии OnResize формы запишите:
procedure TForm1.FormResize(Sender: TObject); begin { Устанавливаем панель по центру формы } Panel1.Left:= (Form1.ClientWidth div 2) - Panel1.Width div 2; Panel1.Top:= (Form1.ClientHeight div 2) - Panel1.Height div 2; Image1.Picture:= nil; end;
Далее напишем обработчик сообщения WM_GETMINMAXINFO:
private { Private declarations } procedure WMGetMinMaxInfo( var Msg: TWMGetMinMaxInfo); message WM_GETMINMAXINFO; { ... } procedure TForm1.WMGetMinMaxInfo(var Msg: TWMGetMinMaxInfo); begin inherited; { Минимальный размер формы } Msg.MinMaxInfo^.ptMinTrackSize:= Point(158, 177); { Максимальный размер формы } Msg.MinMaxInfo^.ptMaxTrackSize:= Point(350, 350); end;
Теперь будем отслеживать события в таймере:
procedure TForm1.Timer1Timer(Sender: TObject); var srect, drect, posForm: TRect; iWidth, iHeight, dmX, dmY: integer; itmpX, itmpY: real; c: TCanvas; hDesktop: HWND; cur: TPoint; begin if not IsIconic(Application.Handle) then begin hDesktop:= GetDesktopWindow; GetCursorPos(cur); posForm:= Rect(Form1.Left, Form1.Top, Form1.Left + Form1.Width, Form1.Top + Form1.Height); if not PtInRect(posForm, cur) then begin if Panel1.Visible then Panel1.Visible:= false; if not Image1.Visible then Image1.Visible:= true; iWidth:= Image1.Width; iHeight:= Image1.Height; drect:= Rect(0, 0, iWidth, iHeight); itmpX:= iWidth / (Slider.Position * 4); itmpY:= iHeight / (Slider.Position * 4); srect:= Rect(cur.X, cur.Y, cur.X, cur.Y); InflateRect(srect, round(itmpX), round(itmpY)); { перемещаем, если выходит за пределы } if srect.Left < 0 then OffsetRect(srect, -srect.Left, 0); if srect.Top < 0 then OffsetRect(srect, 0, -srect.Top); if srect.Right > Screen.Width then OffsetRect(srect, -(srect.Right - Screen.Width), 0); if srect.Bottom > Screen.Height then OffsetRect(srect, 0, -(srect.Bottom - Screen.Height)); c:= TCanvas.Create; try c.Handle:= GetDC(GetDesktopWindow); Image1.Canvas.CopyRect(drect, c, srect); finally ReleaseDC(hDesktop, c.Handle); c.Free; end; if cbShowCursor.Checked then begin with Image1.Canvas do begin dmX:= Slider.Position * 2 * (cur.X - srect.Left); dmY:= Slider.Position * 2 * (cur.Y - srect.Top); { рисуем перекрестье } MoveTo(dmX - (iWidth div 4), dmY); LineTo(dmX + (iWidth div 4), dmY); MoveTo(dmX, dmY - (iHeight div 4)); LineTo(dmX, dmY + (iHeight div 4)); end; end; Application.ProcessMessages; end else begin if not Panel1.Visible then Panel1.Visible:= true; if Image1.Visible then Image1.Visible:= false; end; end; end;
И, наконец, отключаем таймер при выходе из приложения:
procedure TForm1.FormDestroy(Sender: TObject); begin Timer1.Interval:= 0; end;
Исходник программы находится здесь.
Комментарии