Improved locking. A bit. :-)

git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@11879 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Adi Oanca
2005-03-17 17:41:00 +00:00
parent 211de495df
commit ddf57545a2
4 changed files with 112 additions and 129 deletions
+4 -4
View File
@@ -50,7 +50,7 @@
# define STRACE(x) ; # define STRACE(x) ;
#endif #endif
#define DEBUG_LAYER_REBUILD //#define DEBUG_LAYER_REBUILD
#ifdef DEBUG_LAYER_REBUILD #ifdef DEBUG_LAYER_REBUILD
# define RBTRACE(x) printf x # define RBTRACE(x) printf x
#else #else
@@ -763,7 +763,7 @@ void Layer::RebuildFullRegion(void)
void Layer::RebuildRegions( const BRegion& reg, uint32 action, BPoint pt, BPoint ptOffset) void Layer::RebuildRegions( const BRegion& reg, uint32 action, BPoint pt, BPoint ptOffset)
{ {
STRACE(("Layer(%s)::RebuildRegions() START\n", GetName())); STRACE(("Layer(%s)::RebuildRegions() START\n", GetName()));
// TODO:/NOTE: this method must be executed as quickly as possible. // TODO:/NOTE: this method must be executed as quickly as possible.
// Currently SendView[Moved/Resized]Msg() simply constructs a message and calls // Currently SendView[Moved/Resized]Msg() simply constructs a message and calls
@@ -876,12 +876,12 @@ void Layer::RebuildRegions( const BRegion& reg, uint32 action, BPoint pt, BPoint
if (!IsHidden()) if (!IsHidden())
{ {
fFullVisible.MakeEmpty();
fVisible = fFull;
#ifdef DEBUG_LAYER_REBUILD #ifdef DEBUG_LAYER_REBUILD
printf("Layer(%s) real action START\n", GetName()); printf("Layer(%s) real action START\n", GetName());
fFull.PrintToStream(); fFull.PrintToStream();
#endif #endif
fFullVisible.MakeEmpty();
fVisible = fFull;
if (fParent && fVisible.CountRects() > 0) if (fParent && fVisible.CountRects() > 0)
{ {
+6 -29
View File
@@ -539,6 +539,7 @@ void RootLayer::RemoveSubsetWinBorder(WinBorder *winBorder, WinBorder *fromWinBo
void RootLayer::SetActiveWorkspace(int32 index) void RootLayer::SetActiveWorkspace(int32 index)
{ {
STRACE(("RootLayer(%s)::SetActiveWorkspace(%ld)\n", GetName(), index)); STRACE(("RootLayer(%s)::SetActiveWorkspace(%ld)\n", GetName(), index));
// we need to lock the window list here so no other window can be created
desktop->Lock(); desktop->Lock();
// if fWorkspace[index] object does not exist, create and add allowed WinBorders // if fWorkspace[index] object does not exist, create and add allowed WinBorders
@@ -896,9 +897,9 @@ bool RootLayer::SetScreenResolution(int32 width, int32 height, uint32 colorspace
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
// Input related methods // Input related methods
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
inline
void RootLayer::MouseEventHandler(int32 code, BPortLink& msg) void RootLayer::MouseEventHandler(int32 code, BPortLink& msg)
{ {
// TODO: locking mechanism needs SERIOUS rethought
switch(code) switch(code)
{ {
case B_MOUSE_DOWN: case B_MOUSE_DOWN:
@@ -956,12 +957,11 @@ void RootLayer::MouseEventHandler(int32 code, BPortLink& msg)
} }
else else
{ {
if (!(target->Window()->Flags() & B_WILL_ACCEPT_FIRST_CLICK)) if (exFocus != FocusWinBorder()
&& !(target->Window()->Flags() & B_WILL_ACCEPT_FIRST_CLICK))
sendMessage = false; sendMessage = false;
target->Window()->Lock();
target->MouseDown(evt, sendMessage); target->MouseDown(evt, sendMessage);
target->Window()->Unlock();
} }
fMouseTarget = target; fMouseTarget = target;
@@ -991,9 +991,7 @@ void RootLayer::MouseEventHandler(int32 code, BPortLink& msg)
// currently mouse up goes to the same window which received mouse down // currently mouse up goes to the same window which received mouse down
if (fMouseTarget) if (fMouseTarget)
{ {
fMouseTarget->Window()->Lock();
fMouseTarget->MouseUp(evt); fMouseTarget->MouseUp(evt);
fMouseTarget->Window()->Unlock();
fMouseTarget = NULL; fMouseTarget = NULL;
} }
@@ -1042,9 +1040,7 @@ void RootLayer::MouseEventHandler(int32 code, BPortLink& msg)
} }
else else
{ {
fMouseTarget->Window()->Lock();
fMouseTarget->MouseMoved(evt); fMouseTarget->MouseMoved(evt);
fMouseTarget->Window()->Unlock();
} }
} }
else else
@@ -1052,9 +1048,7 @@ void RootLayer::MouseEventHandler(int32 code, BPortLink& msg)
WinBorder *target = WinBorderAt(evt.where); WinBorder *target = WinBorderAt(evt.where);
if (target) if (target)
{ {
target->Window()->Lock();
target->MouseMoved(evt); target->MouseMoved(evt);
target->Window()->Unlock();
} }
} }
@@ -1077,9 +1071,7 @@ void RootLayer::MouseEventHandler(int32 code, BPortLink& msg)
if (FocusWinBorder()) if (FocusWinBorder())
{ {
BPoint cursorPos = GetDisplayDriver()->GetCursorPosition(); BPoint cursorPos = GetDisplayDriver()->GetCursorPosition();
FocusWinBorder()->Window()->Lock();
FocusWinBorder()->MouseWheel(evt, cursorPos); FocusWinBorder()->MouseWheel(evt, cursorPos);
FocusWinBorder()->Window()->Unlock();
} }
break; break;
} }
@@ -1091,6 +1083,7 @@ void RootLayer::MouseEventHandler(int32 code, BPortLink& msg)
} }
} }
inline
void RootLayer::KeyboardEventHandler(int32 code, BPortLink& msg) void RootLayer::KeyboardEventHandler(int32 code, BPortLink& msg)
{ {
@@ -1268,8 +1261,6 @@ void RootLayer::KeyboardEventHandler(int32 code, BPortLink& msg)
Workspace *ws=ActiveWorkspace(); Workspace *ws=ActiveWorkspace();
Lock();
WinBorder *target=ws->Focus(); WinBorder *target=ws->Focus();
if(target) if(target)
{ {
@@ -1295,8 +1286,6 @@ void RootLayer::KeyboardEventHandler(int32 code, BPortLink& msg)
} }
} }
Unlock();
if (string) if (string)
free(string); free(string);
break; break;
@@ -1364,8 +1353,6 @@ void RootLayer::KeyboardEventHandler(int32 code, BPortLink& msg)
Workspace *ws=ActiveWorkspace(); Workspace *ws=ActiveWorkspace();
Lock();
WinBorder *target=ws->Focus(); WinBorder *target=ws->Focus();
if(target) if(target)
{ {
@@ -1389,8 +1376,6 @@ void RootLayer::KeyboardEventHandler(int32 code, BPortLink& msg)
} }
} }
Unlock();
if (string) if (string)
free(string); free(string);
break; break;
@@ -1416,8 +1401,6 @@ void RootLayer::KeyboardEventHandler(int32 code, BPortLink& msg)
Workspace *ws=ActiveWorkspace(); Workspace *ws=ActiveWorkspace();
Lock();
WinBorder *target=ws->Focus(); WinBorder *target=ws->Focus();
if(target) if(target)
{ {
@@ -1434,7 +1417,6 @@ void RootLayer::KeyboardEventHandler(int32 code, BPortLink& msg)
} }
} }
Unlock();
break; break;
} }
case B_UNMAPPED_KEY_UP: case B_UNMAPPED_KEY_UP:
@@ -1458,8 +1440,6 @@ void RootLayer::KeyboardEventHandler(int32 code, BPortLink& msg)
Workspace *ws=ActiveWorkspace(); Workspace *ws=ActiveWorkspace();
Lock();
WinBorder *target=ws->Focus(); WinBorder *target=ws->Focus();
if(target) if(target)
{ {
@@ -1476,7 +1456,6 @@ void RootLayer::KeyboardEventHandler(int32 code, BPortLink& msg)
} }
} }
Unlock();
break; break;
} }
case B_MODIFIERS_CHANGED: case B_MODIFIERS_CHANGED:
@@ -1498,8 +1477,6 @@ void RootLayer::KeyboardEventHandler(int32 code, BPortLink& msg)
Workspace *ws=ActiveWorkspace(); Workspace *ws=ActiveWorkspace();
Lock();
WinBorder *target=ws->Focus(); WinBorder *target=ws->Focus();
if(target) if(target)
{ {
@@ -1515,7 +1492,7 @@ void RootLayer::KeyboardEventHandler(int32 code, BPortLink& msg)
win->SendMessageToClient(&keymsg); win->SendMessageToClient(&keymsg);
} }
} }
Unlock();
break; break;
} }
default: default:
+5 -8
View File
@@ -249,9 +249,7 @@ void ServerWindow::ReplaceDecorator(void)
//! Requests that the ServerWindow's BWindow quit //! Requests that the ServerWindow's BWindow quit
void ServerWindow::Quit(void) void ServerWindow::Quit(void)
{ {
if (!IsLocked()) // NOTE: if you do something else, other than sending a port message, PLEASE lock
debugger("you must lock a ServerWindow object before calling ::Quit()\n");
STRACE(("ServerWindow %s: Quit\n",fTitle.String())); STRACE(("ServerWindow %s: Quit\n",fTitle.String()));
BMessage msg; BMessage msg;
@@ -263,9 +261,8 @@ void ServerWindow::Quit(void)
//! Shows the window's WinBorder //! Shows the window's WinBorder
void ServerWindow::Show(void) void ServerWindow::Show(void)
{ {
// NOTE: if you do something else, other than sending a port message, PLEASE lock
STRACE(("ServerWindow %s: Show\n",fTitle.String())); STRACE(("ServerWindow %s: Show\n",fTitle.String()));
if (!IsLocked())
debugger("you must lock a ServerWindow object before calling ::Show()\n");
if(!fWinBorder->IsHidden()) if(!fWinBorder->IsHidden())
return; return;
@@ -276,9 +273,8 @@ void ServerWindow::Show(void)
//! Hides the window's WinBorder //! Hides the window's WinBorder
void ServerWindow::Hide(void) void ServerWindow::Hide(void)
{ {
// NOTE: if you do something else, other than sending a port message, PLEASE lock
STRACE(("ServerWindow %s: Hide\n",fTitle.String())); STRACE(("ServerWindow %s: Hide\n",fTitle.String()));
if (!IsLocked())
debugger("you must lock a ServerWindow object before calling ::Hide()\n");
if(fWinBorder->IsHidden()) if(fWinBorder->IsHidden())
return; return;
@@ -297,10 +293,10 @@ bool ServerWindow::IsHidden(void) const
//------------------------------------------------------------------------------ //------------------------------------------------------------------------------
void ServerWindow::Minimize(bool status) void ServerWindow::Minimize(bool status)
{ {
// NOTE: if you do something else, other than sending a port message, PLEASE lock
// This function doesn't need much -- check to make sure that we should and // This function doesn't need much -- check to make sure that we should and
// send the message to the client. According to the BeBook, the BWindow hook function // send the message to the client. According to the BeBook, the BWindow hook function
// does all the heavy lifting for us. :) // does all the heavy lifting for us. :)
bool sendMessages = false; bool sendMessages = false;
if (status) if (status)
@@ -334,6 +330,7 @@ void ServerWindow::Minimize(bool status)
// Sends a message to the client to perform a Zoom // Sends a message to the client to perform a Zoom
void ServerWindow::Zoom(void) void ServerWindow::Zoom(void)
{ {
// NOTE: if you do something else, other than sending a port message, PLEASE lock
BMessage msg; BMessage msg;
msg.what=B_ZOOM; msg.what=B_ZOOM;
SendMessageToClient(&msg); SendMessageToClient(&msg);
+97 -88
View File
@@ -163,79 +163,74 @@ click_type WinBorder::TellWhat(PointerEvent& evt) const
*/ */
void WinBorder::MouseDown(PointerEvent& evt, bool sendMessage) void WinBorder::MouseDown(PointerEvent& evt, bool sendMessage)
{ {
if (!(Window()->IsLocked())) // user clicked on WinBorder's full visible region,
debugger("you must lock the attached ServerWindow object\n\t before calling WinBorder::MouseDown()\n"); // find out if the user clicked the decorator.
// this is important to determine how much we should resize or move the Layer(WinBorder)(window) click_type action;
// user clicked on WinBorder's visible region, which is in fact decorator's. // find out where user clicked in Decorator
// so, if true, we find out if the user clicked the decorator. action = fDecorator->Clicked(evt.where, evt.buttons, evt.modifiers);
switch(action)
Layer *target = LayerAt(evt.where);
if (target == this)
{ {
click_type action; case DEC_CLOSE:
// find out where user clicked in Decorator
action = fDecorator->Clicked(evt.where, evt.buttons, evt.modifiers);
switch(action)
{ {
case DEC_CLOSE: fIsClosing = true;
fDecorator->SetClose(true);
fDecorator->DrawClose();
STRACE_CLICK(("===> DEC_CLOSE\n"));
break;
}
case DEC_ZOOM:
{
fIsZooming = true;
fDecorator->SetZoom(true);
fDecorator->DrawZoom();
STRACE_CLICK(("===> DEC_ZOOM\n"));
break;
}
case DEC_MINIMIZE:
{
fIsMinimizing = true;
fDecorator->SetMinimize(true);
fDecorator->DrawMinimize();
STRACE_CLICK(("===> DEC_MINIMIZE\n"));
break;
}
case DEC_RESIZE:
case DEC_DRAG:
case DEC_MOVETOBACK:
{
// do nothing - RootLayer takes care of that
STRACE_CLICK(("===> DEC_RESIZE || DEC_DRAG || DEC_MOVETOBACK \n"));
break;
}
case DEC_NONE:
{
Window()->Lock();
// TODO: you can improve performance by doing this search client-side!
Layer *target = LayerAt(evt.where);
if (sendMessage && target && target != fTopLayer)
{ {
fIsClosing = true; BMessage msg;
fDecorator->SetClose(true); msg.what = B_MOUSE_DOWN;
fDecorator->DrawClose(); msg.AddInt64("when", evt.when);
STRACE_CLICK(("===> DEC_CLOSE\n")); msg.AddPoint("where", evt.where);
break; msg.AddInt32("modifiers", evt.modifiers);
} msg.AddInt32("buttons", evt.buttons);
case DEC_ZOOM: msg.AddInt32("clicks", evt.clicks);
{
fIsZooming = true; Window()->SendMessageToClient(&msg, target->fViewToken, false);
fDecorator->SetZoom(true);
fDecorator->DrawZoom();
STRACE_CLICK(("===> DEC_ZOOM\n"));
break;
}
case DEC_MINIMIZE:
{
fIsMinimizing = true;
fDecorator->SetMinimize(true);
fDecorator->DrawMinimize();
STRACE_CLICK(("===> DEC_MINIMIZE\n"));
break;
}
case DEC_RESIZE:
case DEC_DRAG:
case DEC_MOVETOBACK:
{
// do nothing - RootLayer takes care of that
break;
}
case DEC_NONE:
{
debugger("WinBorder::MouseDown - Decorator should NOT return DEC_NONE\n");
break;
}
default:
{
debugger("WinBorder::MouseDown - Decorator returned UNKNOWN code\n");
break;
} }
Window()->Unlock();
break;
}
default:
{
debugger("WinBorder::MouseDown - Decorator returned UNKNOWN code\n");
break;
} }
} }
else if (sendMessage && target && target != fTopLayer)
{
BMessage msg;
msg.what = B_MOUSE_DOWN;
msg.AddInt64("when", evt.when);
msg.AddPoint("where", evt.where);
msg.AddInt32("modifiers", evt.modifiers);
msg.AddInt32("buttons", evt.buttons);
msg.AddInt32("clicks", evt.clicks);
Window()->SendMessageToClient(&msg, target->fViewToken, false);
}
fLastMousePosition = evt.where; fLastMousePosition = evt.where;
} }
@@ -249,9 +244,6 @@ void WinBorder::MouseDown(PointerEvent& evt, bool sendMessage)
*/ */
void WinBorder::MouseMoved(PointerEvent& evt) void WinBorder::MouseMoved(PointerEvent& evt)
{ {
if (!(Window()->IsLocked()))
debugger("you must lock the attached ServerWindow object\n\t before calling WinBorder::MouseMoved()\n");
// Do a click test only if we have to, which would be now. :) // Do a click test only if we have to, which would be now. :)
click_type location=fDecorator->Clicked(evt.where, evt.buttons,fKeyModifiers); click_type location=fDecorator->Clicked(evt.where, evt.buttons,fKeyModifiers);
@@ -275,12 +267,19 @@ void WinBorder::MouseMoved(PointerEvent& evt)
if (fTopLayer->fFullVisible.Contains(evt.where)) if (fTopLayer->fFullVisible.Contains(evt.where))
{ {
BMessage movemsg(B_MOUSE_MOVED); Window()->Lock();
movemsg.AddInt64("when",evt.when); // TODO: you can improve performance by doing this search client-side!
movemsg.AddPoint("where",evt.where); Layer *target = LayerAt(evt.where);
movemsg.AddInt32("buttons",evt.buttons); if (target)
{
BMessage movemsg(B_MOUSE_MOVED);
movemsg.AddInt64("when",evt.when);
movemsg.AddPoint("where",evt.where);
movemsg.AddInt32("buttons",evt.buttons);
Window()->SendMessageToClient(&movemsg); Window()->SendMessageToClient(&movemsg);
}
Window()->Unlock();
} }
fLastMousePosition = evt.where; fLastMousePosition = evt.where;
@@ -296,14 +295,11 @@ void WinBorder::MouseMoved(PointerEvent& evt)
*/ */
void WinBorder::MouseUp(PointerEvent& evt) void WinBorder::MouseUp(PointerEvent& evt)
{ {
if (!(Window()->IsLocked()))
debugger("you must lock the attached ServerWindow object\n\t before calling WinBorder::MouseUp()\n");
click_type action; click_type action;
// find out where user clicked in Decorator // find out where user clicked in Decorator
action = fDecorator->Clicked(evt.where, evt.buttons, evt.modifiers); action = fDecorator->Clicked(evt.where, evt.buttons, evt.modifiers);
if (fIsZooming) if (fIsZooming)
{ {
fIsZooming = false; fIsZooming = false;
@@ -333,15 +329,21 @@ void WinBorder::MouseUp(PointerEvent& evt)
return; return;
} }
Layer *target = LayerAt(evt.where); if (action == DEC_NONE)
if (target && target != fTopLayer)
{ {
BMessage upmsg(B_MOUSE_UP); Window()->Lock();
upmsg.AddInt64("when",evt.when); // TODO: you can improve performance by doing this search client-side!
upmsg.AddPoint("where",evt.where); Layer *target = LayerAt(evt.where);
upmsg.AddInt32("modifiers",evt.modifiers); if (target && target != fTopLayer)
{
BMessage upmsg(B_MOUSE_UP);
upmsg.AddInt64("when",evt.when);
upmsg.AddPoint("where",evt.where);
upmsg.AddInt32("modifiers",evt.modifiers);
Window()->SendMessageToClient(&upmsg, target->fViewToken, false); Window()->SendMessageToClient(&upmsg, target->fViewToken, false);
}
Window()->Unlock();
} }
} }
@@ -349,12 +351,19 @@ void WinBorder::MouseWheel(PointerEvent& evt, BPoint& ptWhere)
{ {
if (fTopLayer->fFullVisible.Contains(ptWhere)) if (fTopLayer->fFullVisible.Contains(ptWhere))
{ {
BMessage wheelmsg(B_MOUSE_WHEEL_CHANGED); Window()->Lock();
wheelmsg.AddInt64("when",evt.when); // TODO: you can improve performance by doing this search client-side!
wheelmsg.AddFloat("be:wheel_delta_x",evt.wheel_delta_x); Layer *target = LayerAt(evt.where);
wheelmsg.AddFloat("be:wheel_delta_y",evt.wheel_delta_y); if (target && target != fTopLayer)
{
BMessage wheelmsg(B_MOUSE_WHEEL_CHANGED);
wheelmsg.AddInt64("when",evt.when);
wheelmsg.AddFloat("be:wheel_delta_x",evt.wheel_delta_x);
wheelmsg.AddFloat("be:wheel_delta_y",evt.wheel_delta_y);
Window()->SendMessageToClient(&wheelmsg); Window()->SendMessageToClient(&wheelmsg);
}
Window()->Unlock();
} }
} }