QTfrontend/ui/widget/flowlayout.cpp
changeset 8434 4821897a0f10
parent 8386 2aaa2995a32e
equal deleted inserted replaced
8432:f2d57e987ba9 8434:4821897a0f10
    39  ****************************************************************************/
    39  ****************************************************************************/
    40 
    40 
    41  #include <QtGui>
    41  #include <QtGui>
    42 
    42 
    43  #include "flowlayout.h"
    43  #include "flowlayout.h"
    44  
       
    45  FlowLayout::FlowLayout(QWidget *parent, int margin, int hSpacing, int vSpacing)
       
    46      : QLayout(parent), m_hSpace(hSpacing), m_vSpace(vSpacing)
       
    47  {
       
    48      setContentsMargins(margin, margin, margin, margin);
       
    49  }
       
    50 
    44 
    51  FlowLayout::FlowLayout(int margin, int hSpacing, int vSpacing)
    45 FlowLayout::FlowLayout(QWidget *parent, int margin, int hSpacing, int vSpacing)
    52      : m_hSpace(hSpacing), m_vSpace(vSpacing)
    46     : QLayout(parent), m_hSpace(hSpacing), m_vSpace(vSpacing)
    53  {
    47 {
    54      setContentsMargins(margin, margin, margin, margin);
    48     setContentsMargins(margin, margin, margin, margin);
    55  }
    49 }
    56 
    50 
    57  FlowLayout::~FlowLayout()
    51 FlowLayout::FlowLayout(int margin, int hSpacing, int vSpacing)
    58  {
    52     : m_hSpace(hSpacing), m_vSpace(vSpacing)
    59      QLayoutItem *item;
    53 {
    60      while ((item = takeAt(0)))
    54     setContentsMargins(margin, margin, margin, margin);
    61          delete item;
    55 }
    62  }
       
    63 
    56 
    64  void FlowLayout::addItem(QLayoutItem *item)
    57 FlowLayout::~FlowLayout()
    65  {
    58 {
    66      itemList.append(item);
    59     QLayoutItem *item;
    67  }
    60     while ((item = takeAt(0)))
       
    61         delete item;
       
    62 }
    68 
    63 
    69  int FlowLayout::horizontalSpacing() const
    64 void FlowLayout::addItem(QLayoutItem *item)
    70  {
    65 {
    71      if (m_hSpace >= 0) {
    66     itemList.append(item);
    72          return m_hSpace;
    67 }
    73      } else {
       
    74          return smartSpacing(QStyle::PM_LayoutHorizontalSpacing);
       
    75      }
       
    76  }
       
    77 
    68 
    78  int FlowLayout::verticalSpacing() const
    69 int FlowLayout::horizontalSpacing() const
    79  {
    70 {
    80      if (m_vSpace >= 0) {
    71     if (m_hSpace >= 0) {
    81          return m_vSpace;
    72         return m_hSpace;
    82      } else {
    73     } else {
    83          return smartSpacing(QStyle::PM_LayoutVerticalSpacing);
    74         return smartSpacing(QStyle::PM_LayoutHorizontalSpacing);
    84      }
    75     }
    85  }
    76 }
    86 
    77 
    87  int FlowLayout::count() const
    78 int FlowLayout::verticalSpacing() const
    88  {
    79 {
    89      return itemList.size();
    80     if (m_vSpace >= 0) {
    90  }
    81         return m_vSpace;
       
    82     } else {
       
    83         return smartSpacing(QStyle::PM_LayoutVerticalSpacing);
       
    84     }
       
    85 }
    91 
    86 
    92  QLayoutItem *FlowLayout::itemAt(int index) const
    87 int FlowLayout::count() const
    93  {
    88 {
    94      return itemList.value(index);
    89     return itemList.size();
    95  }
    90 }
    96 
    91 
    97  QLayoutItem *FlowLayout::takeAt(int index)
    92 QLayoutItem *FlowLayout::itemAt(int index) const
    98  {
    93 {
    99      if (index >= 0 && index < itemList.size())
    94     return itemList.value(index);
   100          return itemList.takeAt(index);
    95 }
   101      else
       
   102          return 0;
       
   103  }
       
   104 
    96 
   105  Qt::Orientations FlowLayout::expandingDirections() const
    97 QLayoutItem *FlowLayout::takeAt(int index)
   106  {
    98 {
   107      return 0;
    99     if (index >= 0 && index < itemList.size())
   108  }
   100         return itemList.takeAt(index);
       
   101     else
       
   102         return 0;
       
   103 }
   109 
   104 
   110  bool FlowLayout::hasHeightForWidth() const
   105 Qt::Orientations FlowLayout::expandingDirections() const
   111  {
   106 {
   112      return true;
   107     return 0;
   113  }
   108 }
   114 
   109 
   115  int FlowLayout::heightForWidth(int width) const
   110 bool FlowLayout::hasHeightForWidth() const
   116  {
   111 {
   117      int height = doLayout(QRect(0, 0, width, 0), true);
   112     return true;
   118      return height;
   113 }
   119  }
       
   120 
   114 
   121  void FlowLayout::setGeometry(const QRect &rect)
   115 int FlowLayout::heightForWidth(int width) const
   122  {
   116 {
   123      QLayout::setGeometry(rect);
   117     int height = doLayout(QRect(0, 0, width, 0), true);
   124      doLayout(rect, false);
   118     return height;
   125  }
   119 }
   126 
   120 
   127  QSize FlowLayout::sizeHint() const
   121 void FlowLayout::setGeometry(const QRect &rect)
   128  {
   122 {
   129      return minimumSize();
   123     QLayout::setGeometry(rect);
   130  }
   124     doLayout(rect, false);
       
   125 }
   131 
   126 
   132  QSize FlowLayout::minimumSize() const
   127 QSize FlowLayout::sizeHint() const
   133  {
   128 {
   134      QSize size;
   129     return minimumSize();
   135      QLayoutItem *item;
   130 }
   136      foreach (item, itemList)
       
   137          size = size.expandedTo(item->minimumSize());
       
   138 
   131 
   139      size += QSize(2*margin(), 2*margin());
   132 QSize FlowLayout::minimumSize() const
   140      return size;
   133 {
   141  }
   134     QSize size;
       
   135     QLayoutItem *item;
       
   136     foreach (item, itemList)
       
   137         size = size.expandedTo(item->minimumSize());
   142 
   138 
   143  int FlowLayout::doLayout(const QRect &rect, bool testOnly) const
   139     size += QSize(2*margin(), 2*margin());
   144  {
   140     return size;
   145      int left, top, right, bottom;
   141 }
   146      getContentsMargins(&left, &top, &right, &bottom);
       
   147      QRect effectiveRect = rect.adjusted(+left, +top, -right, -bottom);
       
   148      int x = effectiveRect.x();
       
   149      int y = effectiveRect.y();
       
   150      int lineHeight = 0;
       
   151 
   142 
   152      QLayoutItem *item;
   143 int FlowLayout::doLayout(const QRect &rect, bool testOnly) const
   153      foreach (item, itemList) {
   144 {
   154          QWidget *wid = item->widget();
   145     int left, top, right, bottom;
   155          int spaceX = horizontalSpacing();
   146     getContentsMargins(&left, &top, &right, &bottom);
   156          if (spaceX == -1)
   147     QRect effectiveRect = rect.adjusted(+left, +top, -right, -bottom);
   157              spaceX = wid->style()->layoutSpacing(
   148     int x = effectiveRect.x();
   158                  QSizePolicy::PushButton, QSizePolicy::PushButton, Qt::Horizontal);
   149     int y = effectiveRect.y();
   159          int spaceY = verticalSpacing();
   150     int lineHeight = 0;
   160          if (spaceY == -1)
       
   161              spaceY = wid->style()->layoutSpacing(
       
   162                  QSizePolicy::PushButton, QSizePolicy::PushButton, Qt::Vertical);
       
   163          int nextX = x + item->sizeHint().width() + spaceX;
       
   164          if (nextX - spaceX > effectiveRect.right() && lineHeight > 0) {
       
   165              x = effectiveRect.x();
       
   166              y = y + lineHeight + spaceY;
       
   167              nextX = x + item->sizeHint().width() + spaceX;
       
   168              lineHeight = 0;
       
   169          }
       
   170 
   151 
   171          if (!testOnly)
   152     QLayoutItem *item;
   172              item->setGeometry(QRect(QPoint(x, y), item->sizeHint()));
   153     foreach (item, itemList) {
       
   154         QWidget *wid = item->widget();
       
   155         int spaceX = horizontalSpacing();
       
   156         if (spaceX == -1)
       
   157             spaceX = wid->style()->layoutSpacing(
       
   158                 QSizePolicy::PushButton, QSizePolicy::PushButton, Qt::Horizontal);
       
   159         int spaceY = verticalSpacing();
       
   160         if (spaceY == -1)
       
   161             spaceY = wid->style()->layoutSpacing(
       
   162                 QSizePolicy::PushButton, QSizePolicy::PushButton, Qt::Vertical);
       
   163         int nextX = x + item->sizeHint().width() + spaceX;
       
   164         if (nextX - spaceX > effectiveRect.right() && lineHeight > 0) {
       
   165             x = effectiveRect.x();
       
   166             y = y + lineHeight + spaceY;
       
   167             nextX = x + item->sizeHint().width() + spaceX;
       
   168             lineHeight = 0;
       
   169         }
   173 
   170 
   174          x = nextX;
   171         if (!testOnly)
   175          lineHeight = qMax(lineHeight, item->sizeHint().height());
   172             item->setGeometry(QRect(QPoint(x, y), item->sizeHint()));
   176      }
   173 
   177      return y + lineHeight - rect.y() + bottom;
   174         x = nextX;
   178  }
   175         lineHeight = qMax(lineHeight, item->sizeHint().height());
   179  int FlowLayout::smartSpacing(QStyle::PixelMetric pm) const
   176     }
   180  {
   177     return y + lineHeight - rect.y() + bottom;
   181      QObject *parent = this->parent();
   178 }
   182      if (!parent) {
   179 int FlowLayout::smartSpacing(QStyle::PixelMetric pm) const
   183          return -1;
   180 {
   184      } else if (parent->isWidgetType()) {
   181     QObject *parent = this->parent();
   185          QWidget *pw = static_cast<QWidget *>(parent);
   182     if (!parent) {
   186          return pw->style()->pixelMetric(pm, 0, pw);
   183         return -1;
   187      } else {
   184     } else if (parent->isWidgetType()) {
   188          return static_cast<QLayout *>(parent)->spacing();
   185         QWidget *pw = static_cast<QWidget *>(parent);
   189      }
   186         return pw->style()->pixelMetric(pm, 0, pw);
   190  }
   187     } else {
       
   188         return static_cast<QLayout *>(parent)->spacing();
       
   189     }
       
   190 }