Since SF cannot be reached currently, this fix gets into the Haiku tree first:
ExpandoMenuBar::ItemAtPoint() was broken, which could cause a crash when doing the "vulcan death grip" over a window item. This fixes bug #379. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@16964 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -589,8 +589,8 @@ TBarView::DragStart()
|
|||||||
|
|
||||||
if (fExpando && fExpando->Frame().Contains(loc)) {
|
if (fExpando && fExpando->Frame().Contains(loc)) {
|
||||||
ConvertToScreen(&loc);
|
ConvertToScreen(&loc);
|
||||||
BPoint expandoloc = fExpando->ConvertFromScreen(loc);
|
BPoint expandoLocation = fExpando->ConvertFromScreen(loc);
|
||||||
TTeamMenuItem *item = fExpando->ItemAtPoint(expandoloc);
|
TTeamMenuItem *item = fExpando->TeamItemAtPoint(expandoLocation);
|
||||||
|
|
||||||
if (fLastDragItem)
|
if (fLastDragItem)
|
||||||
init_tracking_hook(fLastDragItem, NULL, NULL);
|
init_tracking_hook(fLastDragItem, NULL, NULL);
|
||||||
@@ -623,14 +623,14 @@ TBarView::MenuTrackingHook(BMenu *menu, void *castToThis)
|
|||||||
BPoint location;
|
BPoint location;
|
||||||
menu->GetMouse(&location, &buttons);
|
menu->GetMouse(&location, &buttons);
|
||||||
|
|
||||||
bool returnvalue = true;
|
bool endMenu = true;
|
||||||
BRect frame(menu->Bounds());
|
BRect frame(menu->Bounds());
|
||||||
frame.InsetBy(-kMenuTrackMargin, -kMenuTrackMargin);
|
frame.InsetBy(-kMenuTrackMargin, -kMenuTrackMargin);
|
||||||
|
|
||||||
if (frame.Contains(location)) {
|
if (frame.Contains(location)) {
|
||||||
// if current loc is still in the menu
|
// if current loc is still in the menu
|
||||||
// keep tracking
|
// keep tracking
|
||||||
returnvalue = false;
|
endMenu = false;
|
||||||
} else {
|
} else {
|
||||||
// see if the mouse is in the team/be menu item
|
// see if the mouse is in the team/be menu item
|
||||||
menu->ConvertToScreen(&location);
|
menu->ConvertToScreen(&location);
|
||||||
@@ -641,23 +641,23 @@ TBarView::MenuTrackingHook(BMenu *menu, void *castToThis)
|
|||||||
if (bemenu && bemenu->LockLooper()) {
|
if (bemenu && bemenu->LockLooper()) {
|
||||||
bemenu->ConvertFromScreen(&location);
|
bemenu->ConvertFromScreen(&location);
|
||||||
if (bemenu->Frame().Contains(location))
|
if (bemenu->Frame().Contains(location))
|
||||||
returnvalue = false;
|
endMenu = false;
|
||||||
|
|
||||||
bemenu->UnlockLooper();
|
bemenu->UnlockLooper();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (returnvalue && expando) {
|
if (endMenu && expando) {
|
||||||
expando->ConvertFromScreen(&location);
|
expando->ConvertFromScreen(&location);
|
||||||
TTeamMenuItem *item = expando->ItemAtPoint(location);
|
BMenuItem *item = expando->TeamItemAtPoint(location);
|
||||||
if (item)
|
if (item)
|
||||||
returnvalue = false;
|
endMenu = false;
|
||||||
}
|
}
|
||||||
barview->UnlockLooper();
|
barview->UnlockLooper();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
menu->UnlockLooper();
|
menu->UnlockLooper();
|
||||||
return returnvalue;
|
return endMenu;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -278,8 +278,7 @@ TExpandoMenuBar::MessageReceived(BMessage *message)
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
TShowHideMenuItem::TeamShowHideCommon(B_BRING_TO_FRONT,
|
TShowHideMenuItem::TeamShowHideCommon(B_BRING_TO_FRONT,
|
||||||
item->Teams(),
|
item->Teams(), item->Menu()->ConvertToScreen(item->Frame()),
|
||||||
item->Menu()->ConvertToScreen(item->Frame()),
|
|
||||||
true);
|
true);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@@ -305,9 +304,9 @@ TExpandoMenuBar::MouseDown(BPoint where)
|
|||||||
&& (modifiers & B_OPTION_KEY) != 0
|
&& (modifiers & B_OPTION_KEY) != 0
|
||||||
&& (modifiers & B_SHIFT_KEY) != 0
|
&& (modifiers & B_SHIFT_KEY) != 0
|
||||||
&& !fBarView->Dragging()) {
|
&& !fBarView->Dragging()) {
|
||||||
|
TTeamMenuItem *item = TeamItemAtPoint(where);
|
||||||
|
|
||||||
TTeamMenuItem *item = ItemAtPoint(where);
|
if (item != NULL) {
|
||||||
if (item) {
|
|
||||||
const BList *teams = item->Teams();
|
const BList *teams = item->Teams();
|
||||||
int32 teamCount = teams->CountItems();
|
int32 teamCount = teams->CountItems();
|
||||||
|
|
||||||
@@ -325,8 +324,6 @@ TExpandoMenuBar::MouseDown(BPoint where)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const int32 count = CountItems();
|
|
||||||
|
|
||||||
// This feature is broken because the menu bar never receives
|
// This feature is broken because the menu bar never receives
|
||||||
// the second click
|
// the second click
|
||||||
#ifdef DOUBLECLICKBRINGSTOFRONT
|
#ifdef DOUBLECLICKBRINGSTOFRONT
|
||||||
@@ -358,34 +355,22 @@ TExpandoMenuBar::MouseDown(BPoint where)
|
|||||||
message->FindInt32("modifiers", &modifiers);
|
message->FindInt32("modifiers", &modifiers);
|
||||||
if ((modifiers & B_CONTROL_KEY) != 0
|
if ((modifiers & B_CONTROL_KEY) != 0
|
||||||
&& ! fBarView->Dragging()) {
|
&& ! fBarView->Dragging()) {
|
||||||
int32 lastApp = -1;
|
TTeamMenuItem *item = TeamItemAtPoint(where);
|
||||||
|
if (item != NULL) {
|
||||||
// find the clicked item
|
|
||||||
for (int32 i = fFirstApp; i < count; i++) {
|
|
||||||
const TTeamMenuItem *item = (TTeamMenuItem *)ItemAt(i);
|
|
||||||
|
|
||||||
// check if this item is really a team item (what a cruel way...)
|
|
||||||
// "lastApp" will always point to the last application in
|
|
||||||
// the list - the other entries might be windows (due to the team expander)
|
|
||||||
if (item->Submenu())
|
|
||||||
lastApp = i;
|
|
||||||
|
|
||||||
if (item->Frame().Contains(where)) {
|
|
||||||
// show/hide item's teams
|
// show/hide item's teams
|
||||||
BMessage showMessage((modifiers & B_SHIFT_KEY) != 0
|
BMessage showMessage((modifiers & B_SHIFT_KEY) != 0
|
||||||
? M_MINIMIZE_TEAM : M_BRING_TEAM_TO_FRONT);
|
? M_MINIMIZE_TEAM : M_BRING_TEAM_TO_FRONT);
|
||||||
showMessage.AddInt32("itemIndex", lastApp);
|
showMessage.AddInt32("itemIndex", IndexOf(item));
|
||||||
Window()->PostMessage(&showMessage, this);
|
Window()->PostMessage(&showMessage, this);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
// Check the bounds of the expand Team icon
|
// Check the bounds of the expand Team icon
|
||||||
if (fShowTeamExpander && fVertical && !fBarView->Dragging()) {
|
if (fShowTeamExpander && fVertical && !fBarView->Dragging()) {
|
||||||
TTeamMenuItem *item = ItemAtPoint(where);
|
TTeamMenuItem *item = TeamItemAtPoint(where);
|
||||||
if (item->Submenu()) {
|
if (item != NULL) {
|
||||||
BRect expanderRect = item->ExpanderBounds();
|
BRect expanderRect = item->ExpanderBounds();
|
||||||
if (expanderRect.Contains(where)) {
|
if (expanderRect.Contains(where)) {
|
||||||
// Let the update thread wait...
|
// Let the update thread wait...
|
||||||
@@ -429,7 +414,7 @@ TExpandoMenuBar::MouseMoved(BPoint where, uint32 code, const BMessage *message)
|
|||||||
|
|
||||||
case B_EXITED_VIEW:
|
case B_EXITED_VIEW:
|
||||||
if (fBarView->Dragging() && buttons != 0) {
|
if (fBarView->Dragging() && buttons != 0) {
|
||||||
if (!ItemAtPoint(where)
|
if (!TeamItemAtPoint(where)
|
||||||
&& !InBeMenu(where)
|
&& !InBeMenu(where)
|
||||||
&& (fSeparatorItem && !fSeparatorItem->Frame().Contains(where))
|
&& (fSeparatorItem && !fSeparatorItem->Frame().Contains(where))
|
||||||
&& !Frame().Contains(where))
|
&& !Frame().Contains(where))
|
||||||
@@ -461,17 +446,37 @@ TExpandoMenuBar::InBeMenu(BPoint loc) const
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/** Returns the team menu item that belongs to the item under the
|
||||||
|
* specified \a point.
|
||||||
|
* If \a _item is given, it will return the exact menu item under
|
||||||
|
* that point (which might be a window item when the expander is on).
|
||||||
|
*/
|
||||||
|
|
||||||
TTeamMenuItem *
|
TTeamMenuItem *
|
||||||
TExpandoMenuBar::ItemAtPoint(BPoint point)
|
TExpandoMenuBar::TeamItemAtPoint(BPoint point, BMenuItem **_item)
|
||||||
{
|
{
|
||||||
TTeamMenuItem *item = NULL;
|
TTeamMenuItem *lastApp = NULL;
|
||||||
int32 count = CountItems();
|
int32 count = CountItems();
|
||||||
|
|
||||||
for (int32 i = fFirstApp; i < count; i++) {
|
for (int32 i = fFirstApp; i < count; i++) {
|
||||||
item = (TTeamMenuItem *)ItemAt(i);
|
BMenuItem *item = ItemAt(i);
|
||||||
if (item && item->Frame().Contains(point))
|
|
||||||
return item;
|
if (dynamic_cast<TTeamMenuItem *>(item) != NULL)
|
||||||
|
lastApp = (TTeamMenuItem *)item;
|
||||||
|
|
||||||
|
if (item && item->Frame().Contains(point)) {
|
||||||
|
if (_item != NULL)
|
||||||
|
*_item = item;
|
||||||
|
|
||||||
|
return lastApp;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// no item found
|
||||||
|
|
||||||
|
if (_item != NULL)
|
||||||
|
*_item = NULL;
|
||||||
|
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -31,8 +31,8 @@ of Be Incorporated in the United States and other countries. Other brand product
|
|||||||
names are registered trademarks or trademarks of their respective holders.
|
names are registered trademarks or trademarks of their respective holders.
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
*/
|
*/
|
||||||
#ifndef EXPANDOMENUBAR_H
|
#ifndef EXPANDO_MENU_BAR_H
|
||||||
#define EXPANDOMENUBAR_H
|
#define EXPANDO_MENU_BAR_H
|
||||||
|
|
||||||
// application list
|
// application list
|
||||||
// top level at window
|
// top level at window
|
||||||
@@ -70,8 +70,8 @@ class TExpandoMenuBar : public BMenuBar {
|
|||||||
virtual void Draw(BRect update);
|
virtual void Draw(BRect update);
|
||||||
virtual void DrawBackground(BRect update);
|
virtual void DrawBackground(BRect update);
|
||||||
|
|
||||||
|
TTeamMenuItem *TeamItemAtPoint(BPoint location, BMenuItem **_item = NULL);
|
||||||
bool InBeMenu(BPoint) const;
|
bool InBeMenu(BPoint) const;
|
||||||
TTeamMenuItem *ItemAtPoint(BPoint loc);
|
|
||||||
|
|
||||||
void CheckItemSizes(int32 delta);
|
void CheckItemSizes(int32 delta);
|
||||||
|
|
||||||
@@ -113,4 +113,4 @@ class TExpandoMenuBar : public BMenuBar {
|
|||||||
static BLocker sMonLocker;
|
static BLocker sMonLocker;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif /* EXPANDOMENUBAR_H */
|
#endif /* EXPANDO_MENU_BAR_H */
|
||||||
|
|||||||
Reference in New Issue
Block a user