Newer
Older
Steven Bennetts
committed
return NULL;
}
S32 LLTabContainer::getCurrentPanelIndex()
{
return mCurrentTabIdx;
}
S32 LLTabContainer::getTabCount()
Steven Bennetts
committed
return mTabList.size();
}
Steven Bennetts
committed
LLPanel* LLTabContainer::getPanelByIndex(S32 index)
{
if (index >= 0 && index < (S32)mTabList.size())
Steven Bennetts
committed
return mTabList[index]->mTabPanel;
}
return NULL;
}
Steven Bennetts
committed
S32 LLTabContainer::getIndexForPanel(LLPanel* panel)
{
for (S32 index = 0; index < (S32)mTabList.size(); index++)
{
if (mTabList[index]->mTabPanel == panel)
Steven Bennetts
committed
return index;
Steven Bennetts
committed
return -1;
}
S32 LLTabContainer::getPanelIndexByTitle(const std::string& title)
Steven Bennetts
committed
{
for (S32 index = 0 ; index < (S32)mTabList.size(); index++)
Steven Bennetts
committed
if (title == mTabList[index]->mButton->getLabelSelected())
{
return index;
}
Steven Bennetts
committed
return -1;
LLPanel *LLTabContainer::getPanelByName(const std::string& name)
Steven Bennetts
committed
for (S32 index = 0 ; index < (S32)mTabList.size(); index++)
Steven Bennetts
committed
LLPanel *panel = mTabList[index]->mTabPanel;
if (name == panel->getName())
Steven Bennetts
committed
return panel;
Steven Bennetts
committed
return NULL;
}
// Change the name of the button for the current tab.
void LLTabContainer::setCurrentTabName(const std::string& name)
Steven Bennetts
committed
1062
1063
1064
1065
1066
1067
1068
1069
1070
1071
1072
1073
1074
1075
1076
1077
1078
1079
1080
1081
1082
1083
1084
1085
1086
1087
1088
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100
1101
1102
1103
1104
1105
1106
1107
1108
1109
1110
1111
1112
1113
1114
1115
1116
1117
1118
1119
1120
1121
1122
{
// Might not have a tab selected
if (mCurrentTabIdx < 0) return;
mTabList[mCurrentTabIdx]->mButton->setLabelSelected(name);
mTabList[mCurrentTabIdx]->mButton->setLabelUnselected(name);
}
void LLTabContainer::selectFirstTab()
{
selectTab( 0 );
}
void LLTabContainer::selectLastTab()
{
selectTab( mTabList.size()-1 );
}
void LLTabContainer::selectNextTab()
{
BOOL tab_has_focus = FALSE;
if (mCurrentTabIdx >= 0 && mTabList[mCurrentTabIdx]->mButton->hasFocus())
{
tab_has_focus = TRUE;
}
S32 idx = mCurrentTabIdx+1;
if (idx >= (S32)mTabList.size())
idx = 0;
while (!selectTab(idx) && idx != mCurrentTabIdx)
{
idx = (idx + 1 ) % (S32)mTabList.size();
}
if (tab_has_focus)
{
mTabList[idx]->mButton->setFocus(TRUE);
}
}
void LLTabContainer::selectPrevTab()
{
BOOL tab_has_focus = FALSE;
if (mCurrentTabIdx >= 0 && mTabList[mCurrentTabIdx]->mButton->hasFocus())
{
tab_has_focus = TRUE;
}
S32 idx = mCurrentTabIdx-1;
if (idx < 0)
idx = mTabList.size()-1;
while (!selectTab(idx) && idx != mCurrentTabIdx)
{
idx = idx - 1;
if (idx < 0)
idx = mTabList.size()-1;
}
if (tab_has_focus)
{
mTabList[idx]->mButton->setFocus(TRUE);
}
}
Steven Bennetts
committed
BOOL LLTabContainer::selectTabPanel(LLPanel* child)
Steven Bennetts
committed
S32 idx = 0;
for(tuple_list_t::iterator iter = mTabList.begin(); iter != mTabList.end(); ++iter)
{
LLTabTuple* tuple = *iter;
if( tuple->mTabPanel == child )
{
return selectTab( idx );
}
idx++;
}
return FALSE;
}
BOOL LLTabContainer::selectTab(S32 which)
{
Steven Bennetts
committed
if (which >= getTabCount()) return FALSE;
if (which < 0) return FALSE;
//if( gFocusMgr.childHasKeyboardFocus( this ) )
//{
Steven Bennetts
committed
LLTabTuple* selected_tuple = getTab(which);
if (!selected_tuple)
{
return FALSE;
}
1154
1155
1156
1157
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
1168
1169
1170
1171
1172
1173
1174
1175
1176
1177
1178
1179
1180
1181
1182
if (!selected_tuple->mPrecommitChangeCallback)
{
return setTab(which);
}
mNextTabIdx = which;
selected_tuple->mPrecommitChangeCallback(selected_tuple->mUserData, false);
return TRUE;
}
BOOL LLTabContainer::setTab(S32 which)
{
if (which == -1)
{
if (mNextTabIdx == -1)
{
return FALSE;
}
which = mNextTabIdx;
mNextTabIdx = -1;
}
LLTabTuple* selected_tuple = getTab(which);
if (!selected_tuple)
{
return FALSE;
}
Steven Bennetts
committed
BOOL is_visible = FALSE;
if (selected_tuple->mButton->getEnabled())
Steven Bennetts
committed
setCurrentPanelIndex(which);
S32 i = 0;
for(tuple_list_t::iterator iter = mTabList.begin(); iter != mTabList.end(); ++iter)
{
LLTabTuple* tuple = *iter;
BOOL is_selected = ( tuple == selected_tuple );
tuple->mTabPanel->setVisible( is_selected );
// tuple->mTabPanel->setFocus(is_selected); // not clear that we want to do this here.
tuple->mButton->setToggleState( is_selected );
// RN: this limits tab-stops to active button only, which would require arrow keys to switch tabs
tuple->mButton->setTabStop( is_selected );
Steven Bennetts
committed
if( is_selected && (mIsVertical || (getMaxScrollPos() > 0)))
{
// Make sure selected tab is within scroll region
Steven Bennetts
committed
if (mIsVertical)
Steven Bennetts
committed
S32 num_visible = getTabCount() - getMaxScrollPos();
if( i >= getScrollPos() && i <= getScrollPos() + num_visible)
{
setCurrentPanelIndex(which);
is_visible = TRUE;
}
else
{
is_visible = FALSE;
}
Steven Bennetts
committed
if( i < getScrollPos() )
{
setScrollPos(i);
}
else
Steven Bennetts
committed
S32 available_width_with_arrows = getRect().getWidth() - mRightTabBtnOffset - 2 * (LLPANEL_BORDER_WIDTH + TABCNTR_ARROW_BTN_SIZE + TABCNTR_ARROW_BTN_SIZE + 1);
S32 running_tab_width = tuple->mButton->getRect().getWidth();
S32 j = i - 1;
S32 min_scroll_pos = i;
if (running_tab_width < available_width_with_arrows)
Steven Bennetts
committed
while (j >= 0)
Steven Bennetts
committed
LLTabTuple* other_tuple = getTab(j);
running_tab_width += other_tuple->mButton->getRect().getWidth();
if (running_tab_width > available_width_with_arrows)
{
break;
}
j--;
Steven Bennetts
committed
min_scroll_pos = j + 1;
Steven Bennetts
committed
setScrollPos(llclamp(getScrollPos(), min_scroll_pos, i));
setScrollPos(llmin(getScrollPos(), getMaxScrollPos()));
Steven Bennetts
committed
is_visible = TRUE;
}
}
i++;
}
if( selected_tuple->mOnChangeCallback )
{
selected_tuple->mOnChangeCallback( selected_tuple->mUserData, false );
}
}
Steven Bennetts
committed
if (mIsVertical && getCurrentPanelIndex() >= 0)
Steven Bennetts
committed
LLTabTuple* tuple = getTab(getCurrentPanelIndex());
tuple->mTabPanel->setVisible( TRUE );
tuple->mButton->setToggleState( TRUE );
Steven Bennetts
committed
return is_visible;
BOOL LLTabContainer::selectTabByName(const std::string& name)
Steven Bennetts
committed
LLPanel* panel = getPanelByName(name);
if (!panel)
Steven Bennetts
committed
llwarns << "LLTabContainer::selectTabByName("
<< name << ") failed" << llendl;
return FALSE;
}
Steven Bennetts
committed
BOOL result = selectTabPanel(panel);
return result;
}
BOOL LLTabContainer::getTabPanelFlashing(LLPanel *child)
{
LLTabTuple* tuple = getTabByPanel(child);
if( tuple )
{
return tuple->mButton->getFlashing();
Steven Bennetts
committed
return FALSE;
}
Steven Bennetts
committed
void LLTabContainer::setTabPanelFlashing(LLPanel* child, BOOL state )
{
LLTabTuple* tuple = getTabByPanel(child);
if( tuple )
Steven Bennetts
committed
tuple->mButton->setFlashing( state );
}
}
Steven Bennetts
committed
void LLTabContainer::setTabImage(LLPanel* child, std::string image_name, const LLColor4& color)
{
LLTabTuple* tuple = getTabByPanel(child);
if( tuple )
{
tuple->mButton->setImageOverlay(image_name, LLFontGL::RIGHT, color);
Steven Bennetts
committed
if (!mIsVertical)
const LLFontGL* fontp = LLResMgr::getInstance()->getRes( LLFONT_SANSSERIF_SMALL );
Steven Bennetts
committed
// remove current width from total tab strip width
mTotalTabWidth -= tuple->mButton->getRect().getWidth();
Steven Bennetts
committed
S32 image_overlay_width = tuple->mButton->getImageOverlay().notNull() ?
tuple->mButton->getImageOverlay()->getImage()->getWidth(0) :
0;
Steven Bennetts
committed
tuple->mPadding = image_overlay_width;
Steven Bennetts
committed
tuple->mButton->setRightHPad(6);
tuple->mButton->reshape(llclamp(fontp->getWidth(tuple->mButton->getLabelSelected()) + TAB_PADDING + tuple->mPadding, mMinTabWidth, mMaxTabWidth),
tuple->mButton->getRect().getHeight());
// add back in button width to total tab strip width
mTotalTabWidth += tuple->mButton->getRect().getWidth();
Steven Bennetts
committed
// tabs have changed size, might need to scroll to see current tab
updateMaxScrollPos();
}
}
}
void LLTabContainer::setTitle(const std::string& title)
Steven Bennetts
committed
{
if (mTitleBox)
{
mTitleBox->setText( title );
}
}
const std::string LLTabContainer::getPanelTitle(S32 index)
Steven Bennetts
committed
{
if (index >= 0 && index < (S32)mTabList.size())
{
LLButton* tab_button = mTabList[index]->mButton;
return tab_button->getLabelSelected();
}
return LLStringUtil::null;
Steven Bennetts
committed
}
Steven Bennetts
committed
void LLTabContainer::setTopBorderHeight(S32 height)
{
mTopBorderHeight = height;
}
S32 LLTabContainer::getTopBorderHeight() const
{
return mTopBorderHeight;
}
Steven Bennetts
committed
void LLTabContainer::setTabChangeCallback(LLPanel* tab, void (*on_tab_clicked)(void*, bool))
{
LLTabTuple* tuplep = getTabByPanel(tab);
if (tuplep)
{
tuplep->mOnChangeCallback = on_tab_clicked;
void LLTabContainer::setTabPrecommitChangeCallback(LLPanel* tab, void (*on_precommit)(void*, bool))
{
LLTabTuple* tuplep = getTabByPanel(tab);
if (tuplep)
{
tuplep->mPrecommitChangeCallback = on_precommit;
}
}
Steven Bennetts
committed
void LLTabContainer::setTabUserData(LLPanel* tab, void* userdata)
{
LLTabTuple* tuplep = getTabByPanel(tab);
if (tuplep)
{
tuplep->mUserData = userdata;
}
}
void LLTabContainer::setRightTabBtnOffset(S32 offset)
{
Steven Bennetts
committed
mNextArrowBtn->translate( -offset - mRightTabBtnOffset, 0 );
mRightTabBtnOffset = offset;
updateMaxScrollPos();
}
void LLTabContainer::setPanelTitle(S32 index, const std::string& title)
Steven Bennetts
committed
if (index >= 0 && index < getTabCount())
{
LLTabTuple* tuple = getTab(index);
LLButton* tab_button = tuple->mButton;
const LLFontGL* fontp = LLResMgr::getInstance()->getRes( LLFONT_SANSSERIF_SMALL );
Steven Bennetts
committed
mTotalTabWidth -= tab_button->getRect().getWidth();
tab_button->reshape(llclamp(fontp->getWidth(title) + TAB_PADDING + tuple->mPadding, mMinTabWidth, mMaxTabWidth), tab_button->getRect().getHeight());
mTotalTabWidth += tab_button->getRect().getWidth();
tab_button->setLabelSelected(title);
tab_button->setLabelUnselected(title);
}
updateMaxScrollPos();
}
Steven Bennetts
committed
// static
void LLTabContainer::onTabBtn( void* userdata )
{
LLTabTuple* tuple = (LLTabTuple*) userdata;
LLTabContainer* self = tuple->mTabContainer;
self->selectTabPanel( tuple->mTabPanel );
tuple->mTabPanel->setFocus(TRUE);
}
// static
void LLTabContainer::onCloseBtn( void* userdata )
{
LLTabContainer* self = (LLTabContainer*) userdata;
if( self->mCloseCallback )
Steven Bennetts
committed
self->mCloseCallback( self->mCallbackUserdata );
Steven Bennetts
committed
}
Steven Bennetts
committed
// static
void LLTabContainer::onNextBtn( void* userdata )
{
// Scroll tabs to the left
LLTabContainer* self = (LLTabContainer*) userdata;
if (!self->mScrolled)
Steven Bennetts
committed
self->scrollNext();
Steven Bennetts
committed
self->mScrolled = FALSE;
Steven Bennetts
committed
// static
void LLTabContainer::onNextBtnHeld( void* userdata )
Steven Bennetts
committed
LLTabContainer* self = (LLTabContainer*) userdata;
if (self->mScrollTimer.getElapsedTimeF32() > SCROLL_STEP_TIME)
{
self->mScrollTimer.reset();
self->scrollNext();
self->mScrolled = TRUE;
}
}
Steven Bennetts
committed
// static
void LLTabContainer::onPrevBtn( void* userdata )
{
LLTabContainer* self = (LLTabContainer*) userdata;
if (!self->mScrolled)
{
self->scrollPrev();
Steven Bennetts
committed
1458
1459
1460
1461
1462
1463
1464
1465
1466
1467
1468
1469
1470
1471
1472
1473
1474
1475
1476
1477
1478
1479
self->mScrolled = FALSE;
}
// static
void LLTabContainer::onJumpFirstBtn( void* userdata )
{
LLTabContainer* self = (LLTabContainer*) userdata;
self->mScrollPos = 0;
}
// static
void LLTabContainer::onJumpLastBtn( void* userdata )
{
LLTabContainer* self = (LLTabContainer*) userdata;
self->mScrollPos = self->mMaxScrollPos;
}
// static
void LLTabContainer::onPrevBtnHeld( void* userdata )
{
LLTabContainer* self = (LLTabContainer*) userdata;
if (self->mScrollTimer.getElapsedTimeF32() > SCROLL_STEP_TIME)
Steven Bennetts
committed
self->mScrollTimer.reset();
self->scrollPrev();
self->mScrolled = TRUE;
Steven Bennetts
committed
// static
LLView* LLTabContainer::fromXML(LLXMLNodePtr node, LLView *parent, LLUICtrlFactory *factory)
std::string name("tab_container");
Steven Bennetts
committed
node->getAttributeString("name", name);
Steven Bennetts
committed
// Figure out if we are creating a vertical or horizontal tab container.
bool is_vertical = false;
LLTabContainer::TabPosition tab_position = LLTabContainer::TOP;
if (node->hasAttribute("tab_position"))
std::string tab_position_string;
Steven Bennetts
committed
node->getAttributeString("tab_position", tab_position_string);
LLStringUtil::toLower(tab_position_string);
Steven Bennetts
committed
if ("top" == tab_position_string)
Josh Bell
committed
{
Steven Bennetts
committed
tab_position = LLTabContainer::TOP;
is_vertical = false;
Josh Bell
committed
}
Steven Bennetts
committed
else if ("bottom" == tab_position_string)
Steven Bennetts
committed
tab_position = LLTabContainer::BOTTOM;
is_vertical = false;
Steven Bennetts
committed
else if ("left" == tab_position_string)
Steven Bennetts
committed
is_vertical = true;
Steven Bennetts
committed
BOOL border = FALSE;
node->getAttributeBOOL("border", border);
LLTabContainer* tab_container = new LLTabContainer(name, LLRect::null, tab_position, border, is_vertical);
S32 tab_min_width = tab_container->mMinTabWidth;
if (node->hasAttribute("tab_width"))
Steven Bennetts
committed
node->getAttributeS32("tab_width", tab_min_width);
}
else if( node->hasAttribute("tab_min_width"))
{
node->getAttributeS32("tab_min_width", tab_min_width);
Steven Bennetts
committed
S32 tab_max_width = tab_container->mMaxTabWidth;
if (node->hasAttribute("tab_max_width"))
Steven Bennetts
committed
1535
1536
1537
1538
1539
1540
1541
1542
1543
1544
1545
1546
1547
1548
1549
1550
1551
1552
1553
1554
1555
1556
1557
1558
1559
node->getAttributeS32("tab_max_width", tab_max_width);
}
tab_container->setMinTabWidth(tab_min_width);
tab_container->setMaxTabWidth(tab_max_width);
BOOL hidden(tab_container->getTabsHidden());
node->getAttributeBOOL("hide_tabs", hidden);
tab_container->setTabsHidden(hidden);
tab_container->setPanelParameters(node, parent);
if (LLFloater::getFloaterHost())
{
LLFloater::getFloaterHost()->setTabContainer(tab_container);
}
//parent->addChild(tab_container);
// Add all tab panels.
LLXMLNodePtr child;
for (child = node->getFirstChild(); child.notNull(); child = child->getNextSibling())
{
LLView *control = factory->createCtrlWidget(tab_container, child);
if (control && control->isPanel())
Steven Bennetts
committed
LLPanel* panelp = (LLPanel*)control;
std::string label;
Steven Bennetts
committed
child->getAttributeString("label", label);
if (label.empty())
Steven Bennetts
committed
label = panelp->getLabel();
Steven Bennetts
committed
BOOL placeholder = FALSE;
child->getAttributeBOOL("placeholder", placeholder);
tab_container->addTabPanel(panelp, label, false,
Steven Bennetts
committed
NULL, NULL, 0, placeholder);
Steven Bennetts
committed
tab_container->selectFirstTab();
tab_container->postBuild();
tab_container->initButtons(); // now that we have the correct rect
return tab_container;
Steven Bennetts
committed
// private
void LLTabContainer::initButtons()
Steven Bennetts
committed
// Hack:
if (getRect().getHeight() == 0 || mPrevArrowBtn)
Steven Bennetts
committed
return; // Don't have a rect yet or already got called
}
std::string out_id;
std::string in_id;
Steven Bennetts
committed
if (mIsVertical)
{
// Left and right scroll arrows (for when there are too many tabs to show all at once).
S32 btn_top = getRect().getHeight();
S32 btn_top_lower = getRect().mBottom+TABCNTRV_ARROW_BTN_SIZE;
LLRect up_arrow_btn_rect;
up_arrow_btn_rect.setLeftTopAndSize( mMinTabWidth/2 , btn_top, TABCNTRV_ARROW_BTN_SIZE, TABCNTRV_ARROW_BTN_SIZE );
LLRect down_arrow_btn_rect;
down_arrow_btn_rect.setLeftTopAndSize( mMinTabWidth/2 , btn_top_lower, TABCNTRV_ARROW_BTN_SIZE, TABCNTRV_ARROW_BTN_SIZE );
out_id = "UIImgBtnScrollUpOutUUID";
in_id = "UIImgBtnScrollUpInUUID";
mPrevArrowBtn = new LLButton(std::string("Up Arrow"), up_arrow_btn_rect,
out_id, in_id, LLStringUtil::null,
Steven Bennetts
committed
&onPrevBtn, this, NULL );
mPrevArrowBtn->setFollowsTop();
mPrevArrowBtn->setFollowsLeft();
out_id = "UIImgBtnScrollDownOutUUID";
in_id = "UIImgBtnScrollDownInUUID";
mNextArrowBtn = new LLButton(std::string("Down Arrow"), down_arrow_btn_rect,
out_id, in_id, LLStringUtil::null,
Steven Bennetts
committed
&onNextBtn, this, NULL );
mNextArrowBtn->setFollowsBottom();
mNextArrowBtn->setFollowsLeft();
}
else // Horizontal
{
S32 arrow_fudge = 1; // match new art better
// tabs on bottom reserve room for resize handle (just in case)
if (getTabPosition() == BOTTOM)
Steven Bennetts
committed
mRightTabBtnOffset = RESIZE_HANDLE_WIDTH;
Steven Bennetts
committed
1635
1636
1637
1638
1639
1640
1641
1642
1643
1644
1645
1646
1647
1648
1649
1650
1651
1652
1653
1654
1655
1656
1657
1658
// Left and right scroll arrows (for when there are too many tabs to show all at once).
S32 btn_top = (getTabPosition() == TOP ) ? getRect().getHeight() - getTopBorderHeight() : TABCNTR_ARROW_BTN_SIZE + 1;
LLRect left_arrow_btn_rect;
left_arrow_btn_rect.setLeftTopAndSize( LLPANEL_BORDER_WIDTH+1+TABCNTR_ARROW_BTN_SIZE, btn_top + arrow_fudge, TABCNTR_ARROW_BTN_SIZE, TABCNTR_ARROW_BTN_SIZE );
LLRect jump_left_arrow_btn_rect;
jump_left_arrow_btn_rect.setLeftTopAndSize( LLPANEL_BORDER_WIDTH+1, btn_top + arrow_fudge, TABCNTR_ARROW_BTN_SIZE, TABCNTR_ARROW_BTN_SIZE );
S32 right_pad = TABCNTR_ARROW_BTN_SIZE + LLPANEL_BORDER_WIDTH + 1;
LLRect right_arrow_btn_rect;
right_arrow_btn_rect.setLeftTopAndSize( getRect().getWidth() - mRightTabBtnOffset - right_pad - TABCNTR_ARROW_BTN_SIZE,
btn_top + arrow_fudge,
TABCNTR_ARROW_BTN_SIZE, TABCNTR_ARROW_BTN_SIZE );
LLRect jump_right_arrow_btn_rect;
jump_right_arrow_btn_rect.setLeftTopAndSize( getRect().getWidth() - mRightTabBtnOffset - right_pad,
btn_top + arrow_fudge,
TABCNTR_ARROW_BTN_SIZE, TABCNTR_ARROW_BTN_SIZE );
out_id = "UIImgBtnJumpLeftOutUUID";
in_id = "UIImgBtnJumpLeftInUUID";
mJumpPrevArrowBtn = new LLButton(std::string("Jump Left Arrow"), jump_left_arrow_btn_rect,
out_id, in_id, LLStringUtil::null,
&LLTabContainer::onJumpFirstBtn, this, LLFontGL::getFontSansSerif() );
Steven Bennetts
committed
mJumpPrevArrowBtn->setFollowsLeft();
out_id = "UIImgBtnScrollLeftOutUUID";
in_id = "UIImgBtnScrollLeftInUUID";
mPrevArrowBtn = new LLButton(std::string("Left Arrow"), left_arrow_btn_rect,
out_id, in_id, LLStringUtil::null,
&LLTabContainer::onPrevBtn, this, LLFontGL::getFontSansSerif() );
Steven Bennetts
committed
mPrevArrowBtn->setHeldDownCallback(onPrevBtnHeld);
mPrevArrowBtn->setFollowsLeft();
out_id = "UIImgBtnJumpRightOutUUID";
in_id = "UIImgBtnJumpRightInUUID";
mJumpNextArrowBtn = new LLButton(std::string("Jump Right Arrow"), jump_right_arrow_btn_rect,
out_id, in_id, LLStringUtil::null,
Steven Bennetts
committed
&LLTabContainer::onJumpLastBtn, this,
Steven Bennetts
committed
mJumpNextArrowBtn->setFollowsRight();
out_id = "UIImgBtnScrollRightOutUUID";
in_id = "UIImgBtnScrollRightInUUID";
mNextArrowBtn = new LLButton(std::string("Right Arrow"), right_arrow_btn_rect,
out_id, in_id, LLStringUtil::null,
Steven Bennetts
committed
&LLTabContainer::onNextBtn, this,
Steven Bennetts
committed
mNextArrowBtn->setFollowsRight();
if( getTabPosition() == TOP )
Steven Bennetts
committed
mNextArrowBtn->setFollowsTop();
mPrevArrowBtn->setFollowsTop();
mJumpPrevArrowBtn->setFollowsTop();
mJumpNextArrowBtn->setFollowsTop();
}
else
{
mNextArrowBtn->setFollowsBottom();
mPrevArrowBtn->setFollowsBottom();
mJumpPrevArrowBtn->setFollowsBottom();
mJumpNextArrowBtn->setFollowsBottom();
Steven Bennetts
committed
mPrevArrowBtn->setHeldDownCallback(onPrevBtnHeld);
mPrevArrowBtn->setSaveToXML(false);
mPrevArrowBtn->setTabStop(FALSE);
addChild(mPrevArrowBtn);
Steven Bennetts
committed
mNextArrowBtn->setHeldDownCallback(onNextBtnHeld);
mNextArrowBtn->setSaveToXML(false);
mNextArrowBtn->setTabStop(FALSE);
addChild(mNextArrowBtn);
Steven Bennetts
committed
if (mJumpPrevArrowBtn)
Steven Bennetts
committed
mJumpPrevArrowBtn->setSaveToXML(false);
mJumpPrevArrowBtn->setTabStop(FALSE);
addChild(mJumpPrevArrowBtn);
Steven Bennetts
committed
if (mJumpNextArrowBtn)
Steven Bennetts
committed
mJumpNextArrowBtn->setSaveToXML(false);
mJumpNextArrowBtn->setTabStop(FALSE);
addChild(mJumpNextArrowBtn);
Steven Bennetts
committed
// set default tab group to be panel contents
setDefaultTabGroup(1);
}
Steven Bennetts
committed
LLTabContainer::LLTabTuple* LLTabContainer::getTabByPanel(LLPanel* child)
{
for(tuple_list_t::iterator iter = mTabList.begin(); iter != mTabList.end(); ++iter)
Steven Bennetts
committed
LLTabTuple* tuple = *iter;
if( tuple->mTabPanel == child )
Steven Bennetts
committed
return tuple;
Steven Bennetts
committed
return NULL;
}
Steven Bennetts
committed
void LLTabContainer::insertTuple(LLTabTuple * tuple, eInsertionPoint insertion_point)
{
switch(insertion_point)
Steven Bennetts
committed
case START:
// insert the new tab in the front of the list
mTabList.insert(mTabList.begin() + mLockedTabCount, tuple);
break;
case LEFT_OF_CURRENT:
// insert the new tab before the current tab (but not before mLockedTabCount)
Steven Bennetts
committed
tuple_list_t::iterator current_iter = mTabList.begin() + llmax(mLockedTabCount, mCurrentTabIdx);
mTabList.insert(current_iter, tuple);
}
break;
case RIGHT_OF_CURRENT:
// insert the new tab after the current tab (but not before mLockedTabCount)
{
tuple_list_t::iterator current_iter = mTabList.begin() + llmax(mLockedTabCount, mCurrentTabIdx + 1);
mTabList.insert(current_iter, tuple);
Steven Bennetts
committed
break;
case END:
default:
mTabList.push_back( tuple );
Steven Bennetts
committed
void LLTabContainer::updateMaxScrollPos()
Steven Bennetts
committed
BOOL no_scroll = TRUE;
if (mIsVertical)
Steven Bennetts
committed
S32 tab_total_height = (BTN_HEIGHT + TABCNTRV_PAD) * getTabCount();
S32 available_height = getRect().getHeight() - getTopBorderHeight();
if( tab_total_height > available_height )
Steven Bennetts
committed
S32 available_height_with_arrows = getRect().getHeight() - 2*(TABCNTRV_ARROW_BTN_SIZE + 3*TABCNTRV_PAD);
S32 additional_needed = tab_total_height - available_height_with_arrows;
setMaxScrollPos((S32) ceil(additional_needed / float(BTN_HEIGHT) ) );
no_scroll = FALSE;
Steven Bennetts
committed
}
else
{
S32 tab_space = 0;
S32 available_space = 0;
tab_space = mTotalTabWidth;
available_space = getRect().getWidth() - mRightTabBtnOffset - 2 * (LLPANEL_BORDER_WIDTH + TABCNTR_TAB_H_PAD);
Steven Bennetts
committed
if( tab_space > available_space )
Steven Bennetts
committed
S32 available_width_with_arrows = getRect().getWidth() - mRightTabBtnOffset - 2 * (LLPANEL_BORDER_WIDTH + TABCNTR_ARROW_BTN_SIZE + TABCNTR_ARROW_BTN_SIZE + 1);
// subtract off reserved portion on left
available_width_with_arrows -= TABCNTR_TAB_PARTIAL_WIDTH;
S32 running_tab_width = 0;
setMaxScrollPos(getTabCount());
for(tuple_list_t::reverse_iterator tab_it = mTabList.rbegin(); tab_it != mTabList.rend(); ++tab_it)
Steven Bennetts
committed
running_tab_width += (*tab_it)->mButton->getRect().getWidth();
if (running_tab_width > available_width_with_arrows)
{
break;
}
setMaxScrollPos(getMaxScrollPos()-1);
Steven Bennetts
committed
// in case last tab doesn't actually fit on screen, make it the last scrolling position
setMaxScrollPos(llmin(getMaxScrollPos(), getTabCount() - 1));
no_scroll = FALSE;
Steven Bennetts
committed
if (no_scroll)
{
setMaxScrollPos(0);
setScrollPos(0);
}
if (getScrollPos() > getMaxScrollPos())
{
setScrollPos(getMaxScrollPos()); // maybe just enforce this via limits in setScrollPos instead?
}
Steven Bennetts
committed
void LLTabContainer::commitHoveredButton(S32 x, S32 y)
{
Steven Bennetts
committed
if (hasMouseCapture())
{
Steven Bennetts
committed
for(tuple_list_t::iterator iter = mTabList.begin(); iter != mTabList.end(); ++iter)
{
LLTabTuple* tuple = *iter;
tuple->mButton->setVisible( TRUE );
S32 local_x = x - tuple->mButton->getRect().mLeft;
S32 local_y = y - tuple->mButton->getRect().mBottom;
if (tuple->mButton->pointInView(local_x, local_y) && tuple->mButton->getEnabled() && !tuple->mTabPanel->getVisible())
{
tuple->mButton->onCommit();
}
}
}
Steven Bennetts
committed