Resolved a TODO in BBitmap: now the bitmap area is cloned when needed: i.e. when Bits() or ImportBits() is called. Works fine, but I'd feel better if someone reviewed

git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@16014 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Stefano Ceccherini
2006-01-21 09:22:15 +00:00
parent a91b2ce415
commit 3276412ef2
+28 -17
View File
@@ -819,6 +819,7 @@ BBitmap::BBitmap(BMessage *data)
InitObject(bounds, cspace, flags, rowBytes, B_MAIN_SCREEN_ID); InitObject(bounds, cspace, flags, rowBytes, B_MAIN_SCREEN_ID);
if (data->HasData("_data", B_RAW_TYPE) && InitCheck() == B_OK) { if (data->HasData("_data", B_RAW_TYPE) && InitCheck() == B_OK) {
AssertPtr();
ssize_t size = 0; ssize_t size = 0;
const void *buffer; const void *buffer;
if (data->FindData("_data", B_RAW_TYPE, &buffer, &size) == B_OK) if (data->FindData("_data", B_RAW_TYPE, &buffer, &size) == B_OK)
@@ -880,7 +881,7 @@ BBitmap::Archive(BMessage *data, bool deep) const
// true and it does save all formats as B_RAW_TYPE and it does save // true and it does save all formats as B_RAW_TYPE and it does save
// the data even if B_BITMAP_ACCEPTS_VIEWS is set (as opposed to // the data even if B_BITMAP_ACCEPTS_VIEWS is set (as opposed to
// the BeBook) // the BeBook)
const_cast<BBitmap *>(this)->AssertPtr();
data->AddData("_data", B_RAW_TYPE, fBasePtr, fSize); data->AddData("_data", B_RAW_TYPE, fBasePtr, fSize);
} }
@@ -942,6 +943,7 @@ BBitmap::Area() const
void * void *
BBitmap::Bits() const BBitmap::Bits() const
{ {
const_cast<BBitmap *>(this)->AssertPtr();
return fBasePtr; return fBasePtr;
} }
@@ -1821,6 +1823,8 @@ status_t
BBitmap::ImportBits(const void *data, int32 length, int32 bpr, int32 offset, BBitmap::ImportBits(const void *data, int32 length, int32 bpr, int32 offset,
color_space colorSpace) color_space colorSpace)
{ {
AssertPtr();
status_t error = (InitCheck() == B_OK ? B_OK : B_NO_INIT); status_t error = (InitCheck() == B_OK ? B_OK : B_NO_INIT);
// check params // check params
if (error == B_OK && (data == NULL || offset > fSize || length < 0)) if (error == B_OK && (data == NULL || offset > fSize || length < 0))
@@ -2255,43 +2259,36 @@ BBitmap::InitObject(BRect bounds, color_space colorSpace, uint32 flags,
// Get token // Get token
link.Read<int32>(&fServerToken); link.Read<int32>(&fServerToken);
area_id area;
int32 areaOffset; int32 areaOffset;
link.Read<area_id>(&area); link.Read<area_id>(&fOrigArea);
link.Read<int32>(&areaOffset); link.Read<int32>(&areaOffset);
// Get the area in which the data resides // TODO: We save the area offset into "fArea" because
// TODO: the actual cloning doesn't have to happen before someone calls Bits() // we need it into AssertPtr(), and we can't add any member
// that would make bitmap creation a lot cheaper and faster... // to BBitmap due to binary compatibility
fArea = clone_area("shared bitmap area", fArea = (area_id)areaOffset;
(void**)&fBasePtr,
B_ANY_ADDRESS,
B_READ_AREA | B_WRITE_AREA,
area);
if (fArea >= B_OK) {
// Jump to the location in the area
fBasePtr = (int8*)fBasePtr + areaOffset;
if (fOrigArea >= B_OK) {
fSize = size; fSize = size;
fColorSpace = colorSpace; fColorSpace = colorSpace;
fBounds = bounds; fBounds = bounds;
fBytesPerRow = bytesPerRow; fBytesPerRow = bytesPerRow;
fFlags = flags; fFlags = flags;
} else } else
error = fArea; error = fOrigArea;
} }
if (error < B_OK) { if (error < B_OK) {
fBasePtr = NULL; fBasePtr = NULL;
fServerToken = -1; fServerToken = -1;
fArea = -1; fArea = -1;
fOrigArea = -1;
// NOTE: why not "0" in case of error? // NOTE: why not "0" in case of error?
fFlags = flags; fFlags = flags;
} }
} }
fWindow = NULL; fWindow = NULL;
fToken = -1; fToken = -1;
fOrigArea = -1;
} }
fInitError = error; fInitError = error;
@@ -2342,6 +2339,20 @@ BBitmap::CleanUp()
void void
BBitmap::AssertPtr() BBitmap::AssertPtr()
{ {
// TODO: what's this supposed to do? if (fBasePtr == NULL && InitCheck() == B_OK) {
// Offset was saved into "fArea" as we can't add
// any member variable due to Binary compatibility
int32 offset = (int32)fArea;
// Get the area in which the data resides
fArea = clone_area("shared bitmap area", (void **)&fBasePtr, B_ANY_ADDRESS,
B_READ_AREA | B_WRITE_AREA, fOrigArea);
if (fArea >= B_OK) {
// Jump to the location in the area
fBasePtr = (int8 *)fBasePtr + offset;
} else
fBasePtr = NULL;
}
} }