Ignore:
Timestamp:
Feb 11, 2010, 11:19:06 PM (15 years ago)
Author:
Dmitry A. Kuminov
Message:

trunk: Merged in qt 4.6.1 sources.

Location:
trunk
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • trunk

  • trunk/src/gui/widgets/qtabbar.cpp

    r2 r561  
    22**
    33** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
    4 ** Contact: Qt Software Information (qt-info@nokia.com)
     4** All rights reserved.
     5** Contact: Nokia Corporation (qt-info@nokia.com)
    56**
    67** This file is part of the QtGui module of the Qt Toolkit.
     
    2122** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
    2223**
    23 ** In addition, as a special exception, Nokia gives you certain
    24 ** additional rights. These rights are described in the Nokia Qt LGPL
    25 ** Exception version 1.0, included in the file LGPL_EXCEPTION.txt in this
    26 ** package.
     24** In addition, as a special exception, Nokia gives you certain additional
     25** rights.  These rights are described in the Nokia Qt LGPL Exception
     26** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
    2727**
    2828** GNU General Public License Usage
     
    3434** met: http://www.gnu.org/copyleft/gpl.html.
    3535**
    36 ** If you are unsure which license is appropriate for your use, please
    37 ** contact the sales department at qt-sales@nokia.com.
     36** If you have questions regarding the use of this file, please contact
     37** Nokia at qt-info@nokia.com.
    3838** $QT_END_LICENSE$
    3939**
     
    8888        // TODO: test tab bar position
    8989
    90         // push the black line at the bottom of the menu bar down to the client are so we can paint over it
     90        OSWindowRef window = qt_mac_window_for(q);
     91
     92        // push base line separator down to the client are so we can paint over it (Carbon)
    9193        metrics.top = (documentMode && q->isVisible()) ? 1 : 0;
    9294        metrics.bottom = 0;
    9395        metrics.left = 0;
    9496        metrics.right = 0;
    95 
    96         qt_mac_updateContentBorderMetricts(qt_mac_window_for(q), metrics);
     97        qt_mac_updateContentBorderMetricts(window, metrics);
     98       
     99        // hide the base line separator if the tabs have docuemnt mode enabled (Cocoa)
     100        qt_mac_showBaseLineSeparator(window, !documentMode);
    97101    }
    98102#endif
     
    132136    if (isActiveWindow())
    133137        option->state |= QStyle::State_Active;
    134     if (option->rect == d->hoverRect)
     138    if (!d->dragInProgress && option->rect == d->hoverRect)
    135139        option->state |= QStyle::State_MouseOver;
    136140    option->shape = d->shape;
     
    177181            option->cornerWidgets |= QStyleOptionTab::RightCornerWidget;
    178182    }
     183#endif
    179184
    180185    QRect textRect = style()->subElementRect(QStyle::SE_TabBarTabText, option, this);
    181 
    182186    option->text = fontMetrics().elidedText(option->text, d->elideMode, textRect.width(),
    183187                        Qt::TextShowMnemonic);
    184 #endif
    185188}
    186189
     
    190193
    191194    \ingroup basicwidgets
    192     \mainclass
     195
    193196
    194197    QTabBar is straightforward to use; it draws the tabs using one of
     
    455458    }
    456459
    457     if (pressedIndex != -1 && movable)
    458         grabCache(0, tabList.count(), true);
    459 
    460460    Q_ASSERT(tabChainIndex == tabChain.count() - 1); // add an assert just to make sure.
    461461    // Mirror our front item.
     
    668668        && movable
    669669        && QApplication::mouseButtons() == Qt::NoButton) {
    670         _q_moveTabFinished(pressedIndex);
     670        moveTabFinished(pressedIndex);
    671671        if (!validIndex(pressedIndex))
    672672            pressedIndex = -1;
     
    10891089
    10901090/*!
    1091     Returns the datad of the tab at position \a index, or a null
     1091    Returns the data of the tab at position \a index, or a null
    10921092    variant if \a index is out of range.
    10931093*/
     
    11011101
    11021102/*!
    1103     Returns the visual rectangle of the of the tab at position \a
     1103    Returns the visual rectangle of the tab at position \a
    11041104    index, or a null rectangle if \a index is out of range.
    11051105*/
     
    11711171        update();
    11721172        d->makeVisible(index);
     1173        d->tabList[index].lastTab = oldIndex;
     1174        d->layoutWidgets(oldIndex);
     1175        d->layoutWidgets(index);
    11731176#ifdef QT3_SUPPORT
    11741177        emit selected(index);
    11751178#endif
    11761179        emit currentChanged(index);
    1177         d->tabList[index].lastTab = oldIndex;
    1178         d->layoutWidgets(oldIndex);
    1179         d->layoutWidgets(index);
    11801180    }
    11811181}
     
    12941294QSize QTabBar::tabSizeHint(int index) const
    12951295{
     1296    //Note: this must match with the computations in QCommonStylePrivate::tabLayout
    12961297    Q_D(const QTabBar);
    12971298    if (const QTabBarPrivate::Tab *tab = d->at(index)) {
     
    13101311        int widgetHeight = 0;
    13111312        int padding = 0;
    1312         if (opt.leftButtonSize.isValid()) {
    1313             padding += 6 + 2;
     1313        if (!opt.leftButtonSize.isEmpty()) {
     1314            padding += 4;
    13141315            widgetWidth += opt.leftButtonSize.width();
    13151316            widgetHeight += opt.leftButtonSize.height();
    13161317        }
    1317         if (opt.rightButtonSize.isValid()) {
    1318             padding += 6 + 2;
     1318        if (!opt.rightButtonSize.isEmpty()) {
     1319            padding += 4;
    13191320            widgetWidth += opt.rightButtonSize.width();
    13201321            widgetHeight += opt.rightButtonSize.height();
    13211322        }
    1322         if (opt.iconSize.isValid())
    1323             padding += 2;
     1323        if (!opt.icon.isNull())
     1324            padding += 4;
    13241325
    13251326        QSize csz;
     
    14851486    QStyleOptionTab cutTab;
    14861487    selected = d->currentIndex;
     1488    if (d->dragInProgress)
     1489        selected = d->pressedIndex;
    14871490
    14881491    for (int i = 0; i < d->tabList.count(); ++i)
     
    15231526            continue;
    15241527
    1525         if (!d->tabList[i].animatingCache.isNull() && d->paintWithOffsets) {
    1526             p.drawPixmap(tab.rect, d->tabList[i].animatingCache);
    1527         } else {
    1528             p.drawControl(QStyle::CE_TabBarTab, tab);
    1529         }
     1528        p.drawControl(QStyle::CE_TabBarTab, tab);
    15301529    }
    15311530
     
    15401539                tab.rect.moveLeft(tab.rect.x() + d->tabList[selected].dragOffset);
    15411540        }
    1542         p.drawControl(QStyle::CE_TabBarTab, tab);
     1541        if (!d->dragInProgress)
     1542            p.drawControl(QStyle::CE_TabBarTab, tab);
     1543        else {
     1544            int taboverlap = style()->pixelMetric(QStyle::PM_TabBarTabOverlap, 0, this);
     1545            d->movingTab->setGeometry(tab.rect.adjusted(-taboverlap, 0, taboverlap, 0));
     1546        }
    15431547    }
    15441548
     
    16641668    int postLocation = vertical ? q->tabRect(to).y() : q->tabRect(to).x();
    16651669    int length = postLocation - preLocation;
    1666     tabList[to].makeTimeLine(q);
    1667     tabList[to].dragOffset += -1 * length;
    1668     tabList[to].timeLine->setFrameRange(tabList[to].dragOffset, 0);
    1669     animations[tabList[to].timeLine] = to;
    1670     tabList[to].timeLine->setDuration(ANIMATION_DURATION);
    1671     if (tabList[to].timeLine->state() != QTimeLine::Running)
    1672         tabList[to].timeLine->start();
    1673 }
    1674 
    1675 void QTabBarPrivate::_q_moveTab(int offset)
    1676 {
    1677     Q_Q(QTabBar);
    1678     if (QTimeLine *timeLine = qobject_cast<QTimeLine *>(q->sender())) {
    1679         int index = animations[timeLine];
    1680         if (!validIndex(index))
    1681             return;
    1682         tabList[index].dragOffset = offset;
    1683         q->update();
    1684     }
     1670    tabList[to].dragOffset -= length;
     1671    tabList[to].startAnimation(this, ANIMATION_DURATION);
     1672}
     1673
     1674void QTabBarPrivate::moveTab(int index, int offset)
     1675{
     1676    if (!validIndex(index))
     1677        return;
     1678    tabList[index].dragOffset = offset;
     1679    layoutTab(index); // Make buttons follow tab
     1680    q_func()->update();
    16851681}
    16861682
     
    16961692    // Be safe!
    16971693    if (d->pressedIndex != -1 && d->movable)
    1698         d->_q_moveTabFinished(d->pressedIndex);
     1694        d->moveTabFinished(d->pressedIndex);
    16991695
    17001696    d->pressedIndex = d->indexAtPos(event->pos());
     1697#ifdef Q_WS_MAC
     1698    d->previousPressedIndex = d->pressedIndex;
     1699#endif
    17011700    if (d->validIndex(d->pressedIndex)) {
    17021701        QStyleOptionTabBarBaseV2 optTabBase;
     
    17221721        if (d->pressedIndex != -1
    17231722            && event->buttons() == Qt::NoButton)
    1724             d->_q_moveTabFinished(d->pressedIndex);
     1723            d->moveTabFinished(d->pressedIndex);
    17251724       
    17261725        // Start drag
     
    17281727            if ((event->pos() - d->dragStartPosition).manhattanLength() > QApplication::startDragDistance()) {
    17291728                d->dragInProgress = true;
    1730                 if (d->animations.isEmpty())
    1731                     d->grabCache(0, d->tabList.count(), false);
     1729                d->setupMovableTab();
    17321730            }
    17331731        }
     
    17741772                        d->slide(i + offset, d->pressedIndex);
    17751773                }
    1776 
    17771774            }
    17781775            // Buttons needs to follow the dragged tab
     
    17811778            update();
    17821779        }
     1780#ifdef Q_WS_MAC
     1781    } else if (!d->documentMode && event->buttons() == Qt::LeftButton && d->previousPressedIndex != -1) {
     1782        int newPressedIndex = d->indexAtPos(event->pos());
     1783        if (d->pressedIndex == -1 && d->previousPressedIndex == newPressedIndex) {
     1784            d->pressedIndex = d->previousPressedIndex;
     1785            update(tabRect(d->pressedIndex));
     1786        } else if(d->pressedIndex != newPressedIndex) {
     1787            d->pressedIndex = -1;
     1788            update(tabRect(d->previousPressedIndex));
     1789        }
     1790#endif
    17831791    }
    17841792
     
    17921800}
    17931801
    1794 void QTabBarPrivate::_q_moveTabFinished()
     1802void QTabBarPrivate::setupMovableTab()
    17951803{
    17961804    Q_Q(QTabBar);
    1797     if (QTimeLine *timeLine = qobject_cast<QTimeLine *>(q->sender())) {
    1798         int index = animations[timeLine];
    1799         animations.remove(timeLine);
    1800         _q_moveTabFinished(index);
    1801     }
    1802 }
    1803 
    1804 void QTabBarPrivate::grabCache(int start, int end, bool unhide)
    1805 {
    1806     Q_Q(QTabBar);
    1807     paintWithOffsets = false;
    1808     bool showButtonsAgain = rightB->isVisible();
    1809     rightB->hide();
    1810     leftB->hide();
    1811 
    1812     QWidget *topLevel = q->window();
    1813     QPoint topLevelOffset(q->mapTo(topLevel, QPoint()));
    1814     for (int i = start; i < end; ++i) {
    1815         QRect tabRect = q->tabRect(i);
    1816         tabRect.translate(topLevelOffset);
    1817         if (unhide) {
    1818             tabList[i].unHideWidgets();
    1819             layoutWidgets(i);
    1820         }
    1821         tabList[i].animatingCache = QPixmap::grabWidget(topLevel, tabRect);
    1822         if (i != pressedIndex)
    1823             tabList[i].hideWidgets();
    1824     }
    1825     if (showButtonsAgain) {
    1826         rightB->show();
    1827         leftB->show();
    1828     }
    1829     paintWithOffsets = true;
    1830 }
    1831 
    1832 void QTabBarPrivate::_q_moveTabFinished(int index)
     1805    if (!movingTab)
     1806        movingTab = new QWidget(q);
     1807
     1808    int taboverlap = q->style()->pixelMetric(QStyle::PM_TabBarTabOverlap, 0 ,q);
     1809    QRect grabRect = q->tabRect(pressedIndex);
     1810    grabRect.adjust(-taboverlap, 0, taboverlap, 0);
     1811
     1812    QPixmap grabImage(grabRect.size());
     1813    grabImage.fill(Qt::transparent);
     1814    QStylePainter p(&grabImage, q);
     1815    p.initFrom(q);
     1816
     1817    QStyleOptionTabV3 tab;
     1818    q->initStyleOption(&tab, pressedIndex);
     1819    tab.rect.moveTopLeft(QPoint(taboverlap, 0));
     1820    p.drawControl(QStyle::CE_TabBarTab, tab);
     1821    p.end();
     1822
     1823    QPalette pal;
     1824    pal.setBrush(QPalette::All, QPalette::Window, grabImage);
     1825    movingTab->setPalette(pal);
     1826    movingTab->setGeometry(grabRect);
     1827    movingTab->setAutoFillBackground(true);
     1828    movingTab->raise();
     1829
     1830    // Re-arrange widget order to avoid overlaps
     1831    if (tabList[pressedIndex].leftWidget)
     1832        tabList[pressedIndex].leftWidget->raise();
     1833    if (tabList[pressedIndex].rightWidget)
     1834        tabList[pressedIndex].rightWidget->raise();
     1835    if (leftB)
     1836        leftB->raise();
     1837    if (rightB)
     1838        rightB->raise();
     1839    movingTab->setVisible(true);
     1840}
     1841
     1842void QTabBarPrivate::moveTabFinished(int index)
    18331843{
    18341844    Q_Q(QTabBar);
    18351845    bool cleanup = (pressedIndex == index) || (pressedIndex == -1) || !validIndex(index);
    1836     if (animations.isEmpty() && cleanup) {
     1846    bool allAnimationsFinished = true;
     1847#ifndef QT_NO_ANIMATION
     1848    for(int i = 0; allAnimationsFinished && i < tabList.count(); ++i) {
     1849        const Tab &t = tabList.at(i);
     1850        if (t.animation && t.animation->state() == QAbstractAnimation::Running)
     1851            allAnimationsFinished = false;
     1852    }
     1853#endif //QT_NO_ANIMATION
     1854    if (allAnimationsFinished && cleanup) {
     1855        if(movingTab)
     1856            movingTab->setVisible(false); // We might not get a mouse release
    18371857        for (int i = 0; i < tabList.count(); ++i) {
    18381858            tabList[i].dragOffset = 0;
    1839             tabList[i].unHideWidgets();
    1840             tabList[i].animatingCache = QPixmap();
    18411859        }
    18421860        if (pressedIndex != -1 && movable) {
     
    18631881        return;
    18641882    }
    1865 
     1883#ifdef Q_WS_MAC
     1884    d->previousPressedIndex = -1;
     1885#endif
    18661886    if (d->movable && d->dragInProgress && d->validIndex(d->pressedIndex)) {
    18671887        int length = d->tabList[d->pressedIndex].dragOffset;
     
    18701890            : tabRect(d->pressedIndex).width();
    18711891        int duration = qMin(ANIMATION_DURATION,
    1872                 ((length < 0 ? (-1 * length) : length) * ANIMATION_DURATION) / width);
    1873         if (duration > 0) {
    1874             d->tabList[d->pressedIndex].makeTimeLine(this);
    1875             d->tabList[d->pressedIndex].timeLine->setFrameRange(length, 0);
    1876             d->animations[d->tabList[d->pressedIndex].timeLine] = d->pressedIndex;
    1877             d->tabList[d->pressedIndex].timeLine->setDuration(duration);
    1878             if (d->tabList[d->pressedIndex].timeLine->state() != QTimeLine::Running)
    1879                 d->tabList[d->pressedIndex].timeLine->start();
    1880         } else {
    1881             d->_q_moveTabFinished(d->pressedIndex);
    1882         }
     1892                (qAbs(length) * ANIMATION_DURATION) / width);
     1893        d->tabList[d->pressedIndex].startAnimation(d, duration);
    18831894        d->dragInProgress = false;
     1895        d->movingTab->setVisible(false);
    18841896        d->dragStartPosition = QPoint();
    18851897    }
     
    19031915        return;
    19041916    }
    1905     int dx = event->key() == (isRightToLeft() ? Qt::Key_Right : Qt::Key_Left) ? -1 : 1;
    1906     for (int index = d->currentIndex + dx; d->validIndex(index); index += dx) {
    1907         if (d->tabList.at(index).enabled) {
    1908             setCurrentIndex(index);
    1909             break;
    1910         }
    1911     }
     1917    int offset = event->key() == (isRightToLeft() ? Qt::Key_Right : Qt::Key_Left) ? -1 : 1;   
     1918    d->setCurrentNextEnabledIndex(offset);
    19121919}
    19131920
     
    19181925{
    19191926    Q_D(QTabBar);
    1920     int overIndex = d->indexAtPos(event->pos());
    1921     if (overIndex != -1) {
    1922         int offset = event->delta() > 0 ? -1 : 1;
    1923         setCurrentIndex(currentIndex() + offset);
    1924     }
     1927    int offset = event->delta() > 0 ? -1 : 1;
     1928    d->setCurrentNextEnabledIndex(offset);
    19251929    QWidget::wheelEvent(event);
    19261930}
    19271931#endif //QT_NO_WHEELEVENT
     1932
     1933void QTabBarPrivate::setCurrentNextEnabledIndex(int offset)
     1934{
     1935    Q_Q(QTabBar);
     1936    for (int index = currentIndex + offset; validIndex(index); index += offset) {
     1937        if (tabList.at(index).enabled) {
     1938            q->setCurrentIndex(index);
     1939            break;
     1940        }
     1941    }
     1942}
    19281943
    19291944/*!\reimp
     
    19341949    if (event->type() == QEvent::StyleChange) {
    19351950        d->elideMode = Qt::TextElideMode(style()->styleHint(QStyle::SH_TabBar_ElideMode, 0, this));
    1936         d->useScrollButtons = !style()->styleHint(QStyle::SH_TabBar_PreferNoArrows, 0, this);
    1937     }
    1938     d->refresh();
     1951        if (!d->useScrollButtonsSetByUser)
     1952            d->useScrollButtons = !style()->styleHint(QStyle::SH_TabBar_PreferNoArrows, 0, this);
     1953        d->refresh();
     1954    } else if (event->type() == QEvent::FontChange) {
     1955        d->refresh();
     1956    }
    19391957    QWidget::changeEvent(event);
    19401958}
     
    19872005{
    19882006    Q_D(QTabBar);
     2007    d->useScrollButtonsSetByUser = true;
    19892008    if (d->useScrollButtons == useButtons)
    19902009        return;
     
    22042223        // make sure our left and right widgets stay on top
    22052224        widget->lower();
     2225        widget->show();
    22062226    }
    22072227    if (position == LeftSide) {
     
    22092229            d->tabList[index].leftWidget->hide();
    22102230        d->tabList[index].leftWidget = widget;
    2211         if(!d->tabList[index].hidLeft && widget)
    2212             widget->show();
    22132231    } else {
    22142232        if (d->tabList[index].rightWidget)
    22152233            d->tabList[index].rightWidget->hide();
    22162234        d->tabList[index].rightWidget = widget;
    2217         if(!d->tabList[index].hidRight && widget)
    2218             widget->show();
    22192235    }
    22202236    d->layoutTabs();
     2237    d->refresh();
    22212238    update();
    22222239}
Note: See TracChangeset for help on using the changeset viewer.