void QDeclarativeBasePositioner::prePositioning() { Q_D(QDeclarativeBasePositioner); if (!isComponentComplete()) return; d->queuedPositioning = false; //Need to order children by creation order modified by stacking order QList<QGraphicsItem *> children = d->QGraphicsItemPrivate::children; qSort(children.begin(), children.end(), d->insertionOrder); QPODVector<PositionedItem,8> oldItems; positionedItems.copyAndClear(oldItems); for (int ii = 0; ii < children.count(); ++ii) { QDeclarativeItem *child = qobject_cast<QDeclarativeItem *>(children.at(ii)); if (!child) continue; PositionedItem *item = 0; PositionedItem posItem(child); int wIdx = oldItems.find(posItem); if (wIdx < 0) { d->watchChanges(child); positionedItems.append(posItem); item = &positionedItems[positionedItems.count()-1]; item->isNew = true; if (child->opacity() <= 0.0 || !child->isVisible()) item->isVisible = false; } else { item = &oldItems[wIdx]; if (child->opacity() <= 0.0 || !child->isVisible()) { item->isVisible = false; } else if (!item->isVisible) { item->isVisible = true; item->isNew = true; } else { item->isNew = false; } positionedItems.append(*item); } } doPositioning(); if(d->addTransition || d->moveTransition) finishApplyTransitions(); //Set implicit size to the size of its children qreal h = 0.0f; qreal w = 0.0f; for (int i = 0; i < positionedItems.count(); ++i) { const PositionedItem &posItem = positionedItems.at(i); if (posItem.isVisible) { h = qMax(h, posItem.item->y() + posItem.item->height()); w = qMax(w, posItem.item->x() + posItem.item->width()); } } setImplicitHeight(h); setImplicitWidth(w); }
void QDeclarativeBasePositioner::prePositioning() { Q_D(QDeclarativeBasePositioner); if (!isComponentComplete()) return; if (d->doingPositioning) return; d->queuedPositioning = false; d->doingPositioning = true; //Need to order children by creation order modified by stacking order QList<QGraphicsItem *> children = d->QGraphicsItemPrivate::children; qSort(children.begin(), children.end(), d->insertionOrder); QPODVector<PositionedItem,8> oldItems; positionedItems.copyAndClear(oldItems); for (int ii = 0; ii < children.count(); ++ii) { QDeclarativeItem *child = qobject_cast<QDeclarativeItem *>(children.at(ii)); if (!child) continue; QDeclarativeItemPrivate *childPrivate = static_cast<QDeclarativeItemPrivate*>(QGraphicsItemPrivate::get(child)); PositionedItem *item = 0; PositionedItem posItem(child); int wIdx = oldItems.find(posItem); if (wIdx < 0) { d->watchChanges(child); positionedItems.append(posItem); item = &positionedItems[positionedItems.count()-1]; item->isNew = true; if (child->opacity() <= 0.0 || childPrivate->explicitlyHidden) item->isVisible = false; } else { item = &oldItems[wIdx]; // Items are only omitted from positioning if they are explicitly hidden // i.e. their positioning is not affected if an ancestor is hidden. if (child->opacity() <= 0.0 || childPrivate->explicitlyHidden) { item->isVisible = false; } else if (!item->isVisible) { item->isVisible = true; item->isNew = true; } else { item->isNew = false; } positionedItems.append(*item); } } QSizeF contentSize; doPositioning(&contentSize); if(d->addTransition || d->moveTransition) finishApplyTransitions(); d->doingPositioning = false; //Set implicit size to the size of its children setImplicitHeight(contentSize.height()); setImplicitWidth(contentSize.width()); }
QVariant QDeclarativeExpressionPrivate::value(QObject *secondaryScope, bool *isUndefined) { Q_Q(QDeclarativeExpression); QVariant rv; if (!q->engine()) { qWarning("QDeclarativeExpression: Attempted to evaluate an expression in an invalid context"); return rv; } if (data->expression.isEmpty()) return rv; QDeclarativeEnginePrivate *ep = QDeclarativeEnginePrivate::get(q->engine()); QDeclarativeExpression *lastCurrentExpression = ep->currentExpression; bool lastCaptureProperties = ep->captureProperties; QPODVector<QDeclarativeEnginePrivate::CapturedProperty> lastCapturedProperties; ep->capturedProperties.copyAndClear(lastCapturedProperties); ep->currentExpression = q; ep->captureProperties = data->trackChange; // This object might be deleted during the eval QDeclarativeExpressionData *localData = data; localData->addref(); rv = evalQtScript(secondaryScope, isUndefined); ep->currentExpression = lastCurrentExpression; ep->captureProperties = lastCaptureProperties; // Check if we were deleted if (localData->q) { if ((!data->trackChange || !ep->capturedProperties.count()) && data->guardList) { clearGuards(); } else if(data->trackChange) { updateGuards(ep->capturedProperties); } } localData->release(); lastCapturedProperties.copyAndClear(ep->capturedProperties); return rv; }
QScriptValue QDeclarativeQtScriptExpression::scriptValue(QObject *secondaryScope, bool *isUndefined) { Q_ASSERT(context() && context()->engine); Q_ASSERT(!trackChange || (guardObject && guardObjectNotifyIndex != -1)); if (!expressionFunction.isValid()) { if (isUndefined) *isUndefined = true; return QScriptValue(); } DeleteWatcher watcher(this); QDeclarativeEnginePrivate *ep = QDeclarativeEnginePrivate::get(context()->engine); bool lastCaptureProperties = ep->captureProperties; QPODVector<QDeclarativeEnginePrivate::CapturedProperty> lastCapturedProperties; ep->captureProperties = trackChange; ep->capturedProperties.copyAndClear(lastCapturedProperties); QScriptValue value = eval(secondaryScope, isUndefined); if (!watcher.wasDeleted() && trackChange) { if (ep->capturedProperties.count() == 0) { if (guardList) clearGuards(); } else { updateGuards(ep->capturedProperties); } } lastCapturedProperties.copyAndClear(ep->capturedProperties); ep->captureProperties = lastCaptureProperties; return value; }
void QDeclarativeExpressionPrivate::updateGuards(const QPODVector<QDeclarativeEnginePrivate::CapturedProperty> &properties) { Q_Q(QDeclarativeExpression); static int notifyIdx = -1; if (notifyIdx == -1) notifyIdx = QDeclarativeExpression::staticMetaObject.indexOfMethod("__q_notify()"); if (properties.count() != data->guardListLength) { QDeclarativeNotifierEndpoint *newGuardList = new QDeclarativeNotifierEndpoint[properties.count()]; for (int ii = 0; ii < qMin(data->guardListLength, properties.count()); ++ii) data->guardList[ii].copyAndClear(newGuardList[ii]); delete [] data->guardList; data->guardList = newGuardList; data->guardListLength = properties.count(); } bool outputWarningHeader = false; bool noChanges = true; for (int ii = 0; ii < properties.count(); ++ii) { QDeclarativeNotifierEndpoint &guard = data->guardList[ii]; const QDeclarativeEnginePrivate::CapturedProperty &property = properties.at(ii); guard.target = q; guard.targetMethod = notifyIdx; if (property.notifier != 0) { if (!noChanges && guard.isConnected(property.notifier)) { // Nothing to do } else { noChanges = false; bool existing = false; for (int jj = 0; !existing && jj < ii; ++jj) if (data->guardList[jj].isConnected(property.notifier)) existing = true; if (existing) { // duplicate guard.disconnect(); } else { guard.connect(property.notifier); } } } else if (property.notifyIndex != -1) { if (!noChanges && guard.isConnected(property.object, property.notifyIndex)) { // Nothing to do } else { noChanges = false; bool existing = false; for (int jj = 0; !existing && jj < ii; ++jj) if (data->guardList[jj].isConnected(property.object, property.notifyIndex)) existing = true; if (existing) { // duplicate guard.disconnect(); } else { guard.connect(property.object, property.notifyIndex); } } } else { if (!outputWarningHeader) { outputWarningHeader = true; qWarning() << "QDeclarativeExpression: Expression" << q->expression() << "depends on non-NOTIFYable properties:"; } const QMetaObject *metaObj = property.object->metaObject(); QMetaProperty metaProp = metaObj->property(property.coreIndex); qWarning().nospace() << " " << metaObj->className() << "::" << metaProp.name(); } } }
void QDeclarativeGrid::doPositioning(QSizeF *contentSize) { QDeclarativeBasePositionerPrivate *d = static_cast<QDeclarativeBasePositionerPrivate*>(QDeclarativeBasePositionerPrivate::get(this)); int c = m_columns; int r = m_rows; //Is allocating the extra QPODVector too much overhead? QPODVector<PositionedItem, 8> visibleItems;//we aren't concerned with invisible items visibleItems.reserve(positionedItems.count()); for(int i=0; i<positionedItems.count(); i++) if(positionedItems[i].item && positionedItems[i].isVisible) visibleItems.append(positionedItems[i]); int numVisible = visibleItems.count(); if (m_columns <= 0 && m_rows <= 0) { c = 4; r = (numVisible+3)/4; } else if (m_rows <= 0) { r = (numVisible+(m_columns-1))/m_columns; } else if (m_columns <= 0) { c = (numVisible+(m_rows-1))/m_rows; } if(r==0 || c==0) return; //Nothing to do QList<int> maxColWidth; QList<int> maxRowHeight; int childIndex =0; if (m_flow == LeftToRight) { for (int i=0; i < r; i++) { for (int j=0; j < c; j++) { if (j==0) maxRowHeight << 0; if (i==0) maxColWidth << 0; if (childIndex == visibleItems.count()) break; const PositionedItem &child = visibleItems.at(childIndex++); QGraphicsItemPrivate *childPrivate = QGraphicsItemPrivate::get(child.item); if (childPrivate->width() > maxColWidth[j]) maxColWidth[j] = childPrivate->width(); if (childPrivate->height() > maxRowHeight[i]) maxRowHeight[i] = childPrivate->height(); } } } else { for (int j=0; j < c; j++) { for (int i=0; i < r; i++) { if (j==0) maxRowHeight << 0; if (i==0) maxColWidth << 0; if (childIndex == visibleItems.count()) break; const PositionedItem &child = visibleItems.at(childIndex++); QGraphicsItemPrivate *childPrivate = QGraphicsItemPrivate::get(child.item); if (childPrivate->width() > maxColWidth[j]) maxColWidth[j] = childPrivate->width(); if (childPrivate->height() > maxRowHeight[i]) maxRowHeight[i] = childPrivate->height(); } } } int widthSum = 0; for(int j=0; j < maxColWidth.size(); j++) { if(j) widthSum += spacing(); widthSum += maxColWidth[j]; } int heightSum = 0; for(int i=0; i < maxRowHeight.size(); i++) { if(i) heightSum += spacing(); heightSum += maxRowHeight[i]; } contentSize->setHeight(heightSum); contentSize->setWidth(widthSum); int end = 0; if(widthValid()) end = width(); else end = widthSum; int xoffset=0; if(!d->isLeftToRight()) xoffset=end; int yoffset=0; int curRow =0; int curCol =0; for (int i = 0; i < visibleItems.count(); ++i) { const PositionedItem &child = visibleItems.at(i); int childXOffset = xoffset; if(!d->isLeftToRight()) childXOffset -= QGraphicsItemPrivate::get(child.item)->width(); if((child.item->x()!=childXOffset)||(child.item->y()!=yoffset)) { positionX(childXOffset, child); positionY(yoffset, child); } if (m_flow == LeftToRight) { if(d->isLeftToRight()) xoffset+=maxColWidth[curCol]+spacing(); else xoffset-=maxColWidth[curCol]+spacing(); curCol++; curCol%=c; if (!curCol) { yoffset+=maxRowHeight[curRow]+spacing(); if(d->isLeftToRight()) xoffset=0; else xoffset=end; curRow++; if (curRow>=r) break; } } else { yoffset+=maxRowHeight[curRow]+spacing(); curRow++; curRow%=r; if (!curRow) { if(d->isLeftToRight()) xoffset+=maxColWidth[curCol]+spacing(); else xoffset-=maxColWidth[curCol]+spacing(); yoffset=0; curCol++; if (curCol>=c) break; } } } }