Форум: "WinAPI";
Текущий архив: 2007.09.02;
Скачать: [xml.tar.bz2];
ВнизКурсор над кнопкой Найти похожие ветки
← →
Dmitry_177 (2007-03-05 20:22) [0]Создаю кнопки с флагом BS_OWNERDRAW, чтобы самому перерисовывать их в WM_DRAWITEM..
По идее в структуре DrawItemStruct, т.е. так:(PDrawItemStruct(lParam)^.itemState and ODS_HOTLIGHT) <> 0
если это выполняется то курсор над кнопкой, но так почему-то не работает... А с пунктами меню так работает.. Как мне тогда определить над кнопкой ли курсор, чтобы перерисовать кнопку?
← →
tesseract © (2007-03-06 14:40) [1]
> А с пунктами меню так работает.. Как мне тогда определить
> над кнопкой ли курсор,
OnMouseLeave/OnMouseEnter.
← →
DVM © (2007-03-06 14:43) [2]
> OnMouseLeave/OnMouseEnter.
Это же по WinApi конференция.
← →
tesseract © (2007-03-06 14:49) [3]тогда см TrackMouseEvent + WM_MOUSEHOVER WM_MOUSELEAVE
← →
Dmitry_177 (2007-03-06 16:22) [4]Помогите примером пожалуйста с TrackMouseEvent, что-то я не пойму как она работает...:(
← →
Dmitry_177 (2007-03-06 17:19) [5]Я как понимаю функция срабатывает ОДИН раз, где-то вычитал что в сообщении WM_MOUSELEAVE нужно устанавливать функцию на TME_HOVER, а в WM_MOUSEHOVER на TME_LEAVE, т.е. чтобы одно сообщение вызывало на другую.. Т.е. примерно так:
function WindowProc(Window: HWnd; Message: Cardinal; wParam: WPARAM; lParam: LPARAM): LRESULT; stdcall;
var
tme: TTRACKMOUSEEVENT;
...
case Message of
WM_MOUSELEAVE: begin
tme.cbSize := SizeOf(TTRACKMOUSEEVENT);
tme.dwFlags := TME_HOVER;
tme.hwndTrack := Window;
tme.dwHoverTime := HOVER_DEFAULT;
TrackMouseEvent(tme);
// действия, когда курсор вышел за границы..
end;
WM_MOUSEHOVER: begin
tme.cbSize := SizeOf(TTRACKMOUSEEVENT);
tme.dwFlags := TME_LEAVE;
tme.hwndTrack := Window;
tme.dwHoverTime := HOVER_DEFAULT;
TrackMouseEvent(tme);
// действия, когда курсор зашел в пределы..
end;
Но вопрос в том, как ее изначально вызвать? Ведь сообщения WM_MOUSELEAVE и WM_MOUSEHOVER сами ниоткуда то не придут...
← →
tesseract © (2007-03-07 14:13) [6]
> Но вопрос в том, как ее изначально вызвать?
The TrackMouseEvent function posts messages when the mouse pointer leaves a window or hovers over a window for a specified amount of time.
The TRACKMOUSEEVENT structure is used by the TrackMouseEvent function to track when the mouse pointer leaves a window or hovers over a window for a specified amount of time.
TRACKMOUSEEVENT.dwHoverTime
Specifies the hover time-out (if TME_HOVER was specified in dwFlags), in milliseconds. Can be HOVER_DEFAULT, which means to use the system default hover time-out.
← →
Dmitry_177 (2007-03-11 19:35) [7]Попробовал я вобщем так сделать, вроде работает.. Но блин, пропала прорисовка кнопки при нажатии на нее, я ее обрабатывал в WM_DRAWITEM главной процедуре окна, т.е. в WindowProc. Может из за сабклассинга уже не доходит WM_DRAWITEM главному окну??? Вот весь код тестового проекта:
program TestButton;
uses
Windows,
Messages;
const
WindowName = "TestButton";
ID_TestBtn = 10;
var
WindowClass: TWndClass;
hWindow: HWND;
hTestBtn: HWND;
AMessage: TMsg;
old_proc: Pointer;
bNextButtonTrack: boolean = false;
tme: tagTRACKMOUSEEVENT;
function ButtonProc(Window: HWnd; Message: Cardinal; wParam: WPARAM; lParam: LPARAM): LRESULT; stdcall;
var
DC: HDC;
PStruct: PAINTSTRUCT;
Pen: HPEN;
Brush: HBRUSH;
SelObjPn: HGDIOBJ;
SelObjBr: HGDIOBJ;
begin
case Message of
WM_MOUSEMOVE: begin
if not bNextButtonTrack then
begin
tme.cbSize := SizeOf(tagTRACKMOUSEEVENT);
tme.hwndTrack := Window;
tme.dwFlags := TME_LEAVE;
tme.dwHoverTime := HOVER_DEFAULT;
bNextButtonTrack := TrackMouseEvent(tme);
InvalidateRect(Window, nil, true);
end;
end;
WM_MOUSELEAVE: begin
bNextButtonTrack := false;
InvalidateRect(Window, nil, true);
end;
WM_PAINT: begin
if bNextButtonTrack then
begin
DC := BeginPaint(Window, PStruct);
Pen := CreatePen(PS_SOLID, 1, $00000000);
SelObjPn := SelectObject(DC, Pen);
Brush := CreateSolidBrush($0000FF00);
SelObjBr := SelectObject(DC, Brush);
Rectangle(DC, PStruct.rcPaint.Left, PStruct.rcPaint.Top, PStruct.rcPaint.Right, PStruct.rcPaint.Bottom);
SelectObject(DC, SelObjPn);
DeleteObject(Pen);
SelectObject(DC, SelObjBr);
DeleteObject(Brush);
EndPaint(Window, PStruct);
end
else
begin
DC := BeginPaint(Window, PStruct);
Pen := CreatePen(PS_SOLID, 1, $00000000);
SelObjPn := SelectObject(DC, Pen);
Brush := CreateSolidBrush($00FFFFFF);
SelObjBr := SelectObject(DC, Brush);
Rectangle(DC, PStruct.rcPaint.Left, PStruct.rcPaint.Top, PStruct.rcPaint.Right, PStruct.rcPaint.Bottom);
SelectObject(DC, SelObjPn);
DeleteObject(Pen);
SelectObject(DC, SelObjBr);
DeleteObject(Brush);
EndPaint(Window, PStruct);
end;
end;
end;
Result := CallWindowProc(old_proc, Window, Message, wParam, lParam);
end;
function WindowProc(Window: HWnd; Message: Cardinal; wParam: WPARAM; lParam: LPARAM): LRESULT; stdcall;
var
Pen: HPEN;
Brush: HBRUSH;
SelObjPn: HGDIOBJ;
SelObjBr: HGDIOBJ;
begin
Result := 0;
case Message of
WM_CREATE: begin
hTestBtn := CreateWindow("BUTTON", "TestButton", BS_OWNERDRAW or WS_CHILD or WS_VISIBLE, 20, 20, 30, 32, Window, ID_TestBtn, HInstance, nil);
old_proc := Pointer(GetWindowLong(Window, GWL_WNDPROC));
SetWindowLong(hTestBtn, GWL_WNDPROC, LongInt(@ButtonProc));
end;
WM_DRAWITEM: begin
with PDrawItemStruct(lParam)^ do
begin
FrameRect(hDC, rcItem, GetStockObject(WHITE_BRUSH));
if (itemState and ODS_SELECTED) <> 0 then
begin
Pen := CreatePen(PS_SOLID, 1, $00000000);
SelObjPn := SelectObject(hDC, Pen);
Brush := CreateSolidBrush($000000FF);
SelObjBr := SelectObject(hDC, Brush);
Rectangle(hDC, rcItem.Left, rcItem.Top, rcItem.Right, rcItem.Bottom);
SelectObject(hDC, SelObjPn);
DeleteObject(Pen);
SelectObject(hDC, SelObjBr);
DeleteObject(Brush);
end;
end;
Result := 1;
end;
WM_DESTROY: begin
PostQuitMessage(0);
Exit;
end;
else
Result := DefWindowProc(Window, Message, wParam, lParam);
end;
end;
begin
with WindowClass do
begin
lpszClassName := WindowName;
lpfnWndProc := @WindowProc;
cbClsExtra := 0;
cbWndExtra := 0;
hInstance := 0;
lpszMenuName := nil;
hIcon := LoadIcon(0, IDI_APPLICATION);
hCursor := LoadCursor(0, IDC_ARROW);
hbrBackground := GetStockObject(WHITE_BRUSH);
end;
if RegisterClass(WindowClass) = 0 then Exit;
hWindow := CreateWindow(WindowName, WindowName, WS_OVERLAPPEDWINDOW, (GetSystemMetrics(SM_CXSCREEN) - 500) div 2, (GetSystemMetrics(SM_CYSCREEN) - 300) div 2, 500, 300, 0, 0, HInstance, nil);
ShowWindow(hWindow, SW_SHOWNORMAL);
UpdateWindow(hWindow);
while GetMessage(AMessage, 0, 0, 0) do
begin
TranslateMessage(AMessage);
DispatchMessage(AMessage);
end;
end.
Можно просто скопировать его в Delphi и компилировать.. Можно конечно обрабатывать WM_LBUTTONDOWN/WM_LBUTTONUP кнопки, но это же только с мышкой, а на кнопку же можно еще нажать и с помощью клавиатуры.. Лучше всего было бы обрабатывать нажатие, чтобы перерисовывать ее в WM_DRAWITEM мне так кажется.. Помогите пожалуста, может кто-то уже делал что я хочу, чтобы не придумывать велосипед..
Страницы: 1 вся ветка
Форум: "WinAPI";
Текущий архив: 2007.09.02;
Скачать: [xml.tar.bz2];
Память: 0.5 MB
Время: 0.038 c