xref: /haiku/src/apps/deskbar/DeskbarMenu.cpp (revision ac121994b122349558d8621012759d23c8609c8d)
1323b6546SOliver Tappe /*
2323b6546SOliver Tappe Open Tracker License
3323b6546SOliver Tappe 
4323b6546SOliver Tappe Terms and Conditions
5323b6546SOliver Tappe 
6323b6546SOliver Tappe Copyright (c) 1991-2000, Be Incorporated. All rights reserved.
7323b6546SOliver Tappe 
8323b6546SOliver Tappe Permission is hereby granted, free of charge, to any person obtaining a copy of
9323b6546SOliver Tappe this software and associated documentation files (the "Software"), to deal in
10323b6546SOliver Tappe the Software without restriction, including without limitation the rights to
11323b6546SOliver Tappe use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
12323b6546SOliver Tappe of the Software, and to permit persons to whom the Software is furnished to do
13323b6546SOliver Tappe so, subject to the following conditions:
14323b6546SOliver Tappe 
15323b6546SOliver Tappe The above copyright notice and this permission notice applies to all licensees
16323b6546SOliver Tappe and shall be included in all copies or substantial portions of the Software.
17323b6546SOliver Tappe 
18323b6546SOliver Tappe THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19323b6546SOliver Tappe IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF TITLE, MERCHANTABILITY,
20323b6546SOliver Tappe FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
21323b6546SOliver Tappe BE INCORPORATED BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
22323b6546SOliver Tappe AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF, OR IN CONNECTION
23323b6546SOliver Tappe WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24323b6546SOliver Tappe 
25323b6546SOliver Tappe Except as contained in this notice, the name of Be Incorporated shall not be
26323b6546SOliver Tappe used in advertising or otherwise to promote the sale, use or other dealings in
27323b6546SOliver Tappe this Software without prior written authorization from Be Incorporated.
28323b6546SOliver Tappe 
29323b6546SOliver Tappe Tracker(TM), Be(R), BeOS(R), and BeIA(TM) are trademarks or registered
30323b6546SOliver Tappe trademarks of Be Incorporated in the United States and other countries. Other
31323b6546SOliver Tappe brand product names are registered trademarks or trademarks of their respective
32323b6546SOliver Tappe holders.
33323b6546SOliver Tappe All rights reserved.
34323b6546SOliver Tappe */
35323b6546SOliver Tappe 
361cd61330SJohn Scipione 
371cd61330SJohn Scipione #include "DeskbarMenu.h"
381cd61330SJohn Scipione 
39323b6546SOliver Tappe #include <Debug.h>
40323b6546SOliver Tappe #include <Bitmap.h>
41323b6546SOliver Tappe #include <Catalog.h>
42323b6546SOliver Tappe #include <Dragger.h>
43323b6546SOliver Tappe #include <Locale.h>
44323b6546SOliver Tappe #include <Menu.h>
45323b6546SOliver Tappe #include <MenuItem.h>
46323b6546SOliver Tappe #include <Roster.h>
47323b6546SOliver Tappe 
48323b6546SOliver Tappe #include "BarApp.h"
49323b6546SOliver Tappe #include "BarView.h"
50323b6546SOliver Tappe #include "DeskbarUtils.h"
51323b6546SOliver Tappe #include "IconMenuItem.h"
52323b6546SOliver Tappe #include "MountMenu.h"
53323b6546SOliver Tappe #include "RecentItems.h"
54323b6546SOliver Tappe #include "StatusView.h"
55039f5926SJohn Scipione 
56323b6546SOliver Tappe #include "tracker_private.h"
57323b6546SOliver Tappe 
58546208a5SOliver Tappe #undef B_TRANSLATION_CONTEXT
59546208a5SOliver Tappe #define B_TRANSLATION_CONTEXT "DeskbarMenu"
60323b6546SOliver Tappe 
61323b6546SOliver Tappe #define ROSTER_SIG "application/x-vnd.Be-ROST"
62323b6546SOliver Tappe 
63323b6546SOliver Tappe #ifdef MOUNT_MENU_IN_DESKBAR
64323b6546SOliver Tappe class DeskbarMountMenu : public BPrivate::MountMenu {
65323b6546SOliver Tappe public:
66323b6546SOliver Tappe 	DeskbarMountMenu(const char* name);
67323b6546SOliver Tappe 	virtual bool AddDynamicItem(add_state s);
68323b6546SOliver Tappe };
69088a9620SJohn Scipione #endif	// MOUNT_MENU_IN_DESKBAR
70323b6546SOliver Tappe 
71323b6546SOliver Tappe //#define SHOW_RECENT_FIND_ITEMS
72323b6546SOliver Tappe 
73323b6546SOliver Tappe namespace BPrivate {
74323b6546SOliver Tappe 	BMenu* TrackerBuildRecentFindItemsMenu(const char*);
75323b6546SOliver Tappe }
76323b6546SOliver Tappe 
77323b6546SOliver Tappe using namespace BPrivate;
78323b6546SOliver Tappe 
79323b6546SOliver Tappe 
80088a9620SJohn Scipione //	#pragma mark - TDeskbarMenu
81323b6546SOliver Tappe 
82323b6546SOliver Tappe 
TDeskbarMenu(TBarView * barView)83323b6546SOliver Tappe TDeskbarMenu::TDeskbarMenu(TBarView* barView)
84fe624b39SJohn Scipione 	:
85fe624b39SJohn Scipione 	BNavMenu("DeskbarMenu", B_REFS_RECEIVED, DefaultTarget()),
86323b6546SOliver Tappe 	fAddState(kStart),
87323b6546SOliver Tappe 	fBarView(barView)
88323b6546SOliver Tappe {
89323b6546SOliver Tappe }
90323b6546SOliver Tappe 
91323b6546SOliver Tappe 
92323b6546SOliver Tappe void
AttachedToWindow()93323b6546SOliver Tappe TDeskbarMenu::AttachedToWindow()
94323b6546SOliver Tappe {
95088a9620SJohn Scipione 	if (fBarView != NULL && fBarView->LockLooper()) {
96323b6546SOliver Tappe 		if (fBarView->Dragging()) {
97323b6546SOliver Tappe 			SetTypesList(fBarView->CachedTypesList());
98323b6546SOliver Tappe 			SetTarget(BMessenger(fBarView));
99323b6546SOliver Tappe 			SetTrackingHookDeep(this, fBarView->MenuTrackingHook,
100323b6546SOliver Tappe 				fBarView->GetTrackingHookData());
101323b6546SOliver Tappe 			fBarView->DragStart();
102323b6546SOliver Tappe 		} else {
103323b6546SOliver Tappe 			SetTypesList(NULL);
104323b6546SOliver Tappe 			SetTarget(DefaultTarget());
105323b6546SOliver Tappe 			SetTrackingHookDeep(this, NULL, NULL);
106323b6546SOliver Tappe 		}
107323b6546SOliver Tappe 
108323b6546SOliver Tappe 		fBarView->UnlockLooper();
109323b6546SOliver Tappe 	}
110323b6546SOliver Tappe 
111323b6546SOliver Tappe 	BNavMenu::AttachedToWindow();
112323b6546SOliver Tappe }
113323b6546SOliver Tappe 
114323b6546SOliver Tappe 
115323b6546SOliver Tappe void
DetachedFromWindow()116323b6546SOliver Tappe TDeskbarMenu::DetachedFromWindow()
117323b6546SOliver Tappe {
118088a9620SJohn Scipione 	if (fBarView != NULL) {
119323b6546SOliver Tappe 		BLooper* looper = fBarView->Looper();
120088a9620SJohn Scipione 		if (looper != NULL && looper->Lock()) {
121323b6546SOliver Tappe 			fBarView->DragStop();
122323b6546SOliver Tappe 			looper->Unlock();
123323b6546SOliver Tappe 		}
124323b6546SOliver Tappe 	}
125323b6546SOliver Tappe 
126323b6546SOliver Tappe 	// don't call BNavMenu::DetachedFromWindow
127323b6546SOliver Tappe 	// it sets the TypesList to NULL
128323b6546SOliver Tappe 	BMenu::DetachedFromWindow();
129323b6546SOliver Tappe }
130323b6546SOliver Tappe 
131323b6546SOliver Tappe 
132323b6546SOliver Tappe bool
StartBuildingItemList()133323b6546SOliver Tappe TDeskbarMenu::StartBuildingItemList()
134323b6546SOliver Tappe {
135323b6546SOliver Tappe 	RemoveItems(0, CountItems(), true);
136323b6546SOliver Tappe 	fAddState = kStart;
137323b6546SOliver Tappe 	return BNavMenu::StartBuildingItemList();
138323b6546SOliver Tappe }
139323b6546SOliver Tappe 
140323b6546SOliver Tappe 
141323b6546SOliver Tappe void
DoneBuildingItemList()142323b6546SOliver Tappe TDeskbarMenu::DoneBuildingItemList()
143323b6546SOliver Tappe {
144323b6546SOliver Tappe 	if (fItemList->CountItems() <= 0) {
145323b6546SOliver Tappe 		BMenuItem* item
146323b6546SOliver Tappe 			= new BMenuItem(B_TRANSLATE("<Deskbar folder is empty>"), 0);
147323b6546SOliver Tappe 		item->SetEnabled(false);
148323b6546SOliver Tappe 		AddItem(item);
149323b6546SOliver Tappe 	} else
150323b6546SOliver Tappe 		BNavMenu::DoneBuildingItemList();
151323b6546SOliver Tappe }
152323b6546SOliver Tappe 
153323b6546SOliver Tappe 
154323b6546SOliver Tappe bool
AddNextItem()155323b6546SOliver Tappe TDeskbarMenu::AddNextItem()
156323b6546SOliver Tappe {
157323b6546SOliver Tappe 	if (fAddState == kStart)
158323b6546SOliver Tappe 		return AddStandardDeskbarMenuItems();
159323b6546SOliver Tappe 
160323b6546SOliver Tappe 	TrackingHookData* data = fBarView->GetTrackingHookData();
161323b6546SOliver Tappe 	if (fAddState == kAddingRecents) {
162323b6546SOliver Tappe 		static const char* recentTitle[] = {
163323b6546SOliver Tappe 			B_TRANSLATE_MARK("Recent documents"),
164323b6546SOliver Tappe 			B_TRANSLATE_MARK("Recent folders"),
165323b6546SOliver Tappe 			B_TRANSLATE_MARK("Recent applications")};
166323b6546SOliver Tappe 		const int recentType[] = {kRecentDocuments, kRecentFolders,
167323b6546SOliver Tappe 			kRecentApplications};
168323b6546SOliver Tappe 		const int recentTypes = 3;
169323b6546SOliver Tappe 		TRecentsMenu* recentItem[recentTypes];
170323b6546SOliver Tappe 
171323b6546SOliver Tappe 		bool enabled = false;
172323b6546SOliver Tappe 
173323b6546SOliver Tappe 		for (int i = 0; i < recentTypes; i++) {
174323b6546SOliver Tappe 			recentItem[i]
175323b6546SOliver Tappe 				= new TRecentsMenu(B_TRANSLATE_NOCOLLECT(recentTitle[i]),
176323b6546SOliver Tappe 					fBarView, recentType[i]);
177323b6546SOliver Tappe 
178323b6546SOliver Tappe 			if (recentItem[i])
179323b6546SOliver Tappe 				enabled |= recentItem[i]->RecentsEnabled();
180323b6546SOliver Tappe 		}
181323b6546SOliver Tappe 		if (enabled) {
182323b6546SOliver Tappe 			AddSeparatorItem();
183323b6546SOliver Tappe 
184323b6546SOliver Tappe 			for (int i = 0; i < recentTypes; i++) {
185323b6546SOliver Tappe 				if (!recentItem[i])
186323b6546SOliver Tappe 					continue;
187323b6546SOliver Tappe 
188323b6546SOliver Tappe 				if (recentItem[i]->RecentsEnabled()) {
189323b6546SOliver Tappe 					recentItem[i]->SetTypesList(TypesList());
190323b6546SOliver Tappe 					recentItem[i]->SetTarget(Target());
191323b6546SOliver Tappe 					AddItem(recentItem[i]);
192323b6546SOliver Tappe 				}
193323b6546SOliver Tappe 
194323b6546SOliver Tappe 				if (data && fBarView && fBarView->Dragging()) {
195323b6546SOliver Tappe 					recentItem[i]->InitTrackingHook(data->fTrackingHook,
196323b6546SOliver Tappe 						&data->fTarget, data->fDragMessage);
197323b6546SOliver Tappe 				}
198323b6546SOliver Tappe 			}
19980d8697cSMurai Takashi 		} else {
20080d8697cSMurai Takashi 			for (int i = 0; i < recentTypes; i++)
20180d8697cSMurai Takashi 				delete recentItem[i];
202323b6546SOliver Tappe 		}
203323b6546SOliver Tappe 
204323b6546SOliver Tappe 		AddSeparatorItem();
205323b6546SOliver Tappe 		fAddState = kAddingDeskbarMenu;
206323b6546SOliver Tappe 		return true;
207323b6546SOliver Tappe 	}
208323b6546SOliver Tappe 
209323b6546SOliver Tappe 	if (fAddState == kAddingDeskbarMenu) {
210323b6546SOliver Tappe 		// keep reentering and adding items
211323b6546SOliver Tappe 		// until this returns false
212323b6546SOliver Tappe 		bool done = BNavMenu::AddNextItem();
213323b6546SOliver Tappe 		BMenuItem* item = ItemAt(CountItems() - 1);
214323b6546SOliver Tappe 		if (item) {
215323b6546SOliver Tappe 			BNavMenu* menu = dynamic_cast<BNavMenu*>(item->Menu());
216323b6546SOliver Tappe 			if (menu) {
217323b6546SOliver Tappe 				if (data && fBarView->Dragging()) {
218323b6546SOliver Tappe 					menu->InitTrackingHook(data->fTrackingHook,
219323b6546SOliver Tappe 						&data->fTarget, data->fDragMessage);
220323b6546SOliver Tappe 				} else
221323b6546SOliver Tappe 					menu->InitTrackingHook(0, NULL, NULL);
222323b6546SOliver Tappe 			}
223323b6546SOliver Tappe 		}
224323b6546SOliver Tappe 
225323b6546SOliver Tappe 		if (!done)
226323b6546SOliver Tappe 			fAddState = kDone;
227323b6546SOliver Tappe 		return done;
228323b6546SOliver Tappe 	}
229323b6546SOliver Tappe 
230323b6546SOliver Tappe 	return false;
231323b6546SOliver Tappe }
232323b6546SOliver Tappe 
233323b6546SOliver Tappe 
234323b6546SOliver Tappe bool
AddStandardDeskbarMenuItems()235323b6546SOliver Tappe TDeskbarMenu::AddStandardDeskbarMenuItems()
236323b6546SOliver Tappe {
237323b6546SOliver Tappe 	bool dragging = false;
238323b6546SOliver Tappe 	if (fBarView)
239323b6546SOliver Tappe 		dragging = fBarView->Dragging();
240323b6546SOliver Tappe 
241323b6546SOliver Tappe 	BMenuItem* item;
242323b6546SOliver Tappe 
243323b6546SOliver Tappe // One of them is used if HAIKU_DISTRO_COMPATIBILITY_OFFICIAL, and the other if
244323b6546SOliver Tappe // not. However, we want both of them to end up in the catalog, so we have to
245323b6546SOliver Tappe // make them visible to collectcatkeys in either case.
246028ad031SAdrien Destugues - PulkoMandy B_TRANSLATE_MARK_VOID("About Haiku")
247028ad031SAdrien Destugues - PulkoMandy B_TRANSLATE_MARK_VOID("About this system")
248323b6546SOliver Tappe 
249323b6546SOliver Tappe 	item = new BMenuItem(
250323b6546SOliver Tappe #ifdef HAIKU_DISTRO_COMPATIBILITY_OFFICIAL
251028ad031SAdrien Destugues - PulkoMandy 	B_TRANSLATE_NOCOLLECT("About Haiku")
252323b6546SOliver Tappe #else
253028ad031SAdrien Destugues - PulkoMandy 	B_TRANSLATE_NOCOLLECT("About this system")
254323b6546SOliver Tappe #endif
255323b6546SOliver Tappe 		, new BMessage(kShowSplash));
256323b6546SOliver Tappe 	item->SetEnabled(!dragging);
257323b6546SOliver Tappe 	AddItem(item);
258323b6546SOliver Tappe 
259323b6546SOliver Tappe 	static const char* kFindMenuItemStr
260323b6546SOliver Tappe 		= B_TRANSLATE_MARK("Find" B_UTF8_ELLIPSIS);
261323b6546SOliver Tappe 
262323b6546SOliver Tappe #ifdef SHOW_RECENT_FIND_ITEMS
263323b6546SOliver Tappe 	item = new BMenuItem(
264323b6546SOliver Tappe 		TrackerBuildRecentFindItemsMenu(kFindMenuItemStr),
265323b6546SOliver Tappe 		new BMessage(kFindButton));
266323b6546SOliver Tappe #else
267323b6546SOliver Tappe 	item = new BMenuItem(B_TRANSLATE_NOCOLLECT(kFindMenuItemStr),
268323b6546SOliver Tappe 		new BMessage(kFindButton));
269323b6546SOliver Tappe #endif
270323b6546SOliver Tappe 	item->SetEnabled(!dragging);
271323b6546SOliver Tappe 	AddItem(item);
272323b6546SOliver Tappe 
273323b6546SOliver Tappe 	item = new BMenuItem(B_TRANSLATE("Show replicants"),
274323b6546SOliver Tappe 		new BMessage(kToggleDraggers));
275323b6546SOliver Tappe 	item->SetEnabled(!dragging);
276323b6546SOliver Tappe 	item->SetMarked(BDragger::AreDraggersDrawn());
277323b6546SOliver Tappe 	AddItem(item);
278323b6546SOliver Tappe 
279323b6546SOliver Tappe 	static const char* kMountMenuStr = B_TRANSLATE_MARK("Mount");
280323b6546SOliver Tappe 
281323b6546SOliver Tappe #ifdef MOUNT_MENU_IN_DESKBAR
282323b6546SOliver Tappe 	DeskbarMountMenu* mountMenu = new DeskbarMountMenu(
283323b6546SOliver Tappe 		B_TRANSLATE_NOCOLLECT(kMountMenuStr));
284323b6546SOliver Tappe 	mountMenu->SetEnabled(!dragging);
285323b6546SOliver Tappe 	AddItem(mountMenu);
286323b6546SOliver Tappe #endif
287323b6546SOliver Tappe 
288323b6546SOliver Tappe 	item = new BMenuItem(B_TRANSLATE("Deskbar preferences" B_UTF8_ELLIPSIS),
289323b6546SOliver Tappe 		new BMessage(kConfigShow));
290323b6546SOliver Tappe 	item->SetTarget(be_app);
291323b6546SOliver Tappe 	AddItem(item);
292323b6546SOliver Tappe 
293323b6546SOliver Tappe 	AddSeparatorItem();
294323b6546SOliver Tappe 
295323b6546SOliver Tappe 	BMenu* shutdownMenu = new BMenu(B_TRANSLATE("Shutdown" B_UTF8_ELLIPSIS));
296323b6546SOliver Tappe 
297*79ca65acSPanagiotis Vasilopoulos 	item = new BMenuItem(B_TRANSLATE("Power off"),
298*79ca65acSPanagiotis Vasilopoulos 		new BMessage(kShutdownSystem));
299*79ca65acSPanagiotis Vasilopoulos 	item->SetEnabled(!dragging);
300*79ca65acSPanagiotis Vasilopoulos 	shutdownMenu->AddItem(item);
301*79ca65acSPanagiotis Vasilopoulos 
302323b6546SOliver Tappe 	item = new BMenuItem(B_TRANSLATE("Restart system"),
303323b6546SOliver Tappe 		new BMessage(kRebootSystem));
304323b6546SOliver Tappe 	item->SetEnabled(!dragging);
305323b6546SOliver Tappe 	shutdownMenu->AddItem(item);
306323b6546SOliver Tappe 
307028ad031SAdrien Destugues - PulkoMandy 	B_TRANSLATE_MARK_VOID("Suspend");
308323b6546SOliver Tappe 
309323b6546SOliver Tappe #ifdef APM_SUPPORT
310323b6546SOliver Tappe 	if (_kapm_control_(APM_CHECK_ENABLED) == B_OK) {
311028ad031SAdrien Destugues - PulkoMandy 		item = new BMenuItem(B_TRANSLATE_NOCOLLECT("Suspend"),
312323b6546SOliver Tappe 			new BMessage(kSuspendSystem));
313323b6546SOliver Tappe 		item->SetEnabled(!dragging);
314323b6546SOliver Tappe 		shutdownMenu->AddItem(item);
315323b6546SOliver Tappe 	}
316323b6546SOliver Tappe #endif
317323b6546SOliver Tappe 
318323b6546SOliver Tappe 	shutdownMenu->SetTargetForItems(be_app);
319*79ca65acSPanagiotis Vasilopoulos 
320323b6546SOliver Tappe 	BMessage* message = new BMessage(kShutdownSystem);
321323b6546SOliver Tappe 	message->AddBool("confirm", true);
322323b6546SOliver Tappe 	AddItem(new BMenuItem(shutdownMenu, message));
323323b6546SOliver Tappe 
324323b6546SOliver Tappe 	fAddState = kAddingRecents;
325323b6546SOliver Tappe 
326323b6546SOliver Tappe 	return true;
327323b6546SOliver Tappe }
328323b6546SOliver Tappe 
329323b6546SOliver Tappe 
330323b6546SOliver Tappe void
ClearMenuBuildingState()331323b6546SOliver Tappe TDeskbarMenu::ClearMenuBuildingState()
332323b6546SOliver Tappe {
333323b6546SOliver Tappe 	fAddState = kDone;
334323b6546SOliver Tappe 	fMenuBuilt = false;
335323b6546SOliver Tappe 		// force the menu to get rebuilt each time
336323b6546SOliver Tappe 	BNavMenu::ClearMenuBuildingState();
337323b6546SOliver Tappe }
338323b6546SOliver Tappe 
339323b6546SOliver Tappe 
340323b6546SOliver Tappe void
ResetTargets()341323b6546SOliver Tappe TDeskbarMenu::ResetTargets()
342323b6546SOliver Tappe {
343323b6546SOliver Tappe 	// This method does not recurse into submenus
344323b6546SOliver Tappe 	// and does not affect menu items in submenus.
345323b6546SOliver Tappe 	// (e.g. "Restart System" and "Power Off")
346323b6546SOliver Tappe 
347323b6546SOliver Tappe 	BNavMenu::ResetTargets();
348323b6546SOliver Tappe 
349323b6546SOliver Tappe 	// if we are dragging, set the target to whatever was set
350323b6546SOliver Tappe 	// else set it to the default (Tracker)
351323b6546SOliver Tappe 	if (!fBarView->Dragging())
352323b6546SOliver Tappe 		SetTarget(DefaultTarget());
353323b6546SOliver Tappe 
354323b6546SOliver Tappe 	// now set the target for the menuitems to the currently
355323b6546SOliver Tappe 	// set target, which may or may not be tracker
356323b6546SOliver Tappe 	SetTargetForItems(Target());
357323b6546SOliver Tappe 
358323b6546SOliver Tappe 	for (int32 i = 0; ; i++) {
359323b6546SOliver Tappe 		BMenuItem* item = ItemAt(i);
360323b6546SOliver Tappe 		if (item == NULL)
361323b6546SOliver Tappe 			break;
362323b6546SOliver Tappe 
363323b6546SOliver Tappe 		if (item->Message()) {
364323b6546SOliver Tappe 			switch (item->Message()->what) {
365323b6546SOliver Tappe 				case kFindButton:
366323b6546SOliver Tappe 					item->SetTarget(BMessenger(kTrackerSignature));
367323b6546SOliver Tappe 					break;
368323b6546SOliver Tappe 
369323b6546SOliver Tappe 				case kShowSplash:
370323b6546SOliver Tappe 				case kToggleDraggers:
371323b6546SOliver Tappe 				case kConfigShow:
372cb422386SJohn Scipione 				case kConfigQuit:
373323b6546SOliver Tappe 				case kAlwaysTop:
374573f748cSJohn Scipione 				case kExpandNewTeams:
375573f748cSJohn Scipione 				case kHideLabels:
376573f748cSJohn Scipione 				case kResizeTeamIcons:
377573f748cSJohn Scipione 				case kSortRunningApps:
378573f748cSJohn Scipione 				case kTrackerFirst:
379323b6546SOliver Tappe 				case kRebootSystem:
380323b6546SOliver Tappe 				case kSuspendSystem:
381323b6546SOliver Tappe 				case kShutdownSystem:
382c0dc265cSJohn Scipione 				case kRealignReplicants:
383573f748cSJohn Scipione 				case kShowHideTime:
3843cf2d117SJohn Scipione 				case kShowSeconds:
3853cf2d117SJohn Scipione 				case kShowDayOfWeek:
38631c0024dSJohn Scipione 				case kShowTimeZone:
38731c0024dSJohn Scipione 				case kGetClockSettings:
38831c0024dSJohn Scipione 					item->SetTarget(be_app);
389573f748cSJohn Scipione 					break;
390323b6546SOliver Tappe 			}
391323b6546SOliver Tappe 		}
392323b6546SOliver Tappe 	}
393323b6546SOliver Tappe }
394323b6546SOliver Tappe 
395323b6546SOliver Tappe 
396323b6546SOliver Tappe BPoint
ScreenLocation()397323b6546SOliver Tappe TDeskbarMenu::ScreenLocation()
398323b6546SOliver Tappe {
399323b6546SOliver Tappe 	bool vertical = fBarView->Vertical();
4000d2645e4SJohn Scipione 	int32 expando = fBarView->ExpandoState();
4010d2645e4SJohn Scipione 	bool left = fBarView->Left();
402323b6546SOliver Tappe 	BPoint point;
403323b6546SOliver Tappe 
404323b6546SOliver Tappe 	BRect rect = Supermenu()->Bounds();
405323b6546SOliver Tappe 	Supermenu()->ConvertToScreen(&rect);
406323b6546SOliver Tappe 
4070d2645e4SJohn Scipione 	if (vertical && expando && left) {
408323b6546SOliver Tappe 		PRINT(("Left\n"));
409323b6546SOliver Tappe 		point = rect.RightTop() + BPoint(0, 3);
4100d2645e4SJohn Scipione 	} else if (vertical && expando && !left) {
411323b6546SOliver Tappe 		PRINT(("Right\n"));
412323b6546SOliver Tappe 		point = rect.LeftTop() - BPoint(Bounds().Width(), 0) + BPoint(0, 3);
413323b6546SOliver Tappe 	} else
414323b6546SOliver Tappe 		point = BMenu::ScreenLocation();
415323b6546SOliver Tappe 
416323b6546SOliver Tappe 	return point;
417323b6546SOliver Tappe }
418323b6546SOliver Tappe 
419323b6546SOliver Tappe 
420323b6546SOliver Tappe /*static*/
421323b6546SOliver Tappe BMessenger
DefaultTarget()422323b6546SOliver Tappe TDeskbarMenu::DefaultTarget()
423323b6546SOliver Tappe {
424323b6546SOliver Tappe 	// if Tracker is not available we target the BarApp
425323b6546SOliver Tappe 	BMessenger target(kTrackerSignature);
426323b6546SOliver Tappe 	if (target.IsValid())
427323b6546SOliver Tappe 		return target;
428323b6546SOliver Tappe 
429323b6546SOliver Tappe 	return BMessenger(be_app);
430323b6546SOliver Tappe }
431323b6546SOliver Tappe 
432323b6546SOliver Tappe 
433323b6546SOliver Tappe //	#pragma mark -
434323b6546SOliver Tappe 
435323b6546SOliver Tappe 
TRecentsMenu(const char * name,TBarView * bar,int32 which,const char * signature,entry_ref * appRef)436323b6546SOliver Tappe TRecentsMenu::TRecentsMenu(const char* name, TBarView* bar, int32 which,
437323b6546SOliver Tappe 		const char* signature, entry_ref* appRef)
438323b6546SOliver Tappe 	: BNavMenu(name, B_REFS_RECEIVED, TDeskbarMenu::DefaultTarget()),
439323b6546SOliver Tappe 	fWhich(which),
440323b6546SOliver Tappe 	fAppRef(NULL),
441323b6546SOliver Tappe 	fSignature(NULL),
442323b6546SOliver Tappe 	fRecentsCount(0),
443323b6546SOliver Tappe 	fRecentsEnabled(false),
444323b6546SOliver Tappe 	fItemIndex(0),
445323b6546SOliver Tappe 	fBarView(bar)
446323b6546SOliver Tappe {
447323b6546SOliver Tappe 	TBarApp* app = dynamic_cast<TBarApp*>(be_app);
448323b6546SOliver Tappe 	if (app == NULL)
449323b6546SOliver Tappe 		return;
450323b6546SOliver Tappe 
451323b6546SOliver Tappe 	switch (which) {
452323b6546SOliver Tappe 		case kRecentDocuments:
453323b6546SOliver Tappe 			fRecentsCount = app->Settings()->recentDocsCount;
454323b6546SOliver Tappe 			fRecentsEnabled = app->Settings()->recentDocsEnabled;
455323b6546SOliver Tappe 			break;
456323b6546SOliver Tappe 		case kRecentApplications:
457323b6546SOliver Tappe 			fRecentsCount = app->Settings()->recentAppsCount;
458323b6546SOliver Tappe 			fRecentsEnabled = app->Settings()->recentAppsEnabled;
459323b6546SOliver Tappe 			break;
460323b6546SOliver Tappe 		case kRecentAppDocuments:
461323b6546SOliver Tappe 			fRecentsCount = app->Settings()->recentDocsCount;
462323b6546SOliver Tappe 			fRecentsEnabled = app->Settings()->recentDocsEnabled;
463323b6546SOliver Tappe 			if (signature != NULL)
464323b6546SOliver Tappe 				fSignature = strdup(signature);
465323b6546SOliver Tappe 			if (appRef != NULL)
466323b6546SOliver Tappe 				fAppRef = new entry_ref(*appRef);
467323b6546SOliver Tappe 			break;
468323b6546SOliver Tappe 		case kRecentFolders:
469323b6546SOliver Tappe 			fRecentsCount = app->Settings()->recentFoldersCount;
470323b6546SOliver Tappe 			fRecentsEnabled = app->Settings()->recentFoldersEnabled;
471323b6546SOliver Tappe 			break;
472323b6546SOliver Tappe 	}
473323b6546SOliver Tappe }
474323b6546SOliver Tappe 
475323b6546SOliver Tappe 
~TRecentsMenu()476323b6546SOliver Tappe TRecentsMenu::~TRecentsMenu()
477323b6546SOliver Tappe {
478323b6546SOliver Tappe 	delete fAppRef;
479323b6546SOliver Tappe 	free(fSignature);
480323b6546SOliver Tappe }
481323b6546SOliver Tappe 
482323b6546SOliver Tappe 
483323b6546SOliver Tappe void
DetachedFromWindow()484323b6546SOliver Tappe TRecentsMenu::DetachedFromWindow()
485323b6546SOliver Tappe {
486323b6546SOliver Tappe 	// BNavMenu::DetachedFromWindow sets the TypesList to NULL
487323b6546SOliver Tappe 	BMenu::DetachedFromWindow();
488323b6546SOliver Tappe }
489323b6546SOliver Tappe 
490323b6546SOliver Tappe 
491323b6546SOliver Tappe bool
StartBuildingItemList()492323b6546SOliver Tappe TRecentsMenu::StartBuildingItemList()
493323b6546SOliver Tappe {
494323b6546SOliver Tappe 	RemoveItems(0, CountItems(), true);
495323b6546SOliver Tappe 
496323b6546SOliver Tappe 	// !! note: don't call inherited from here
497323b6546SOliver Tappe 	// the navref is not set for this menu
498323b6546SOliver Tappe 	// but it still needs to be a draggable navmenu
499323b6546SOliver Tappe 	// simply return true so that AddNextItem is called
500323b6546SOliver Tappe 	//
501323b6546SOliver Tappe 	// return BNavMenu::StartBuildingItemList();
502323b6546SOliver Tappe 	return true;
503323b6546SOliver Tappe }
504323b6546SOliver Tappe 
505323b6546SOliver Tappe 
506323b6546SOliver Tappe bool
AddNextItem()507323b6546SOliver Tappe TRecentsMenu::AddNextItem()
508323b6546SOliver Tappe {
509323b6546SOliver Tappe 	if (fRecentsCount > 0 && fRecentsEnabled && AddRecents(fRecentsCount))
510323b6546SOliver Tappe 		return true;
511323b6546SOliver Tappe 
512323b6546SOliver Tappe 	fItemIndex = 0;
513323b6546SOliver Tappe 	return false;
514323b6546SOliver Tappe }
515323b6546SOliver Tappe 
516323b6546SOliver Tappe 
517323b6546SOliver Tappe bool
AddRecents(int32 count)518323b6546SOliver Tappe TRecentsMenu::AddRecents(int32 count)
519323b6546SOliver Tappe {
520323b6546SOliver Tappe 	if (fItemIndex == 0) {
521323b6546SOliver Tappe 		fRecentList.MakeEmpty();
522323b6546SOliver Tappe 		BRoster roster;
523323b6546SOliver Tappe 
524323b6546SOliver Tappe 		switch (fWhich) {
525323b6546SOliver Tappe 			case kRecentDocuments:
526323b6546SOliver Tappe 				roster.GetRecentDocuments(&fRecentList, count);
527323b6546SOliver Tappe 				break;
528323b6546SOliver Tappe 			case kRecentApplications:
529323b6546SOliver Tappe 				roster.GetRecentApps(&fRecentList, count);
530323b6546SOliver Tappe 				break;
531323b6546SOliver Tappe 			case kRecentAppDocuments:
532323b6546SOliver Tappe 				roster.GetRecentDocuments(&fRecentList, count, NULL,
533323b6546SOliver Tappe 					fSignature);
534323b6546SOliver Tappe 				break;
535323b6546SOliver Tappe 			case kRecentFolders:
536323b6546SOliver Tappe 				roster.GetRecentFolders(&fRecentList, count);
537323b6546SOliver Tappe 				break;
538323b6546SOliver Tappe 			default:
539323b6546SOliver Tappe 				return false;
540323b6546SOliver Tappe 		}
541323b6546SOliver Tappe 	}
542323b6546SOliver Tappe 
543323b6546SOliver Tappe 	for (;;) {
544323b6546SOliver Tappe 		entry_ref ref;
545323b6546SOliver Tappe 		if (fRecentList.FindRef("refs", fItemIndex++, &ref) != B_OK)
546323b6546SOliver Tappe 			break;
547323b6546SOliver Tappe 
548323b6546SOliver Tappe 		if (ref.name && strlen(ref.name) > 0) {
549323b6546SOliver Tappe 			Model model(&ref, true);
550323b6546SOliver Tappe 
551323b6546SOliver Tappe 			if (fWhich != kRecentApplications) {
552323b6546SOliver Tappe 				BMessage* message = new BMessage(B_REFS_RECEIVED);
553323b6546SOliver Tappe 				if (fWhich == kRecentAppDocuments) {
554323b6546SOliver Tappe 					// add application as handler
555323b6546SOliver Tappe 					message->AddRef("handler", fAppRef);
556323b6546SOliver Tappe 				}
557323b6546SOliver Tappe 
558323b6546SOliver Tappe 				ModelMenuItem* item = BNavMenu::NewModelItem(&model,
559323b6546SOliver Tappe 					message, Target(), false, NULL, TypesList());
560323b6546SOliver Tappe 
561323b6546SOliver Tappe 				if (item)
562323b6546SOliver Tappe 					AddItem(item);
563323b6546SOliver Tappe 			} else {
564323b6546SOliver Tappe 				// The application items expand to a list of recent documents
565323b6546SOliver Tappe 				// for that application - so they must be handled extra
566323b6546SOliver Tappe 				BFile file(&ref, B_READ_ONLY);
567323b6546SOliver Tappe 				char signature[B_MIME_TYPE_LENGTH];
568323b6546SOliver Tappe 
569323b6546SOliver Tappe 				BAppFileInfo appInfo(&file);
570323b6546SOliver Tappe 				if (appInfo.InitCheck() != B_OK
571323b6546SOliver Tappe 					|| appInfo.GetSignature(signature) != B_OK)
572323b6546SOliver Tappe 					continue;
573323b6546SOliver Tappe 
574323b6546SOliver Tappe 				ModelMenuItem* item = NULL;
575323b6546SOliver Tappe 				BMessage doc;
576323b6546SOliver Tappe 				be_roster->GetRecentDocuments(&doc, 1, NULL, signature);
577323b6546SOliver Tappe 					// ToDo: check if the documents do exist at all to
578323b6546SOliver Tappe 					//		avoid the creation of the submenu.
579323b6546SOliver Tappe 
580323b6546SOliver Tappe 				if (doc.CountNames(B_REF_TYPE) > 0) {
581323b6546SOliver Tappe 					// create recents menu that will contain the recent docs of
582323b6546SOliver Tappe 					// this app
583323b6546SOliver Tappe 					TRecentsMenu* docs = new TRecentsMenu(model.Name(),
584323b6546SOliver Tappe 						fBarView, kRecentAppDocuments, signature, &ref);
585323b6546SOliver Tappe 					docs->SetTypesList(TypesList());
586323b6546SOliver Tappe 					docs->SetTarget(Target());
587323b6546SOliver Tappe 
588323b6546SOliver Tappe 					item = new ModelMenuItem(&model, docs);
589323b6546SOliver Tappe 				} else
590323b6546SOliver Tappe 					item = new ModelMenuItem(&model, model.Name(), NULL);
591323b6546SOliver Tappe 
592323b6546SOliver Tappe 				if (item) {
593323b6546SOliver Tappe 					// add refs-message so that the recent app can be launched
594323b6546SOliver Tappe 					BMessage* msg = new BMessage(B_REFS_RECEIVED);
595323b6546SOliver Tappe 					msg->AddRef("refs", &ref);
596323b6546SOliver Tappe 					item->SetMessage(msg);
597323b6546SOliver Tappe 					item->SetTarget(Target());
598323b6546SOliver Tappe 
599323b6546SOliver Tappe 					AddItem(item);
600323b6546SOliver Tappe 				}
601323b6546SOliver Tappe 			}
602323b6546SOliver Tappe 
603323b6546SOliver Tappe 			// return true so that we know to reenter this list
604323b6546SOliver Tappe 			return true;
605323b6546SOliver Tappe 		}
606323b6546SOliver Tappe 	}
607323b6546SOliver Tappe 
608323b6546SOliver Tappe 	// return false if we are done with this list
609323b6546SOliver Tappe 	return false;
610323b6546SOliver Tappe }
611323b6546SOliver Tappe 
612323b6546SOliver Tappe 
613323b6546SOliver Tappe void
DoneBuildingItemList()614323b6546SOliver Tappe TRecentsMenu::DoneBuildingItemList()
615323b6546SOliver Tappe {
616323b6546SOliver Tappe 	// !! note: don't call inherited here
617323b6546SOliver Tappe 	// the object list is not built
618323b6546SOliver Tappe 	// and this list does not need to be sorted
619323b6546SOliver Tappe 	// BNavMenu::DoneBuildingItemList();
620323b6546SOliver Tappe 
621323b6546SOliver Tappe 	if (CountItems() > 0)
622323b6546SOliver Tappe 		SetTargetForItems(Target());
623323b6546SOliver Tappe }
624323b6546SOliver Tappe 
625323b6546SOliver Tappe 
626323b6546SOliver Tappe void
ClearMenuBuildingState()627323b6546SOliver Tappe TRecentsMenu::ClearMenuBuildingState()
628323b6546SOliver Tappe {
629323b6546SOliver Tappe 	fMenuBuilt = false;
630323b6546SOliver Tappe 	BNavMenu::ClearMenuBuildingState();
631323b6546SOliver Tappe }
632323b6546SOliver Tappe 
633323b6546SOliver Tappe 
634323b6546SOliver Tappe void
ResetTargets()635323b6546SOliver Tappe TRecentsMenu::ResetTargets()
636323b6546SOliver Tappe {
637323b6546SOliver Tappe 	BNavMenu::ResetTargets();
638323b6546SOliver Tappe 
639323b6546SOliver Tappe 	// if we are dragging, set the target to whatever was set
640323b6546SOliver Tappe 	// else set it to the default (Tracker)
641323b6546SOliver Tappe 	if (!fBarView->Dragging())
642323b6546SOliver Tappe 		SetTarget(TDeskbarMenu::DefaultTarget());
643323b6546SOliver Tappe 
644323b6546SOliver Tappe 	// now set the target for the menuitems to the currently
645323b6546SOliver Tappe 	// set target, which may or may not be tracker
646323b6546SOliver Tappe 	SetTargetForItems(Target());
647323b6546SOliver Tappe }
648323b6546SOliver Tappe 
649323b6546SOliver Tappe 
650088a9620SJohn Scipione //	#pragma mark - DeskbarMountMenu
651323b6546SOliver Tappe 
652323b6546SOliver Tappe 
653323b6546SOliver Tappe #ifdef MOUNT_MENU_IN_DESKBAR
DeskbarMountMenu(const char * name)654323b6546SOliver Tappe DeskbarMountMenu::DeskbarMountMenu(const char* name)
655323b6546SOliver Tappe 	: BPrivate::MountMenu(name)
656323b6546SOliver Tappe {
657323b6546SOliver Tappe }
658323b6546SOliver Tappe 
659323b6546SOliver Tappe 
660323b6546SOliver Tappe bool
AddDynamicItem(add_state s)661323b6546SOliver Tappe DeskbarMountMenu::AddDynamicItem(add_state s)
662323b6546SOliver Tappe {
663323b6546SOliver Tappe 	BPrivate::MountMenu::AddDynamicItem(s);
664323b6546SOliver Tappe 
665323b6546SOliver Tappe 	SetTargetForItems(BMessenger(kTrackerSignature));
666323b6546SOliver Tappe 
667323b6546SOliver Tappe 	return false;
668323b6546SOliver Tappe }
669088a9620SJohn Scipione #endif	// MOUNT_MENU_IN_DESKBAR
670