1621a8324SAxel Dörfler/*
2bea2387bSAxel Dörfler * Copyright 2001-2012, Haiku.
3621a8324SAxel Dörfler * Distributed under the terms of the MIT License.
4621a8324SAxel Dörfler *
5621a8324SAxel Dörfler * Authors:
6621a8324SAxel Dörfler *		Marc Flerackers (mflerackers@androme.be)
73cead3c6SRene Gollent *		Rene Gollent (rene@gollent.com)
8c51d0337SAlexandre Deckner *		Alexandre Deckner (alex@zappotek.com)
9621a8324SAxel Dörfler */
10621a8324SAxel Dörfler
11bea2387bSAxel Dörfler
12621a8324SAxel Dörfler//!	BDragger represents a replicant "handle".
13621a8324SAxel Dörfler
14cf2aeb20SAxel Dörfler
151cbfe2efSIngo Weinhold#include <pthread.h>
1639fbf550SOliver Tappe#include <stdio.h>
1739fbf550SOliver Tappe#include <stdlib.h>
18621a8324SAxel Dörfler
19a5f7275dSStefano Ceccherini#include <Alert.h>
20a5f7275dSStefano Ceccherini#include <Beep.h>
21a5f7275dSStefano Ceccherini#include <Bitmap.h>
22a5f7275dSStefano Ceccherini#include <Dragger.h>
23a5f7275dSStefano Ceccherini#include <MenuItem.h>
24a5f7275dSStefano Ceccherini#include <Message.h>
25a5f7275dSStefano Ceccherini#include <PopUpMenu.h>
26a5f7275dSStefano Ceccherini#include <Shelf.h>
2760f75e90SOliver Tappe#include <SystemCatalog.h>
28a5f7275dSStefano Ceccherini#include <Window.h>
29a5f7275dSStefano Ceccherini
301cbfe2efSIngo Weinhold#include <AutoLocker.h>
311cbfe2efSIngo Weinhold
3239fbf550SOliver Tappe#include <AppServerLink.h>
33c51d0337SAlexandre Deckner#include <DragTrackingFilter.h>
3439fbf550SOliver Tappe#include <binary_compatibility/Interface.h>
3539fbf550SOliver Tappe#include <ServerProtocol.h>
3639fbf550SOliver Tappe#include <ViewPrivate.h>
37ac2284edSStefano Ceccherini
3839fbf550SOliver Tappe#include "ZombieReplicantView.h"
39a5f7275dSStefano Ceccherini
4060f75e90SOliver Tappeusing BPrivate::gSystemCatalog;
414115645aSSiarzhuk Zharski
42546208a5SOliver Tappe#undef B_TRANSLATION_CONTEXT
43546208a5SOliver Tappe#define B_TRANSLATION_CONTEXT "Dragger"
444115645aSSiarzhuk Zharski
454115645aSSiarzhuk Zharski#undef B_TRANSLATE
464115645aSSiarzhuk Zharski#define B_TRANSLATE(str) \
47eaa5e093SOliver Tappe	gSystemCatalog.GetString(B_TRANSLATE_MARK(str), "Dragger")
483a15790eSStefano Ceccherini
49a5f7275dSStefano Ceccherini
50bea2387bSAxel Dörflerstatic const uint32 kMsgDragStarted = 'Drgs';
51bea2387bSAxel Dörfler
52bea2387bSAxel Dörflerstatic const unsigned char kHandBitmap[] = {
533a15790eSStefano Ceccherini	255, 255,   0,   0,   0, 255, 255, 255,
543a15790eSStefano Ceccherini	255, 255,   0, 131, 131,   0, 255, 255,
553a15790eSStefano Ceccherini	  0,   0,   0,   0, 131, 131,   0,   0,
563a15790eSStefano Ceccherini	  0, 131,   0,   0, 131, 131,   0,   0,
573a15790eSStefano Ceccherini	  0, 131, 131, 131, 131, 131,   0,   0,
583a15790eSStefano Ceccherini	255,   0, 131, 131, 131, 131,   0,   0,
593a15790eSStefano Ceccherini	255, 255,   0,   0,   0,   0,   0,   0,
603a15790eSStefano Ceccherini	255, 255, 255, 255, 255, 255,   0,   0
613a15790eSStefano Ceccherini};
62a5f7275dSStefano Ceccherini
63a5f7275dSStefano Ceccherini
641cbfe2efSIngo Weinholdnamespace {
651cbfe2efSIngo Weinhold
661cbfe2efSIngo Weinholdstruct DraggerManager {
671cbfe2efSIngo Weinhold	bool	visible;
681cbfe2efSIngo Weinhold	bool	visibleInitialized;
691cbfe2efSIngo Weinhold	BList	list;
701cbfe2efSIngo Weinhold
711cbfe2efSIngo Weinhold	DraggerManager()
721cbfe2efSIngo Weinhold		:
731cbfe2efSIngo Weinhold		visible(false),
741cbfe2efSIngo Weinhold		visibleInitialized(false),
751cbfe2efSIngo Weinhold		fLock("BDragger static")
761cbfe2efSIngo Weinhold	{
771cbfe2efSIngo Weinhold	}
781cbfe2efSIngo Weinhold
791cbfe2efSIngo Weinhold	bool Lock()
801cbfe2efSIngo Weinhold	{
811cbfe2efSIngo Weinhold		return fLock.Lock();
821cbfe2efSIngo Weinhold	}
831cbfe2efSIngo Weinhold
841cbfe2efSIngo Weinhold	void Unlock()
851cbfe2efSIngo Weinhold	{
861cbfe2efSIngo Weinhold		fLock.Unlock();
871cbfe2efSIngo Weinhold	}
881cbfe2efSIngo Weinhold
891cbfe2efSIngo Weinhold	static DraggerManager* Default()
901cbfe2efSIngo Weinhold	{
911cbfe2efSIngo Weinhold		if (sDefaultInstance == NULL)
921cbfe2efSIngo Weinhold			pthread_once(&sDefaultInitOnce, &_InitSingleton);
931cbfe2efSIngo Weinhold
941cbfe2efSIngo Weinhold		return sDefaultInstance;
951cbfe2efSIngo Weinhold	}
961cbfe2efSIngo Weinhold
971cbfe2efSIngo Weinholdprivate:
981cbfe2efSIngo Weinhold	static void _InitSingleton()
991cbfe2efSIngo Weinhold	{
1001cbfe2efSIngo Weinhold		sDefaultInstance = new DraggerManager;
1011cbfe2efSIngo Weinhold	}
1021cbfe2efSIngo Weinhold
1031cbfe2efSIngo Weinholdprivate:
1041cbfe2efSIngo Weinhold	BLocker					fLock;
1051cbfe2efSIngo Weinhold
1061cbfe2efSIngo Weinhold	static pthread_once_t	sDefaultInitOnce;
1071cbfe2efSIngo Weinhold	static DraggerManager*	sDefaultInstance;
1081cbfe2efSIngo Weinhold};
1091cbfe2efSIngo Weinhold
1101cbfe2efSIngo Weinholdpthread_once_t DraggerManager::sDefaultInitOnce = PTHREAD_ONCE_INIT;
1111cbfe2efSIngo WeinholdDraggerManager* DraggerManager::sDefaultInstance = NULL;
1121cbfe2efSIngo Weinhold
1131cbfe2efSIngo Weinhold}	// unnamed namespace
1141cbfe2efSIngo Weinhold
1151cbfe2efSIngo Weinhold
11678c12508SJohn ScipioneBDragger::BDragger(BRect frame, BView* target, uint32 resizingMode,
117aabb1481SJohn Scipione	uint32 flags)
118bea2387bSAxel Dörfler	:
11957ec88b6SJohn Scipione	BView(frame, "_dragger_", resizingMode, flags),
120cf2aeb20SAxel Dörfler	fTarget(target),
121cf2aeb20SAxel Dörfler	fRelation(TARGET_UNKNOWN),
122cf2aeb20SAxel Dörfler	fShelf(NULL),
123cf2aeb20SAxel Dörfler	fTransition(false),
124cf2aeb20SAxel Dörfler	fIsZombie(false),
125cf2aeb20SAxel Dörfler	fErrCount(0),
1269cfb11a5SAlexandre Deckner	fPopUpIsCustom(false),
127cf2aeb20SAxel Dörfler	fPopUp(NULL)
128a5f7275dSStefano Ceccherini{
1294115645aSSiarzhuk Zharski	_InitData();
130a5f7275dSStefano Ceccherini}
131a5f7275dSStefano Ceccherini
132a5f7275dSStefano Ceccherini
1334cada380SAdrien DestuguesBDragger::BDragger(BView* target, uint32 flags)
1344cada380SAdrien Destugues	:
1354cada380SAdrien Destugues	BView("_dragger_", flags),
1364cada380SAdrien Destugues	fTarget(target),
1374cada380SAdrien Destugues	fRelation(TARGET_UNKNOWN),
1384cada380SAdrien Destugues	fShelf(NULL),
1394cada380SAdrien Destugues	fTransition(false),
1404cada380SAdrien Destugues	fIsZombie(false),
1414cada380SAdrien Destugues	fErrCount(0),
1424cada380SAdrien Destugues	fPopUpIsCustom(false),
1434cada380SAdrien Destugues	fPopUp(NULL)
1444cada380SAdrien Destugues{
1454cada380SAdrien Destugues	_InitData();
1464cada380SAdrien Destugues}
1474cada380SAdrien Destugues
1484cada380SAdrien Destugues
149bea2387bSAxel DörflerBDragger::BDragger(BMessage* data)
150bea2387bSAxel Dörfler	:
151bea2387bSAxel Dörfler	BView(data),
152cf2aeb20SAxel Dörfler	fTarget(NULL),
153cf2aeb20SAxel Dörfler	fRelation(TARGET_UNKNOWN),
154cf2aeb20SAxel Dörfler	fShelf(NULL),
155cf2aeb20SAxel Dörfler	fTransition(false),
156cf2aeb20SAxel Dörfler	fIsZombie(false),
157cf2aeb20SAxel Dörfler	fErrCount(0),
1589cfb11a5SAlexandre Deckner	fPopUpIsCustom(false),
159cf2aeb20SAxel Dörfler	fPopUp(NULL)
160a5f7275dSStefano Ceccherini{
161bea2387bSAxel Dörfler	data->FindInt32("_rel", (int32*)&fRelation);
162a5f7275dSStefano Ceccherini
1634115645aSSiarzhuk Zharski	_InitData();
164a5f7275dSStefano Ceccherini
165a5f7275dSStefano Ceccherini	BMessage popupMsg;
166a5f7275dSStefano Ceccherini	if (data->FindMessage("_popup", &popupMsg) == B_OK) {
167bea2387bSAxel Dörfler		BArchivable* archivable = instantiate_object(&popupMsg);
168a5f7275dSStefano Ceccherini
1699cfb11a5SAlexandre Deckner		if (archivable) {
170bea2387bSAxel Dörfler			fPopUp = dynamic_cast<BPopUpMenu*>(archivable);
1719cfb11a5SAlexandre Deckner			fPopUpIsCustom = true;
1729cfb11a5SAlexandre Deckner		}
173a5f7275dSStefano Ceccherini	}
174a5f7275dSStefano Ceccherini}
175a5f7275dSStefano Ceccherini
176a5f7275dSStefano Ceccherini
177a5f7275dSStefano CeccheriniBDragger::~BDragger()
178a5f7275dSStefano Ceccherini{
1799cfb11a5SAlexandre Deckner	delete fPopUp;
180a5f7275dSStefano Ceccherini	delete fBitmap;
181a5f7275dSStefano Ceccherini}
182a5f7275dSStefano Ceccherini
183a5f7275dSStefano Ceccherini
184a5f7275dSStefano CeccheriniBArchivable	*
185bea2387bSAxel DörflerBDragger::Instantiate(BMessage* data)
186a5f7275dSStefano Ceccherini{
187a5f7275dSStefano Ceccherini	if (validate_instantiation(data, "BDragger"))
188a5f7275dSStefano Ceccherini		return new BDragger(data);
1898cc767eeSStefano Ceccherini	return NULL;
190a5f7275dSStefano Ceccherini}
191a5f7275dSStefano Ceccherini
192a5f7275dSStefano Ceccherini
1931cbfe2efSIngo Weinholdstatus_t
194bea2387bSAxel DörflerBDragger::Archive(BMessage* data, bool deep) const
195a5f7275dSStefano Ceccherini{
1968cc767eeSStefano Ceccherini	status_t ret = BView::Archive(data, deep);
1978cc767eeSStefano Ceccherini	if (ret != B_OK)
1988cc767eeSStefano Ceccherini		return ret;
199a5f7275dSStefano Ceccherini
2008cc767eeSStefano Ceccherini	BMessage popupMsg;
2011cbfe2efSIngo Weinhold
202bea2387bSAxel Dörfler	if (fPopUp != NULL && fPopUpIsCustom) {
203642cc131SAlexandre Deckner		bool windowLocked = fPopUp->Window()->Lock();
204642cc131SAlexandre Deckner
205642cc131SAlexandre Deckner		ret = fPopUp->Archive(&popupMsg, deep);
206642cc131SAlexandre Deckner
207bea2387bSAxel Dörfler		if (windowLocked) {
20882e6d2ffSAlexandre Deckner			fPopUp->Window()->Unlock();
209642cc131SAlexandre Deckner				// TODO: Investigate, in some (rare) occasions the menu window
210642cc131SAlexandre Deckner				//		 has already been unlocked
211bea2387bSAxel Dörfler		}
212642cc131SAlexandre Deckner
213642cc131SAlexandre Deckner		if (ret == B_OK)
214642cc131SAlexandre Deckner			ret = data->AddMessage("_popup", &popupMsg);
215a5f7275dSStefano Ceccherini	}
216a5f7275dSStefano Ceccherini
2174fdedfbdSJérôme Duval	if (ret == B_OK)
2184fdedfbdSJérôme Duval		ret = data->AddInt32("_rel", fRelation);
2198cc767eeSStefano Ceccherini	return ret;
220a5f7275dSStefano Ceccherini}
221a5f7275dSStefano Ceccherini
222a5f7275dSStefano Ceccherini
223a5f7275dSStefano Ceccherinivoid
2241cbfe2efSIngo WeinholdBDragger::AttachedToWindow()
225a5f7275dSStefano Ceccherini{
226a5f7275dSStefano Ceccherini	if (fIsZombie) {
227a5f7275dSStefano Ceccherini		SetLowColor(kZombieColor);
228a5f7275dSStefano Ceccherini		SetViewColor(kZombieColor);
229a5f7275dSStefano Ceccherini	} else {
230a5f7275dSStefano Ceccherini		SetLowColor(B_TRANSPARENT_COLOR);
231a5f7275dSStefano Ceccherini		SetViewColor(B_TRANSPARENT_COLOR);
232a5f7275dSStefano Ceccherini	}
233a5f7275dSStefano Ceccherini
2346e0e4ca6SAxel Dörfler	_DetermineRelationship();
2356e0e4ca6SAxel Dörfler	_AddToList();
236c51d0337SAlexandre Deckner
237c51d0337SAlexandre Deckner	AddFilter(new DragTrackingFilter(this, kMsgDragStarted));
238a5f7275dSStefano Ceccherini}
239a5f7275dSStefano Ceccherini
240a5f7275dSStefano Ceccherini
241a5f7275dSStefano Ceccherinivoid
242a5f7275dSStefano CeccheriniBDragger::DetachedFromWindow()
243a5f7275dSStefano Ceccherini{
2446e0e4ca6SAxel Dörfler	_RemoveFromList();
245a5f7275dSStefano Ceccherini}
246a5f7275dSStefano Ceccherini
247a5f7275dSStefano Ceccherini
248a5f7275dSStefano Ceccherinivoid
249a5f7275dSStefano CeccheriniBDragger::Draw(BRect update)
250a5f7275dSStefano Ceccherini{
251a5f7275dSStefano Ceccherini	BRect bounds(Bounds());
252a5f7275dSStefano Ceccherini
253bea2387bSAxel Dörfler	if (AreDraggersDrawn() && (fShelf == NULL || fShelf->AllowsDragging())) {
254bea2387bSAxel Dörfler		if (Parent() != NULL && (Parent()->Flags() & B_DRAW_ON_CHILDREN) == 0) {
25506ab1718SStephan Aßmus			uint32 flags = Parent()->Flags();
25606ab1718SStephan Aßmus			Parent()->SetFlags(flags | B_DRAW_ON_CHILDREN);
257b7aac5d2SAdrien Destugues			SetHighColor(Parent()->ViewColor());
258b7aac5d2SAdrien Destugues			FillRect(Bounds());
25906ab1718SStephan Aßmus			Parent()->Draw(Frame() & ConvertToParent(update));
26006ab1718SStephan Aßmus			Parent()->Flush();
26106ab1718SStephan Aßmus			Parent()->SetFlags(flags);
26206ab1718SStephan Aßmus		}
26306ab1718SStephan Aßmus
26406ab1718SStephan Aßmus		BPoint where = bounds.RightBottom() - BPoint(fBitmap->Bounds().Width(),
26506ab1718SStephan Aßmus			fBitmap->Bounds().Height());
266a5f7275dSStefano Ceccherini		SetDrawingMode(B_OP_OVER);
2671b7f1654SStefano Ceccherini		DrawBitmap(fBitmap, where);
268a5f7275dSStefano Ceccherini		SetDrawingMode(B_OP_COPY);
269a5f7275dSStefano Ceccherini
270a5f7275dSStefano Ceccherini		if (fIsZombie) {
271a5f7275dSStefano Ceccherini			// TODO: should draw it differently ?
272a5f7275dSStefano Ceccherini		}
273a5f7275dSStefano Ceccherini	} else if (IsVisibilityChanging()) {
274bea2387bSAxel Dörfler		if (Parent() != NULL) {
27506ab1718SStephan Aßmus			if ((Parent()->Flags() & B_DRAW_ON_CHILDREN) == 0) {
27606ab1718SStephan Aßmus				uint32 flags = Parent()->Flags();
27706ab1718SStephan Aßmus				Parent()->SetFlags(flags | B_DRAW_ON_CHILDREN);
27806ab1718SStephan Aßmus				Parent()->Invalidate(Frame() & ConvertToParent(update));
27906ab1718SStephan Aßmus				Parent()->SetFlags(flags);
28006ab1718SStephan Aßmus			}
28106ab1718SStephan Aßmus		} else {
282a5f7275dSStefano Ceccherini			SetHighColor(255, 255, 255);
283a5f7275dSStefano Ceccherini			FillRect(bounds);
284a5f7275dSStefano Ceccherini		}
285a5f7275dSStefano Ceccherini	}
286a5f7275dSStefano Ceccherini}
287a5f7275dSStefano Ceccherini
288a5f7275dSStefano Ceccherini
289a5f7275dSStefano Ceccherinivoid
290a5f7275dSStefano CeccheriniBDragger::MouseDown(BPoint where)
291a5f7275dSStefano Ceccherini{
292bea2387bSAxel Dörfler	if (fTarget == NULL || !AreDraggersDrawn())
293a5f7275dSStefano Ceccherini		return;
294a5f7275dSStefano Ceccherini
295f6e671ccSStefano Ceccherini	uint32 buttons;
296bea2387bSAxel Dörfler	Window()->CurrentMessage()->FindInt32("buttons", (int32*)&buttons);
297a5f7275dSStefano Ceccherini
298bea2387bSAxel Dörfler	if (fShelf != NULL && (buttons & B_SECONDARY_MOUSE_BUTTON) != 0)
2996e0e4ca6SAxel Dörfler		_ShowPopUp(fTarget, where);
300a5f7275dSStefano Ceccherini}
301a5f7275dSStefano Ceccherini
302a5f7275dSStefano Ceccherini
303a5f7275dSStefano Ceccherinivoid
3043a15790eSStefano CeccheriniBDragger::MouseUp(BPoint point)
305a5f7275dSStefano Ceccherini{
3063a15790eSStefano Ceccherini	BView::MouseUp(point);
307a5f7275dSStefano Ceccherini}
308a5f7275dSStefano Ceccherini
309a5f7275dSStefano Ceccherini
310a5f7275dSStefano Ceccherinivoid
311bea2387bSAxel DörflerBDragger::MouseMoved(BPoint point, uint32 code, const BMessage* msg)
312a5f7275dSStefano Ceccherini{
3133a15790eSStefano Ceccherini	BView::MouseMoved(point, code, msg);
314a5f7275dSStefano Ceccherini}
315a5f7275dSStefano Ceccherini
316a5f7275dSStefano Ceccherini
317a5f7275dSStefano Ceccherinivoid
318bea2387bSAxel DörflerBDragger::MessageReceived(BMessage* msg)
319a5f7275dSStefano Ceccherini{
32006ab1718SStephan Aßmus	switch (msg->what) {
32106ab1718SStephan Aßmus		case B_TRASH_TARGET:
32206ab1718SStephan Aßmus			if (fShelf != NULL)
32306ab1718SStephan Aßmus				Window()->PostMessage(kDeleteReplicant, fTarget, NULL);
32406ab1718SStephan Aßmus			else {
325aed35104SHumdinger				BAlert* alert = new BAlert(B_TRANSLATE("Warning"),
3264115645aSSiarzhuk Zharski					B_TRANSLATE("Can't delete this replicant from its original "
3274115645aSSiarzhuk Zharski					"application. Life goes on."),
3284115645aSSiarzhuk Zharski					B_TRANSLATE("OK"), NULL, NULL, B_WIDTH_FROM_WIDEST,
329aed35104SHumdinger					B_WARNING_ALERT);
330aed35104SHumdinger				alert->SetFlags(alert->Flags() | B_CLOSE_ON_ESCAPE);
331aed35104SHumdinger				alert->Go(NULL);
33206ab1718SStephan Aßmus			}
33306ab1718SStephan Aßmus			break;
33406ab1718SStephan Aßmus
33506ab1718SStephan Aßmus		case _SHOW_DRAG_HANDLES_:
33606ab1718SStephan Aßmus			// This code is used whenever the "are draggers drawn" option is
33706ab1718SStephan Aßmus			// changed.
33806ab1718SStephan Aßmus			if (fRelation == TARGET_IS_CHILD) {
33906ab1718SStephan Aßmus				fTransition = true;
34006ab1718SStephan Aßmus				Draw(Bounds());
34106ab1718SStephan Aßmus				Flush();
34206ab1718SStephan Aßmus				fTransition = false;
34306ab1718SStephan Aßmus			} else {
344bea2387bSAxel Dörfler				if ((fShelf != NULL && fShelf->AllowsDragging()
345bea2387bSAxel Dörfler						&& AreDraggersDrawn())
34694af9087SAlexandre Deckner					|| AreDraggersDrawn()) {
34706ab1718SStephan Aßmus					Show();
34894af9087SAlexandre Deckner				} else
34906ab1718SStephan Aßmus					Hide();
35006ab1718SStephan Aßmus			}
35106ab1718SStephan Aßmus			break;
35206ab1718SStephan Aßmus
353c51d0337SAlexandre Deckner		case kMsgDragStarted:
354c51d0337SAlexandre Deckner			if (fTarget != NULL) {
355c51d0337SAlexandre Deckner				BMessage archive(B_ARCHIVED_OBJECT);
356c51d0337SAlexandre Deckner
357c51d0337SAlexandre Deckner				if (fRelation == TARGET_IS_PARENT)
358c51d0337SAlexandre Deckner					fTarget->Archive(&archive);
359c51d0337SAlexandre Deckner				else if (fRelation == TARGET_IS_CHILD)
360c51d0337SAlexandre Deckner					Archive(&archive);
361bea2387bSAxel Dörfler				else if (fTarget->Archive(&archive)) {
362bea2387bSAxel Dörfler					BMessage archivedSelf(B_ARCHIVED_OBJECT);
363c51d0337SAlexandre Deckner
364bea2387bSAxel Dörfler					if (Archive(&archivedSelf))
365bea2387bSAxel Dörfler						archive.AddMessage("__widget", &archivedSelf);
366c51d0337SAlexandre Deckner				}
367c51d0337SAlexandre Deckner
368c51d0337SAlexandre Deckner				archive.AddInt32("be:actions", B_TRASH_TARGET);
369c51d0337SAlexandre Deckner				BPoint offset;
370c51d0337SAlexandre Deckner				drawing_mode mode;
371bea2387bSAxel Dörfler				BBitmap* bitmap = DragBitmap(&offset, &mode);
372c51d0337SAlexandre Deckner				if (bitmap != NULL)
373c51d0337SAlexandre Deckner					DragMessage(&archive, bitmap, mode, offset, this);
374c51d0337SAlexandre Deckner				else {
375bea2387bSAxel Dörfler					DragMessage(&archive, ConvertFromScreen(
376bea2387bSAxel Dörfler						fTarget->ConvertToScreen(fTarget->Bounds())), this);
377c51d0337SAlexandre Deckner				}
378c51d0337SAlexandre Deckner			}
379c51d0337SAlexandre Deckner			break;
380c51d0337SAlexandre Deckner
38106ab1718SStephan Aßmus		default:
38206ab1718SStephan Aßmus			BView::MessageReceived(msg);
38306ab1718SStephan Aßmus			break;
38406ab1718SStephan Aßmus	}
385a5f7275dSStefano Ceccherini}
386a5f7275dSStefano Ceccherini
387a5f7275dSStefano Ceccherini
388a5f7275dSStefano Ceccherinivoid
3893a15790eSStefano CeccheriniBDragger::FrameMoved(BPoint newPosition)
390a5f7275dSStefano Ceccherini{
3913a15790eSStefano Ceccherini	BView::FrameMoved(newPosition);
392a5f7275dSStefano Ceccherini}
393a5f7275dSStefano Ceccherini
394a5f7275dSStefano Ceccherini
395a5f7275dSStefano Ceccherinivoid
3963a15790eSStefano CeccheriniBDragger::FrameResized(float newWidth, float newHeight)
397a5f7275dSStefano Ceccherini{
3983a15790eSStefano Ceccherini	BView::FrameResized(newWidth, newHeight);
399a5f7275dSStefano Ceccherini}
400a5f7275dSStefano Ceccherini
401a5f7275dSStefano Ceccherini
402a5f7275dSStefano Ceccherinistatus_t
403a5f7275dSStefano CeccheriniBDragger::ShowAllDraggers()
404a5f7275dSStefano Ceccherini{
405cf2aeb20SAxel Dörfler	BPrivate::AppServerLink link;
406cf2aeb20SAxel Dörfler	link.StartMessage(AS_SET_SHOW_ALL_DRAGGERS);
407cf2aeb20SAxel Dörfler	link.Attach<bool>(true);
408cf2aeb20SAxel Dörfler
409cf2aeb20SAxel Dörfler	status_t status = link.Flush();
410cf2aeb20SAxel Dörfler	if (status == B_OK) {
4111cbfe2efSIngo Weinhold		DraggerManager* manager = DraggerManager::Default();
4121cbfe2efSIngo Weinhold		AutoLocker<DraggerManager> locker(manager);
4131cbfe2efSIngo Weinhold		manager->visible = true;
4141cbfe2efSIngo Weinhold		manager->visibleInitialized = true;
415cf2aeb20SAxel Dörfler	}
416cf2aeb20SAxel Dörfler
417cf2aeb20SAxel Dörfler	return status;
418a5f7275dSStefano Ceccherini}
419a5f7275dSStefano Ceccherini
420a5f7275dSStefano Ceccherini
421a5f7275dSStefano Ceccherinistatus_t
422a5f7275dSStefano CeccheriniBDragger::HideAllDraggers()
423a5f7275dSStefano Ceccherini{
424cf2aeb20SAxel Dörfler	BPrivate::AppServerLink link;
425cf2aeb20SAxel Dörfler	link.StartMessage(AS_SET_SHOW_ALL_DRAGGERS);
426cf2aeb20SAxel Dörfler	link.Attach<bool>(false);
427cf2aeb20SAxel Dörfler
428cf2aeb20SAxel Dörfler	status_t status = link.Flush();
429cf2aeb20SAxel Dörfler	if (status == B_OK) {
4301cbfe2efSIngo Weinhold		DraggerManager* manager = DraggerManager::Default();
4311cbfe2efSIngo Weinhold		AutoLocker<DraggerManager> locker(manager);
4321cbfe2efSIngo Weinhold		manager->visible = false;
4331cbfe2efSIngo Weinhold		manager->visibleInitialized = true;
434cf2aeb20SAxel Dörfler	}
435cf2aeb20SAxel Dörfler
436cf2aeb20SAxel Dörfler	return status;
437a5f7275dSStefano Ceccherini}
438a5f7275dSStefano Ceccherini
439a5f7275dSStefano Ceccherini
440a5f7275dSStefano Ceccherinibool
441a5f7275dSStefano CeccheriniBDragger::AreDraggersDrawn()
442a5f7275dSStefano Ceccherini{
4431cbfe2efSIngo Weinhold	DraggerManager* manager = DraggerManager::Default();
4441cbfe2efSIngo Weinhold	AutoLocker<DraggerManager> locker(manager);
4456e0e4ca6SAxel Dörfler
4461cbfe2efSIngo Weinhold	if (!manager->visibleInitialized) {
447cf2aeb20SAxel Dörfler		BPrivate::AppServerLink link;
448cf2aeb20SAxel Dörfler		link.StartMessage(AS_GET_SHOW_ALL_DRAGGERS);
449cf2aeb20SAxel Dörfler
450cf2aeb20SAxel Dörfler		status_t status;
451cf2aeb20SAxel Dörfler		if (link.FlushWithReply(status) == B_OK && status == B_OK) {
4521cbfe2efSIngo Weinhold			link.Read<bool>(&manager->visible);
4531cbfe2efSIngo Weinhold			manager->visibleInitialized = true;
454cf2aeb20SAxel Dörfler		} else
455cf2aeb20SAxel Dörfler			return false;
4566e0e4ca6SAxel Dörfler	}
457cf2aeb20SAxel Dörfler
4581cbfe2efSIngo Weinhold	return manager->visible;
459a5f7275dSStefano Ceccherini}
460a5f7275dSStefano Ceccherini
461a5f7275dSStefano Ceccherini
4626e0e4ca6SAxel DörflerBHandler*
4636e0e4ca6SAxel DörflerBDragger::ResolveSpecifier(BMessage* message, int32 index, BMessage* specifier,
4646e0e4ca6SAxel Dörfler	int32 form, const char* property)
465a5f7275dSStefano Ceccherini{
4666e0e4ca6SAxel Dörfler	return BView::ResolveSpecifier(message, index, specifier, form, property);
467a5f7275dSStefano Ceccherini}
468a5f7275dSStefano Ceccherini
469a5f7275dSStefano Ceccherini
470a5f7275dSStefano Ceccherinistatus_t
4716e0e4ca6SAxel DörflerBDragger::GetSupportedSuites(BMessage* data)
472a5f7275dSStefano Ceccherini{
4733a15790eSStefano Ceccherini	return BView::GetSupportedSuites(data);
474a5f7275dSStefano Ceccherini}
475a5f7275dSStefano Ceccherini
476a5f7275dSStefano Ceccherini
477a5f7275dSStefano Ceccherinistatus_t
47839fbf550SOliver TappeBDragger::Perform(perform_code code, void* _data)
47939fbf550SOliver Tappe{
48039fbf550SOliver Tappe	switch (code) {
48139fbf550SOliver Tappe		case PERFORM_CODE_MIN_SIZE:
48239fbf550SOliver Tappe			((perform_data_min_size*)_data)->return_value
48339fbf550SOliver Tappe				= BDragger::MinSize();
48439fbf550SOliver Tappe			return B_OK;
48539fbf550SOliver Tappe		case PERFORM_CODE_MAX_SIZE:
48639fbf550SOliver Tappe			((perform_data_max_size*)_data)->return_value
48739fbf550SOliver Tappe				= BDragger::MaxSize();
48839fbf550SOliver Tappe			return B_OK;
48939fbf550SOliver Tappe		case PERFORM_CODE_PREFERRED_SIZE:
49039fbf550SOliver Tappe			((perform_data_preferred_size*)_data)->return_value
49139fbf550SOliver Tappe				= BDragger::PreferredSize();
49239fbf550SOliver Tappe			return B_OK;
49339fbf550SOliver Tappe		case PERFORM_CODE_LAYOUT_ALIGNMENT:
49439fbf550SOliver Tappe			((perform_data_layout_alignment*)_data)->return_value
49539fbf550SOliver Tappe				= BDragger::LayoutAlignment();
49639fbf550SOliver Tappe			return B_OK;
49739fbf550SOliver Tappe		case PERFORM_CODE_HAS_HEIGHT_FOR_WIDTH:
49839fbf550SOliver Tappe			((perform_data_has_height_for_width*)_data)->return_value
49939fbf550SOliver Tappe				= BDragger::HasHeightForWidth();
50039fbf550SOliver Tappe			return B_OK;
50139fbf550SOliver Tappe		case PERFORM_CODE_GET_HEIGHT_FOR_WIDTH:
50239fbf550SOliver Tappe		{
50339fbf550SOliver Tappe			perform_data_get_height_for_width* data
50439fbf550SOliver Tappe				= (perform_data_get_height_for_width*)_data;
50539fbf550SOliver Tappe			BDragger::GetHeightForWidth(data->width, &data->min, &data->max,
50639fbf550SOliver Tappe				&data->preferred);
50739fbf550SOliver Tappe			return B_OK;
50839fbf550SOliver Tappe}
50939fbf550SOliver Tappe		case PERFORM_CODE_SET_LAYOUT:
51039fbf550SOliver Tappe		{
51139fbf550SOliver Tappe			perform_data_set_layout* data = (perform_data_set_layout*)_data;
51239fbf550SOliver Tappe			BDragger::SetLayout(data->layout);
51339fbf550SOliver Tappe			return B_OK;
51439fbf550SOliver Tappe		}
515eee4243dSAlex Wilson		case PERFORM_CODE_LAYOUT_INVALIDATED:
51639fbf550SOliver Tappe		{
517eee4243dSAlex Wilson			perform_data_layout_invalidated* data
518eee4243dSAlex Wilson				= (perform_data_layout_invalidated*)_data;
519eee4243dSAlex Wilson			BDragger::LayoutInvalidated(data->descendants);
52039fbf550SOliver Tappe			return B_OK;
52139fbf550SOliver Tappe		}
52239fbf550SOliver Tappe		case PERFORM_CODE_DO_LAYOUT:
52339fbf550SOliver Tappe		{
52439fbf550SOliver Tappe			BDragger::DoLayout();
52539fbf550SOliver Tappe			return B_OK;
52639fbf550SOliver Tappe		}
52739fbf550SOliver Tappe	}
52839fbf550SOliver Tappe
52939fbf550SOliver Tappe	return BView::Perform(code, _data);
530a5f7275dSStefano Ceccherini}
531a5f7275dSStefano Ceccherini
532a5f7275dSStefano Ceccherini
533a5f7275dSStefano Ceccherinivoid
534a5f7275dSStefano CeccheriniBDragger::ResizeToPreferred()
535a5f7275dSStefano Ceccherini{
536a5f7275dSStefano Ceccherini	BView::ResizeToPreferred();
537a5f7275dSStefano Ceccherini}
538a5f7275dSStefano Ceccherini
539a5f7275dSStefano Ceccherini
540a5f7275dSStefano Ceccherinivoid
5416e0e4ca6SAxel DörflerBDragger::GetPreferredSize(float* _width, float* _height)
542a5f7275dSStefano Ceccherini{
5436e0e4ca6SAxel Dörfler	BView::GetPreferredSize(_width, _height);
544a5f7275dSStefano Ceccherini}
545a5f7275dSStefano Ceccherini
546a5f7275dSStefano Ceccherini
547a5f7275dSStefano Ceccherinivoid
548a5f7275dSStefano CeccheriniBDragger::MakeFocus(bool state)
549a5f7275dSStefano Ceccherini{
550a5f7275dSStefano Ceccherini	BView::MakeFocus(state);
551a5f7275dSStefano Ceccherini}
552a5f7275dSStefano Ceccherini
553a5f7275dSStefano Ceccherini
554a5f7275dSStefano Ceccherinivoid
555a5f7275dSStefano CeccheriniBDragger::AllAttached()
556a5f7275dSStefano Ceccherini{
557a5f7275dSStefano Ceccherini	BView::AllAttached();
558a5f7275dSStefano Ceccherini}
559a5f7275dSStefano Ceccherini
560a5f7275dSStefano Ceccherini
561a5f7275dSStefano Ceccherinivoid
562a5f7275dSStefano CeccheriniBDragger::AllDetached()
563a5f7275dSStefano Ceccherini{
564a5f7275dSStefano Ceccherini	BView::AllDetached();
565a5f7275dSStefano Ceccherini}
566a5f7275dSStefano Ceccherini
567a5f7275dSStefano Ceccherini
568a5f7275dSStefano Ceccherinistatus_t
569bea2387bSAxel DörflerBDragger::SetPopUp(BPopUpMenu* menu)
570a5f7275dSStefano Ceccherini{
5719cfb11a5SAlexandre Deckner	if (menu != NULL && menu != fPopUp) {
572a5f7275dSStefano Ceccherini		delete fPopUp;
5739cfb11a5SAlexandre Deckner		fPopUp = menu;
5749cfb11a5SAlexandre Deckner		fPopUpIsCustom = true;
5759cfb11a5SAlexandre Deckner		return B_OK;
5769cfb11a5SAlexandre Deckner	}
5779cfb11a5SAlexandre Deckner	return B_ERROR;
578a5f7275dSStefano Ceccherini}
579a5f7275dSStefano Ceccherini
580a5f7275dSStefano Ceccherini
581bea2387bSAxel DörflerBPopUpMenu*
582a5f7275dSStefano CeccheriniBDragger::PopUp() const
583a5f7275dSStefano Ceccherini{
5846e0e4ca6SAxel Dörfler	if (fPopUp == NULL && fTarget)
585bea2387bSAxel Dörfler		const_cast<BDragger*>(this)->_BuildDefaultPopUp();
5866e0e4ca6SAxel Dörfler
587a5f7275dSStefano Ceccherini	return fPopUp;
588a5f7275dSStefano Ceccherini}
589a5f7275dSStefano Ceccherini
590a5f7275dSStefano Ceccherini
591a5f7275dSStefano Ceccherinibool
592a5f7275dSStefano CeccheriniBDragger::InShelf() const
593a5f7275dSStefano Ceccherini{
594a5f7275dSStefano Ceccherini	return fShelf != NULL;
595a5f7275dSStefano Ceccherini}
596a5f7275dSStefano Ceccherini
597a5f7275dSStefano Ceccherini
598bea2387bSAxel DörflerBView*
599a5f7275dSStefano CeccheriniBDragger::Target() const
600a5f7275dSStefano Ceccherini{
601a5f7275dSStefano Ceccherini	return fTarget;
602a5f7275dSStefano Ceccherini}
603a5f7275dSStefano Ceccherini
604a5f7275dSStefano Ceccherini
605bea2387bSAxel DörflerBBitmap*
606bea2387bSAxel DörflerBDragger::DragBitmap(BPoint* offset, drawing_mode* mode)
607a5f7275dSStefano Ceccherini{
608a5f7275dSStefano Ceccherini	return NULL;
609a5f7275dSStefano Ceccherini}
610a5f7275dSStefano Ceccherini
611a5f7275dSStefano Ceccherini
612a5f7275dSStefano Ceccherinibool
613a5f7275dSStefano CeccheriniBDragger::IsVisibilityChanging() const
614a5f7275dSStefano Ceccherini{
615a5f7275dSStefano Ceccherini	return fTransition;
616a5f7275dSStefano Ceccherini}
617a5f7275dSStefano Ceccherini
618a5f7275dSStefano Ceccherini
619a5f7275dSStefano Ceccherinivoid BDragger::_ReservedDragger2() {}
620a5f7275dSStefano Ceccherinivoid BDragger::_ReservedDragger3() {}
621a5f7275dSStefano Ceccherinivoid BDragger::_ReservedDragger4() {}
622a5f7275dSStefano Ceccherini
623a5f7275dSStefano Ceccherini
624bea2387bSAxel DörflerBDragger&
625bea2387bSAxel DörflerBDragger::operator=(const BDragger&)
626a5f7275dSStefano Ceccherini{
627a5f7275dSStefano Ceccherini	return *this;
628a5f7275dSStefano Ceccherini}
629a5f7275dSStefano Ceccherini
630a5f7275dSStefano Ceccherini
631cf2aeb20SAxel Dörfler/*static*/ void
632cf2aeb20SAxel DörflerBDragger::_UpdateShowAllDraggers(bool visible)
633cf2aeb20SAxel Dörfler{
6341cbfe2efSIngo Weinhold	DraggerManager* manager = DraggerManager::Default();
6351cbfe2efSIngo Weinhold	AutoLocker<DraggerManager> locker(manager);
636cf2aeb20SAxel Dörfler
6371cbfe2efSIngo Weinhold	manager->visibleInitialized = true;
6381cbfe2efSIngo Weinhold	manager->visible = visible;
639cf2aeb20SAxel Dörfler
6401cbfe2efSIngo Weinhold	for (int32 i = manager->list.CountItems(); i-- > 0;) {
6411cbfe2efSIngo Weinhold		BDragger* dragger = (BDragger*)manager->list.ItemAt(i);
642cf2aeb20SAxel Dörfler		BMessenger target(dragger);
643cf2aeb20SAxel Dörfler		target.SendMessage(_SHOW_DRAG_HANDLES_);
6441cbfe2efSIngo Weinhold	}
645cf2aeb20SAxel Dörfler}
646cf2aeb20SAxel Dörfler
647cf2aeb20SAxel Dörfler
6484115645aSSiarzhuk Zharskivoid
6494115645aSSiarzhuk ZharskiBDragger::_InitData()
6504115645aSSiarzhuk Zharski{
6514115645aSSiarzhuk Zharski	fBitmap = new BBitmap(BRect(0.0f, 0.0f, 7.0f, 7.0f), B_CMAP8, false, false);
6524115645aSSiarzhuk Zharski	fBitmap->SetBits(kHandBitmap, fBitmap->BitsLength(), 0, B_CMAP8);
6534115645aSSiarzhuk Zharski}
6544115645aSSiarzhuk Zharski
6554115645aSSiarzhuk Zharski
656a5f7275dSStefano Ceccherinivoid
6576e0e4ca6SAxel DörflerBDragger::_AddToList()
658a5f7275dSStefano Ceccherini{
6591cbfe2efSIngo Weinhold	DraggerManager* manager = DraggerManager::Default();
6601cbfe2efSIngo Weinhold	AutoLocker<DraggerManager> locker(manager);
6611cbfe2efSIngo Weinhold	manager->list.AddItem(this);
662a5f7275dSStefano Ceccherini
6636e0e4ca6SAxel Dörfler	bool allowsDragging = true;
6646e0e4ca6SAxel Dörfler	if (fShelf)
6656e0e4ca6SAxel Dörfler		allowsDragging = fShelf->AllowsDragging();
666a5f7275dSStefano Ceccherini
6676e0e4ca6SAxel Dörfler	if (!AreDraggersDrawn() || !allowsDragging) {
6686e0e4ca6SAxel Dörfler		// The dragger is not shown - but we can't hide us in case we're the
6696e0e4ca6SAxel Dörfler		// parent of the actual target view (because then you couldn't see
6706e0e4ca6SAxel Dörfler		// it anymore).
67194af9087SAlexandre Deckner		if (fRelation != TARGET_IS_CHILD && !IsHidden())
6726e0e4ca6SAxel Dörfler			Hide();
6736e0e4ca6SAxel Dörfler	}
6746e0e4ca6SAxel Dörfler}
675a5f7275dSStefano Ceccherini
676a5f7275dSStefano Ceccherini
6776e0e4ca6SAxel Dörflervoid
6786e0e4ca6SAxel DörflerBDragger::_RemoveFromList()
6796e0e4ca6SAxel Dörfler{
6801cbfe2efSIngo Weinhold	DraggerManager* manager = DraggerManager::Default();
6811cbfe2efSIngo Weinhold	AutoLocker<DraggerManager> locker(manager);
6821cbfe2efSIngo Weinhold	manager->list.RemoveItem(this);
683a5f7275dSStefano Ceccherini}
684a5f7275dSStefano Ceccherini
685a5f7275dSStefano Ceccherini
686a5f7275dSStefano Ceccherinistatus_t
6876e0e4ca6SAxel DörflerBDragger::_DetermineRelationship()
688a5f7275dSStefano Ceccherini{
689bea2387bSAxel Dörfler	if (fTarget != NULL) {
690a5f7275dSStefano Ceccherini		if (fTarget == Parent())
691a5f7275dSStefano Ceccherini			fRelation = TARGET_IS_PARENT;
692a5f7275dSStefano Ceccherini		else if (fTarget == ChildAt(0))
693a5f7275dSStefano Ceccherini			fRelation = TARGET_IS_CHILD;
694a5f7275dSStefano Ceccherini		else
695a5f7275dSStefano Ceccherini			fRelation = TARGET_IS_SIBLING;
696a5f7275dSStefano Ceccherini	} else {
697a5f7275dSStefano Ceccherini		if (fRelation == TARGET_IS_PARENT)
698a5f7275dSStefano Ceccherini			fTarget = Parent();
699a5f7275dSStefano Ceccherini		else if (fRelation == TARGET_IS_CHILD)
700a5f7275dSStefano Ceccherini			fTarget = ChildAt(0);
701a5f7275dSStefano Ceccherini		else
702cf2aeb20SAxel Dörfler			return B_ERROR;
703a5f7275dSStefano Ceccherini	}
704a5f7275dSStefano Ceccherini
7051bbf044eSRene Gollent	if (fRelation == TARGET_IS_PARENT) {
706bea2387bSAxel Dörfler		BRect bounds(Frame());
707bea2387bSAxel Dörfler		BRect parentBounds(Parent()->Bounds());
708bea2387bSAxel Dörfler		if (!parentBounds.Contains(bounds)) {
7093cead3c6SRene Gollent			MoveTo(parentBounds.right - bounds.Width(),
7101cbfe2efSIngo Weinhold				parentBounds.bottom - bounds.Height());
711bea2387bSAxel Dörfler		}
7121cbfe2efSIngo Weinhold	}
7131bbf044eSRene Gollent
714cf2aeb20SAxel Dörfler	return B_OK;
715a5f7275dSStefano Ceccherini}
716a5f7275dSStefano Ceccherini
717a5f7275dSStefano Ceccherini
718a5f7275dSStefano Ceccherinistatus_t
719bea2387bSAxel DörflerBDragger::_SetViewToDrag(BView* target)
720a5f7275dSStefano Ceccherini{
721a5f7275dSStefano Ceccherini	if (target->Window() != Window())
722a5f7275dSStefano Ceccherini		return B_ERROR;
723a5f7275dSStefano Ceccherini
724a5f7275dSStefano Ceccherini	fTarget = target;
725a5f7275dSStefano Ceccherini
726bea2387bSAxel Dörfler	if (Window() != NULL)
7276e0e4ca6SAxel Dörfler		_DetermineRelationship();
728a5f7275dSStefano Ceccherini
729a5f7275dSStefano Ceccherini	return B_OK;
730a5f7275dSStefano Ceccherini}
731a5f7275dSStefano Ceccherini
732a5f7275dSStefano Ceccherini
733a5f7275dSStefano Ceccherinivoid
734bea2387bSAxel DörflerBDragger::_SetShelf(BShelf* shelf)
735a5f7275dSStefano Ceccherini{
736a5f7275dSStefano Ceccherini	fShelf = shelf;
737a5f7275dSStefano Ceccherini}
738a5f7275dSStefano Ceccherini
739a5f7275dSStefano Ceccherini
740a5f7275dSStefano Ceccherinivoid
7416e0e4ca6SAxel DörflerBDragger::_SetZombied(bool state)
742a5f7275dSStefano Ceccherini{
743a5f7275dSStefano Ceccherini	fIsZombie = state;
744a5f7275dSStefano Ceccherini
745f6e671ccSStefano Ceccherini	if (state) {
746f6e671ccSStefano Ceccherini		SetLowColor(kZombieColor);
747f6e671ccSStefano Ceccherini		SetViewColor(kZombieColor);
748f6e671ccSStefano Ceccherini	}
749a5f7275dSStefano Ceccherini}
750a5f7275dSStefano Ceccherini
751a5f7275dSStefano Ceccherini
752a5f7275dSStefano Ceccherinivoid
7536e0e4ca6SAxel DörflerBDragger::_BuildDefaultPopUp()
754a5f7275dSStefano Ceccherini{
755a5f7275dSStefano Ceccherini	fPopUp = new BPopUpMenu("Shelf", false, false, B_ITEMS_IN_COLUMN);
756a5f7275dSStefano Ceccherini
757a5f7275dSStefano Ceccherini	// About
758bea2387bSAxel Dörfler	BMessage* msg = new BMessage(B_ABOUT_REQUESTED);
759a5f7275dSStefano Ceccherini
760bea2387bSAxel Dörfler	const char* name = fTarget->Name();
761bea2387bSAxel Dörfler	if (name != NULL)
762a5f7275dSStefano Ceccherini		msg->AddString("target", name);
763a5f7275dSStefano Ceccherini
76457e43684SJohn Scipione	BString about(B_TRANSLATE("About %app" B_UTF8_ELLIPSIS));
7654115645aSSiarzhuk Zharski	about.ReplaceFirst("%app", name);
7661cbfe2efSIngo Weinhold
7674115645aSSiarzhuk Zharski	fPopUp->AddItem(new BMenuItem(about.String(), msg));
768931aebe9SStefano Ceccherini	fPopUp->AddSeparatorItem();
7694115645aSSiarzhuk Zharski	fPopUp->AddItem(new BMenuItem(B_TRANSLATE("Remove replicant"),
77021f11263SStephan Aßmus		new BMessage(kDeleteReplicant)));
771a5f7275dSStefano Ceccherini}
772a5f7275dSStefano Ceccherini
773a5f7275dSStefano Ceccherini
774a5f7275dSStefano Ceccherinivoid
775bea2387bSAxel DörflerBDragger::_ShowPopUp(BView* target, BPoint where)
776a5f7275dSStefano Ceccherini{
777a5f7275dSStefano Ceccherini	BPoint point = ConvertToScreen(where);
778a5f7275dSStefano Ceccherini
779bea2387bSAxel Dörfler	if (fPopUp == NULL && fTarget != NULL)
7806e0e4ca6SAxel Dörfler		_BuildDefaultPopUp();
781a5f7275dSStefano Ceccherini
782a5f7275dSStefano Ceccherini	fPopUp->SetTargetForItems(fTarget);
783a5f7275dSStefano Ceccherini
784cc8ef734SStefano Ceccherini	float menuWidth, menuHeight;
785cc8ef734SStefano Ceccherini	fPopUp->GetPreferredSize(&menuWidth, &menuHeight);
786cc8ef734SStefano Ceccherini	BRect rect(0, 0, menuWidth, menuHeight);
787cc8ef734SStefano Ceccherini	rect.InsetBy(-0.5, -0.5);
788cc8ef734SStefano Ceccherini	rect.OffsetTo(point);
7891cbfe2ef