xref: /haiku/src/kits/interface/TextControl.cpp (revision ee001e262a13bdd1f2c445a7ca2ee282b52d01bc)
1105644bfSAxel Dörfler /*
2105644bfSAxel Dörfler  * Copyright 2001-2005, Haiku Inc.
3105644bfSAxel Dörfler  * Distributed under the terms of the MIT License.
4105644bfSAxel Dörfler  *
5105644bfSAxel Dörfler  * Authors:
6105644bfSAxel Dörfler  *		Frans van Nispen (xlr8@tref.nl)
7105644bfSAxel Dörfler  *		Stephan Aßmus <superstippi@gmx.de>
8105644bfSAxel Dörfler  */
9105644bfSAxel Dörfler 
10105644bfSAxel Dörfler /**	BTextControl displays text that can act like a control. */
11105644bfSAxel Dörfler 
12105644bfSAxel Dörfler 
1352a38012Sejakowatz #include <stdio.h>
1452a38012Sejakowatz 
15058691d4SStefano Ceccherini #include <Message.h>
1652a38012Sejakowatz #include <TextControl.h>
1752a38012Sejakowatz #include <Window.h>
1852a38012Sejakowatz 
1952a38012Sejakowatz #include "TextInput.h"
2052a38012Sejakowatz 
2152a38012Sejakowatz 
2252a38012Sejakowatz BTextControl::BTextControl(BRect frame, const char *name, const char *label,
2352a38012Sejakowatz 						   const char *text, BMessage *message, uint32 mask,
2452a38012Sejakowatz 						   uint32 flags)
259cb2dbe2SMarc Flerackers 	: BControl(frame, name, label, message, mask, flags | B_FRAME_EVENTS)
2652a38012Sejakowatz {
279cb2dbe2SMarc Flerackers 	InitData(label, text);
2852a38012Sejakowatz 
29105644bfSAxel Dörfler 	float height;
30*ee001e26SAxel Dörfler 	BTextControl::GetPreferredSize(NULL, &height);
31105644bfSAxel Dörfler 
32105644bfSAxel Dörfler 	ResizeTo(Bounds().Width(), height);
33105644bfSAxel Dörfler 
349cb2dbe2SMarc Flerackers 	float lineHeight = fText->LineHeight(0);
35105644bfSAxel Dörfler 	fText->ResizeTo(fText->Bounds().Width(), lineHeight);
36105644bfSAxel Dörfler 	fText->MoveTo(fText->Frame().left, (height - lineHeight) / 2);
3752a38012Sejakowatz }
38058691d4SStefano Ceccherini 
39058691d4SStefano Ceccherini 
4052a38012Sejakowatz BTextControl::~BTextControl()
4152a38012Sejakowatz {
429cb2dbe2SMarc Flerackers 	SetModificationMessage(NULL);
4352a38012Sejakowatz }
44058691d4SStefano Ceccherini 
45058691d4SStefano Ceccherini 
4652a38012Sejakowatz BTextControl::BTextControl(BMessage *data)
4752a38012Sejakowatz 	:	BControl(data)
4852a38012Sejakowatz {
499cb2dbe2SMarc Flerackers 	InitData(Label(), NULL, data);
5052a38012Sejakowatz 
519cb2dbe2SMarc Flerackers 	int32 _a_label = B_ALIGN_LEFT;
529cb2dbe2SMarc Flerackers 	int32 _a_text = B_ALIGN_LEFT;
5352a38012Sejakowatz 
549cb2dbe2SMarc Flerackers 	if (data->HasInt32("_a_label"))
559cb2dbe2SMarc Flerackers 		data->FindInt32("_a_label", &_a_label);
5652a38012Sejakowatz 
579cb2dbe2SMarc Flerackers 	if (data->HasInt32("_a_text"))
589cb2dbe2SMarc Flerackers 		data->FindInt32("_a_text", &_a_text);
5952a38012Sejakowatz 
609cb2dbe2SMarc Flerackers 	SetAlignment((alignment)_a_label, (alignment)_a_text);
619cb2dbe2SMarc Flerackers 
629cb2dbe2SMarc Flerackers 	if (data->HasFloat("_divide"))
639cb2dbe2SMarc Flerackers 		data->FindFloat("_a_text", &fDivider);
649cb2dbe2SMarc Flerackers 
65058691d4SStefano Ceccherini 	if (data->HasMessage("_mod_msg")) {
669cb2dbe2SMarc Flerackers 		BMessage *_mod_msg = new BMessage;
679cb2dbe2SMarc Flerackers 		data->FindMessage("_mod_msg", _mod_msg);
689cb2dbe2SMarc Flerackers 		SetModificationMessage(_mod_msg);
699cb2dbe2SMarc Flerackers 	}
7052a38012Sejakowatz }
71058691d4SStefano Ceccherini 
72058691d4SStefano Ceccherini 
73058691d4SStefano Ceccherini BArchivable *
74058691d4SStefano Ceccherini BTextControl::Instantiate(BMessage *archive)
7552a38012Sejakowatz {
769cb2dbe2SMarc Flerackers 	if (validate_instantiation(archive, "BTextControl"))
779cb2dbe2SMarc Flerackers 		return new BTextControl(archive);
789cb2dbe2SMarc Flerackers 	else
7952a38012Sejakowatz 		return NULL;
8052a38012Sejakowatz }
81058691d4SStefano Ceccherini 
82058691d4SStefano Ceccherini 
83058691d4SStefano Ceccherini status_t
84058691d4SStefano Ceccherini BTextControl::Archive(BMessage *data, bool deep) const
8552a38012Sejakowatz {
869cb2dbe2SMarc Flerackers 	BView::Archive(data, deep);
8752a38012Sejakowatz 
88058691d4SStefano Ceccherini 	alignment labelAlignment, textAlignment;
8952a38012Sejakowatz 
90058691d4SStefano Ceccherini 	GetAlignment(&labelAlignment, &textAlignment);
919cb2dbe2SMarc Flerackers 
92058691d4SStefano Ceccherini 	data->AddInt32("_a_label", labelAlignment);
93058691d4SStefano Ceccherini 	data->AddInt32("_a_text", textAlignment);
949cb2dbe2SMarc Flerackers 	data->AddFloat("_divide", Divider());
959cb2dbe2SMarc Flerackers 
969cb2dbe2SMarc Flerackers 	if (ModificationMessage())
979cb2dbe2SMarc Flerackers 		data->AddMessage("_mod_msg", ModificationMessage());
989cb2dbe2SMarc Flerackers 
999cb2dbe2SMarc Flerackers 	return B_OK;
10052a38012Sejakowatz }
101058691d4SStefano Ceccherini 
102058691d4SStefano Ceccherini 
103058691d4SStefano Ceccherini void
104058691d4SStefano Ceccherini BTextControl::SetText(const char *text)
10552a38012Sejakowatz {
1069cb2dbe2SMarc Flerackers 	if (InvokeKind() != B_CONTROL_INVOKED)
1079cb2dbe2SMarc Flerackers 		return;
1089cb2dbe2SMarc Flerackers 
10952a38012Sejakowatz 	fText->SetText(text);
1109cb2dbe2SMarc Flerackers 
1119cb2dbe2SMarc Flerackers 	if (IsFocus())
1129cb2dbe2SMarc Flerackers 		fText->SetInitialText();
1139cb2dbe2SMarc Flerackers 
1149cb2dbe2SMarc Flerackers 	fText->Invalidate();
11552a38012Sejakowatz }
116058691d4SStefano Ceccherini 
117058691d4SStefano Ceccherini 
118058691d4SStefano Ceccherini const char *
119058691d4SStefano Ceccherini BTextControl::Text() const
12052a38012Sejakowatz {
12152a38012Sejakowatz 	return fText->Text();
12252a38012Sejakowatz }
123058691d4SStefano Ceccherini 
124058691d4SStefano Ceccherini 
125058691d4SStefano Ceccherini void
126058691d4SStefano Ceccherini BTextControl::SetValue(int32 value)
12752a38012Sejakowatz {
1289cb2dbe2SMarc Flerackers 	BControl::SetValue(value);
12952a38012Sejakowatz }
130058691d4SStefano Ceccherini 
131058691d4SStefano Ceccherini 
132058691d4SStefano Ceccherini status_t
133058691d4SStefano Ceccherini BTextControl::Invoke(BMessage *message)
13452a38012Sejakowatz {
135058691d4SStefano Ceccherini 	return BControl::Invoke(message);
13652a38012Sejakowatz }
137058691d4SStefano Ceccherini 
138058691d4SStefano Ceccherini 
139058691d4SStefano Ceccherini BTextView *
140058691d4SStefano Ceccherini BTextControl::TextView() const
14152a38012Sejakowatz {
1429cb2dbe2SMarc Flerackers 	return fText;
14352a38012Sejakowatz }
144058691d4SStefano Ceccherini 
145058691d4SStefano Ceccherini 
146058691d4SStefano Ceccherini void
147058691d4SStefano Ceccherini BTextControl::SetModificationMessage(BMessage *message)
14852a38012Sejakowatz {
1499cb2dbe2SMarc Flerackers 	delete fModificationMessage;
15052a38012Sejakowatz 	fModificationMessage = message;
15152a38012Sejakowatz }
152058691d4SStefano Ceccherini 
153058691d4SStefano Ceccherini 
154058691d4SStefano Ceccherini BMessage *
155058691d4SStefano Ceccherini BTextControl::ModificationMessage() const
15652a38012Sejakowatz {
15752a38012Sejakowatz 	return fModificationMessage;
15852a38012Sejakowatz }
159058691d4SStefano Ceccherini 
160058691d4SStefano Ceccherini 
161058691d4SStefano Ceccherini void
162058691d4SStefano Ceccherini BTextControl::SetAlignment(alignment labelAlignment, alignment textAlignment)
16352a38012Sejakowatz {
164058691d4SStefano Ceccherini 	fText->SetAlignment(textAlignment);
1659cb2dbe2SMarc Flerackers 	fText->AlignTextRect();
1669cb2dbe2SMarc Flerackers 
167058691d4SStefano Ceccherini 	if (fLabelAlign != labelAlignment) {
168058691d4SStefano Ceccherini 		fLabelAlign = labelAlignment;
1699cb2dbe2SMarc Flerackers 		Invalidate();
1709cb2dbe2SMarc Flerackers 	}
17152a38012Sejakowatz }
172058691d4SStefano Ceccherini 
173058691d4SStefano Ceccherini 
174058691d4SStefano Ceccherini void
175058691d4SStefano Ceccherini BTextControl::GetAlignment(alignment *label, alignment *text) const
17652a38012Sejakowatz {
177058691d4SStefano Ceccherini 	if (label)
17852a38012Sejakowatz 		*label = fLabelAlign;
179058691d4SStefano Ceccherini 	if (text)
18052a38012Sejakowatz 		*text = fText->Alignment();
18152a38012Sejakowatz }
1829cb2dbe2SMarc Flerackers 
183058691d4SStefano Ceccherini 
184058691d4SStefano Ceccherini void
185058691d4SStefano Ceccherini BTextControl::SetDivider(float dividingLine)
186058691d4SStefano Ceccherini {
1872e6a5805SStephan Aßmus 	dividingLine = floorf(dividingLine + 0.5);
1882e6a5805SStephan Aßmus 
189058691d4SStefano Ceccherini 	float dx = fDivider - dividingLine;
190058691d4SStefano Ceccherini 
191058691d4SStefano Ceccherini 	fDivider = dividingLine;
19252a38012Sejakowatz 
1939cb2dbe2SMarc Flerackers 	fText->MoveBy(-dx, 0.0f);
1949cb2dbe2SMarc Flerackers 	fText->ResizeBy(dx, 0.0f);
19552a38012Sejakowatz 
196058691d4SStefano Ceccherini 	if (Window()) {
19752a38012Sejakowatz 		fText->Invalidate();
19852a38012Sejakowatz 		Invalidate();
19952a38012Sejakowatz 	}
2009cb2dbe2SMarc Flerackers }
201058691d4SStefano Ceccherini 
202058691d4SStefano Ceccherini 
203058691d4SStefano Ceccherini float
204058691d4SStefano Ceccherini BTextControl::Divider() const
20552a38012Sejakowatz {
20652a38012Sejakowatz 	return fDivider;
20752a38012Sejakowatz }
208058691d4SStefano Ceccherini 
209058691d4SStefano Ceccherini 
210058691d4SStefano Ceccherini void
211058691d4SStefano Ceccherini BTextControl::Draw(BRect updateRect)
21252a38012Sejakowatz {
213105644bfSAxel Dörfler 	rgb_color noTint = ui_color(B_PANEL_BACKGROUND_COLOR),
214105644bfSAxel Dörfler 	lighten1 = tint_color(noTint, B_LIGHTEN_1_TINT),
215105644bfSAxel Dörfler 	lighten2 = tint_color(noTint, B_LIGHTEN_2_TINT),
216105644bfSAxel Dörfler 	lightenMax = tint_color(noTint, B_LIGHTEN_MAX_TINT),
217105644bfSAxel Dörfler 	darken1 = tint_color(noTint, B_DARKEN_1_TINT),
218105644bfSAxel Dörfler 	darken2 = tint_color(noTint, B_DARKEN_2_TINT),
219105644bfSAxel Dörfler 	darken4 = tint_color(noTint, B_DARKEN_4_TINT),
220105644bfSAxel Dörfler 	darkenMax = tint_color(noTint, B_DARKEN_MAX_TINT),
221105644bfSAxel Dörfler 	navigationColor = ui_color(B_KEYBOARD_NAVIGATION_COLOR);
2229cb2dbe2SMarc Flerackers 
2239cb2dbe2SMarc Flerackers 	bool enabled = IsEnabled();
2249cb2dbe2SMarc Flerackers 	bool active = false;
2259cb2dbe2SMarc Flerackers 
2269cb2dbe2SMarc Flerackers 	if (fText->IsFocus() && Window()->IsActive())
2279cb2dbe2SMarc Flerackers 		active = true;
2289cb2dbe2SMarc Flerackers 
2299cb2dbe2SMarc Flerackers 	BRect rect(fText->Frame());
2309cb2dbe2SMarc Flerackers 	rect.InsetBy(-1.0f, -1.0f);
2319cb2dbe2SMarc Flerackers 
232058691d4SStefano Ceccherini 	if (active) {
233105644bfSAxel Dörfler 		SetHighColor(navigationColor);
2349cb2dbe2SMarc Flerackers 		StrokeRect(rect);
235058691d4SStefano Ceccherini 	} else {
2369cb2dbe2SMarc Flerackers 		if (enabled)
2379cb2dbe2SMarc Flerackers 			SetHighColor(darken4);
2389cb2dbe2SMarc Flerackers 		else
2399cb2dbe2SMarc Flerackers 			SetHighColor(darken2);
2409cb2dbe2SMarc Flerackers 
2419cb2dbe2SMarc Flerackers 		StrokeLine(rect.LeftTop(), rect.LeftBottom());
2429cb2dbe2SMarc Flerackers 		StrokeLine(rect.LeftTop(), rect.RightTop());
2439cb2dbe2SMarc Flerackers 
244105644bfSAxel Dörfler 		SetHighColor(noTint);
2459cb2dbe2SMarc Flerackers 		StrokeLine(BPoint(rect.left + 1.0f, rect.bottom), rect.RightBottom());
2469cb2dbe2SMarc Flerackers 		StrokeLine(BPoint(rect.right, rect.top + 1.0f));
2479cb2dbe2SMarc Flerackers 	}
2489cb2dbe2SMarc Flerackers 
2499cb2dbe2SMarc Flerackers 	rect.InsetBy(-1.0f, -1.0f);
2509cb2dbe2SMarc Flerackers 
2519cb2dbe2SMarc Flerackers 	if (enabled)
2529cb2dbe2SMarc Flerackers 		SetHighColor(darken1);
2539cb2dbe2SMarc Flerackers 	else
254105644bfSAxel Dörfler 		SetHighColor(noTint);
2559cb2dbe2SMarc Flerackers 
2569cb2dbe2SMarc Flerackers 	StrokeLine(rect.LeftBottom(), rect.LeftTop());
2579cb2dbe2SMarc Flerackers 	StrokeLine(rect.RightTop());
2589cb2dbe2SMarc Flerackers 
2599cb2dbe2SMarc Flerackers 	if (enabled)
2609cb2dbe2SMarc Flerackers 		SetHighColor(lighten2);
2619cb2dbe2SMarc Flerackers 	else
2629cb2dbe2SMarc Flerackers 		SetHighColor(lighten1);
2639cb2dbe2SMarc Flerackers 
2649cb2dbe2SMarc Flerackers 	StrokeLine(BPoint(rect.left + 1.0f, rect.bottom), rect.RightBottom());
2659cb2dbe2SMarc Flerackers 	StrokeLine(BPoint(rect.right, rect.top + 1.0f), rect.RightBottom());
26652a38012Sejakowatz 
267058691d4SStefano Ceccherini 	if (Label()) {
268105644bfSAxel Dörfler 		font_height fontHeight;
269105644bfSAxel Dörfler 		GetFontHeight(&fontHeight);
2709cb2dbe2SMarc Flerackers 
271105644bfSAxel Dörfler 		float y = fontHeight.ascent + fText->Frame().top + 1;
27252a38012Sejakowatz 		float x;
2739cb2dbe2SMarc Flerackers 
274058691d4SStefano Ceccherini 		switch (fLabelAlign) {
27552a38012Sejakowatz 			case B_ALIGN_RIGHT:
2769cb2dbe2SMarc Flerackers 				x = fDivider - StringWidth(Label()) - 3.0f;
27752a38012Sejakowatz 				break;
27852a38012Sejakowatz 
27952a38012Sejakowatz 			case B_ALIGN_CENTER:
2809cb2dbe2SMarc Flerackers 				x = fDivider - StringWidth(Label()) / 2.0f;
28152a38012Sejakowatz 				break;
28252a38012Sejakowatz 
28352a38012Sejakowatz 			default:
28452a38012Sejakowatz 				x = 3.0f;
28552a38012Sejakowatz 				break;
28652a38012Sejakowatz 		}
28752a38012Sejakowatz 
288105644bfSAxel Dörfler 		SetHighColor(IsEnabled() ? darkenMax
289105644bfSAxel Dörfler 			: tint_color(ui_color(B_PANEL_BACKGROUND_COLOR), B_DISABLED_LABEL_TINT));
29052a38012Sejakowatz 		DrawString(Label(), BPoint(x, y));
29152a38012Sejakowatz 	}
29252a38012Sejakowatz }
293058691d4SStefano Ceccherini 
294058691d4SStefano Ceccherini 
295058691d4SStefano Ceccherini void
296058691d4SStefano Ceccherini BTextControl::MouseDown(BPoint where)
29752a38012Sejakowatz {
298058691d4SStefano Ceccherini 	if (!fText->IsFocus()) {
2999cb2dbe2SMarc Flerackers 		fText->MakeFocus(true);
3009cb2dbe2SMarc Flerackers 		fText->SelectAll();
30152a38012Sejakowatz 	}
30252a38012Sejakowatz }
303058691d4SStefano Ceccherini 
304058691d4SStefano Ceccherini 
305058691d4SStefano Ceccherini void
306058691d4SStefano Ceccherini BTextControl::AttachedToWindow()
30752a38012Sejakowatz {
30852a38012Sejakowatz 	BControl::AttachedToWindow();
30952a38012Sejakowatz 
3109cb2dbe2SMarc Flerackers 	bool enabled = IsEnabled();
3119cb2dbe2SMarc Flerackers 	rgb_color textColor;
3129cb2dbe2SMarc Flerackers 	rgb_color color = HighColor();
3139cb2dbe2SMarc Flerackers 	BFont font;
3149cb2dbe2SMarc Flerackers 
3159cb2dbe2SMarc Flerackers 	fText->GetFontAndColor(0, &font, &color);
3169cb2dbe2SMarc Flerackers 
3179cb2dbe2SMarc Flerackers 	if (enabled)
3189cb2dbe2SMarc Flerackers 		textColor = color;
3199cb2dbe2SMarc Flerackers 	else
3209cb2dbe2SMarc Flerackers 		textColor = tint_color(color, B_LIGHTEN_2_TINT);
3219cb2dbe2SMarc Flerackers 
3229cb2dbe2SMarc Flerackers 	fText->SetFontAndColor(&font, B_FONT_ALL, &textColor);
3239cb2dbe2SMarc Flerackers 
324058691d4SStefano Ceccherini 	if (enabled) {
3259cb2dbe2SMarc Flerackers 		color.red = 255;
3269cb2dbe2SMarc Flerackers 		color.green = 255;
3279cb2dbe2SMarc Flerackers 		color.blue = 255;
328058691d4SStefano Ceccherini 	} else
3299cb2dbe2SMarc Flerackers 		color = tint_color(color, B_LIGHTEN_2_TINT);
3309cb2dbe2SMarc Flerackers 
3319cb2dbe2SMarc Flerackers 	fText->SetViewColor(color);
3329cb2dbe2SMarc Flerackers 	fText->SetLowColor(color);
3339cb2dbe2SMarc Flerackers 
3349cb2dbe2SMarc Flerackers 	fText->MakeEditable(enabled);
33552a38012Sejakowatz }
336058691d4SStefano Ceccherini 
337058691d4SStefano Ceccherini 
338058691d4SStefano Ceccherini void
339058691d4SStefano Ceccherini BTextControl::MakeFocus(bool state)
34052a38012Sejakowatz {
3416d8d6cadSStephan Aßmus 	if (state != fText->IsFocus()) {
34252a38012Sejakowatz 		fText->MakeFocus(state);
3439cb2dbe2SMarc Flerackers 
3449cb2dbe2SMarc Flerackers 		if (state)
3459cb2dbe2SMarc Flerackers 			fText->SelectAll();
34652a38012Sejakowatz 	}
3476d8d6cadSStephan Aßmus }
348058691d4SStefano Ceccherini 
349058691d4SStefano Ceccherini 
350058691d4SStefano Ceccherini void
351058691d4SStefano Ceccherini BTextControl::SetEnabled(bool state)
35252a38012Sejakowatz {
3539cb2dbe2SMarc Flerackers 	if (IsEnabled() == state)
3549cb2dbe2SMarc Flerackers 		return;
3559cb2dbe2SMarc Flerackers 
356058691d4SStefano Ceccherini 	if (Window()) {
3579cb2dbe2SMarc Flerackers 		fText->MakeEditable(state);
3589cb2dbe2SMarc Flerackers 
3599cb2dbe2SMarc Flerackers 		rgb_color textColor;
3609cb2dbe2SMarc Flerackers 		rgb_color color = {0, 0, 0, 255};
3619cb2dbe2SMarc Flerackers 		BFont font;
3629cb2dbe2SMarc Flerackers 
3639cb2dbe2SMarc Flerackers 		fText->GetFontAndColor(0, &font, &color);
3649cb2dbe2SMarc Flerackers 
3659cb2dbe2SMarc Flerackers 		if (state)
3669cb2dbe2SMarc Flerackers 			textColor = color;
3679cb2dbe2SMarc Flerackers 		else
3689cb2dbe2SMarc Flerackers 			textColor = tint_color(color, B_DISABLED_LABEL_TINT);
3699cb2dbe2SMarc Flerackers 
3709cb2dbe2SMarc Flerackers 		fText->SetFontAndColor(&font, B_FONT_ALL, &textColor);
3719cb2dbe2SMarc Flerackers 
372058691d4SStefano Ceccherini 		if (state) {
3739cb2dbe2SMarc Flerackers 			color.red = 255;
3749cb2dbe2SMarc Flerackers 			color.green = 255;
3759cb2dbe2SMarc Flerackers 			color.blue = 255;
376058691d4SStefano Ceccherini 		} else
3779cb2dbe2SMarc Flerackers 			color = tint_color(ui_color(B_PANEL_BACKGROUND_COLOR),
3789cb2dbe2SMarc Flerackers 				B_LIGHTEN_2_TINT);
3799cb2dbe2SMarc Flerackers 
3809cb2dbe2SMarc Flerackers 		fText->SetViewColor(color);
3819cb2dbe2SMarc Flerackers 		fText->SetLowColor(color);
3829cb2dbe2SMarc Flerackers 
3839cb2dbe2SMarc Flerackers 		fText->Invalidate();
3849cb2dbe2SMarc Flerackers 		Window()->UpdateIfNeeded();
3859cb2dbe2SMarc Flerackers 	}
3869cb2dbe2SMarc Flerackers 
38752a38012Sejakowatz 	BControl::SetEnabled(state);
38852a38012Sejakowatz }
389058691d4SStefano Ceccherini 
390058691d4SStefano Ceccherini 
391058691d4SStefano Ceccherini void
392105644bfSAxel Dörfler BTextControl::GetPreferredSize(float *_width, float *_height)
39352a38012Sejakowatz {
394105644bfSAxel Dörfler 	if (_height) {
395105644bfSAxel Dörfler 		// we need enough space for the label and the child text view
396105644bfSAxel Dörfler 		font_height fontHeight;
397105644bfSAxel Dörfler 		GetFontHeight(&fontHeight);
398105644bfSAxel Dörfler 		float labelHeight = ceil(fontHeight.ascent + fontHeight.descent
399105644bfSAxel Dörfler 			+ fontHeight.leading);
400105644bfSAxel Dörfler 		float textHeight = fText->LineHeight(0) + 4.0;
40152a38012Sejakowatz 
402105644bfSAxel Dörfler 		*_height = max_c(labelHeight, textHeight);
403105644bfSAxel Dörfler 	}
404105644bfSAxel Dörfler 
405105644bfSAxel Dörfler 	if (_width) {
40652a38012Sejakowatz 		// TODO: this one I need to find out
407105644bfSAxel Dörfler 		float width = 20.0f + ceilf(StringWidth(Label()));
408105644bfSAxel Dörfler 		if (width < Bounds().Width())
409105644bfSAxel Dörfler 			width = Bounds().Width();
410105644bfSAxel Dörfler 		*_width = width;
411105644bfSAxel Dörfler 	}
41252a38012Sejakowatz }
413058691d4SStefano Ceccherini 
414058691d4SStefano Ceccherini 
415058691d4SStefano Ceccherini void
416058691d4SStefano Ceccherini BTextControl::ResizeToPreferred()
41752a38012Sejakowatz {
418105644bfSAxel Dörfler 	// TODO: change divider?
419105644bfSAxel Dörfler 	BView::ResizeToPreferred();
42052a38012Sejakowatz }
421058691d4SStefano Ceccherini 
422058691d4SStefano Ceccherini 
423058691d4SStefano Ceccherini void
424058691d4SStefano Ceccherini BTextControl::SetFlags(uint32 flags)
42552a38012Sejakowatz {
426058691d4SStefano Ceccherini 	if (!fSkipSetFlags) {
4279cb2dbe2SMarc Flerackers 		// If the textview is navigable, set it to not navigable if needed
4289cb2dbe2SMarc Flerackers 		// Else if it is not navigable, set it to navigable if needed
429058691d4SStefano Ceccherini 		if (fText->Flags() & B_NAVIGABLE) {
4309cb2dbe2SMarc Flerackers 			if (!(flags & B_NAVIGABLE))
4319cb2dbe2SMarc Flerackers 				fText->SetFlags(fText->Flags() & ~B_NAVIGABLE);
432058691d4SStefano Ceccherini 
433058691d4SStefano Ceccherini 		} else {
4349cb2dbe2SMarc Flerackers 			if (flags & B_NAVIGABLE)
4359cb2dbe2SMarc Flerackers 				fText->SetFlags(fText->Flags() | B_NAVIGABLE);
4369cb2dbe2SMarc Flerackers 		}
4379cb2dbe2SMarc Flerackers 
4389cb2dbe2SMarc Flerackers 		// Don't make this one navigable
4399cb2dbe2SMarc Flerackers 		flags &= ~B_NAVIGABLE;
4409cb2dbe2SMarc Flerackers 	}
4419cb2dbe2SMarc Flerackers 
44252a38012Sejakowatz 	BView::SetFlags(flags);
44352a38012Sejakowatz }
444058691d4SStefano Ceccherini 
445058691d4SStefano Ceccherini 
446058691d4SStefano Ceccherini void
447058691d4SStefano Ceccherini BTextControl::MessageReceived(BMessage *msg)
44852a38012Sejakowatz {
449058691d4SStefano Ceccherini 	switch(msg->what) {
4509cb2dbe2SMarc Flerackers 		case B_SET_PROPERTY:
4519cb2dbe2SMarc Flerackers 		case B_GET_PROPERTY:
4529cb2dbe2SMarc Flerackers 			// TODO
45352a38012Sejakowatz 			break;
45452a38012Sejakowatz 		default:
45552a38012Sejakowatz 			BControl::MessageReceived(msg);
45652a38012Sejakowatz 			break;
45752a38012Sejakowatz 	}
45852a38012Sejakowatz }
459058691d4SStefano Ceccherini 
460058691d4SStefano Ceccherini 
461058691d4SStefano Ceccherini BHandler *
462058691d4SStefano Ceccherini BTextControl::ResolveSpecifier(BMessage *msg, int32 index,
46352a38012Sejakowatz 										 BMessage *specifier, int32 form,
46452a38012Sejakowatz 										 const char *property)
46552a38012Sejakowatz {
4669cb2dbe2SMarc Flerackers 	/*
4679cb2dbe2SMarc Flerackers 	BPropertyInfo propInfo(prop_list);
4689cb2dbe2SMarc Flerackers 	BHandler *target = NULL;
4699cb2dbe2SMarc Flerackers 
4709cb2dbe2SMarc Flerackers 	if (propInfo.FindMatch(message, 0, specifier, what, property) < B_OK)
4719cb2dbe2SMarc Flerackers 		return BControl::ResolveSpecifier(message, index, specifier, what,
4729cb2dbe2SMarc Flerackers 			property);
4739cb2dbe2SMarc Flerackers 	else
4749cb2dbe2SMarc Flerackers 		return this;
4759cb2dbe2SMarc Flerackers 	*/
4769cb2dbe2SMarc Flerackers 	return BControl::ResolveSpecifier(msg, index, specifier, form, property);
47752a38012Sejakowatz }
478058691d4SStefano Ceccherini 
479058691d4SStefano Ceccherini 
480058691d4SStefano Ceccherini status_t
481058691d4SStefano Ceccherini BTextControl::GetSupportedSuites(BMessage *data)
48252a38012Sejakowatz {
4839cb2dbe2SMarc Flerackers 	return BControl::GetSupportedSuites(data);
48452a38012Sejakowatz }
485058691d4SStefano Ceccherini 
486058691d4SStefano Ceccherini 
487058691d4SStefano Ceccherini void
488058691d4SStefano Ceccherini BTextControl::MouseUp(BPoint pt)
48952a38012Sejakowatz {
49052a38012Sejakowatz 	BControl::MouseUp(pt);
49152a38012Sejakowatz }
492058691d4SStefano Ceccherini 
493058691d4SStefano Ceccherini 
494058691d4SStefano Ceccherini void
495058691d4SStefano Ceccherini BTextControl::MouseMoved(BPoint pt, uint32 code, const BMessage *msg)
49652a38012Sejakowatz {
49752a38012Sejakowatz 	BControl::MouseMoved(pt, code, msg);
49852a38012Sejakowatz }
499058691d4SStefano Ceccherini 
500058691d4SStefano Ceccherini 
501058691d4SStefano Ceccherini void
502058691d4SStefano Ceccherini BTextControl::DetachedFromWindow()
50352a38012Sejakowatz {
50452a38012Sejakowatz 	BControl::DetachedFromWindow();
50552a38012Sejakowatz }
506058691d4SStefano Ceccherini 
507058691d4SStefano Ceccherini 
508058691d4SStefano Ceccherini void
509058691d4SStefano Ceccherini BTextControl::AllAttached()
51052a38012Sejakowatz {
51152a38012Sejakowatz 	BControl::AllAttached();
51252a38012Sejakowatz }
513058691d4SStefano Ceccherini 
514058691d4SStefano Ceccherini 
515058691d4SStefano Ceccherini void
516058691d4SStefano Ceccherini BTextControl::AllDetached()
51752a38012Sejakowatz {
51852a38012Sejakowatz 	BControl::AllDetached();
51952a38012Sejakowatz }
520058691d4SStefano Ceccherini 
521058691d4SStefano Ceccherini 
522058691d4SStefano Ceccherini void
523058691d4SStefano Ceccherini BTextControl::FrameMoved(BPoint newPosition)
52452a38012Sejakowatz {
52552a38012Sejakowatz 	BControl::FrameMoved(newPosition);
52652a38012Sejakowatz }
527058691d4SStefano Ceccherini 
528058691d4SStefano Ceccherini 
529058691d4SStefano Ceccherini void
530058691d4SStefano Ceccherini BTextControl::FrameResized(float newWidth, float newHeight)
53152a38012Sejakowatz {
53252a38012Sejakowatz 	BControl::FrameResized(newWidth, newHeight);
53352a38012Sejakowatz }
534058691d4SStefano Ceccherini 
535058691d4SStefano Ceccherini 
536058691d4SStefano Ceccherini void
537058691d4SStefano Ceccherini BTextControl::WindowActivated(bool active)
53852a38012Sejakowatz {
5396d8d6cadSStephan Aßmus 	if (fText->IsFocus()) {
5406d8d6cadSStephan Aßmus 		BRect rect(fText->Frame());
5416d8d6cadSStephan Aßmus 		rect.InsetBy(-1.0, -1.0);
5426d8d6cadSStephan Aßmus 		Invalidate(rect);
5436d8d6cadSStephan Aßmus 	}
54452a38012Sejakowatz }
545058691d4SStefano Ceccherini 
546058691d4SStefano Ceccherini 
547058691d4SStefano Ceccherini status_t
548058691d4SStefano Ceccherini BTextControl::Perform(perform_code d, void *arg)
54952a38012Sejakowatz {
55052a38012Sejakowatz 	return BControl::Perform(d, arg);
55152a38012Sejakowatz }
552058691d4SStefano Ceccherini 
553058691d4SStefano Ceccherini 
5549cb2dbe2SMarc Flerackers void BTextControl::_ReservedTextControl1() {}
5559cb2dbe2SMarc Flerackers void BTextControl::_ReservedTextControl2() {}
5569cb2dbe2SMarc Flerackers void BTextControl::_ReservedTextControl3() {}
5579cb2dbe2SMarc Flerackers void BTextControl::_ReservedTextControl4() {}
558058691d4SStefano Ceccherini 
559058691d4SStefano Ceccherini 
560058691d4SStefano Ceccherini BTextControl &
561058691d4SStefano Ceccherini BTextControl::operator=(const BTextControl&)
56252a38012Sejakowatz {
56352a38012Sejakowatz 	return *this;
56452a38012Sejakowatz }
565058691d4SStefano Ceccherini 
566058691d4SStefano Ceccherini 
567058691d4SStefano Ceccherini void
568058691d4SStefano Ceccherini BTextControl::CommitValue()
5699cb2dbe2SMarc Flerackers {
5709cb2dbe2SMarc Flerackers }
571058691d4SStefano Ceccherini 
572058691d4SStefano Ceccherini 
573058691d4SStefano Ceccherini void
574058691d4SStefano Ceccherini BTextControl::InitData(const char *label, const char *initial_text,
5759cb2dbe2SMarc Flerackers 							BMessage *data)
5769cb2dbe2SMarc Flerackers {
5779cb2dbe2SMarc Flerackers 	BRect bounds(Bounds());
5789cb2dbe2SMarc Flerackers 
5799cb2dbe2SMarc Flerackers 	fText = NULL;
5809cb2dbe2SMarc Flerackers 	fModificationMessage = NULL;
5819cb2dbe2SMarc Flerackers 	fLabelAlign = B_ALIGN_LEFT;
5829cb2dbe2SMarc Flerackers 	fDivider = 0.0f;
5839cb2dbe2SMarc Flerackers 	fPrevWidth = 0;
5849cb2dbe2SMarc Flerackers 	fPrevHeight = 0;
5859cb2dbe2SMarc Flerackers 	fSkipSetFlags = false;
5869cb2dbe2SMarc Flerackers 
5879cb2dbe2SMarc Flerackers 	int32 flags = 0;
5889cb2dbe2SMarc Flerackers 
589918a22d9SDarkWyrm 	BFont font(be_plain_font);
5909cb2dbe2SMarc Flerackers 
5919cb2dbe2SMarc Flerackers 	if (!data || !data->HasString("_fname"))
592058691d4SStefano Ceccherini 		flags |= B_FONT_FAMILY_AND_STYLE;
5939cb2dbe2SMarc Flerackers 
5949cb2dbe2SMarc Flerackers 	if (!data || !data->HasFloat("_fflt"))
595058691d4SStefano Ceccherini 		flags |= B_FONT_SIZE;
5969cb2dbe2SMarc Flerackers 
5979cb2dbe2SMarc Flerackers 	if (flags != 0)
5989cb2dbe2SMarc Flerackers 		SetFont(&font, flags);
5999cb2dbe2SMarc Flerackers 
6009cb2dbe2SMarc Flerackers 	if (label)
6012e6a5805SStephan Aßmus 		fDivider = floorf(bounds.Width() / 2.0f);
6029cb2dbe2SMarc Flerackers 
603105644bfSAxel Dörfler 	uint32 navigableFlags = Flags() & B_NAVIGABLE;
604105644bfSAxel Dörfler 	if (navigableFlags != 0) {
6059cb2dbe2SMarc Flerackers 		fSkipSetFlags = true;
6069cb2dbe2SMarc Flerackers 		SetFlags(Flags() & ~B_NAVIGABLE);
6079cb2dbe2SMarc Flerackers 		fSkipSetFlags = false;
6089cb2dbe2SMarc Flerackers 	}
6099cb2dbe2SMarc Flerackers 
6109cb2dbe2SMarc Flerackers 	if (data)
611058691d4SStefano Ceccherini 		fText = static_cast<_BTextInput_ *>(FindView("_input_"));
612058691d4SStefano Ceccherini 	else {
6132e6a5805SStephan Aßmus 		BRect frame(fDivider, bounds.top,
6142e6a5805SStephan Aßmus 					bounds.right, bounds.bottom);
615105644bfSAxel Dörfler 		// we are stroking the frame around the text view, which
6162e6a5805SStephan Aßmus 		// is 2 pixels wide
617105644bfSAxel Dörfler 		frame.InsetBy(3.0, 3.0);
6189cb2dbe2SMarc Flerackers 		BRect textRect(frame.OffsetToCopy(0.0f, 0.0f));
6199cb2dbe2SMarc Flerackers 
6209cb2dbe2SMarc Flerackers 		fText = new _BTextInput_(frame, textRect,
6217a70a2d6SStephan Aßmus 			B_FOLLOW_LEFT_RIGHT | B_FOLLOW_TOP,
622105644bfSAxel Dörfler 			B_WILL_DRAW | B_FRAME_EVENTS | navigableFlags);
6239cb2dbe2SMarc Flerackers 		AddChild(fText);
6249cb2dbe2SMarc Flerackers 
6259cb2dbe2SMarc Flerackers 		SetText(initial_text);
6269cb2dbe2SMarc Flerackers 		fText->SetAlignment(B_ALIGN_LEFT);
6279cb2dbe2SMarc Flerackers 		fText->AlignTextRect();
6289cb2dbe2SMarc Flerackers 	}
6299cb2dbe2SMarc Flerackers }
630