* Removed superfluous ReplaceDecorator() method.

* Cleanup, no functional change.


git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@32243 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Axel Dörfler
2009-08-11 09:25:26 +00:00
parent fcd5021275
commit 07e13b5fe6
2 changed files with 168 additions and 177 deletions
+159 -169
View File
@@ -1,5 +1,5 @@
/* /*
* Copyright 2001-2008, Haiku. * Copyright 2001-2009, Haiku.
* Distributed under the terms of the MIT License. * Distributed under the terms of the MIT License.
* *
* Authors: * Authors:
@@ -12,19 +12,44 @@
* Philippe Saint-Pierre, [email protected] * Philippe Saint-Pierre, [email protected]
*/ */
/*!
\class ServerWindow
\brief Shadow BWindow class
A ServerWindow handles all the intraserver tasks required of it by its BWindow. There are /*! \class ServerWindow
too many tasks to list as being done by them, but they include handling View transactions,
coordinating and linking a window's Window half with its messaging half, dispatching The ServerWindow class handles all BWindow messaging; it forwards all
mouse and key events from the server to its window, and other such things. BWindow requests to the corresponding app_server classes, that is Desktop,
Window, and View.
Furthermore, it also sends app_server requests/notices to its BWindow. There
is one ServerWindow per BWindow.
*/ */
#include "ServerWindow.h" #include "ServerWindow.h"
#include <syslog.h>
#include <new>
#include <AppDefs.h>
#include <Autolock.h>
#include <Debug.h>
#include <DirectWindow.h>
#include <TokenSpace.h>
#include <View.h>
#include <GradientLinear.h>
#include <GradientRadial.h>
#include <GradientRadialFocus.h>
#include <GradientDiamond.h>
#include <GradientConic.h>
#include <DirectWindowPrivate.h>
#include <MessagePrivate.h>
#include <PortLink.h>
#include <ServerProtocolStructs.h>
#include <ViewPrivate.h>
#include <WindowInfo.h>
#include <WindowPrivate.h>
#include "clipping.h"
#include "AppServer.h" #include "AppServer.h"
#include "Desktop.h" #include "Desktop.h"
#include "DrawingEngine.h" #include "DrawingEngine.h"
@@ -39,32 +64,10 @@
#include "Window.h" #include "Window.h"
#include "WorkspacesView.h" #include "WorkspacesView.h"
#include "clipping.h"
#include <DirectWindowPrivate.h>
#include <MessagePrivate.h>
#include <PortLink.h>
#include <ServerProtocolStructs.h>
#include <ViewPrivate.h>
#include <WindowInfo.h>
#include <WindowPrivate.h>
#include <AppDefs.h>
#include <Autolock.h>
#include <Debug.h>
#include <DirectWindow.h>
#include <TokenSpace.h>
#include <View.h>
#include <GradientLinear.h>
#include <GradientRadial.h>
#include <GradientRadialFocus.h>
#include <GradientDiamond.h>
#include <GradientConic.h>
#include <new>
using std::nothrow; using std::nothrow;
//#define TRACE_SERVER_WINDOW //#define TRACE_SERVER_WINDOW
#ifdef TRACE_SERVER_WINDOW #ifdef TRACE_SERVER_WINDOW
# include <stdio.h> # include <stdio.h>
@@ -177,8 +180,7 @@ direct_window_data::InitCheck() const
// #pragma mark - // #pragma mark -
/*! /*! Sets up the basic BWindow counterpart - you have to call Init() before
Sets up the basic BWindow counterpart - you have to call Init() before
you can actually use it, though. you can actually use it, though.
*/ */
ServerWindow::ServerWindow(const char *title, ServerApp *app, ServerWindow::ServerWindow(const char *title, ServerApp *app,
@@ -236,7 +238,9 @@ compare_message_profiles(const void* _a, const void* _b)
#endif #endif
//! Tears down all connections the main app_server objects, and deletes some internals. /*! Tears down all connections the main app_server objects, and deletes some
internals.
*/
ServerWindow::~ServerWindow() ServerWindow::~ServerWindow()
{ {
STRACE(("ServerWindow(%s@%p):~ServerWindow()\n", fTitle, this)); STRACE(("ServerWindow(%s@%p):~ServerWindow()\n", fTitle, this));
@@ -282,8 +286,9 @@ ServerWindow::~ServerWindow()
p->time / p->count); p->time / p->count);
} }
if (sRedrawProcessingTime.count > 0) { if (sRedrawProcessingTime.count > 0) {
printf("average redraw processing time: %g secs, count: %ld (%lld usecs per call)\n", printf("average redraw processing time: %g secs, count: %ld (%lld "
sRedrawProcessingTime.time / 1000000.0, sRedrawProcessingTime.count, "usecs per call)\n", sRedrawProcessingTime.time / 1000000.0,
sRedrawProcessingTime.count,
sRedrawProcessingTime.time / sRedrawProcessingTime.count); sRedrawProcessingTime.time / sRedrawProcessingTime.count);
} }
// if (sNextMessageTime.count > 0) { // if (sNextMessageTime.count > 0) {
@@ -357,18 +362,6 @@ ServerWindow::_GetLooperName(char* name, size_t length)
} }
//! Forces the window to update its decorator
void
ServerWindow::ReplaceDecorator()
{
if (!IsLocked())
debugger("you must lock a ServerWindow object before calling ::ReplaceDecorator()\n");
STRACE(("ServerWindow %s: Replace Decorator\n", fTitle));
//fWindow->UpdateDecorator();
}
/*! Shows the window's Window. /*! Shows the window's Window.
*/ */
void void
@@ -532,8 +525,7 @@ ServerWindow::ResyncDrawState()
} }
/*! /*! Returns the ServerWindow's Window, if it exists and has been
Returns the ServerWindow's Window, if it exists and has been
added to the Desktop already. added to the Desktop already.
In other words, you cannot assume this method will always give you In other words, you cannot assume this method will always give you
a valid pointer. a valid pointer.
@@ -550,7 +542,7 @@ ServerWindow::Window() const
View* View*
ServerWindow::_CreateView(BPrivate::LinkReceiver &link, View **_parent) ServerWindow::_CreateView(BPrivate::LinkReceiver& link, View** _parent)
{ {
// NOTE: no need to check for a lock. This is a private method. // NOTE: no need to check for a lock. This is a private method.
@@ -638,8 +630,7 @@ fDesktop->LockAllWindows();
} }
/*! /*! Dispatches all window messages, and those view messages that
Dispatches all window messages, and those view messages that
don't need a valid fCurrentView (ie. view creation). don't need a valid fCurrentView (ie. view creation).
*/ */
void void
@@ -711,6 +702,7 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
} }
case AS_SEND_BEHIND: case AS_SEND_BEHIND:
{ {
// Has the all-window lock
int32 token; int32 token;
team_id teamID; team_id teamID;
status_t status = B_ERROR; status_t status = B_ERROR;
@@ -724,11 +716,7 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
Title(), behindOf ? behindOf->Title() : "NULL")); Title(), behindOf ? behindOf->Title() : "NULL"));
if (behindOf != NULL) { if (behindOf != NULL) {
//fDesktop->UnlockSingleWindow();
// TODO: there is a big race condition when we unlock here
// (window could be gone by now)!
fDesktop->SendWindowBehind(fWindow, behindOf); fDesktop->SendWindowBehind(fWindow, behindOf);
//fDesktop->LockSingleWindow();
status = B_OK; status = B_OK;
} else } else
status = B_NAME_NOT_FOUND; status = B_NAME_NOT_FOUND;
@@ -779,6 +767,7 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
case AS_ADD_TO_SUBSET: case AS_ADD_TO_SUBSET:
{ {
// Has the all-window lock
DTRACE(("ServerWindow %s: Message AS_ADD_TO_SUBSET\n", Title())); DTRACE(("ServerWindow %s: Message AS_ADD_TO_SUBSET\n", Title()));
status_t status = B_ERROR; status_t status = B_ERROR;
@@ -789,12 +778,8 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
if (window == NULL || window->Feel() != B_NORMAL_WINDOW_FEEL) { if (window == NULL || window->Feel() != B_NORMAL_WINDOW_FEEL) {
status = B_BAD_VALUE; status = B_BAD_VALUE;
} else { } else {
//fDesktop->UnlockSingleWindow();
// TODO: there is a big race condition when we unlock here
// (window could be gone by now)!
status = fDesktop->AddWindowToSubset(fWindow, window) status = fDesktop->AddWindowToSubset(fWindow, window)
? B_OK : B_NO_MEMORY; ? B_OK : B_NO_MEMORY;
//fDesktop->LockSingleWindow();
} }
} }
@@ -804,6 +789,7 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
} }
case AS_REMOVE_FROM_SUBSET: case AS_REMOVE_FROM_SUBSET:
{ {
// Has the all-window lock
DTRACE(("ServerWindow %s: Message AS_REM_FROM_SUBSET\n", Title())); DTRACE(("ServerWindow %s: Message AS_REM_FROM_SUBSET\n", Title()));
status_t status = B_ERROR; status_t status = B_ERROR;
@@ -812,10 +798,7 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
::Window* window = fDesktop->FindWindowByClientToken(token, ::Window* window = fDesktop->FindWindowByClientToken(token,
App()->ClientTeam()); App()->ClientTeam());
if (window != NULL) { if (window != NULL) {
//fDesktop->UnlockSingleWindow();
// TODO: there is a big race condition when we unlock here (window could be gone by now)!
fDesktop->RemoveWindowFromSubset(fWindow, window); fDesktop->RemoveWindowFromSubset(fWindow, window);
//fDesktop->LockSingleWindow();
status = B_OK; status = B_OK;
} else } else
status = B_BAD_VALUE; status = B_BAD_VALUE;
@@ -828,6 +811,7 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
case AS_SET_LOOK: case AS_SET_LOOK:
{ {
// Has the all-window look
DTRACE(("ServerWindow %s: Message AS_SET_LOOK\n", Title())); DTRACE(("ServerWindow %s: Message AS_SET_LOOK\n", Title()));
status_t status = B_ERROR; status_t status = B_ERROR;
@@ -838,11 +822,8 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
? B_OK : B_BAD_VALUE; ? B_OK : B_BAD_VALUE;
} }
if (status == B_OK && !fWindow->IsOffscreenWindow()) { if (status == B_OK && !fWindow->IsOffscreenWindow())
//fDesktop->UnlockSingleWindow();
fDesktop->SetWindowLook(fWindow, (window_look)look); fDesktop->SetWindowLook(fWindow, (window_look)look);
//fDesktop->LockSingleWindow();
}
fLink.StartMessage(status); fLink.StartMessage(status);
fLink.Flush(); fLink.Flush();
@@ -850,6 +831,7 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
} }
case AS_SET_FEEL: case AS_SET_FEEL:
{ {
// Has the all-window look
DTRACE(("ServerWindow %s: Message AS_SET_FEEL\n", Title())); DTRACE(("ServerWindow %s: Message AS_SET_FEEL\n", Title()));
status_t status = B_ERROR; status_t status = B_ERROR;
@@ -860,11 +842,8 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
? B_OK : B_BAD_VALUE; ? B_OK : B_BAD_VALUE;
} }
if (status == B_OK && !fWindow->IsOffscreenWindow()) { if (status == B_OK && !fWindow->IsOffscreenWindow())
//fDesktop->UnlockSingleWindow();
fDesktop->SetWindowFeel(fWindow, (window_feel)feel); fDesktop->SetWindowFeel(fWindow, (window_feel)feel);
//fDesktop->LockSingleWindow();
}
fLink.StartMessage(status); fLink.StartMessage(status);
fLink.Flush(); fLink.Flush();
@@ -872,6 +851,7 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
} }
case AS_SET_FLAGS: case AS_SET_FLAGS:
{ {
// Has the all-window look
DTRACE(("ServerWindow %s: Message AS_SET_FLAGS\n", Title())); DTRACE(("ServerWindow %s: Message AS_SET_FLAGS\n", Title()));
status_t status = B_ERROR; status_t status = B_ERROR;
@@ -882,11 +862,8 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
? B_OK : B_BAD_VALUE; ? B_OK : B_BAD_VALUE;
} }
if (status == B_OK && !fWindow->IsOffscreenWindow()) { if (status == B_OK && !fWindow->IsOffscreenWindow())
//fDesktop->UnlockSingleWindow();
fDesktop->SetWindowFlags(fWindow, flags); fDesktop->SetWindowFlags(fWindow, flags);
//fDesktop->LockSingleWindow();
}
fLink.StartMessage(status); fLink.StartMessage(status);
fLink.Flush(); fLink.Flush();
@@ -928,6 +905,8 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
} }
case AS_SET_WORKSPACES: case AS_SET_WORKSPACES:
{ {
// Has the all-window lock (but would actually not need to lock at
// all)
uint32 newWorkspaces; uint32 newWorkspaces;
if (link.Read<uint32>(&newWorkspaces) != B_OK) if (link.Read<uint32>(&newWorkspaces) != B_OK)
break; break;
@@ -935,13 +914,12 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
DTRACE(("ServerWindow %s: Message AS_SET_WORKSPACES %lx\n", DTRACE(("ServerWindow %s: Message AS_SET_WORKSPACES %lx\n",
Title(), newWorkspaces)); Title(), newWorkspaces));
//fDesktop->UnlockSingleWindow();
fDesktop->SetWindowWorkspaces(fWindow, newWorkspaces); fDesktop->SetWindowWorkspaces(fWindow, newWorkspaces);
//fDesktop->LockSingleWindow();
break; break;
} }
case AS_WINDOW_RESIZE: case AS_WINDOW_RESIZE:
{ {
// Has the all-window look
float xResizeTo; float xResizeTo;
float yResizeTo; float yResizeTo;
link.Read<float>(&xResizeTo); link.Read<float>(&xResizeTo);
@@ -958,11 +936,9 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
// pragmatically set window bounds // pragmatically set window bounds
// fLink.StartMessage(B_BUSY); // fLink.StartMessage(B_BUSY);
// } else { // } else {
//fDesktop->UnlockSingleWindow();
fDesktop->ResizeWindowBy(fWindow, fDesktop->ResizeWindowBy(fWindow,
xResizeTo - fWindow->Frame().Width(), xResizeTo - fWindow->Frame().Width(),
yResizeTo - fWindow->Frame().Height()); yResizeTo - fWindow->Frame().Height());
//fDesktop->LockSingleWindow();
fLink.StartMessage(B_OK); fLink.StartMessage(B_OK);
// } // }
fLink.Flush(); fLink.Flush();
@@ -970,6 +946,7 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
} }
case AS_WINDOW_MOVE: case AS_WINDOW_MOVE:
{ {
// Has the all-window look
float xMoveTo; float xMoveTo;
float yMoveTo; float yMoveTo;
link.Read<float>(&xMoveTo); link.Read<float>(&xMoveTo);
@@ -984,10 +961,8 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
// pragmatically set window positions // pragmatically set window positions
fLink.StartMessage(B_BUSY); fLink.StartMessage(B_BUSY);
} else { } else {
//fDesktop->UnlockSingleWindow();
fDesktop->MoveWindowBy(fWindow, xMoveTo - fWindow->Frame().left, fDesktop->MoveWindowBy(fWindow, xMoveTo - fWindow->Frame().left,
yMoveTo - fWindow->Frame().top); yMoveTo - fWindow->Frame().top);
//fDesktop->LockSingleWindow();
fLink.StartMessage(B_OK); fLink.StartMessage(B_OK);
} }
fLink.Flush(); fLink.Flush();
@@ -995,6 +970,8 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
} }
case AS_SET_SIZE_LIMITS: case AS_SET_SIZE_LIMITS:
{ {
// Has the all-window look
// Attached Data: // Attached Data:
// 1) float minimum width // 1) float minimum width
// 2) float maximum width // 2) float maximum width
@@ -1018,15 +995,7 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
"x: %ld-%ld, y: %ld-%ld\n", "x: %ld-%ld, y: %ld-%ld\n",
Title(), minWidth, maxWidth, minHeight, maxHeight)); Title(), minWidth, maxWidth, minHeight, maxHeight));
//fDesktop->UnlockSingleWindow(); fWindow->SetSizeLimits(minWidth, maxWidth, minHeight, maxHeight);
if (fDesktop->LockAllWindows()) {
fWindow->SetSizeLimits(minWidth, maxWidth,
minHeight, maxHeight);
fDesktop->UnlockAllWindows();
}
//fDesktop->LockSingleWindow();
// and now, sync the client to the limits that we were able to enforce // and now, sync the client to the limits that we were able to enforce
fWindow->GetSizeLimits(&minWidth, &maxWidth, fWindow->GetSizeLimits(&minWidth, &maxWidth,
@@ -1045,6 +1014,7 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
case AS_SET_DECORATOR_SETTINGS: case AS_SET_DECORATOR_SETTINGS:
{ {
// Has the all-window look
DTRACE(("ServerWindow %s: Message AS_SET_DECORATOR_SETTINGS\n", DTRACE(("ServerWindow %s: Message AS_SET_DECORATOR_SETTINGS\n",
Title())); Title()));
@@ -1053,11 +1023,8 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
char buffer[size]; char buffer[size];
if (link.Read(buffer, size) == B_OK) { if (link.Read(buffer, size) == B_OK) {
BMessage settings; BMessage settings;
if (settings.Unflatten(buffer) == B_OK) { if (settings.Unflatten(buffer) == B_OK)
//fDesktop->UnlockSingleWindow();
fDesktop->SetWindowDecoratorSettings(fWindow, settings); fDesktop->SetWindowDecoratorSettings(fWindow, settings);
//fDesktop->LockSingleWindow();
}
} }
} }
break; break;
@@ -1091,6 +1058,7 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
case AS_SYSTEM_FONT_CHANGED: case AS_SYSTEM_FONT_CHANGED:
{ {
// Has the all-window look
fDesktop->FontsChanged(fWindow); fDesktop->FontsChanged(fWindow);
// TODO: tell client about this, too, and relayout... // TODO: tell client about this, too, and relayout...
break; break;
@@ -1124,9 +1092,9 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
case AS_GET_MOUSE: case AS_GET_MOUSE:
{ {
// Has the all-window look
DTRACE(("ServerWindow %s: Message AS_GET_MOUSE\n", fTitle)); DTRACE(("ServerWindow %s: Message AS_GET_MOUSE\n", fTitle));
//fDesktop->UnlockSingleWindow();
// Returns // Returns
// 1) BPoint mouse location // 1) BPoint mouse location
// 2) int32 button state // 2) int32 button state
@@ -1134,7 +1102,6 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
BPoint where; BPoint where;
int32 buttons; int32 buttons;
fDesktop->GetLastMouseState(&where, &buttons); fDesktop->GetLastMouseState(&where, &buttons);
//fDesktop->LockSingleWindow();
fLink.StartMessage(B_OK); fLink.StartMessage(B_OK);
fLink.Attach<BPoint>(where); fLink.Attach<BPoint>(where);
@@ -1165,15 +1132,14 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
} }
case AS_DIRECT_WINDOW_SET_FULLSCREEN: case AS_DIRECT_WINDOW_SET_FULLSCREEN:
{ {
// Has the all-window look
bool enable; bool enable;
link.Read<bool>(&enable); link.Read<bool>(&enable);
status_t status = B_OK; status_t status = B_OK;
if (fDirectWindowData != NULL) { if (fDirectWindowData != NULL)
//fDesktop->UnlockSingleWindow(); _DirectWindowSetFullScreen(enable);
_DirectWindowSetFullScreen(enable); else
//fDesktop->LockSingleWindow();
} else
status = B_BAD_TYPE; status = B_BAD_TYPE;
fLink.StartMessage(status); fLink.StartMessage(status);
@@ -1948,7 +1914,8 @@ fDesktop->LockSingleWindow();
// search for a picture with the specified token. // search for a picture with the specified token.
ServerPicture *picture = fServerApp->FindPicture(pictureToken); ServerPicture *picture = fServerApp->FindPicture(pictureToken);
// TODO: Increase that picture's reference count.(~ allocate a picture) // TODO: Increase that picture's reference count.
// (~ allocate a picture)
if (picture == NULL) if (picture == NULL)
break; break;
@@ -1967,7 +1934,7 @@ fDesktop->LockSingleWindow();
DTRACE(("ServerWindow %s: Message AS_VIEW_GET_CLIP_REGION: " DTRACE(("ServerWindow %s: Message AS_VIEW_GET_CLIP_REGION: "
"View: %s\n", Title(), fCurrentView->Name())); "View: %s\n", Title(), fCurrentView->Name()));
// if this View is hidden, it is clear that its visible region is void. // if this view is hidden, it has no visible region
fLink.StartMessage(B_OK); fLink.StartMessage(B_OK);
if (!fWindow->IsVisible() || !fCurrentView->IsVisible()) { if (!fWindow->IsVisible() || !fCurrentView->IsVisible()) {
BRegion empty; BRegion empty;
@@ -2078,7 +2045,8 @@ fDesktop->LockSingleWindow();
BMessage dragMessage; BMessage dragMessage;
if (link.Read(buffer, bufferSize) == B_OK if (link.Read(buffer, bufferSize) == B_OK
&& dragMessage.Unflatten(buffer) == B_OK) { && dragMessage.Unflatten(buffer) == B_OK) {
ServerBitmap* bitmap = fServerApp->FindBitmap(bitmapToken); ServerBitmap* bitmap
= fServerApp->FindBitmap(bitmapToken);
// TODO: possible deadlock // TODO: possible deadlock
fDesktop->UnlockSingleWindow(); fDesktop->UnlockSingleWindow();
fDesktop->EventDispatcher().SetDragMessage(dragMessage, fDesktop->EventDispatcher().SetDragMessage(dragMessage,
@@ -2133,8 +2101,8 @@ fDesktop->LockSingleWindow();
link.Read<uint32>(&style); link.Read<uint32>(&style);
// TODO: implement rect tracking (used sometimes for selecting // TODO: implement rect tracking (used sometimes for selecting
// a group of things, also sometimes used to appear to drag something, // a group of things, also sometimes used to appear to drag
// but without real drag message) // something, but without real drag message)
break; break;
} }
case AS_VIEW_END_RECT_TRACK: case AS_VIEW_END_RECT_TRACK:
@@ -2194,8 +2162,7 @@ fDesktop->LockSingleWindow();
} }
/*! /*! Dispatches all view drawing messages.
Dispatches all view drawing messages.
The desktop clipping must be read locked when entering this method. The desktop clipping must be read locked when entering this method.
Requires a valid fCurrentView. Requires a valid fCurrentView.
*/ */
@@ -2266,8 +2233,9 @@ ServerWindow::_DispatchViewDrawingMessage(int32 code,
// do not update the pen position actually call StrokeLine // do not update the pen position actually call StrokeLine
// TODO: Decide where to put this, for example, it cannot be done // TODO: Decide where to put this, for example, it cannot be done
// for DrawString(), also there needs to be a decision, if penlocation // for DrawString(), also there needs to be a decision, if the pen
// is in View coordinates (I think it should be) or in screen coordinates. // location is in View coordinates (I think it should be) or in
// screen coordinates.
fCurrentView->CurrentState()->SetPenLocation(penPos); fCurrentView->CurrentState()->SetPenLocation(penPos);
break; break;
} }
@@ -2324,8 +2292,8 @@ ServerWindow::_DispatchViewDrawingMessage(int32 code,
if (link.ReadGradient(&gradient) != B_OK) if (link.ReadGradient(&gradient) != B_OK)
break; break;
GTRACE(("ServerWindow %s: Message AS_FILL_RECT_GRADIENT: View: %s -> " GTRACE(("ServerWindow %s: Message AS_FILL_RECT_GRADIENT: View: %s "
"BRect(%.1f, %.1f, %.1f, %.1f)\n", Title(), "-> BRect(%.1f, %.1f, %.1f, %.1f)\n", Title(),
fCurrentView->Name(), rect.left, rect.top, rect.right, fCurrentView->Name(), rect.left, rect.top, rect.right,
rect.bottom)); rect.bottom));
@@ -2876,8 +2844,10 @@ ServerWindow::_DispatchPictureMessage(int32 code, BPrivate::LinkReceiver &link)
picture->WriteSetDrawingMode((drawing_mode)drawingMode); picture->WriteSetDrawingMode((drawing_mode)drawingMode);
fCurrentView->CurrentState()->SetDrawingMode((drawing_mode)drawingMode); fCurrentView->CurrentState()->SetDrawingMode(
fWindow->GetDrawingEngine()->SetDrawingMode((drawing_mode)drawingMode); (drawing_mode)drawingMode);
fWindow->GetDrawingEngine()->SetDrawingMode(
(drawing_mode)drawingMode);
break; break;
} }
@@ -3001,7 +2971,8 @@ ServerWindow::_DispatchPictureMessage(int32 code, BPrivate::LinkReceiver &link)
BPoint radii((rect.Width() + 1) / 2, (rect.Height() + 1) / 2); BPoint radii((rect.Width() + 1) / 2, (rect.Height() + 1) / 2);
BPoint center = rect.LeftTop() + radii; BPoint center = rect.LeftTop() + radii;
picture->WriteDrawArc(center, radii, startTheta, arcTheta, code == AS_FILL_ARC); picture->WriteDrawArc(center, radii, startTheta, arcTheta,
code == AS_FILL_ARC);
break; break;
} }
@@ -3172,7 +3143,8 @@ ServerWindow::_DispatchPictureMessage(int32 code, BPrivate::LinkReceiver &link)
// This might seem a bit weird, but under R5, the shapes // This might seem a bit weird, but under R5, the shapes
// are always offset by the current pen location // are always offset by the current pen location
BPoint penLocation = fCurrentView->CurrentState()->PenLocation(); BPoint penLocation
= fCurrentView->CurrentState()->PenLocation();
for (int32 i = 0; i < ptCount; i++) { for (int32 i = 0; i < ptCount; i++) {
ptList[i] += penLocation; ptList[i] += penLocation;
} }
@@ -3211,8 +3183,8 @@ ServerWindow::_DispatchPictureMessage(int32 code, BPrivate::LinkReceiver &link)
ServerPicture *pictureToDraw = App()->FindPicture(token); ServerPicture *pictureToDraw = App()->FindPicture(token);
if (picture != NULL) { if (picture != NULL) {
// We need to make a copy of the picture, since it can change // We need to make a copy of the picture, since it can
// after it has been drawn // change after it has been drawn
ServerPicture *copy = App()->CreatePicture(pictureToDraw); ServerPicture *copy = App()->CreatePicture(pictureToDraw);
picture->NestPicture(copy); picture->NestPicture(copy);
picture->WriteDrawPicture(where, copy->Token()); picture->WriteDrawPicture(where, copy->Token());
@@ -3308,8 +3280,7 @@ ServerWindow::_DispatchPictureMessage(int32 code, BPrivate::LinkReceiver &link)
} }
/*! /*! \brief Message-dispatching loop for the ServerWindow
\brief Message-dispatching loop for the ServerWindow
Watches the ServerWindow's message port and dispatches as necessary Watches the ServerWindow's message port and dispatches as necessary
*/ */
@@ -3341,7 +3312,7 @@ ServerWindow::_MessageLooper()
int32 code; int32 code;
status_t status = receiver.GetNextMessage(code); status_t status = receiver.GetNextMessage(code);
if (status < B_OK) { if (status != B_OK) {
// that shouldn't happen, it's our port // that shouldn't happen, it's our port
printf("Someone deleted our message port!\n"); printf("Someone deleted our message port!\n");
@@ -3358,8 +3329,10 @@ ServerWindow::_MessageLooper()
#ifdef PROFILE_MESSAGE_LOOP #ifdef PROFILE_MESSAGE_LOOP
bigtime_t diff = system_time() - start; bigtime_t diff = system_time() - start;
if (diff > 10000) if (diff > 10000) {
printf("ServerWindow %s: lock acquisition took %Ld usecs\n", Title(), diff); printf("ServerWindow %s: lock acquisition took %Ld usecs\n",
Title(), diff);
}
#endif #endif
int32 messagesProcessed = 0; int32 messagesProcessed = 0;
@@ -3369,8 +3342,8 @@ ServerWindow::_MessageLooper()
while (true) { while (true) {
if (code == AS_DELETE_WINDOW || code == kMsgQuitLooper) { if (code == AS_DELETE_WINDOW || code == kMsgQuitLooper) {
// this means the client has been killed // this means the client has been killed
DTRACE(("ServerWindow %s received 'AS_DELETE_WINDOW' message code\n", DTRACE(("ServerWindow %s received 'AS_DELETE_WINDOW' message "
Title())); "code\n", Title()));
if (code == AS_DELETE_WINDOW) { if (code == AS_DELETE_WINDOW) {
fLink.StartMessage(B_OK); fLink.StartMessage(B_OK);
@@ -3382,7 +3355,8 @@ ServerWindow::_MessageLooper()
quitLoop = true; quitLoop = true;
// ServerWindow's destructor takes care of pulling this object off the desktop. // ServerWindow's destructor takes care of pulling this object
// off the desktop.
ASSERT(fWindow->IsHidden()); ASSERT(fWindow->IsHidden());
break; break;
} }
@@ -3435,15 +3409,18 @@ ServerWindow::_MessageLooper()
#else #else
sMessageProfile[code].time += diff; sMessageProfile[code].time += diff;
#endif #endif
if (diff > 10000) if (diff > 10000) {
printf("ServerWindow %s: message %ld took %Ld usecs\n", Title(), code, diff); printf("ServerWindow %s: message %ld took %Ld usecs\n",
Title(), code, diff);
}
} }
#endif #endif
if (needsAllWindowsLocked) if (needsAllWindowsLocked)
fDesktop->UnlockAllWindows(); fDesktop->UnlockAllWindows();
// only process up to 70 waiting messages at once (we have the Desktop locked) // Only process up to 70 waiting messages at once (we have the
// Desktop locked)
if (!receiver.HasMessages() || ++messagesProcessed > 70) { if (!receiver.HasMessages() || ++messagesProcessed > 70) {
if (lockedDesktop) if (lockedDesktop)
fDesktop->UnlockSingleWindow(); fDesktop->UnlockSingleWindow();
@@ -3467,7 +3444,8 @@ ServerWindow::_MessageLooper()
Unlock(); Unlock();
} }
// we were asked to quit the message loop - either on request or because of an error // We were asked to quit the message loop - either on request or because of
// an error.
Quit(); Quit();
// does not return // does not return
} }
@@ -3510,7 +3488,7 @@ ServerWindow::_EnableDirectWindowMode()
return B_NO_MEMORY; return B_NO_MEMORY;
status_t status = fDirectWindowData->InitCheck(); status_t status = fDirectWindowData->InitCheck();
if (status < B_OK) { if (status != B_OK) {
delete fDirectWindowData; delete fDirectWindowData;
fDirectWindowData = NULL; fDirectWindowData = NULL;
@@ -3535,18 +3513,23 @@ ServerWindow::HandleDirectConnection(int32 bufferState, int32 driverState)
// Don't issue a DirectConnected() notification // Don't issue a DirectConnected() notification
// if the connection is stopped, and we are called // if the connection is stopped, and we are called
// with bufferState == B_DIRECT_MODIFY. // with bufferState == B_DIRECT_MODIFY.
if ((fDirectWindowData->buffer_info->buffer_state & B_DIRECT_MODE_MASK) == B_DIRECT_STOP if ((fDirectWindowData->buffer_info->buffer_state & B_DIRECT_MODE_MASK)
== B_DIRECT_STOP
&& (bufferState & B_DIRECT_MODE_MASK) != B_DIRECT_START) { && (bufferState & B_DIRECT_MODE_MASK) != B_DIRECT_START) {
return; return;
} }
fDirectWindowData->started = true; fDirectWindowData->started = true;
if (bufferState != -1) if (bufferState != -1) {
fDirectWindowData->buffer_info->buffer_state = (direct_buffer_state)bufferState; fDirectWindowData->buffer_info->buffer_state
= (direct_buffer_state)bufferState;
}
if (driverState != -1) if (driverState != -1) {
fDirectWindowData->buffer_info->driver_state = (direct_driver_state)driverState; fDirectWindowData->buffer_info->driver_state
= (direct_driver_state)driverState;
}
if ((bufferState & B_DIRECT_MODE_MASK) != B_DIRECT_STOP) { if ((bufferState & B_DIRECT_MODE_MASK) != B_DIRECT_STOP) {
// TODO: Locking ? // TODO: Locking ?
@@ -3554,6 +3537,7 @@ ServerWindow::HandleDirectConnection(int32 bufferState, int32 driverState)
fDirectWindowData->buffer_info->bits = buffer->Bits(); fDirectWindowData->buffer_info->bits = buffer->Bits();
fDirectWindowData->buffer_info->pci_bits = NULL; // TODO fDirectWindowData->buffer_info->pci_bits = NULL; // TODO
fDirectWindowData->buffer_info->bytes_per_row = buffer->BytesPerRow(); fDirectWindowData->buffer_info->bytes_per_row = buffer->BytesPerRow();
switch (buffer->ColorSpace()) { switch (buffer->ColorSpace()) {
case B_RGB32: case B_RGB32:
case B_RGBA32: case B_RGBA32:
@@ -3576,44 +3560,53 @@ ServerWindow::HandleDirectConnection(int32 bufferState, int32 driverState)
fDirectWindowData->buffer_info->bits_per_pixel = 8; fDirectWindowData->buffer_info->bits_per_pixel = 8;
break; break;
default: default:
fprintf(stderr, "unknown colorspace in HandleDirectConnection()!\n"); syslog(LOG_ERR,
"unknown colorspace in HandleDirectConnection()!\n");
fDirectWindowData->buffer_info->bits_per_pixel = 0; fDirectWindowData->buffer_info->bits_per_pixel = 0;
break; break;
} }
fDirectWindowData->buffer_info->pixel_format = buffer->ColorSpace(); fDirectWindowData->buffer_info->pixel_format = buffer->ColorSpace();
fDirectWindowData->buffer_info->layout = B_BUFFER_NONINTERLEAVED; fDirectWindowData->buffer_info->layout = B_BUFFER_NONINTERLEAVED;
fDirectWindowData->buffer_info->orientation = B_BUFFER_TOP_TO_BOTTOM; // TODO fDirectWindowData->buffer_info->orientation = B_BUFFER_TOP_TO_BOTTOM;
fDirectWindowData->buffer_info->window_bounds = to_clipping_rect(fWindow->Frame()); // TODO
fDirectWindowData->buffer_info->window_bounds
= to_clipping_rect(fWindow->Frame());
// TODO: Review this // TODO: Review this
const int32 kMaxClipRectsCount = (DIRECT_BUFFER_INFO_AREA_SIZE - sizeof(direct_buffer_info)) const int32 kMaxClipRectsCount = (DIRECT_BUFFER_INFO_AREA_SIZE
/ sizeof(clipping_rect); - sizeof(direct_buffer_info)) / sizeof(clipping_rect);
// We just want the region inside the window, border excluded. // We just want the region inside the window, border excluded.
BRegion clipRegion = fWindow->VisibleContentRegion(); BRegion clipRegion = fWindow->VisibleContentRegion();
fDirectWindowData->buffer_info->clip_list_count = min_c(clipRegion.CountRects(), fDirectWindowData->buffer_info->clip_list_count
kMaxClipRectsCount); = min_c(clipRegion.CountRects(), kMaxClipRectsCount);
fDirectWindowData->buffer_info->clip_bounds = clipRegion.FrameInt(); fDirectWindowData->buffer_info->clip_bounds = clipRegion.FrameInt();
for (uint32 i = 0; i < fDirectWindowData->buffer_info->clip_list_count; i++) for (uint32 i = 0; i < fDirectWindowData->buffer_info->clip_list_count;
fDirectWindowData->buffer_info->clip_list[i] = clipRegion.RectAtInt(i); i++) {
fDirectWindowData->buffer_info->clip_list[i]
= clipRegion.RectAtInt(i);
}
} }
// Releasing this sem causes the client to call BDirectWindow::DirectConnected() // Releasing this semaphore causes the client to call
// BDirectWindow::DirectConnected()
release_sem(fDirectWindowData->sem); release_sem(fDirectWindowData->sem);
// TODO: Waiting half a second in the ServerWindow thread is not a problem, // TODO: Waiting half a second in the ServerWindow thread is not a problem,
// but since we are called from the Desktop's thread too, very bad things could happen. // but since we are called from the Desktop's thread too, very bad things
// Find some way to call this method only within ServerWindow's thread (messaging ?) // could happen.
// Find some way to call this method only within ServerWindow's thread
// (messaging ?)
status_t status; status_t status;
do { do {
// TODO: The timeout is 3000000 usecs (3 seconds) on beos. status = acquire_sem_etc(fDirectWindowData->sem_ack, 1, B_TIMEOUT,
// Test, but I think half a second is enough. 500000);
status = acquire_sem_etc(fDirectWindowData->sem_ack, 1, B_TIMEOUT, 500000);
} while (status == B_INTERRUPTED); } while (status == B_INTERRUPTED);
if (status < B_OK) { if (status != B_OK) {
// The client application didn't release the semaphore // The client application didn't release the semaphore
// within the given timeout. Or something else went wrong. // within the given timeout. Or something else went wrong.
// Deleting this member should make it crash. // Deleting this member should make it crash.
@@ -3639,8 +3632,8 @@ ServerWindow::_SetCurrentView(View* view)
&& fWindow->InUpdate()) { && fWindow->InUpdate()) {
DrawingEngine* drawingEngine = fWindow->GetDrawingEngine(); DrawingEngine* drawingEngine = fWindow->GetDrawingEngine();
if (drawingEngine->LockParallelAccess()) { if (drawingEngine->LockParallelAccess()) {
fWindow->GetEffectiveDrawingRegion(fCurrentView,
fWindow->GetEffectiveDrawingRegion(fCurrentView, fCurrentDrawingRegion); fCurrentDrawingRegion);
fCurrentDrawingRegionValid = true; fCurrentDrawingRegionValid = true;
BRegion dirty(fCurrentDrawingRegion); BRegion dirty(fCurrentDrawingRegion);
@@ -3666,9 +3659,9 @@ ServerWindow::_UpdateDrawState(View* view)
// "offsets" passed below would need to be updated again // "offsets" passed below would need to be updated again
DrawingEngine* drawingEngine = fWindow->GetDrawingEngine(); DrawingEngine* drawingEngine = fWindow->GetDrawingEngine();
if (view && drawingEngine) { if (view && drawingEngine) {
BPoint p(0, 0); BPoint leftTop(0, 0);
view->ConvertToScreenForDrawing(&p); view->ConvertToScreenForDrawing(&leftTop);
drawingEngine->SetDrawState(view->CurrentState(), p.x, p.y); drawingEngine->SetDrawState(view->CurrentState(), leftTop.x, leftTop.y);
} }
} }
@@ -3678,8 +3671,7 @@ ServerWindow::_UpdateCurrentDrawingRegion()
{ {
if (!fCurrentDrawingRegionValid if (!fCurrentDrawingRegionValid
|| fWindow->DrawingRegionChanged(fCurrentView)) { || fWindow->DrawingRegionChanged(fCurrentView)) {
fWindow->GetEffectiveDrawingRegion(fCurrentView, fWindow->GetEffectiveDrawingRegion(fCurrentView, fCurrentDrawingRegion);
fCurrentDrawingRegion);
fCurrentDrawingRegionValid = true; fCurrentDrawingRegionValid = true;
} }
} }
@@ -3720,18 +3712,16 @@ ServerWindow::_DirectWindowSetFullScreen(bool enable)
{ {
if (enable) { if (enable) {
fDesktop->HWInterface()->SetCursorVisible(false); fDesktop->HWInterface()->SetCursorVisible(false);
fDirectWindowData->old_window_frame = fWindow->Frame(); fDirectWindowData->old_window_frame = fWindow->Frame();
BRect screenFrame = BRect screenFrame =
fDesktop->ActiveScreen()->Frame(); fDesktop->ActiveScreen()->Frame();
fDirectWindowFeel = fWindow->Feel(); fDirectWindowFeel = fWindow->Feel();
fDesktop->MoveWindowBy(fWindow, fDesktop->MoveWindowBy(fWindow, -fWindow->Frame().left,
- fWindow->Frame().left, -fWindow->Frame().top);
- fWindow->Frame().top);
fDesktop->ResizeWindowBy(fWindow, fDesktop->ResizeWindowBy(fWindow,
screenFrame.Width() - fWindow->Frame().Width(), screenFrame.Width() - fWindow->Frame().Width(),
screenFrame.Height() screenFrame.Height() - fWindow->Frame().Height());
- fWindow->Frame().Height());
} else { } else {
const BRect &oldFrame = fDirectWindowData->old_window_frame; const BRect &oldFrame = fDirectWindowData->old_window_frame;
fDesktop->MoveWindowBy(fWindow, fDesktop->MoveWindowBy(fWindow,
@@ -3740,8 +3730,8 @@ ServerWindow::_DirectWindowSetFullScreen(bool enable)
fDesktop->ResizeWindowBy(fWindow, fDesktop->ResizeWindowBy(fWindow,
oldFrame.Width() - fWindow->Frame().Width(), oldFrame.Width() - fWindow->Frame().Width(),
oldFrame.Height() - fWindow->Frame().Height()); oldFrame.Height() - fWindow->Frame().Height());
fDesktop->HWInterface()->SetCursorVisible(true); fDesktop->HWInterface()->SetCursorVisible(true);
} }
fDesktop->SetWindowFeel(fWindow, fDesktop->SetWindowFeel(fWindow,
@@ -3750,7 +3740,7 @@ ServerWindow::_DirectWindowSetFullScreen(bool enable)
status_t status_t
ServerWindow::PictureToRegion(ServerPicture *picture, BRegion &region, ServerWindow::PictureToRegion(ServerPicture* picture, BRegion& region,
bool inverse, BPoint where) bool inverse, BPoint where)
{ {
fprintf(stderr, "ServerWindow::PictureToRegion() not implemented\n"); fprintf(stderr, "ServerWindow::PictureToRegion() not implemented\n");
+9 -8
View File
@@ -1,5 +1,5 @@
/* /*
* Copyright 2001-2008, Haiku. * Copyright 2001-2009, Haiku.
* Distributed under the terms of the MIT License. * Distributed under the terms of the MIT License.
* *
* Authors: * Authors:
@@ -61,8 +61,6 @@ public:
::EventTarget& EventTarget() { return fEventTarget; } ::EventTarget& EventTarget() { return fEventTarget; }
void ReplaceDecorator();
// methods for sending various messages to client. // methods for sending various messages to client.
void NotifyQuitRequested(); void NotifyQuitRequested();
void NotifyMinimize(bool minimize); void NotifyMinimize(bool minimize);
@@ -105,7 +103,8 @@ public:
void ResyncDrawState(); void ResyncDrawState();
// TODO: Change this // TODO: Change this
inline void UpdateCurrentDrawingRegion() { _UpdateCurrentDrawingRegion(); }; inline void UpdateCurrentDrawingRegion()
{ _UpdateCurrentDrawingRegion(); };
private: private:
View* _CreateView(BPrivate::LinkReceiver &link, View* _CreateView(BPrivate::LinkReceiver &link,
@@ -115,7 +114,8 @@ private:
void _Hide(); void _Hide();
// message handling methods. // message handling methods.
void _DispatchMessage(int32 code, BPrivate::LinkReceiver &link); void _DispatchMessage(int32 code,
BPrivate::LinkReceiver &link);
void _DispatchViewMessage(int32 code, void _DispatchViewMessage(int32 code,
BPrivate::LinkReceiver &link); BPrivate::LinkReceiver &link);
void _DispatchViewDrawingMessage(int32 code, void _DispatchViewDrawingMessage(int32 code,
@@ -130,12 +130,13 @@ private:
void _SetCurrentView(View* view); void _SetCurrentView(View* view);
void _UpdateDrawState(View* view); void _UpdateDrawState(View* view);
public:
void _UpdateCurrentDrawingRegion(); void _UpdateCurrentDrawingRegion();
private:
bool _MessageNeedsAllWindowsLocked(uint32 code) const; bool _MessageNeedsAllWindowsLocked(
uint32 code) const;
void _DirectWindowSetFullScreen(bool set); void _DirectWindowSetFullScreen(bool set);
// TODO: Move me elsewhere // TODO: Move me elsewhere
status_t PictureToRegion(ServerPicture *picture, status_t PictureToRegion(ServerPicture *picture,
BRegion& region, bool inverse, BRegion& region, bool inverse,