* A fake B_MOUSE_MOVED message is now send on workspace change, and when
a window is closed, too (only happened when a new window was shown before). This is done via the new Desktop::_SendFakeMouseMoved() method. This fixes bug #342. * The MouseFilter now always sets Desktop::fWindowUnderMouse, so that one can differentiate between no window under mouse, and decorator under mouse. * EventDispatcher::SendFakeMouseMoved() now expects a BMessenger instead of an EventTarget as target - this guarantees that it can safely be called with any window now (instead of only the current window). git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@16953 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
+66
-27
@@ -218,6 +218,8 @@ MouseFilter::Filter(BMessage* message, EventTarget** _target, int32* _viewToken,
|
|||||||
if (!fDesktop->LockAllWindows())
|
if (!fDesktop->LockAllWindows())
|
||||||
return B_DISPATCH_MESSAGE;
|
return B_DISPATCH_MESSAGE;
|
||||||
|
|
||||||
|
int32 viewToken = B_NULL_TOKEN;
|
||||||
|
|
||||||
WindowLayer* window = fDesktop->MouseEventWindow();
|
WindowLayer* window = fDesktop->MouseEventWindow();
|
||||||
if (window == NULL)
|
if (window == NULL)
|
||||||
window = fDesktop->WindowAt(where);
|
window = fDesktop->WindowAt(where);
|
||||||
@@ -226,30 +228,33 @@ MouseFilter::Filter(BMessage* message, EventTarget** _target, int32* _viewToken,
|
|||||||
// dispatch event in the window layers
|
// dispatch event in the window layers
|
||||||
switch (message->what) {
|
switch (message->what) {
|
||||||
case B_MOUSE_DOWN:
|
case B_MOUSE_DOWN:
|
||||||
window->MouseDown(message, where, _viewToken);
|
window->MouseDown(message, where, &viewToken);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case B_MOUSE_UP:
|
case B_MOUSE_UP:
|
||||||
window->MouseUp(message, where, _viewToken);
|
window->MouseUp(message, where, &viewToken);
|
||||||
fDesktop->SetMouseEventWindow(NULL);
|
fDesktop->SetMouseEventWindow(NULL);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case B_MOUSE_MOVED:
|
case B_MOUSE_MOVED:
|
||||||
window->MouseMoved(message, where, _viewToken,
|
window->MouseMoved(message, where, &viewToken,
|
||||||
latestMouseMoved == NULL || latestMouseMoved == message);
|
latestMouseMoved == NULL || latestMouseMoved == message);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (*_viewToken != B_NULL_TOKEN) {
|
if (viewToken != B_NULL_TOKEN) {
|
||||||
fDesktop->SetViewUnderMouse(window, *_viewToken);
|
fDesktop->SetViewUnderMouse(window, viewToken);
|
||||||
|
|
||||||
|
*_viewToken = viewToken;
|
||||||
*_target = &window->EventTarget();
|
*_target = &window->EventTarget();
|
||||||
} else {
|
|
||||||
fDesktop->SetViewUnderMouse(NULL, B_NULL_TOKEN);
|
|
||||||
*_target = NULL;
|
|
||||||
}
|
}
|
||||||
} else {
|
}
|
||||||
fDesktop->SetViewUnderMouse(NULL, B_NULL_TOKEN);
|
|
||||||
|
if (window == NULL || viewToken == B_NULL_TOKEN) {
|
||||||
|
// mouse is not over a window or over a decorator
|
||||||
|
fDesktop->SetViewUnderMouse(window, B_NULL_TOKEN);
|
||||||
fDesktop->SetCursor(NULL);
|
fDesktop->SetCursor(NULL);
|
||||||
|
|
||||||
*_target = NULL;
|
*_target = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -784,6 +789,8 @@ Desktop::SetWorkspace(int32 index)
|
|||||||
MarkDirty(dirty);
|
MarkDirty(dirty);
|
||||||
|
|
||||||
UnlockAllWindows();
|
UnlockAllWindows();
|
||||||
|
|
||||||
|
_SendFakeMouseMoved();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -980,6 +987,51 @@ Desktop::_WindowChanged(WindowLayer* window)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*!
|
||||||
|
\brief Sends a fake B_MOUSE_MOVED event to the window under the mouse,
|
||||||
|
and also updates the current view under the mouse.
|
||||||
|
|
||||||
|
This has only to be done in case the view changed without user interaction,
|
||||||
|
ie. because of a workspace change or a closing window.
|
||||||
|
|
||||||
|
Windows must not be locked when calling this method.
|
||||||
|
*/
|
||||||
|
void
|
||||||
|
Desktop::_SendFakeMouseMoved(WindowLayer* window)
|
||||||
|
{
|
||||||
|
BPoint where;
|
||||||
|
int32 buttons;
|
||||||
|
EventDispatcher().GetMouse(where, buttons);
|
||||||
|
|
||||||
|
int32 viewToken = B_NULL_TOKEN;
|
||||||
|
BMessenger target;
|
||||||
|
|
||||||
|
LockAllWindows();
|
||||||
|
|
||||||
|
if (window == NULL)
|
||||||
|
window = MouseEventWindow();
|
||||||
|
if (window == NULL)
|
||||||
|
window = WindowAt(where);
|
||||||
|
|
||||||
|
if (window != NULL) {
|
||||||
|
BMessage message;
|
||||||
|
window->MouseMoved(&message, where, &viewToken, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (viewToken != B_NULL_TOKEN)
|
||||||
|
SetViewUnderMouse(window, viewToken);
|
||||||
|
else {
|
||||||
|
SetViewUnderMouse(NULL, B_NULL_TOKEN);
|
||||||
|
SetCursor(NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
UnlockAllWindows();
|
||||||
|
|
||||||
|
if (viewToken != B_NULL_TOKEN)
|
||||||
|
EventDispatcher().SendFakeMouseMoved(target, viewToken);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
Desktop::SetFocusWindow(WindowLayer* focus)
|
Desktop::SetFocusWindow(WindowLayer* focus)
|
||||||
{
|
{
|
||||||
@@ -1245,23 +1297,7 @@ Desktop::ShowWindow(WindowLayer* window)
|
|||||||
// we'll send a fake mouse moved message to the window, so that
|
// we'll send a fake mouse moved message to the window, so that
|
||||||
// it knows the mouse is over it.
|
// it knows the mouse is over it.
|
||||||
|
|
||||||
BPoint where;
|
_SendFakeMouseMoved(window);
|
||||||
int32 buttons;
|
|
||||||
EventDispatcher().GetMouse(where, buttons);
|
|
||||||
|
|
||||||
int32 viewToken = B_NULL_TOKEN;
|
|
||||||
|
|
||||||
LockAllWindows();
|
|
||||||
|
|
||||||
if (WindowAt(where) == window) {
|
|
||||||
ViewLayer* view = window->ViewAt(where);
|
|
||||||
if (view != NULL)
|
|
||||||
viewToken = view->Token();
|
|
||||||
}
|
|
||||||
UnlockAllWindows();
|
|
||||||
|
|
||||||
if (viewToken != B_NULL_TOKEN)
|
|
||||||
EventDispatcher().SendFakeMouseMoved(window->EventTarget(), viewToken);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -1294,6 +1330,9 @@ Desktop::HideWindow(WindowLayer* window)
|
|||||||
fWorkspacesLayer = NULL;
|
fWorkspacesLayer = NULL;
|
||||||
|
|
||||||
UnlockAllWindows();
|
UnlockAllWindows();
|
||||||
|
|
||||||
|
if (window == fWindowUnderMouse)
|
||||||
|
_SendFakeMouseMoved();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -184,6 +184,7 @@ class Desktop : public MessageLooper, public ScreenOwner {
|
|||||||
void _BringWindowsToFront(WindowList& windows,
|
void _BringWindowsToFront(WindowList& windows,
|
||||||
int32 list, bool wereVisible);
|
int32 list, bool wereVisible);
|
||||||
status_t _ActivateApp(team_id team);
|
status_t _ActivateApp(team_id team);
|
||||||
|
void _SendFakeMouseMoved(WindowLayer* window = NULL);
|
||||||
|
|
||||||
void _RebuildClippingForAllWindows(BRegion& stillAvailableOnScreen);
|
void _RebuildClippingForAllWindows(BRegion& stillAvailableOnScreen);
|
||||||
void _TriggerWindowRedrawing(BRegion& newDirtyRegion);
|
void _TriggerWindowRedrawing(BRegion& newDirtyRegion);
|
||||||
|
|||||||
@@ -466,7 +466,7 @@ EventDispatcher::GetMouse(BPoint& where, int32& buttons)
|
|||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
EventDispatcher::SendFakeMouseMoved(EventTarget& target, int32 viewToken)
|
EventDispatcher::SendFakeMouseMoved(BMessenger& target, int32 viewToken)
|
||||||
{
|
{
|
||||||
BAutolock _(this);
|
BAutolock _(this);
|
||||||
|
|
||||||
@@ -482,7 +482,7 @@ EventDispatcher::SendFakeMouseMoved(EventTarget& target, int32 viewToken)
|
|||||||
moved.AddMessage("be:drag_message", &fDragMessage);
|
moved.AddMessage("be:drag_message", &fDragMessage);
|
||||||
}
|
}
|
||||||
|
|
||||||
_SendMessage(target.Messenger(), &moved, kMouseTransitImportance);
|
_SendMessage(target, &moved, kMouseTransitImportance);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -80,7 +80,7 @@ class EventDispatcher : public BLocker {
|
|||||||
void SetKeyboardFilter(EventFilter* filter);
|
void SetKeyboardFilter(EventFilter* filter);
|
||||||
|
|
||||||
void GetMouse(BPoint& where, int32& buttons);
|
void GetMouse(BPoint& where, int32& buttons);
|
||||||
void SendFakeMouseMoved(EventTarget& target, int32 viewToken);
|
void SendFakeMouseMoved(BMessenger& target, int32 viewToken);
|
||||||
|
|
||||||
bool HasCursorThread();
|
bool HasCursorThread();
|
||||||
void SetHWInterface(HWInterface* interface);
|
void SetHWInterface(HWInterface* interface);
|
||||||
|
|||||||
Reference in New Issue
Block a user