LayerData::prevState is now called fPreviousState and is now private. Added new method

PopState() to make this possible.
When a new layer is created, the font state of the desktop will now be set: this fixes
a bug I introduced when separating the font manager's default font and the desktop's
default font.
The scaling stuff looks pretty broken to me.


git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@14675 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Axel Dörfler
2005-11-04 09:52:56 +00:00
parent 7490bd32f1
commit 5abd5613d6
4 changed files with 82 additions and 79 deletions
+17 -30
View File
@@ -1,34 +1,16 @@
//------------------------------------------------------------------------------ /*
// Copyright (c) 2001-2005, Haiku, Inc. * Copyright 2001-2005, Haiku.
// * Distributed under the terms of the MIT License.
// Permission is hereby granted, free of charge, to any person obtaining a *
// copy of this software and associated documentation files (the "Software"), * Authors:
// to deal in the Software without restriction, including without limitation * DarkWyrm <[email protected]>
// the rights to use, copy, modify, merge, publish, distribute, sublicense, * Adi Oanca <[email protected]>
// and/or sell copies of the Software, and to permit persons to whom the * Stephan Aßmus <[email protected]>
// Software is furnished to do so, subject to the following conditions: */
//
// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
// DEALINGS IN THE SOFTWARE.
//
// File Name: LayerData.h
// Author: DarkWyrm <[email protected]>
// Adi Oanca <[email protected]>
// Stephan Aßmus <[email protected]>
// Description: Data classes for working with BView states and draw parameters
//
//------------------------------------------------------------------------------
#ifndef LAYER_DATA_H_ #ifndef LAYER_DATA_H_
#define LAYER_DATA_H_ #define LAYER_DATA_H_
#include <GraphicsDefs.h> #include <GraphicsDefs.h>
#include <InterfaceDefs.h> #include <InterfaceDefs.h>
#include <Point.h> #include <Point.h>
@@ -40,11 +22,13 @@
#include "PatternHandler.h" #include "PatternHandler.h"
class BRegion; class BRegion;
namespace BPrivate { namespace BPrivate {
class LinkReceiver; class LinkReceiver;
class LinkSender; class LinkSender;
}; };
class DrawData { class DrawData {
public: public:
DrawData(); DrawData();
@@ -199,9 +183,12 @@ class LayerData : public DrawData {
void ReadFromLink(BPrivate::LinkReceiver& link); void ReadFromLink(BPrivate::LinkReceiver& link);
void WriteToLink(BPrivate::LinkSender& link) const; void WriteToLink(BPrivate::LinkSender& link) const;
public: LayerData* PreviousState() const { return fPreviousState; }
LayerData* PopState();
private:
// used for the state stack // used for the state stack
LayerData* prevState; LayerData* fPreviousState;
}; };
// inline implementations // inline implementations
+16 -17
View File
@@ -61,8 +61,9 @@
# define RBTRACE(x) ; # define RBTRACE(x) ;
#endif #endif
Layer::Layer(BRect frame, const char* name, int32 token, Layer::Layer(BRect frame, const char* name, int32 token,
uint32 resize, uint32 flags, DisplayDriver* driver) uint32 resize, uint32 flags, DisplayDriver* driver)
: :
fFrame(frame), // in parent coordinates fFrame(frame), // in parent coordinates
// fBoundsLeftTop(0.0, 0.0), // fBoundsLeftTop(0.0, 0.0),
@@ -105,7 +106,7 @@ Layer::Layer(BRect frame, const char* name, int32 token,
fAdFlags(0), fAdFlags(0),
fDriver(driver), fDriver(driver),
fLayerData(new LayerData()), fLayerData(new LayerData),
fRootLayer(NULL), fRootLayer(NULL),
@@ -140,7 +141,7 @@ CRITICAL(helper);
STRACE(("Layer(%s) successfuly created\n", Name())); STRACE(("Layer(%s) successfuly created\n", Name()));
} }
//! Destructor frees all allocated heap space
Layer::~Layer() Layer::~Layer()
{ {
delete fLayerData; delete fLayerData;
@@ -1019,16 +1020,12 @@ Layer::PushState()
void void
Layer::PopState() Layer::PopState()
{ {
if (fLayerData->prevState == NULL) { if (fLayerData->PreviousState() == NULL) {
fprintf(stderr, "WARNING: User called BView(%s)::PopState(), but there is NO state on stack!\n", Name()); fprintf(stderr, "WARNING: User called BView(%s)::PopState(), but there is NO state on stack!\n", Name());
return; return;
} }
LayerData *data = fLayerData; fLayerData = fLayerData->PopState();
fLayerData = fLayerData->prevState;
data->prevState = NULL;
delete data;
fLayerData->SetSubPixelPrecise(fFlags & B_SUBPIXEL_PRECISE); fLayerData->SetSubPixelPrecise(fFlags & B_SUBPIXEL_PRECISE);
} }
@@ -1200,17 +1197,17 @@ Layer::Activated(bool active)
// Empty // Empty
} }
// BoundsOrigin
BPoint BPoint
Layer::BoundsOrigin() const Layer::BoundsOrigin() const
{ {
BPoint origin(0,0); BPoint origin(0,0);
float scale = Scale(); float scale = Scale();
LayerData *ld = fLayerData; LayerData* layerData = fLayerData;
do { do {
origin += ld->Origin(); origin += layerData->Origin();
} while ((ld = ld->prevState)); } while ((layerData = layerData->PreviousState()) != NULL);
origin.x *= scale; origin.x *= scale;
origin.y *= scale; origin.y *= scale;
@@ -1218,19 +1215,21 @@ Layer::BoundsOrigin() const
return origin; return origin;
} }
float float
Layer::Scale() const Layer::Scale() const
{ {
float scale = 1.0f; float scale = 1.0f;
LayerData *ld = fLayerData; LayerData* layerData = fLayerData;
do { do {
scale *= ld->Scale(); scale *= layerData->Scale();
} while ((ld = ld->prevState)); } while ((layerData = layerData->PreviousState()) != NULL);
return scale; return scale;
} }
//! Converts the passed point to parent coordinates //! Converts the passed point to parent coordinates
BPoint BPoint
Layer::ConvertToParent(BPoint pt) Layer::ConvertToParent(BPoint pt)
@@ -2544,7 +2543,7 @@ Layer::_GetWantedRegion(BRegion &reg)
// reg.IntersectWith(&screenReg); // reg.IntersectWith(&screenReg);
reg.IntersectWith(stackData->ClippingRegion()); reg.IntersectWith(stackData->ClippingRegion());
} }
stackData = stackData->prevState; stackData = stackData->PreviousState();
} }
} }
+26 -15
View File
@@ -18,6 +18,7 @@
#include "LinkReceiver.h" #include "LinkReceiver.h"
#include "LinkSender.h" #include "LinkSender.h"
#include "DesktopSettings.h"
#include "LayerData.h" #include "LayerData.h"
@@ -322,44 +323,42 @@ DrawData::SetMiterLimit(float limit)
fMiterLimit = limit; fMiterLimit = limit;
} }
//----------------------------LayerData----------------------
// #pragmamark -
// constructpr // #pragma mark -
LayerData::LayerData() LayerData::LayerData()
: DrawData(), : DrawData(),
prevState(NULL) fPreviousState(NULL)
{ {
} }
// LayerData
LayerData::LayerData(const LayerData& data) LayerData::LayerData(const LayerData& data)
: DrawData() : DrawData(data),
fPreviousState(data.fPreviousState)
{ {
fClippingRegion = NULL;
*this = data;
} }
// LayerData
LayerData::LayerData(LayerData* data) LayerData::LayerData(LayerData* data)
: DrawData(data), : DrawData(data),
prevState(data) fPreviousState(data)
{ {
} }
// destructor
LayerData::~LayerData() LayerData::~LayerData()
{ {
delete prevState; delete fPreviousState;
} }
// operator=
LayerData& LayerData&
LayerData::operator=(const LayerData& from) LayerData::operator=(const LayerData& from)
{ {
DrawData::operator=(from); DrawData::operator=(from);
fPreviousState = from.PreviousState();
prevState = from.prevState;
return *this; return *this;
} }
@@ -539,3 +538,15 @@ LayerData::WriteToLink(BPrivate::LinkSender& link) const
} }
} }
LayerData*
LayerData::PopState()
{
LayerData* previous = PreviousState();
fPreviousState = NULL;
delete this;
return previous;
}
+19 -13
View File
@@ -446,7 +446,7 @@ ServerWindow::SetLayerState(Layer *layer, BPrivate::LinkReceiver &link)
} }
inline Layer* Layer*
ServerWindow::CreateLayerTree(BPrivate::LinkReceiver &link, Layer **_parent) ServerWindow::CreateLayerTree(BPrivate::LinkReceiver &link, Layer **_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.
@@ -481,13 +481,16 @@ ServerWindow::CreateLayerTree(BPrivate::LinkReceiver &link, Layer **_parent)
if (link.Code() == AS_LAYER_CREATE_ROOT if (link.Code() == AS_LAYER_CREATE_ROOT
&& (fWinBorder->WindowFlags() & kWorkspacesWindowFlag) != 0) { && (fWinBorder->WindowFlags() & kWorkspacesWindowFlag) != 0) {
// this is a workspaces window! // this is a workspaces window!
newLayer = new WorkspacesLayer(frame, name, token, resizeMask, newLayer = new (nothrow) WorkspacesLayer(frame, name, token, resizeMask,
flags, fWinBorder->GetDisplayDriver()); flags, fWinBorder->GetDisplayDriver());
} else { } else {
newLayer = new Layer(frame, name, token, resizeMask, newLayer = new (nothrow) Layer(frame, name, token, resizeMask, flags,
flags, fDesktop->GetDisplayDriver()); fWinBorder->GetDisplayDriver());
} }
if (newLayer == NULL)
return NULL;
free(name); free(name);
// there is no way of setting this, other than manually :-) // there is no way of setting this, other than manually :-)
@@ -497,6 +500,11 @@ ServerWindow::CreateLayerTree(BPrivate::LinkReceiver &link, Layer **_parent)
newLayer->fEventOptions = eventOptions; newLayer->fEventOptions = eventOptions;
newLayer->fOwner = fWinBorder; newLayer->fOwner = fWinBorder;
DesktopSettings settings(fDesktop);
ServerFont font;
settings.GetDefaultPlainFont(font);
newLayer->fLayerData->SetFont(font);
// TODO: rework the clipping stuff to remove RootLayer dependency and then // TODO: rework the clipping stuff to remove RootLayer dependency and then
// remove this hack: // remove this hack:
if (fWinBorder->IsOffscreenWindow()) { if (fWinBorder->IsOffscreenWindow()) {
@@ -920,33 +928,31 @@ ServerWindow::_DispatchMessage(int32 code, BPrivate::LinkReceiver &link)
case AS_LAYER_GET_SCALE: case AS_LAYER_GET_SCALE:
{ {
DTRACE(("ServerWindow %s: Message AS_LAYER_GET_SCALE: Layer: %s\n", Title(), fCurrentLayer->Name())); DTRACE(("ServerWindow %s: Message AS_LAYER_GET_SCALE: Layer: %s\n", Title(), fCurrentLayer->Name()));
LayerData *ld = fCurrentLayer->fLayerData; LayerData* layerData = fCurrentLayer->fLayerData;
// TODO: And here, we're taking that into account, but not above // TODO: And here, we're taking that into account, but not above
// -> refactor put scale into Layer, or better yet, when the // -> refactor put scale into Layer, or better yet, when the
// state stack is within Layer, PushState() should multiply // state stack is within Layer, PushState() should multiply
// by the previous last states scale. Would fix the problem above too. // by the previous last states scale. Would fix the problem above too.
float scale = ld->Scale(); float scale = layerData->Scale();
while ((ld = ld->prevState)) while ((layerData = layerData->PreviousState()) != NULL)
scale *= ld->Scale(); scale *= layerData->Scale();
fLink.StartMessage(SERVER_TRUE); fLink.StartMessage(SERVER_TRUE);
fLink.Attach<float>(scale); fLink.Attach<float>(scale);
fLink.Flush(); fLink.Flush();
break; break;
} }
case AS_LAYER_SET_PEN_LOC: case AS_LAYER_SET_PEN_LOC:
{ {
DTRACE(("ServerWindow %s: Message AS_LAYER_SET_PEN_LOC: Layer: %s\n", Title(), fCurrentLayer->Name())); DTRACE(("ServerWindow %s: Message AS_LAYER_SET_PEN_LOC: Layer: %s\n", Title(), fCurrentLayer->Name()));
float x, y; float x, y;
link.Read<float>(&x); link.Read<float>(&x);
link.Read<float>(&y); link.Read<float>(&y);
fCurrentLayer->fLayerData->SetPenLocation(BPoint(x, y)); fCurrentLayer->fLayerData->SetPenLocation(BPoint(x, y));
break; break;
} }
case AS_LAYER_GET_PEN_LOC: case AS_LAYER_GET_PEN_LOC:
@@ -2382,7 +2388,7 @@ ServerWindow::MakeWinBorder(BRect frame, const char* name,
{ {
// The non-offscreen ServerWindow uses the DisplayDriver instance from the desktop. // The non-offscreen ServerWindow uses the DisplayDriver instance from the desktop.
return new(nothrow) WinBorder(frame, name, look, feel, flags, return new(nothrow) WinBorder(frame, name, look, feel, flags,
workspace, this, fDesktop->GetDisplayDriver()); workspace, this, fDesktop->GetDisplayDriver());
} }