[haiku-commits] BRANCH looncraz-github.setviewuicolor [a23ee539ac57] src/kits/interface headers/private/interface headers/os/interface

  • From: looncraz-github.setviewuicolor <community@xxxxxxxxxxxx>
  • To: haiku-commits@xxxxxxxxxxxxx
  • Date: Thu, 15 Oct 2015 01:02:09 +0200 (CEST)

added 1 changeset to branch 'refs/remotes/looncraz-github/setviewuicolor'
old head: 7fdb5256fe14de80642802b9e0478a9002a510ea
new head: a23ee539ac57a8cfcc304b994ba64ca966abc6e0
overview: https://github.com/looncraz/haiku/compare/7fdb5256fe14...a23ee539ac57

----------------------------------------------------------------------------

a23ee539ac57: BColorSet - Shared Data

BColorSet can no, selectively, share its reference-counted data. Its data
implementation is also more hidden to make future changes more transparent.

This means that BViews creating a BColorSet from a B_COLORS_UPDATED message
will simply be sharing data with the window and all other BViews.

There are some incidental style cleanups as well.

[ looncraz <looncraz@xxxxxxxxxxxx> ]

----------------------------------------------------------------------------

Commit: a23ee539ac57a8cfcc304b994ba64ca966abc6e0
Author: looncraz <looncraz@xxxxxxxxxxxx>
Date: Wed Oct 14 23:58:07 2015 UTC

----------------------------------------------------------------------------

4 files changed, 228 insertions(+), 43 deletions(-)
headers/os/interface/ColorSet.h | 12 +-
headers/private/interface/ColorSetPrivate.h | 31 +++-
src/kits/interface/ColorSet.cpp | 223 ++++++++++++++++++++----
src/kits/interface/Window.cpp | 5 +

----------------------------------------------------------------------------

diff --git a/headers/os/interface/ColorSet.h b/headers/os/interface/ColorSet.h
index 9b338c4..b8e9811 100644
--- a/headers/os/interface/ColorSet.h
+++ b/headers/os/interface/ColorSet.h
@@ -1,5 +1,5 @@
/*
- * Copyright 2001-2010 Haiku, Inc. All rights reserved.
+ * Copyright 2015 Haiku, Inc. All rights reserved.
* Distributed under the terms of the MIT License.
*/
#ifndef _B_COLOR_SET
@@ -8,10 +8,10 @@

#include <Archivable.h>
#include <InterfaceDefs.h>
-#include <ObjectList.h>


namespace BPrivate {
+ class BColorSetData;
class BColorSetPrivate;
};

@@ -35,6 +35,8 @@ public:
static const BColorSet* DefaultColorSet();
static const BColorSet* CurrentColorSet();

+ status_t InitCheck() const;
+
// Adding and removing colors.
// Will fail if key currently in use
status_t Add(const BColorPair*
pair);
@@ -79,9 +81,13 @@ private:

status_t _Add(BColorPair* pair);
void _Init(BMessage* from);
+ status_t _InitCopyOnWrite();

- typedef BObjectList<BColorPair> ColorList;
+ typedef BPrivate::BColorSetData* ColorList;
ColorList fColors;
+ bool fSharedData;
+
+ status_t fInitStatus;
};


diff --git a/headers/private/interface/ColorSetPrivate.h
b/headers/private/interface/ColorSetPrivate.h
index fac1a4f..674154e 100644
--- a/headers/private/interface/ColorSetPrivate.h
+++ b/headers/private/interface/ColorSetPrivate.h
@@ -1,27 +1,42 @@
+/*
+ * Copyright 2015, Haiku.
+ * Distributed under the terms of the MIT License.
+*/
#ifndef _B_COLORSET_PRIVATE_H_
#define _B_COLORSET_PRIVATE_H_


#include <ColorSet.h>
+#include <ObjectList.h>
+#include <Referenceable.h>


namespace BPrivate {


+//! Shared data for BColorSet
+class BColorSetData : public BReferenceable, public BObjectList<BColorPair> {
+public:
+ BColorSetData();
+
BColorSetData(const BColorSetData& other);
+ virtual ~BColorSetData();
+
+};
+
+
+//! Provide direct read-only access to private BColorSet data
class BColorSetPrivate {
public:
static const BObjectList<BColorPair>& GetList(const BColorSet&
colorSet);
-};

+ static bool AcquireSharedPointer(BColorSet*
pointer,
+
BMessage* message);
+
+ static void ReleaseSharedPointer(BMessage*
message);
+};

-const BObjectList<BColorPair>&
-BColorSetPrivate::GetList(const BColorSet& colorSet)
-{
- return colorSet.fColors;
-}

-
-};
+}; // end namespace BPrivate


#endif //_B_COLORSET_PRIVATE_H_
diff --git a/src/kits/interface/ColorSet.cpp b/src/kits/interface/ColorSet.cpp
index 4a640d8..789e453 100644
--- a/src/kits/interface/ColorSet.cpp
+++ b/src/kits/interface/ColorSet.cpp
@@ -12,22 +12,31 @@
#include <ColorSet.h>
#include <Locker.h>

+#include <ColorSetPrivate.h>
#include <DefaultColors.h>
#include <ServerReadOnlyMemory.h>


+// helpful macros
+#define CHECK_READ_STATUS(X) if (InitCheck() != B_OK) return X ;
+#define CHECK_WRITE_STATUS(X) if (_InitCopyOnWrite() != B_OK) return X ;
+
+
// not extern'd
static BLocker be_global_colorset_lock;
static BColorSet* be_default_colorset = NULL;
static BColorSet* be_current_colorset = NULL;


+static const char* kColorSetPointerName = "_be_colorset_pointer_";
static const rgb_color kFailureColor = make_color(0,0,0,0);


BColorSet::BColorSet()
:
- fColors(5, true)
+ fColors(NULL),
+ fSharedData(false),
+ fInitStatus(B_OK)
{
_Init(NULL);
}
@@ -35,15 +44,22 @@ BColorSet::BColorSet()

BColorSet::BColorSet(const BColorSet& other)
:
- fColors(other.fColors)
+ fColors(other.fColors),
+ fSharedData(true),
+ fInitStatus(B_OK)
{
- _Init(NULL);
+ if (fColors != NULL)
+ fColors->AcquireReference();
+ else
+ fInitStatus = B_BAD_VALUE;
}


BColorSet::BColorSet(BMessage* from)
:
- fColors(5, true)
+ fColors(NULL),
+ fSharedData(false),
+ fInitStatus(B_OK)
{
_Init(from);
}
@@ -51,10 +67,15 @@ BColorSet::BColorSet(BMessage* from)

BColorSet::~BColorSet()
{
+ BAutolock _(be_global_colorset_lock);
if (this == be_current_colorset)
be_current_colorset = NULL;
else if (this == be_default_colorset)
be_default_colorset = NULL;
+
+ // fColors will delete itself
+ if (fColors != NULL)
+ fColors->ReleaseReference();
}


@@ -64,6 +85,8 @@ BColorSet::~BColorSet()
status_t
BColorSet::Archive(BMessage* into, bool deep) const
{
+ CHECK_READ_STATUS(fInitStatus);
+
if (into == NULL)
return B_BAD_VALUE;

@@ -113,10 +136,10 @@ BColorSet::DefaultColorSet()
return NULL;
}

- for (int32 which = 1; which < kColorWhichLastContinuous + 1; ++which)
- be_default_colorset->Add(which,
- BPrivate::kDefaultColors[
+ for (int32 which = 1; which < kColorWhichLastContinuous + 1; ++which) {
+ be_default_colorset->Add(which, BPrivate::kDefaultColors[
color_which_to_index((color_which)which)]);
+ }

be_default_colorset->Add((int32)B_SUCCESS_COLOR,

BPrivate::kDefaultColors[color_which_to_index(B_SUCCESS_COLOR)]);
@@ -158,12 +181,21 @@ BColorSet::CurrentColorSet()
}


+status_t
+BColorSet::InitCheck() const
+{
+ return fInitStatus;
+}
+
+
// #pragma mark Add


status_t
BColorSet::Add(const BColorPair* pair)
{
+ CHECK_WRITE_STATUS(fInitStatus);
+
if (pair == NULL)
return B_BAD_VALUE;

@@ -177,8 +209,9 @@ BColorSet::Add(const BColorPair* pair)
status_t
BColorSet::Add(int32 key, rgb_color color)
{
- BColorPair* pair = Find(key);
+ CHECK_WRITE_STATUS(fInitStatus);

+ BColorPair* pair = Find(key);
if (pair != NULL)
return B_BAD_INDEX;

@@ -196,6 +229,8 @@ BColorSet::Add(color_which which, rgb_color color)
status_t
BColorSet::Add(const BColorSet& colorSet)
{
+ CHECK_WRITE_STATUS(fInitStatus);
+
// Technically not an error
if (colorSet.CountColors() == 0)
return B_OK;
@@ -216,11 +251,12 @@ BColorSet::Add(const BColorSet& colorSet)
status_t
BColorSet::Set(const BColorPair* pair)
{
+ CHECK_WRITE_STATUS(fInitStatus);
+
if (pair == NULL)
return B_BAD_VALUE;

BColorPair* set = Find(pair->key);
-
if (set == NULL)
return Add(pair);

@@ -232,8 +268,9 @@ BColorSet::Set(const BColorPair* pair)
status_t
BColorSet::Set(int32 key, rgb_color color)
{
- BColorPair* pair = Find(key);
+ CHECK_WRITE_STATUS(fInitStatus);

+ BColorPair* pair = Find(key);
if (pair == NULL)
return Add(key, color);

@@ -253,6 +290,8 @@ BColorSet::Set(color_which which, rgb_color color)
status_t
BColorSet::Set(const BColorSet& colorSet)
{
+ CHECK_WRITE_STATUS(fInitStatus);
+
// Technically not an error
if (colorSet.CountColors() == 0)
return B_OK;
@@ -274,30 +313,34 @@ BColorSet::Set(const BColorSet& colorSet)
status_t
BColorSet::RemoveAt(int32 index)
{
+ CHECK_WRITE_STATUS(fInitStatus);
+
BColorPair* pair = ColorPairAt(index);

if (pair == NULL)
return B_BAD_INDEX;

- return fColors.RemoveItem(pair) ? B_OK : B_ERROR;
+ return fColors->RemoveItem(pair) ? B_OK : B_ERROR;
}


status_t
BColorSet::Remove(const BColorPair* pair)
{
+ CHECK_WRITE_STATUS(fInitStatus);
+
if (pair == NULL)
return B_BAD_VALUE;

// See if we are being handed our own pointer...
- if (fColors.RemoveItem(const_cast<BColorPair*>(pair)))
+ if (fColors->RemoveItem(const_cast<BColorPair*>(pair)))
return B_OK;

BColorPair* ours = Find(pair->key);
if (ours == NULL)
return B_BAD_INDEX;

- return fColors.RemoveItem(ours) ? B_OK : B_ERROR;
+ return fColors->RemoveItem(ours) ? B_OK : B_ERROR;
}


@@ -318,6 +361,8 @@ BColorSet::Remove(color_which which)
status_t
BColorSet::Remove(const BColorSet& colorSet)
{
+ CHECK_WRITE_STATUS(fInitStatus);
+
if (colorSet.CountColors() == 0)
return B_OK;

@@ -339,7 +384,8 @@ BColorSet::Remove(const BColorSet& colorSet)
void
BColorSet::MakeEmpty()
{
- fColors.MakeEmpty();
+ if (fColors != NULL)
+ fColors->MakeEmpty();
}


@@ -349,6 +395,8 @@ BColorSet::MakeEmpty()
rgb_color
BColorSet::ColorAt(int32 index) const
{
+ CHECK_READ_STATUS(kFailureColor);
+
const BColorPair* pair = ColorPairAt(index);

if (pair == NULL)
@@ -361,6 +409,8 @@ BColorSet::ColorAt(int32 index) const
int32
BColorSet::ColorKeyAt(int32 index) const
{
+ CHECK_READ_STATUS((int32)fInitStatus);
+
const BColorPair* pair = ColorPairAt(index);

if (pair == NULL)
@@ -373,24 +423,27 @@ BColorSet::ColorKeyAt(int32 index) const
const BColorPair*
BColorSet::ColorPairAt(int32 index) const
{
- return fColors.ItemAt(index);
+ CHECK_READ_STATUS(NULL);
+ return fColors->ItemAt(index);
}


BColorPair*
BColorSet::ColorPairAt(int32 index)
{
- return fColors.ItemAt(index);
+ CHECK_READ_STATUS(NULL);
+ return fColors->ItemAt(index);
}


const BColorPair*
BColorSet::Find(int32 key) const
{
- const BColorPair* pair;
+ CHECK_READ_STATUS(NULL);

+ const BColorPair* pair;
for (int32 index = 0; index < CountColors(); ++index) {
- pair = fColors.ItemAt(index);
+ pair = fColors->ItemAt(index);

if (pair->key == key)
return pair;
@@ -403,10 +456,11 @@ BColorSet::Find(int32 key) const
BColorPair*
BColorSet::Find(int32 key)
{
- BColorPair* pair;
+ CHECK_READ_STATUS(NULL);

+ BColorPair* pair;
for (int32 index = 0; index < CountColors(); ++index) {
- pair = fColors.ItemAt(index);
+ pair = fColors->ItemAt(index);

if (pair->key == key)
return pair;
@@ -443,7 +497,8 @@ BColorSet::HasKey(int32 key) const
int32
BColorSet::CountColors() const
{
- return fColors.CountItems();
+ CHECK_READ_STATUS(0);
+ return fColors->CountItems();
}


@@ -460,6 +515,9 @@ BColorSet::PrintToStream() const
printf("BColorSet: %li colors {\n", CountColors());
const BColorPair* pair;

+ if (fInitStatus != B_OK)
+ printf("\tINIT FAILURE: %li\n", fInitStatus);
+
for (int32 index = 0; index < CountColors(); ++index) {
pair = ColorPairAt(index);
printf("\t%-5li %-10li rgb_color(%3i, %3i, %3i, %3i)\n", index,
@@ -479,7 +537,7 @@ BColorSet::_Add(BColorPair* newPair)
if (newPair == NULL)
return B_NO_MEMORY;

- if (!fColors.AddItem(newPair)) {
+ if (!fColors->AddItem(newPair)) {
delete newPair;
return B_ERROR;
}
@@ -491,25 +549,34 @@ BColorSet::_Add(BColorPair* newPair)
void
BColorSet::_Init(BMessage* from)
{
- // Get default and current colorsets
- if (be_app != NULL) {
- if (be_default_colorset == NULL) {
- // TODO...
- }
+ if (from == NULL) {
+ if (fColors == NULL) {
+ fColors = new(std::nothrow) BPrivate::BColorSetData();
+ fSharedData = false;

- if (be_current_colorset == NULL) {
- // TODO...
+ if (fColors == NULL)
+ fInitStatus = B_NO_MEMORY;
}
- }
-
- if (from == NULL)
return;
+ }

int32 count;
int32 key;
rgb_color color;
int32 intColor;

+ if (from->FindPointer(kColorSetPointerName, (void**)&fColors) != B_OK) {
+ fColors = new(std::nothrow) BPrivate::BColorSetData();
+ if (fColors == NULL) {
+ fInitStatus = B_NO_MEMORY;
+ return;
+ }
+ } else {
+ fSharedData = true;
+ fColors->AcquireReference();
+ return;
+ }
+
if (from->FindInt32("_count", &count) == B_OK
&& count > 0) {

@@ -520,11 +587,103 @@ BColorSet::_Init(BMessage* from)
intColor = B_HOST_TO_BENDIAN_INT32(intColor);
color = *(rgb_color*)&intColor;
Add(key, color);
+
} else {
fprintf(stderr, "Error instantiating BColorSet
- bad message data!\n");
+ fprintf(stderr, "\tError %li at index: %li\n",
fInitStatus, index - 1);
from->PrintToStream();
break;
}
}
}
}
+
+
+status_t
+BColorSet::_InitCopyOnWrite()
+{
+ // If we can't read, we can't copy for writing...
+ CHECK_READ_STATUS(fInitStatus);
+
+ if (fSharedData) {
+ BPrivate::BColorSetData* newData = new(std::nothrow) BPrivate
+ ::BColorSetData(*fColors);
+
+ if (newData == NULL)
+ return B_NO_MEMORY;
+
+ fSharedData = false;
+ return B_OK;
+ }
+
+ return B_OK;
+}
+
+// #pragma mark BColorSetData
+
+namespace BPrivate {
+
+BColorSetData::BColorSetData()
+ :
+ BObjectList<BColorPair>(5, true)
+{
+}
+
+
+BColorSetData::BColorSetData(const BColorSetData& other)
+ :
+ BObjectList<BColorPair>(other)
+{
+}
+
+
+BColorSetData::~BColorSetData()
+{
+}
+
+
+// #pragma mark BColorSetPrivate
+
+
+const BObjectList<BColorPair>&
+BColorSetPrivate::GetList(const BColorSet& colorSet)
+{
+ return *colorSet.fColors;
+}
+
+
+bool
+BColorSetPrivate::AcquireSharedPointer(BColorSet* colorSet, BMessage* message)
+{
+ if (colorSet == NULL || message == NULL || colorSet->InitCheck() != B_OK
+ || colorSet->fColors == NULL)
+ return false;
+
+ BColorSetData* data = colorSet->fColors;
+
+ data->AcquireReference();
+ message->RemoveName(kColorSetPointerName);
+ if (message->AddPointer(kColorSetPointerName, data) != B_OK) {
+ data->ReleaseReference();
+ return false;
+ }
+
+ return true;
+}
+
+
+void
+BColorSetPrivate::ReleaseSharedPointer(BMessage* message)
+{
+ BColorSetData* pointer = NULL;
+ if (message != NULL && message->FindPointer(kColorSetPointerName,
+ (void**)&pointer) == B_OK
+ && pointer != NULL) {
+
+ pointer->ReleaseReference();
+ message->RemoveName(kColorSetPointerName);
+ }
+}
+
+
+}; // end namespace BPrivate
diff --git a/src/kits/interface/Window.cpp b/src/kits/interface/Window.cpp
index 3470562..618b09e 100644
--- a/src/kits/interface/Window.cpp
+++ b/src/kits/interface/Window.cpp
@@ -40,6 +40,7 @@
#include <AppServerLink.h>
#include <ApplicationPrivate.h>
#include <binary_compatibility/Interface.h>
+#include <ColorSetPrivate.h>
#include <DirectMessageTarget.h>
#include <input_globals.h>
#include <InputServerTypes.h>
@@ -1447,8 +1448,12 @@ FrameMoved(origin);
if (colorSet.CountColors() == 0)
break;

+ BPrivate::BColorSetPrivate
+ ::AcquireSharedPointer(&colorSet, message);
fTopView->_ColorsUpdated(message, colorSet);
target->MessageReceived(message);
+ BPrivate::BColorSetPrivate
+ ::ReleaseSharedPointer(message);
break;
}



Other related posts:

  • » [haiku-commits] BRANCH looncraz-github.setviewuicolor [a23ee539ac57] src/kits/interface headers/private/interface headers/os/interface - looncraz-github . setviewuicolor