FreePascal:如何在Mouseover上更改TPaint对象的颜色

时间:2014-05-28 16:42:11

标签: freepascal lazarus

我的自定义菜单很顺利,可以检测鼠标何时位于链接矩形的边界内并响应鼠标事件。我现在想要做的是当用户将鼠标悬停在其边界内时更改链接矩形的颜色。我以前用这种方式设置颜色属性,但是手动而不是动态。

基本上没有任何反应。调试显示鼠标位置例程工作正常,但矩形保持相同的颜色。

我创建了一个简单的ButtonStates数组并为它们分配颜色:

type
   T_ButtonState = (bttn_off);
private
{ Private declarations }
bttnStatus : TOC_ButtonState; 

const stateColor : array[T_ButtonState, false..true] of TColor = ((clDkGray, clGray));

我现在正试图操纵T_ButtonState的值,以便我可以在我的绘图程序中设置颜色:

// User actions
procedure T_MenuPanel.MouseMove(Shift:TShiftState; X,Y:Integer);
var
  loop : integer;
begin
 for loop := 0 to High(MenuRects) do
   begin
     if PtInRect(MenuRects[loop], Point(X, Y)) then
       bttnStatus := bttn_off;
   end;
inherited;
end;

这是我的绘图程序:

for count := 0 to fLinesText.Count - 1 do
   begin
     // Define y2
     y2 := TextHeight(fLinesText.strings[count])*2;

     // Draw the rectangle
     itemR := Rect(x1, y1, x2, y2*(count+1));
     Pen.color := clGray;

     Brush.color := stateColor[bttn_off][bttnStatus = bttn_off]; // Nothing Happens!!!

     Rectangle(itemR);

     // Push rectangle info to array
     MenuRects[count] := itemR;

     // Draw the text
     TextRect(itemR, x1+5,  y1+5, fLinesText.strings[count]);

     // inc y1 for positioning the next box
     y1 := y1+y2;
   end;         

1 个答案:

答案 0 :(得分:4)

您正在检测鼠标移动时的位置,并且您在绘制时会考虑该检测。但是,移动鼠标不一定会使控件重新绘制,因此在您的控件中移动不明显。当您检测到鼠标移动时,通过调用其Invalidate方法向控件发出需要重新绘制的信号。

procedure T_MenuPanel.MouseMove(Shift:TShiftState; X,Y:Integer);
var
  loop: integer;
begin
  for loop := 0 to High(MenuRects) do begin
     if PtInRect(MenuRects[loop], Point(X, Y)) then begin
       bttnStatus := bttn_off;
       // Ssgnal that we need repainting
       Invalidate;
     end;
  end;
  inherited;
end;

当操作系统下一次有机会时,它会要求您的控件重新绘制自己。这通常已足够,但如果您希望立即进行直观更新,则可以拨打Refresh而不是Invalidate