* Copyright 2007, Ingo Weinhold <bonefish@cs.tu-berlin.de>.
* All rights reserved. Distributed under the terms of the MIT License.
*/
#include "RadioButton.h"
#include <View.h>
#include "StringView.h"
RadioButton::RadioButton(BMessage* message, BMessenger target)
: AbstractButton(BUTTON_POLICY_SELECT_ON_RELEASE, message, target)
{
SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR));
}
BSize
RadioButton::MinSize()
{
return BSize(12, 12);
}
BSize
RadioButton::MaxSize()
{
return MinSize();
}
void
RadioButton::Draw(BView* container, BRect updateRect)
{
BRect rect(Bounds());
if (IsPressed())
container->SetHighColor((rgb_color){ 120, 0, 0, 255 });
else
container->SetHighColor((rgb_color){ 0, 0, 0, 255 });
container->StrokeRect(rect);
if (IsSelected()) {
rect.InsetBy(4, 4);
container->FillRect(rect);
}
}
LabeledRadioButton::LabeledRadioButton(const char* label, BMessage* message,
BMessenger target)
: GroupView(B_HORIZONTAL),
fRadioButton(new RadioButton(message, target))
{
SetSpacing(8, 0);
AddChild(fRadioButton);
if (label)
AddChild(new StringView(label));
}
void
LabeledRadioButton::SetTarget(BMessenger messenger)
{
fRadioButton->SetTarget(messenger);
}
void
LabeledRadioButton::SetSelected(bool selected)
{
fRadioButton->SetSelected(selected);
}
bool
LabeledRadioButton::IsSelected() const
{
return fRadioButton->IsSelected();
}
RadioButtonGroup::RadioButtonGroup(BMessage* message, BMessenger target)
: BInvoker(message, target),
fButtons(10),
fSelected(NULL)
{
}
RadioButtonGroup::~RadioButtonGroup()
{
for (int32 i = 0; AbstractButton* button = ButtonAt(i); i++)
button->RemoveListener(this);
}
void
RadioButtonGroup::AddButton(AbstractButton* button)
{
if (!button || fButtons.HasItem(button))
return;
button->SetPolicy(BUTTON_POLICY_SELECT_ON_RELEASE);
if (fSelected)
button->SetSelected(false);
button->AddListener(this);
fButtons.AddItem(button);
}
bool
RadioButtonGroup::RemoveButton(AbstractButton* button)
{
return RemoveButton(IndexOfButton(button));
}
AbstractButton*
RadioButtonGroup::RemoveButton(int32 index)
{
AbstractButton* button = (AbstractButton*)fButtons.RemoveItem(index);
if (!button)
return NULL;
button->RemoveListener(this);
if (button == fSelected) {
fSelected = NULL;
_SelectionChanged();
}
return button;
}
int32
RadioButtonGroup::CountButtons() const
{
return fButtons.CountItems();
}
AbstractButton*
RadioButtonGroup::ButtonAt(int32 index) const
{
return (AbstractButton*)fButtons.ItemAt(index);
}
int32
RadioButtonGroup::IndexOfButton(AbstractButton* button) const
{
return fButtons.IndexOf(button);
}
void
RadioButtonGroup::SelectButton(AbstractButton* button)
{
if (button && fButtons.HasItem(button))
button->SetSelected(true);
}
void
RadioButtonGroup::SelectButton(int32 index)
{
if (AbstractButton* button = ButtonAt(index))
button->SetSelected(true);
}
AbstractButton*
RadioButtonGroup::SelectedButton() const
{
return fSelected;
}
int32
RadioButtonGroup::SelectedIndex() const
{
return (fSelected ? IndexOfButton(fSelected) : -1);
}
void
RadioButtonGroup::SelectionChanged(AbstractButton* button)
{
if (!button || !fButtons.HasItem(button) || !button->IsSelected()
|| button == fSelected) {
return;
}
AbstractButton* oldSelected = fSelected;
fSelected = button;
if (oldSelected)
oldSelected->SetSelected(false);
_SelectionChanged();
}
void
RadioButtonGroup::_SelectionChanged()
{
if (Message()) {
BMessage message(*Message());
message.AddPointer("button group", this);
message.AddPointer("selected button", fSelected);
message.AddInt32("selected index", SelectedIndex());
InvokeNotify(&message);
}
}