Deskbar: Persist ExpandoMenuBar

Add private BMenu::_SetMenuLayout() method. Set TExpandoMenuBar
as a friend class in BMenu to call this method. A little hacky,
but, this keeps SetMenuLayout() from being exposed as part of
the public API.

Don't destroy and rebuild the ExpandoMenuBar when switching from
horizontal to vertical mode. Instead build the TExpandoMenuBar
when the application starts and then switch it from B_ITEMS_IN_ROW
to B_ITEMS_IN_COLUMNS by using the newly added _SetMenuLayout()
method.

When we resize from vertical to horizontal, recalc the max
menu item widths, this resizes the application menu items so
that they take up the right amount of space.

Since we no longer destroy the menu bar we no longer have to
save whether menu items are expanded or not in a separate list.
Instead we can store that information in directly in
TExpandoMenuBar. This removes a lot of code.

Fixes #9350
This commit is contained in:
John Scipione
2015-02-19 19:02:39 -05:00
parent c9d2a320a3
commit deaae5fc20
10 changed files with 173 additions and 213 deletions
+2
View File
@@ -173,6 +173,7 @@ public:
private: private:
friend class BMenuBar; friend class BMenuBar;
friend class BPrivate::MenuPrivate; friend class BPrivate::MenuPrivate;
friend class TExpandoMenuBar;
friend status_t _init_interface_kit_(); friend status_t _init_interface_kit_();
friend status_t set_menu_info(menu_info* info); friend status_t set_menu_info(menu_info* info);
friend status_t get_menu_info(menu_info* info); friend status_t get_menu_info(menu_info* info);
@@ -269,6 +270,7 @@ private:
int _State(BMenuItem** _item = NULL) const; int _State(BMenuItem** _item = NULL) const;
void _InvokeItem(BMenuItem* item, bool now = false); void _InvokeItem(BMenuItem* item, bool now = false);
void _QuitTracking(bool onlyThis = true); void _QuitTracking(bool onlyThis = true);
void _SetMenuLayout(menu_layout layout) { fLayout = layout; };
static menu_info sMenuInfo; static menu_info sMenuInfo;
-11
View File
@@ -129,8 +129,6 @@ TBarApp::TBarApp()
fSwitcherMessenger = BMessenger(new TSwitchManager(fSettings.switcherLoc)); fSwitcherMessenger = BMessenger(new TSwitchManager(fSettings.switcherLoc));
fBarWindow->Show(); fBarWindow->Show();
// Call UpdatePlacement() after the window is shown because expanded
// apps need to resize the window.
fBarWindow->Lock(); fBarWindow->Lock();
fBarView->UpdatePlacement(); fBarView->UpdatePlacement();
fBarWindow->Unlock(); fBarWindow->Unlock();
@@ -505,7 +503,6 @@ TBarApp::MessageReceived(BMessage* message)
break; break;
fBarWindow->Lock(); fBarWindow->Lock();
fBarView->SaveExpandedItems();
fBarView->PlaceApplicationBar(); fBarView->PlaceApplicationBar();
fBarWindow->Unlock(); fBarWindow->Unlock();
break; break;
@@ -521,7 +518,6 @@ TBarApp::MessageReceived(BMessage* message)
break; break;
fBarWindow->Lock(); fBarWindow->Lock();
fBarView->SaveExpandedItems();
fBarView->PlaceApplicationBar(); fBarView->PlaceApplicationBar();
fBarWindow->Unlock(); fBarWindow->Unlock();
break; break;
@@ -545,7 +541,6 @@ TBarApp::MessageReceived(BMessage* message)
break; break;
fBarWindow->Lock(); fBarWindow->Lock();
fBarView->SaveExpandedItems();
fBarView->PlaceApplicationBar(); fBarView->PlaceApplicationBar();
fBarWindow->Unlock(); fBarWindow->Unlock();
break; break;
@@ -561,7 +556,6 @@ TBarApp::MessageReceived(BMessage* message)
break; break;
fBarWindow->Lock(); fBarWindow->Lock();
fBarView->SaveExpandedItems();
fBarView->PlaceApplicationBar(); fBarView->PlaceApplicationBar();
fBarWindow->Unlock(); fBarWindow->Unlock();
break; break;
@@ -577,7 +571,6 @@ TBarApp::MessageReceived(BMessage* message)
break; break;
fBarWindow->Lock(); fBarWindow->Lock();
fBarView->SaveExpandedItems();
fBarView->PlaceApplicationBar(); fBarView->PlaceApplicationBar();
fBarWindow->Unlock(); fBarWindow->Unlock();
break; break;
@@ -611,7 +604,6 @@ TBarApp::MessageReceived(BMessage* message)
break; break;
fBarWindow->Lock(); fBarWindow->Lock();
fBarView->SaveExpandedItems();
if (!fBarView->Vertical()) { if (!fBarView->Vertical()) {
// Must also resize the Deskbar menu and replicant tray in // Must also resize the Deskbar menu and replicant tray in
// horizontal mode // horizontal mode
@@ -805,9 +797,6 @@ TBarApp::AddTeam(team_id team, uint32 flags, const char* sig, entry_ref* ref)
barInfo->teams->AddItem((void*)(addr_t)team); barInfo->teams->AddItem((void*)(addr_t)team);
sBarTeamInfoList.AddItem(barInfo); sBarTeamInfoList.AddItem(barInfo);
if (fSettings.expandNewTeams)
fBarView->AddExpandedItem(sig);
int32 subsCount = sSubscribers.CountItems(); int32 subsCount = sSubscribers.CountItems();
if (subsCount > 0) { if (subsCount > 0) {
for (int32 i = 0; i < subsCount; i++) { for (int32 i = 0; i < subsCount; i++) {
+25 -129
View File
@@ -168,10 +168,9 @@ TBarView::TBarView(BRect frame, bool vertical, bool left, bool top,
AddChild(fDragRegion); AddChild(fDragRegion);
// create and add the application menubar // create and add the application menubar
fExpandoMenuBar = new TExpandoMenuBar(BRect(0, 0, 0, 0), fExpandoMenuBar = new TExpandoMenuBar("ExpandoMenuBar", this, fVertical);
"ExpandoMenuBar", this, fVertical); fInlineScrollView = new TInlineScrollView(fExpandoMenuBar,
fInlineScrollView = new TInlineScrollView(BRect(0, 0, 0, 0), fVertical ? B_VERTICAL : B_HORIZONTAL);
fExpandoMenuBar, fVertical ? B_VERTICAL : B_HORIZONTAL);
AddChild(fInlineScrollView); AddChild(fInlineScrollView);
// If mini mode, hide the application menubar // If mini mode, hide the application menubar
@@ -185,8 +184,6 @@ TBarView::~TBarView()
delete fDragMessage; delete fDragMessage;
delete fCachedTypesList; delete fCachedTypesList;
delete fBarMenuBar; delete fBarMenuBar;
RemoveExpandedItems();
} }
@@ -473,19 +470,12 @@ TBarView::PlaceApplicationBar()
BRect expandoFrame(0, 0, 0, 0); BRect expandoFrame(0, 0, 0, 0);
if (fVertical) { if (fVertical) {
// left or right // left or right
if (fTrayLocation != 0) { expandoFrame.top = fTrayLocation != 0 ? fDragRegion->Frame().bottom + 1
expandoFrame.top = fDragRegion->Frame().bottom + 1; : fBarMenuBar->Frame().bottom + 1;
expandoFrame.left = fDragRegion->Frame().left; expandoFrame.left = fDragRegion->Frame().left;
} else {
expandoFrame.top = fBarMenuBar->Frame().bottom + 1;
expandoFrame.left = fDragRegion->Frame().left;
}
expandoFrame.right = expandoFrame.left + sMinimumWindowWidth; expandoFrame.right = expandoFrame.left + sMinimumWindowWidth;
if (fState == kFullState) expandoFrame.bottom = fState == kFullState ? screenFrame.bottom
expandoFrame.bottom = screenFrame.bottom; : expandoFrame.top + 1;
else
expandoFrame.bottom = expandoFrame.top + 1;
} else { } else {
// top or bottom // top or bottom
expandoFrame.top = 0; expandoFrame.top = 0;
@@ -514,9 +504,8 @@ TBarView::PlaceApplicationBar()
fExpandoMenuBar->SetMaxItemWidth(); fExpandoMenuBar->SetMaxItemWidth();
} }
fExpandoMenuBar->BuildItems(); if (fState == kExpandoState)
if (fVertical) fExpandoMenuBar->BuildItems();
ExpandItems();
SizeWindow(screenFrame); SizeWindow(screenFrame);
PositionWindow(screenFrame); PositionWindow(screenFrame);
@@ -581,7 +570,8 @@ TBarView::GetPreferredWindowSize(BRect screenFrame, float* width, float* height)
void void
TBarView::SizeWindow(BRect screenFrame) TBarView::SizeWindow(BRect screenFrame)
{ {
float windowWidth, windowHeight; float windowWidth;
float windowHeight;
GetPreferredWindowSize(screenFrame, &windowWidth, &windowHeight); GetPreferredWindowSize(screenFrame, &windowWidth, &windowHeight);
Window()->ResizeTo(windowWidth, windowHeight); Window()->ResizeTo(windowWidth, windowHeight);
} }
@@ -590,7 +580,8 @@ TBarView::SizeWindow(BRect screenFrame)
void void
TBarView::PositionWindow(BRect screenFrame) TBarView::PositionWindow(BRect screenFrame)
{ {
float windowWidth, windowHeight; float windowWidth;
float windowHeight;
GetPreferredWindowSize(screenFrame, &windowWidth, &windowHeight); GetPreferredWindowSize(screenFrame, &windowWidth, &windowHeight);
BPoint moveLoc(0, 0); BPoint moveLoc(0, 0);
@@ -661,73 +652,6 @@ TBarView::ChangeState(int32 state, bool vertical, bool left, bool top,
} }
void
TBarView::SaveExpandedItems()
{
if (fExpandoMenuBar == NULL)
return;
// Get a list of the signatures of expanded apps. Can't use
// team_id because there can be more than one team per application
int32 count = fExpandoMenuBar->CountItems();
for (int32 i = 0; i < count; i++) {
TTeamMenuItem* teamItem
= dynamic_cast<TTeamMenuItem*>(fExpandoMenuBar->ItemAt(i));
if (teamItem != NULL && teamItem->IsExpanded())
AddExpandedItem(teamItem->Signature());
}
}
void
TBarView::RemoveExpandedItems()
{
while (!fExpandedItems.IsEmpty())
delete static_cast<BString*>(fExpandedItems.RemoveItem((int32)0));
fExpandedItems.MakeEmpty();
}
void
TBarView::ExpandItems()
{
if (fExpandoMenuBar == NULL || !fVertical || fState != kExpandoState
|| !fBarApp->Settings()->superExpando
|| fExpandedItems.CountItems() <= 0) {
return;
}
// Start at the 'bottom' of the list working up.
// Prevents being thrown off by expanding items.
for (int32 i = fExpandoMenuBar->CountItems() - 1; i >= 0; i--) {
TTeamMenuItem* teamItem
= dynamic_cast<TTeamMenuItem*>(fExpandoMenuBar->ItemAt(i));
if (teamItem != NULL) {
// Start at the 'bottom' of the fExpandedItems list working up
// matching the order of the fExpandoMenuBar list in the outer loop.
for (int32 j = fExpandedItems.CountItems() - 1; j >= 0; j--) {
BString* itemSig =
static_cast<BString*>(fExpandedItems.ItemAt(j));
if (itemSig->Compare(teamItem->Signature()) == 0) {
// Found it, expand the item and delete signature from
// the list so that we don't consider it for later items.
teamItem->ToggleExpandState(false);
fExpandedItems.RemoveItem(j);
delete itemSig;
break;
}
}
}
}
// Clean up the expanded items list
RemoveExpandedItems();
}
void void
TBarView::_ChangeState(BMessage* message) TBarView::_ChangeState(BMessage* message)
{ {
@@ -745,31 +669,21 @@ TBarView::_ChangeState(BMessage* message)
fLeft = left; fLeft = left;
fTop = top; fTop = top;
SaveExpandedItems();
if (stateChanged || vertSwap) { if (stateChanged || vertSwap) {
be_app->PostMessage(kStateChanged); be_app->PostMessage(kStateChanged);
// Send a message to the preferences window to let it know to // Send a message to the preferences window to let it know to
// enable or disable preference items. // enable or disable preference items.
// If switching to expando state, rebuild expando menu bar. if (vertSwap && fExpandoMenuBar != NULL) {
if (fState == kExpandoState) { if (fVertical) {
if (fInlineScrollView != NULL) { fInlineScrollView->SetOrientation(B_VERTICAL);
fInlineScrollView->DetachScrollers(); fExpandoMenuBar->SetMenuLayout(B_ITEMS_IN_COLUMN);
fInlineScrollView->RemoveSelf(); fExpandoMenuBar->StartMonitoringWindows();
delete fInlineScrollView; } else {
fInlineScrollView = NULL; fInlineScrollView->SetOrientation(B_HORIZONTAL);
fExpandoMenuBar->SetMenuLayout(B_ITEMS_IN_ROW);
fExpandoMenuBar->StopMonitoringWindows();
} }
if (fExpandoMenuBar != NULL) {
delete fExpandoMenuBar;
fExpandoMenuBar = NULL;
}
fExpandoMenuBar = new TExpandoMenuBar(BRect(0, 0, 0, 0),
"ExpandoMenuBar", this, fVertical);
fInlineScrollView = new TInlineScrollView(BRect(0, 0, 0, 0),
fExpandoMenuBar, fVertical ? B_VERTICAL : B_HORIZONTAL);
AddChild(fInlineScrollView);
} }
} }
@@ -779,25 +693,6 @@ TBarView::_ChangeState(BMessage* message)
} }
void
TBarView::AddExpandedItem(const char* signature)
{
bool shouldAdd = true;
for (int32 i = 0; i < fExpandedItems.CountItems(); i++) {
BString *itemSig = static_cast<BString*>(fExpandedItems.ItemAt(i));
if (itemSig->Compare(signature) == 0) {
// already in the list, don't add the signature
shouldAdd = false;
break;
}
}
if (shouldAdd)
fExpandedItems.AddItem(static_cast<void*>(new BString(signature)));
}
void void
TBarView::RaiseDeskbar(bool raise) TBarView::RaiseDeskbar(bool raise)
{ {
@@ -1040,7 +935,7 @@ status_t
TBarView::SendDragMessage(const char* signature, entry_ref* ref) TBarView::SendDragMessage(const char* signature, entry_ref* ref)
{ {
status_t err = B_ERROR; status_t err = B_ERROR;
if (fDragMessage) { if (fDragMessage != NULL) {
if (fRefsRcvdOnly) { if (fRefsRcvdOnly) {
// current message sent to apps is only B_REFS_RECEIVED // current message sent to apps is only B_REFS_RECEIVED
fDragMessage->what = B_REFS_RECEIVED; fDragMessage->what = B_REFS_RECEIVED;
@@ -1059,6 +954,7 @@ TBarView::SendDragMessage(const char* signature, entry_ref* ref)
} else if (signature != NULL && *signature != '\0') } else if (signature != NULL && *signature != '\0')
roster.Launch(signature, fDragMessage); roster.Launch(signature, fDragMessage);
} }
return err; return err;
} }
-6
View File
@@ -158,7 +158,6 @@ public:
float* width, float* height); float* width, float* height);
void SizeWindow(BRect screenFrame); void SizeWindow(BRect screenFrame);
void PositionWindow(BRect screenFrame); void PositionWindow(BRect screenFrame);
void AddExpandedItem(const char* signature);
void CheckForScrolling(); void CheckForScrolling();
@@ -179,10 +178,6 @@ private:
void PlaceTray(bool vertSwap, bool leftSwap); void PlaceTray(bool vertSwap, bool leftSwap);
void PlaceApplicationBar(); void PlaceApplicationBar();
void SaveExpandedItems();
void RemoveExpandedItems();
void ExpandItems();
void _ChangeState(BMessage* message); void _ChangeState(BMessage* message);
TBarApp* fBarApp; TBarApp* fBarApp;
@@ -209,7 +204,6 @@ private:
uint32 fMaxRecentApps; uint32 fMaxRecentApps;
TTeamMenuItem* fLastDragItem; TTeamMenuItem* fLastDragItem;
BList fExpandedItems;
BMessageFilter* fMouseFilter; BMessageFilter* fMouseFilter;
}; };
+126 -55
View File
@@ -38,6 +38,8 @@ All rights reserved.
#include <strings.h> #include <strings.h>
#include <map>
#include <Autolock.h> #include <Autolock.h>
#include <Bitmap.h> #include <Bitmap.h>
#include <ControlLook.h> #include <ControlLook.h>
@@ -77,11 +79,16 @@ bool TExpandoMenuBar::sDoMonitor = false;
thread_id TExpandoMenuBar::sMonThread = B_ERROR; thread_id TExpandoMenuBar::sMonThread = B_ERROR;
BLocker TExpandoMenuBar::sMonLocker("expando monitor"); BLocker TExpandoMenuBar::sMonLocker("expando monitor");
typedef std::map<BString, TTeamMenuItem*> TeamMenuItemMap;
TExpandoMenuBar::TExpandoMenuBar(BRect frame, const char* name,
TBarView* barView, bool vertical) // #pragma mark - TExpandoMenuBar
TExpandoMenuBar::TExpandoMenuBar(const char* name, TBarView* barView,
bool vertical)
: :
BMenuBar(frame, name, B_FOLLOW_NONE, BMenuBar(BRect(0, 0, 0, 0), name, B_FOLLOW_NONE,
vertical ? B_ITEMS_IN_COLUMN : B_ITEMS_IN_ROW), vertical ? B_ITEMS_IN_COLUMN : B_ITEMS_IN_ROW),
fBarView(barView), fBarView(barView),
fVertical(vertical), fVertical(vertical),
@@ -122,12 +129,8 @@ TExpandoMenuBar::AttachedToWindow()
fTeamList.MakeEmpty(); fTeamList.MakeEmpty();
if (fVertical) { if (fVertical)
sDoMonitor = true; StartMonitoringWindows();
sMonThread = spawn_thread(monitor_team_windows,
"Expando Window Watcher", B_LOW_PRIORITY, this);
resume_thread(sMonThread);
}
} }
@@ -136,14 +139,7 @@ TExpandoMenuBar::DetachedFromWindow()
{ {
BMenuBar::DetachedFromWindow(); BMenuBar::DetachedFromWindow();
if (sMonThread != B_ERROR) { StopMonitoringWindows();
sDoMonitor = false;
status_t returnCode;
wait_for_thread(sMonThread, &returnCode);
sMonThread = B_ERROR;
}
BMessenger self(this); BMessenger self(this);
BMessage message(kUnsubscribe); BMessage message(kUnsubscribe);
@@ -471,37 +467,79 @@ TExpandoMenuBar::BuildItems()
fShowTeamExpander = settings->superExpando; fShowTeamExpander = settings->superExpando;
fExpandNewTeams = settings->expandNewTeams; fExpandNewTeams = settings->expandNewTeams;
float itemWidth = -0.1f; float itemWidth = fVertical ? Frame().Width()
if (fVertical) : iconSize + (fDrawLabel ? sMinimumWindowWidth - kMinimumIconSize
itemWidth = Frame().Width(); : kIconPadding * 2);
else {
itemWidth = iconSize;
if (fDrawLabel)
itemWidth += sMinimumWindowWidth - kMinimumIconSize;
else
itemWidth += kIconPadding * 2;
}
float itemHeight = -1.0f; float itemHeight = -1.0f;
RemoveItems(0, CountItems(), true); TeamMenuItemMap items;
// remove all items int32 itemCount = CountItems();
BList itemList(itemCount);
for (int32 i = 0; i < itemCount; i++) {
BMenuItem* menuItem = RemoveItem((int32)0);
itemList.AddItem(menuItem);
TTeamMenuItem* item = dynamic_cast<TTeamMenuItem*>(menuItem);
if (item != NULL)
items[BString(item->Signature()).ToLower()] = item;
}
if (settings->sortRunningApps) if (settings->sortRunningApps)
fTeamList.SortItems(CompareByName); fTeamList.SortItems(CompareByName);
int32 count = fTeamList.CountItems(); int32 teamCount = fTeamList.CountItems();
for (int32 i = 0; i < count; i++) { for (int32 i = 0; i < teamCount; i++) {
// add items back
BarTeamInfo* barInfo = (BarTeamInfo*)fTeamList.ItemAt(i); BarTeamInfo* barInfo = (BarTeamInfo*)fTeamList.ItemAt(i);
TTeamMenuItem* item = new TTeamMenuItem(barInfo->teams, TeamMenuItemMap::const_iterator iter
barInfo->icon, barInfo->name, barInfo->sig, itemWidth, = items.find(BString(barInfo->sig).ToLower());
itemHeight, fDrawLabel, fVertical); if (iter == items.end()) {
// new team
TTeamMenuItem* item = new TTeamMenuItem(barInfo->teams,
barInfo->icon, barInfo->name, barInfo->sig, itemWidth,
itemHeight);
if (settings->trackerAlwaysFirst if (settings->trackerAlwaysFirst
&& strcmp(barInfo->sig, kTrackerSignature) == 0) { && strcasecmp(barInfo->sig, kTrackerSignature) == 0) {
AddItem(item, 0); AddItem(item, 0);
} else } else
AddItem(item); AddItem(item);
} else {
// existing team, update info and add it
TTeamMenuItem* item = iter->second;
item->SetIcon(barInfo->icon);
item->SetOverrideWidth(itemWidth);
item->SetOverrideHeight(itemHeight);
if (settings->trackerAlwaysFirst
&& strcasecmp(barInfo->sig, kTrackerSignature) == 0) {
AddItem(item, 0);
} else
AddItem(item);
// add window items back
int32 index = itemList.IndexOf(item);
TWindowMenuItem* windowItem;
TWindowMenu* submenu = dynamic_cast<TWindowMenu*>(item->Submenu());
bool hasWindowItems = false;
while ((windowItem = dynamic_cast<TWindowMenuItem*>(
(BMenuItem*)(itemList.ItemAt(++index)))) != NULL) {
if (fVertical)
AddItem(windowItem);
else {
delete windowItem;
hasWindowItems = submenu != NULL;
}
}
// unexpand if turn off show team expander
if (fVertical && !fShowTeamExpander && item->IsExpanded())
item->ToggleExpandState(false);
if (hasWindowItems) {
// add (new) window items in submenu
submenu->SetExpanded(false, 0);
submenu->AttachedToWindow();
}
}
} }
if (CountItems() == 0) { if (CountItems() == 0) {
@@ -572,16 +610,9 @@ TExpandoMenuBar::AddTeam(BList* team, BBitmap* icon, char* name,
desk_settings* settings = static_cast<TBarApp*>(be_app)->Settings(); desk_settings* settings = static_cast<TBarApp*>(be_app)->Settings();
int32 iconSize = static_cast<TBarApp*>(be_app)->IconSize(); int32 iconSize = static_cast<TBarApp*>(be_app)->IconSize();
float itemWidth = -1.0f; float itemWidth = fVertical ? Frame().Width()
if (fVertical) : iconSize + (fDrawLabel ? sMinimumWindowWidth - kMinimumIconSize
itemWidth = fBarView->Bounds().Width(); : kIconPadding * 2);
else {
itemWidth = iconSize;
if (fDrawLabel)
itemWidth += sMinimumWindowWidth - kMinimumIconSize;
else
itemWidth += kIconPadding * 2;
}
float itemHeight = -1.0f; float itemHeight = -1.0f;
TTeamMenuItem* item = new TTeamMenuItem(team, icon, name, signature, TTeamMenuItem* item = new TTeamMenuItem(team, icon, name, signature,
@@ -597,7 +628,7 @@ TExpandoMenuBar::AddTeam(BList* team, BBitmap* icon, char* name,
// if Tracker should always be the first item, we need to skip it // if Tracker should always be the first item, we need to skip it
// when sorting in the current item // when sorting in the current item
if (settings->trackerAlwaysFirst && teamItem != NULL if (settings->trackerAlwaysFirst && teamItem != NULL
&& !strcasecmp(teamItem->Signature(), kTrackerSignature)) { && strcasecmp(teamItem->Signature(), kTrackerSignature) == 0) {
firstApp++; firstApp++;
} }
@@ -617,10 +648,8 @@ TExpandoMenuBar::AddTeam(BList* team, BBitmap* icon, char* name,
} else } else
AddItem(item); AddItem(item);
if (fVertical) { if (fShowTeamExpander && fExpandNewTeams)
if (item && fShowTeamExpander && fExpandNewTeams) item->ToggleExpandState(false);
item->ToggleExpandState(false);
}
SizeWindow(1); SizeWindow(1);
Window()->UpdateIfNeeded(); Window()->UpdateIfNeeded();
@@ -660,10 +689,13 @@ TExpandoMenuBar::RemoveTeam(team_id team, bool partial)
RemoveItem(i); RemoveItem(i);
if (item == fPreviousDragTargetItem) if (item == fPreviousDragTargetItem)
fPreviousDragTargetItem = NULL; fPreviousDragTargetItem = NULL;
if (item == fLastMousedOverItem) if (item == fLastMousedOverItem)
fLastMousedOverItem = NULL; fLastMousedOverItem = NULL;
if (item == fLastClickedItem) if (item == fLastClickedItem)
fLastClickedItem = NULL; fLastClickedItem = NULL;
delete item; delete item;
while ((windowItem = dynamic_cast<TWindowMenuItem*>( while ((windowItem = dynamic_cast<TWindowMenuItem*>(
ItemAt(i))) != NULL) { ItemAt(i))) != NULL) {
@@ -671,8 +703,10 @@ TExpandoMenuBar::RemoveTeam(team_id team, bool partial)
RemoveItem(i); RemoveItem(i);
if (windowItem == fLastMousedOverItem) if (windowItem == fLastMousedOverItem)
fLastMousedOverItem = NULL; fLastMousedOverItem = NULL;
if (windowItem == fLastClickedItem) if (windowItem == fLastClickedItem)
fLastClickedItem = NULL; fLastClickedItem = NULL;
delete windowItem; delete windowItem;
} }
SizeWindow(-1); SizeWindow(-1);
@@ -751,6 +785,16 @@ TExpandoMenuBar::MenuLayout() const
} }
void
TExpandoMenuBar::SetMenuLayout(menu_layout layout)
{
fVertical = layout == B_ITEMS_IN_COLUMN;
BMenu::_SetMenuLayout(layout);
SetMaxItemWidth();
// when the menu layout changes, make sure to set the max width
}
void void
TExpandoMenuBar::Draw(BRect updateRect) TExpandoMenuBar::Draw(BRect updateRect)
{ {
@@ -859,6 +903,33 @@ TExpandoMenuBar::SizeWindow(int32 delta)
} }
void
TExpandoMenuBar::StartMonitoringWindows()
{
if (sMonThread != B_ERROR)
return;
sDoMonitor = true;
sMonThread = spawn_thread(monitor_team_windows,
"Expando Window Watcher", B_LOW_PRIORITY, this);
resume_thread(sMonThread);
}
void
TExpandoMenuBar::StopMonitoringWindows()
{
if (sMonThread == B_ERROR)
return;
sDoMonitor = false;
status_t returnCode;
wait_for_thread(sMonThread, &returnCode);
sMonThread = B_ERROR;
}
int32 int32
TExpandoMenuBar::monitor_team_windows(void* arg) TExpandoMenuBar::monitor_team_windows(void* arg)
{ {
+5 -1
View File
@@ -61,7 +61,7 @@ class TTeamMenuItem;
class TExpandoMenuBar : public BMenuBar { class TExpandoMenuBar : public BMenuBar {
public: public:
TExpandoMenuBar(BRect frame, const char* name, TExpandoMenuBar(const char* name,
TBarView* barView, bool vertical); TBarView* barView, bool vertical);
virtual void AttachedToWindow(); virtual void AttachedToWindow();
@@ -86,12 +86,16 @@ public:
void CheckItemSizes(int32 delta); void CheckItemSizes(int32 delta);
menu_layout MenuLayout() const; menu_layout MenuLayout() const;
void SetMenuLayout(menu_layout layout);
void SetMaxItemWidth(); void SetMaxItemWidth();
void SizeWindow(int32 delta); void SizeWindow(int32 delta);
bool CheckForSizeOverrun(); bool CheckForSizeOverrun();
void StartMonitoringWindows();
void StopMonitoringWindows();
private: private:
static int CompareByName(const void* first, static int CompareByName(const void* first,
const void* second); const void* second);
+2 -2
View File
@@ -363,10 +363,10 @@ RightScrollArrow::MouseDown(BPoint where)
// #pragma mark - // #pragma mark -
TInlineScrollView::TInlineScrollView(BRect frame, BView* target, TInlineScrollView::TInlineScrollView(BView* target,
enum orientation orientation) enum orientation orientation)
: :
BView(frame, "inline scroll view", B_FOLLOW_NONE, B_WILL_DRAW), BView(BRect(0, 0, 0, 0), "inline scroll view", B_FOLLOW_NONE, B_WILL_DRAW),
fTarget(target), fTarget(target),
fBeginScrollArrow(NULL), fBeginScrollArrow(NULL),
fEndScrollArrow(NULL), fEndScrollArrow(NULL),
+5 -1
View File
@@ -20,7 +20,7 @@ class ScrollArrow;
class TInlineScrollView : public BView { class TInlineScrollView : public BView {
public: public:
TInlineScrollView(BRect frame, BView* target, TInlineScrollView(BView* target,
enum orientation orientation = B_VERTICAL); enum orientation orientation = B_VERTICAL);
virtual ~TInlineScrollView(); virtual ~TInlineScrollView();
@@ -38,6 +38,10 @@ public:
float* _largeStep) const; float* _largeStep) const;
void ScrollBy(const float& step); void ScrollBy(const float& step);
bool Orientation() const { return fOrientation; };
void SetOrientation(int32 orienation)
{ fOrientation = orienation; };
private: private:
BView* fTarget; BView* fTarget;
ScrollArrow* fBeginScrollArrow; ScrollArrow* fBeginScrollArrow;
+1 -1
View File
@@ -142,7 +142,7 @@ TReplicantTray::TReplicantTray(TBarView* parent, bool vertical)
const BBitmap* logoBitmap = AppResSet()->FindBitmap(B_MESSAGE_TYPE, const BBitmap* logoBitmap = AppResSet()->FindBitmap(B_MESSAGE_TYPE,
R_LeafLogoBitmap); R_LeafLogoBitmap);
if (logoBitmap != NULL) { if (logoBitmap != NULL) {
sMinimumWindowWidth = max_c(sMinimumWindowWidth, sMinimumWindowWidth = std::max(sMinimumWindowWidth,
2 * (logoBitmap->Bounds().Width() + 8)); 2 * (logoBitmap->Bounds().Width() + 8));
fMinimumTrayWidth = sMinimumWindowWidth - kGutter - kDragRegionWidth; fMinimumTrayWidth = sMinimumWindowWidth - kGutter - kDragRegionWidth;
} }
+7 -7
View File
@@ -371,8 +371,8 @@ TTeamMenuItem::ToggleExpandState(bool resizeWindow)
int myindex = parent->IndexOf(this) + 1; int myindex = parent->IndexOf(this) + 1;
TWindowMenuItem* windowItem = NULL; TWindowMenuItem* windowItem = NULL;
int childIndex = 0; int32 childIndex = 0;
int totalChildren = sub->CountItems() - 4; int32 totalChildren = sub->CountItems() - 4;
// hide, show, close, separator. // hide, show, close, separator.
for (; childIndex < totalChildren; childIndex++) { for (; childIndex < totalChildren; childIndex++) {
windowItem = static_cast<TWindowMenuItem*> windowItem = static_cast<TWindowMenuItem*>
@@ -393,11 +393,11 @@ TTeamMenuItem::ToggleExpandState(bool resizeWindow)
TExpandoMenuBar* parent = static_cast<TExpandoMenuBar*>(Menu()); TExpandoMenuBar* parent = static_cast<TExpandoMenuBar*>(Menu());
TWindowMenuItem* windowItem = NULL; TWindowMenuItem* windowItem = NULL;
int childIndex = parent->IndexOf(this) + 1; int32 childIndex = parent->IndexOf(this) + 1;
while (!parent->SubmenuAt(childIndex) && childIndex while (parent->SubmenuAt(childIndex) == NULL
< parent->CountItems()) { && childIndex < parent->CountItems()) {
windowItem = static_cast<TWindowMenuItem*> windowItem
(parent->RemoveItem(childIndex)); = static_cast<TWindowMenuItem*>(parent->RemoveItem(childIndex));
sub->AddItem(windowItem, 0); sub->AddItem(windowItem, 0);
windowItem->ExpandedItem(false); windowItem->ExpandedItem(false);
} }