Updated BMenuField and its custom BLayoutItems for layout-safe archiving. Added an _InitMenu(const BMessage*) method that inits the menu during unarchival.
git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@37778 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -35,6 +35,8 @@ public:
|
|||||||
static BArchivable* Instantiate(BMessage* archive);
|
static BArchivable* Instantiate(BMessage* archive);
|
||||||
virtual status_t Archive(BMessage* archive,
|
virtual status_t Archive(BMessage* archive,
|
||||||
bool deep = true) const;
|
bool deep = true) const;
|
||||||
|
virtual status_t AllArchived(BMessage* into) const;
|
||||||
|
virtual status_t AllUnarchived(const BMessage* from);
|
||||||
|
|
||||||
virtual void Draw(BRect update);
|
virtual void Draw(BRect update);
|
||||||
virtual void AttachedToWindow();
|
virtual void AttachedToWindow();
|
||||||
@@ -122,6 +124,7 @@ private:
|
|||||||
void _UpdateFrame();
|
void _UpdateFrame();
|
||||||
void _InitMenuBar(BMenu* menu,
|
void _InitMenuBar(BMenu* menu,
|
||||||
BRect frame, bool fixedSize);
|
BRect frame, bool fixedSize);
|
||||||
|
void _InitMenuBar(const BMessage* archive);
|
||||||
|
|
||||||
void _ValidateLayoutData();
|
void _ValidateLayoutData();
|
||||||
float _MenuBarOffset() const;
|
float _MenuBarOffset() const;
|
||||||
|
|||||||
@@ -23,6 +23,7 @@
|
|||||||
#include <Window.h>
|
#include <Window.h>
|
||||||
|
|
||||||
#include <binary_compatibility/Interface.h>
|
#include <binary_compatibility/Interface.h>
|
||||||
|
#include <binary_compatibility/Support.h>
|
||||||
|
|
||||||
|
|
||||||
//#define TRACE_MENU_FIELD
|
//#define TRACE_MENU_FIELD
|
||||||
@@ -40,9 +41,17 @@
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
namespace {
|
||||||
|
const char* const kFrameField = "BMenuField:layoutItem:frame";
|
||||||
|
const char* const kMenuBarItemField = "BMenuField:barItem";
|
||||||
|
const char* const kLabelItemField = "BMenuField:labelItem";
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
class BMenuField::LabelLayoutItem : public BAbstractLayoutItem {
|
class BMenuField::LabelLayoutItem : public BAbstractLayoutItem {
|
||||||
public:
|
public:
|
||||||
LabelLayoutItem(BMenuField* parent);
|
LabelLayoutItem(BMenuField* parent);
|
||||||
|
LabelLayoutItem(BMessage* archive);
|
||||||
|
|
||||||
virtual bool IsVisible();
|
virtual bool IsVisible();
|
||||||
virtual void SetVisible(bool visible);
|
virtual void SetVisible(bool visible);
|
||||||
@@ -50,6 +59,7 @@ public:
|
|||||||
virtual BRect Frame();
|
virtual BRect Frame();
|
||||||
virtual void SetFrame(BRect frame);
|
virtual void SetFrame(BRect frame);
|
||||||
|
|
||||||
|
void SetParent(BMenuField* parent);
|
||||||
virtual BView* View();
|
virtual BView* View();
|
||||||
|
|
||||||
virtual BSize BaseMinSize();
|
virtual BSize BaseMinSize();
|
||||||
@@ -57,6 +67,9 @@ public:
|
|||||||
virtual BSize BasePreferredSize();
|
virtual BSize BasePreferredSize();
|
||||||
virtual BAlignment BaseAlignment();
|
virtual BAlignment BaseAlignment();
|
||||||
|
|
||||||
|
virtual status_t Archive(BMessage* into, bool deep = true) const;
|
||||||
|
static BArchivable* Instantiate(BMessage* from);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
BMenuField* fParent;
|
BMenuField* fParent;
|
||||||
BRect fFrame;
|
BRect fFrame;
|
||||||
@@ -66,6 +79,7 @@ private:
|
|||||||
class BMenuField::MenuBarLayoutItem : public BAbstractLayoutItem {
|
class BMenuField::MenuBarLayoutItem : public BAbstractLayoutItem {
|
||||||
public:
|
public:
|
||||||
MenuBarLayoutItem(BMenuField* parent);
|
MenuBarLayoutItem(BMenuField* parent);
|
||||||
|
MenuBarLayoutItem(BMessage* from);
|
||||||
|
|
||||||
virtual bool IsVisible();
|
virtual bool IsVisible();
|
||||||
virtual void SetVisible(bool visible);
|
virtual void SetVisible(bool visible);
|
||||||
@@ -73,6 +87,7 @@ public:
|
|||||||
virtual BRect Frame();
|
virtual BRect Frame();
|
||||||
virtual void SetFrame(BRect frame);
|
virtual void SetFrame(BRect frame);
|
||||||
|
|
||||||
|
void SetParent(BMenuField* parent);
|
||||||
virtual BView* View();
|
virtual BView* View();
|
||||||
|
|
||||||
virtual BSize BaseMinSize();
|
virtual BSize BaseMinSize();
|
||||||
@@ -80,6 +95,9 @@ public:
|
|||||||
virtual BSize BasePreferredSize();
|
virtual BSize BasePreferredSize();
|
||||||
virtual BAlignment BaseAlignment();
|
virtual BAlignment BaseAlignment();
|
||||||
|
|
||||||
|
virtual status_t Archive(BMessage* into, bool deep = true) const;
|
||||||
|
static BArchivable* Instantiate(BMessage* from);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
BMenuField* fParent;
|
BMenuField* fParent;
|
||||||
BRect fFrame;
|
BRect fFrame;
|
||||||
@@ -176,38 +194,23 @@ BMenuField::BMenuField(const char* label, BMenu* menu, BMessage* message)
|
|||||||
|
|
||||||
BMenuField::BMenuField(BMessage* data)
|
BMenuField::BMenuField(BMessage* data)
|
||||||
:
|
:
|
||||||
BView(data)
|
BView(BUnarchiver::PrepareArchive(data))
|
||||||
{
|
{
|
||||||
|
BUnarchiver unarchiver(data);
|
||||||
const char* label = NULL;
|
const char* label = NULL;
|
||||||
data->FindString("_label", &label);
|
data->FindString("_label", &label);
|
||||||
|
|
||||||
InitObject(label);
|
InitObject(label);
|
||||||
|
|
||||||
fMenuBar = (BMenuBar*)FindView("_mc_mb_");
|
|
||||||
if (!fMenuBar)
|
|
||||||
_InitMenuBar(new BMenu(""), BRect(0, 0, 100, 15), false);
|
|
||||||
fMenu = fMenuBar->SubmenuAt(0);
|
|
||||||
|
|
||||||
InitObject2();
|
|
||||||
|
|
||||||
bool disable;
|
|
||||||
if (data->FindBool("_disable", &disable) == B_OK)
|
|
||||||
SetEnabled(!disable);
|
|
||||||
|
|
||||||
int32 align;
|
|
||||||
data->FindInt32("_align", &align);
|
|
||||||
SetAlignment((alignment)align);
|
|
||||||
|
|
||||||
data->FindFloat("_divide", &fDivider);
|
data->FindFloat("_divide", &fDivider);
|
||||||
|
|
||||||
bool fixed;
|
int32 align;
|
||||||
if (data->FindBool("be:fixeds", &fixed) == B_OK)
|
if (data->FindInt32("_align", &align) == B_OK)
|
||||||
fFixedSizeMB = fixed;
|
SetAlignment((alignment)align);
|
||||||
|
|
||||||
bool dmark = false;
|
if (!BUnarchiver::IsArchiveManaged(data))
|
||||||
data->FindBool("be:dmark", &dmark);
|
_InitMenuBar(data);
|
||||||
if (_BMCMenuBar_* menuBar = dynamic_cast<_BMCMenuBar_*>(fMenuBar))
|
unarchiver.Finish();
|
||||||
menuBar->TogglePopUpMarker(dmark);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -236,6 +239,7 @@ BMenuField::Instantiate(BMessage* data)
|
|||||||
status_t
|
status_t
|
||||||
BMenuField::Archive(BMessage* data, bool deep) const
|
BMenuField::Archive(BMessage* data, bool deep) const
|
||||||
{
|
{
|
||||||
|
BArchiver archiver(data);
|
||||||
status_t ret = BView::Archive(data, deep);
|
status_t ret = BView::Archive(data, deep);
|
||||||
|
|
||||||
if (ret == B_OK && Label())
|
if (ret == B_OK && Label())
|
||||||
@@ -258,7 +262,66 @@ BMenuField::Archive(BMessage* data, bool deep) const
|
|||||||
|
|
||||||
data->AddBool("be:dmark", dmark);
|
data->AddBool("be:dmark", dmark);
|
||||||
|
|
||||||
return ret;
|
return archiver.Finish(ret);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
BMenuField::AllArchived(BMessage* into) const
|
||||||
|
{
|
||||||
|
status_t err;
|
||||||
|
if ((err = BView::AllArchived(into)) != B_OK)
|
||||||
|
return err;
|
||||||
|
|
||||||
|
BArchiver archiver(into);
|
||||||
|
|
||||||
|
BArchivable* menuBarItem = fLayoutData->menu_bar_layout_item;
|
||||||
|
if (archiver.IsArchived(menuBarItem))
|
||||||
|
err = archiver.AddArchivable(kMenuBarItemField, menuBarItem);
|
||||||
|
|
||||||
|
if (err != B_OK)
|
||||||
|
return err;
|
||||||
|
|
||||||
|
BArchivable* labelBarItem = fLayoutData->label_layout_item;
|
||||||
|
if (archiver.IsArchived(labelBarItem))
|
||||||
|
err = archiver.AddArchivable(kLabelItemField, labelBarItem);
|
||||||
|
|
||||||
|
return err;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
BMenuField::AllUnarchived(const BMessage* from)
|
||||||
|
{
|
||||||
|
BUnarchiver unarchiver(from);
|
||||||
|
|
||||||
|
status_t err = B_OK;
|
||||||
|
if ((err = BView::AllUnarchived(from)) != B_OK)
|
||||||
|
return err;
|
||||||
|
|
||||||
|
_InitMenuBar(from);
|
||||||
|
|
||||||
|
if (unarchiver.IsInstantiated(kMenuBarItemField)) {
|
||||||
|
MenuBarLayoutItem*& menuItem = fLayoutData->menu_bar_layout_item;
|
||||||
|
err = unarchiver.FindObject(kMenuBarItemField,
|
||||||
|
BUnarchiver::B_DONT_ASSUME_OWNERSHIP, menuItem);
|
||||||
|
|
||||||
|
if (err == B_OK)
|
||||||
|
menuItem->SetParent(this);
|
||||||
|
else
|
||||||
|
return err;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (unarchiver.IsInstantiated(kLabelItemField)) {
|
||||||
|
LabelLayoutItem*& labelItem = fLayoutData->label_layout_item;
|
||||||
|
err = unarchiver.FindObject(kLabelItemField,
|
||||||
|
BUnarchiver::B_DONT_ASSUME_OWNERSHIP, labelItem);
|
||||||
|
|
||||||
|
if (err == B_OK)
|
||||||
|
labelItem->SetParent(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
return err;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -794,6 +857,22 @@ BMenuField::Perform(perform_code code, void* _data)
|
|||||||
BMenuField::DoLayout();
|
BMenuField::DoLayout();
|
||||||
return B_OK;
|
return B_OK;
|
||||||
}
|
}
|
||||||
|
case PERFORM_CODE_ALL_UNARCHIVED:
|
||||||
|
{
|
||||||
|
perform_data_all_unarchived* data
|
||||||
|
= (perform_data_all_unarchived*)_data;
|
||||||
|
|
||||||
|
data->return_value = BMenuField::AllUnarchived(data->archive);
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
|
case PERFORM_CODE_ALL_ARCHIVED:
|
||||||
|
{
|
||||||
|
perform_data_all_archived* data
|
||||||
|
= (perform_data_all_archived*)_data;
|
||||||
|
|
||||||
|
data->return_value = BMenuField::AllArchived(data->archive);
|
||||||
|
return B_OK;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return BView::Perform(code, _data);
|
return BView::Perform(code, _data);
|
||||||
@@ -1062,6 +1141,35 @@ BMenuField::_InitMenuBar(BMenu* menu, BRect frame, bool fixedSize)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void
|
||||||
|
BMenuField::_InitMenuBar(const BMessage* archive)
|
||||||
|
{
|
||||||
|
bool fixed;
|
||||||
|
if (archive->FindBool("be:fixeds", &fixed) == B_OK)
|
||||||
|
fFixedSizeMB = fixed;
|
||||||
|
|
||||||
|
fMenuBar = (BMenuBar*)FindView("_mc_mb_");
|
||||||
|
if (!fMenuBar) {
|
||||||
|
_InitMenuBar(new BMenu(""), BRect(0, 0, 100, 15), fFixedSizeMB);
|
||||||
|
InitObject2();
|
||||||
|
} else {
|
||||||
|
fMenuBar->AddFilter(new _BMCFilter_(this, B_MOUSE_DOWN));
|
||||||
|
// this is normally done in InitObject2()
|
||||||
|
}
|
||||||
|
|
||||||
|
fMenu = fMenuBar->SubmenuAt(0);
|
||||||
|
|
||||||
|
bool disable;
|
||||||
|
if (archive->FindBool("_disable", &disable) == B_OK)
|
||||||
|
SetEnabled(!disable);
|
||||||
|
|
||||||
|
bool dmark = false;
|
||||||
|
archive->FindBool("be:dmark", &dmark);
|
||||||
|
if (_BMCMenuBar_* menuBar = dynamic_cast<_BMCMenuBar_*>(fMenuBar))
|
||||||
|
menuBar->TogglePopUpMarker(dmark);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
BMenuField::_ValidateLayoutData()
|
BMenuField::_ValidateLayoutData()
|
||||||
{
|
{
|
||||||
@@ -1144,6 +1252,16 @@ BMenuField::LabelLayoutItem::LabelLayoutItem(BMenuField* parent)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BMenuField::LabelLayoutItem::LabelLayoutItem(BMessage* from)
|
||||||
|
:
|
||||||
|
BAbstractLayoutItem(from),
|
||||||
|
fParent(NULL),
|
||||||
|
fFrame()
|
||||||
|
{
|
||||||
|
from->FindRect(kFrameField, &fFrame);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
bool
|
bool
|
||||||
BMenuField::LabelLayoutItem::IsVisible()
|
BMenuField::LabelLayoutItem::IsVisible()
|
||||||
{
|
{
|
||||||
@@ -1173,6 +1291,13 @@ BMenuField::LabelLayoutItem::SetFrame(BRect frame)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void
|
||||||
|
BMenuField::LabelLayoutItem::SetParent(BMenuField* parent)
|
||||||
|
{
|
||||||
|
fParent = parent;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
BView*
|
BView*
|
||||||
BMenuField::LabelLayoutItem::View()
|
BMenuField::LabelLayoutItem::View()
|
||||||
{
|
{
|
||||||
@@ -1214,6 +1339,28 @@ BMenuField::LabelLayoutItem::BaseAlignment()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
BMenuField::LabelLayoutItem::Archive(BMessage* into, bool deep) const
|
||||||
|
{
|
||||||
|
BArchiver archiver(into);
|
||||||
|
status_t err = BAbstractLayoutItem::Archive(into, deep);
|
||||||
|
|
||||||
|
if (err == B_OK)
|
||||||
|
err = into->AddRect(kFrameField, fFrame);
|
||||||
|
|
||||||
|
return archiver.Finish(err);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BArchivable*
|
||||||
|
BMenuField::LabelLayoutItem::Instantiate(BMessage* from)
|
||||||
|
{
|
||||||
|
if (validate_instantiation(from, "BMenuField::LabelLayoutItem"))
|
||||||
|
return new LabelLayoutItem(from);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// #pragma mark -
|
// #pragma mark -
|
||||||
|
|
||||||
|
|
||||||
@@ -1228,6 +1375,16 @@ BMenuField::MenuBarLayoutItem::MenuBarLayoutItem(BMenuField* parent)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BMenuField::MenuBarLayoutItem::MenuBarLayoutItem(BMessage* from)
|
||||||
|
:
|
||||||
|
BAbstractLayoutItem(from),
|
||||||
|
fParent(NULL),
|
||||||
|
fFrame()
|
||||||
|
{
|
||||||
|
from->FindRect(kFrameField, &fFrame);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
bool
|
bool
|
||||||
BMenuField::MenuBarLayoutItem::IsVisible()
|
BMenuField::MenuBarLayoutItem::IsVisible()
|
||||||
{
|
{
|
||||||
@@ -1257,6 +1414,13 @@ BMenuField::MenuBarLayoutItem::SetFrame(BRect frame)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void
|
||||||
|
BMenuField::MenuBarLayoutItem::SetParent(BMenuField* parent)
|
||||||
|
{
|
||||||
|
fParent = parent;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
BView*
|
BView*
|
||||||
BMenuField::MenuBarLayoutItem::View()
|
BMenuField::MenuBarLayoutItem::View()
|
||||||
{
|
{
|
||||||
@@ -1299,3 +1463,25 @@ BMenuField::MenuBarLayoutItem::BaseAlignment()
|
|||||||
return BAlignment(B_ALIGN_USE_FULL_WIDTH, B_ALIGN_USE_FULL_HEIGHT);
|
return BAlignment(B_ALIGN_USE_FULL_WIDTH, B_ALIGN_USE_FULL_HEIGHT);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
BMenuField::MenuBarLayoutItem::Archive(BMessage* into, bool deep) const
|
||||||
|
{
|
||||||
|
BArchiver archiver(into);
|
||||||
|
status_t err = BAbstractLayoutItem::Archive(into, deep);
|
||||||
|
|
||||||
|
if (err == B_OK)
|
||||||
|
err = into->AddRect(kFrameField, fFrame);
|
||||||
|
|
||||||
|
return archiver.Finish(err);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BArchivable*
|
||||||
|
BMenuField::MenuBarLayoutItem::Instantiate(BMessage* from)
|
||||||
|
{
|
||||||
|
if (validate_instantiation(from, "BMenuField::MenuBarLayoutItem"))
|
||||||
|
return new MenuBarLayoutItem(from);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user