void TwoDModelScene::reshapeWall(QGraphicsSceneMouseEvent *event) { const QPointF pos = event->scenePos(); if (mCurrentWall) { const QPointF oldPos = mCurrentWall->end(); mCurrentWall->setX2(pos.x()); mCurrentWall->setY2(pos.y()); if (SettingsManager::value("2dShowGrid").toBool()) { mCurrentWall->reshapeBeginWithGrid(SettingsManager::value("2dGridCellSize").toInt()); mCurrentWall->reshapeEndWithGrid(SettingsManager::value("2dGridCellSize").toInt()); } else { const QPainterPath shape = mCurrentWall->realShape(); for (RobotItem * const robotItem : mRobots.values()) { if (shape.intersects(robotItem->realBoundingRect())) { mCurrentWall->setX2(oldPos.x()); mCurrentWall->setY2(oldPos.y()); break; } } if (event->modifiers() & Qt::ShiftModifier) { mCurrentWall->reshapeRectWithShift(); } } } }
QRegion KRITAIMAGE_EXPORT splitPath(const QPainterPath &path) { QRect totalRect = path.boundingRect().toAlignedRect(); // adjust the rect for antialiasing to work totalRect = totalRect.adjusted(-1,-1,1,1); const int step = 64; const int right = totalRect.x() + totalRect.width(); const int bottom = totalRect.y() + totalRect.height(); QRegion dirtyRegion; for (int y = totalRect.y(); y < bottom;) { int nextY = qMin((y + step) & ~(step-1), bottom); for (int x = totalRect.x(); x < right;) { int nextX = qMin((x + step) & ~(step-1), right); QRect rect(x, y, nextX - x, nextY - y); if(path.intersects(rect)) { dirtyRegion |= rect; } x = nextX; } y = nextY; } return dirtyRegion; }
void EditorArea::paintEdges(QPainter &painter) { bool firstTime = true; QVector<int> edgesIds = workspace->getEdgesIds(); for (int i=0; i < edgesIds.size(); i++) { QPoint nodesOfEdge = workspace->getNodesOfEdge(edgesIds[i]); QPointF screenXYFirst = graph2screen(workspace->getNodePosition(nodesOfEdge.x())); QPointF screenXYSecond = graph2screen(workspace->getNodePosition(nodesOfEdge.y())); QPointF screenMidPoint = graph2screen(workspace->getThirdPointPos(edgesIds[i])); QPainterPath path; path.moveTo(screenXYFirst); path.quadTo(screenMidPoint, screenXYSecond); path.quadTo(screenMidPoint, screenXYFirst); painter.drawPath(path); QVector<QPointF> pointsOnBezier; QVector<float> sOnEdge; for (int k = 0; k < edgeDiscretization + 1; k++) { float t = float(k) / edgeDiscretization; QPointF coord = (1 - t) * (1 - t) * screenXYFirst + 2 * (1 - t) * t * screenMidPoint + t * t * screenXYSecond; pointsOnBezier << coord; } for (int k = 0; k < pointsOnBezier.size(); k++) { if (k == 0) { sOnEdge << 0.0; } else { float sJesima = workspace->distance(pointsOnBezier[k], pointsOnBezier[k - 1]); sOnEdge << sJesima; } } for (int k = 1; k < pointsOnBezier.size(); k++) { sOnEdge[k] = sOnEdge[k] + sOnEdge[k - 1]; } float length = sOnEdge.last(); for (int k = 0; k < sOnEdge.size(); k++) { sOnEdge[k] = sOnEdge[k] / length; } sOnBezier.insert(edgesIds[i], sOnEdge); if (path.intersects(QRectF(mouseCurrentPos.x() - 7, mouseCurrentPos.y() - 7, 14, 14))) { if (firstTime) { firstTime = false; hitElements.clear(); } QPoint temp(2, edgesIds[i]); hitElements.append(temp); } } }
bool BrLine::intersects(BrLine& line) const{ //il y a une intersection entre deux lignes si elles sont reliées au même //point, du coup, on teste l'intersection avec une courbe de bezier sans //les deux points extrêmes QPainterPath* withoutPoints = new QPainterPath(_line->pointAt(0.000000001)); withoutPoints->cubicTo(_contr->coord(), _contr->coord(), _line->pointAt(0.999999999)); return withoutPoints->intersects(line.bezierCurve()); }
static bool intersect_path(const QGraphicsItem *item, const QRectF &exposeRect, Qt::ItemSelectionMode mode, const QTransform &deviceTransform, const void *intersectData) { const QPainterPath scenePath = *static_cast<const QPainterPath *>(intersectData); QRectF brect = item->boundingRect(); _q_adjustRect(&brect); // ### Add test for this (without making things slower?) Q_UNUSED(exposeRect); bool keep = true; const QGraphicsItemPrivate *itemd = QGraphicsItemPrivate::get(item); if (itemd->itemIsUntransformable()) { // Untransformable items; map the scene rect to item coordinates. const QTransform transform = item->deviceTransform(deviceTransform); QPainterPath itemPath = (deviceTransform * transform.inverted()).map(scenePath); if (mode == Qt::ContainsItemShape || mode == Qt::ContainsItemBoundingRect) keep = itemPath.contains(brect); else keep = itemPath.intersects(brect); if (keep && (mode == Qt::ContainsItemShape || mode == Qt::IntersectsItemShape)) keep = QGraphicsSceneIndexPrivate::itemCollidesWithPath(item, itemPath, mode); } else { Q_ASSERT(!itemd->dirtySceneTransform); const QRectF itemSceneBoundingRect = itemd->sceneTransformTranslateOnly ? brect.translated(itemd->sceneTransform.dx(), itemd->sceneTransform.dy()) : itemd->sceneTransform.mapRect(brect); if (mode == Qt::ContainsItemShape || mode == Qt::ContainsItemBoundingRect) keep = scenePath.contains(itemSceneBoundingRect); else keep = scenePath.intersects(itemSceneBoundingRect); if (keep && (mode == Qt::ContainsItemShape || mode == Qt::IntersectsItemShape)) { QPainterPath itemPath = itemd->sceneTransformTranslateOnly ? scenePath.translated(-itemd->sceneTransform.dx(), -itemd->sceneTransform.dy()) : itemd->sceneTransform.inverted().map(scenePath); keep = QGraphicsSceneIndexPrivate::itemCollidesWithPath(item, itemPath, mode); } } return keep; }
bool WorldModel::checkCollision(QPolygonF const &robotRegion) const { QPainterPath robotPath; robotPath.addPolygon(robotRegion); QPainterPathStroker pathStroker; pathStroker.setWidth(3); robotPath = pathStroker.createStroke(robotPath); QPainterPath wallPath = buildWallPath(); return wallPath.intersects(robotPath); }
void D2ModelScene::worldWallDragged(items::WallItem *wall, QPainterPath const &shape, QPointF const &oldPos) { bool const isNeedStop = shape.intersects(mRobot->realBoundingRect()); wall->onOverlappedWithRobot(isNeedStop); if (wall->isDragged() && ((mDrawingAction == none) || (mDrawingAction == D2ModelScene::wall && mCurrentWall == wall))) { wall->setFlag(QGraphicsItem::ItemIsMovable, !isNeedStop); if (isNeedStop) { wall->setPos(oldPos); } } }
bool CCJKShapeRect::Intersect( const QRect &rect ) { CJK_D(const CCJKShapeRect); if (d->brush.style() != Qt::NoBrush) { return d->boundRect.intersects(rect); } else { QPainterPath path = StrokePath(GetPath()); return path.intersects(rect); } return false; }
bool WorldModel::touchSensorReading(QPoint const &position, qreal direction, inputPort::InputPortEnum const port) { Q_UNUSED(direction) QPainterPathStroker pathStroker; pathStroker.setWidth(3); QPainterPath robotPath; robotPath.moveTo(mTouchSensorPositionOld[port]); robotPath.lineTo(position); mTouchSensorPositionOld[port] = position; QPainterPath wallPath = buildWallPath(); return wallPath.intersects(robotPath); }
int WorldModel::sonarReading(QPoint const &position, qreal direction) const { int const maxSonarRangeCms = 255; QPainterPath const wallPath = buildWallPath(); for (int currentRangeInCm = 1; currentRangeInCm <= maxSonarRangeCms; ++currentRangeInCm) { QPainterPath rayPath = sonarScanningRegion(position, direction, currentRangeInCm); if (rayPath.intersects(wallPath)) { Tracer::debug(tracer::d2Model, "WorldModel::sonarReading", "Sonar sensor. Reading: " + QString(currentRangeInCm)); return currentRangeInCm; } } Tracer::debug(tracer::d2Model, "WorldModel::sonarReading", "Sonar sensor. Reading: max (" + QString(maxSonarRangeCms) + ")"); return maxSonarRangeCms; }
const QList<QPainterPath> TextItems::generateZones(const int Width, const int ToleranceR, const int ToleranceY, const int Columns) const { // Assumes that items are already in column, y, x order! // Phase #1: Generate the zones QList<QPainterPath> zones; foreach (const TextItem &item, items) { if (zones.isEmpty()) { // First word becomes first zone QPainterPath zone; zone.addRect(item.rect); zones << zone; } else { // Add to an existing zone within tolerance or a new one const QRectF tolerantRect = item.rect.adjusted(-ToleranceR, -ToleranceR, ToleranceR, ToleranceR); bool found = false; for (int i = 0; i < zones.count(); ++i) { QPainterPath zone = zones.at(i); if (zone.intersects(tolerantRect)) { zone.addRect(item.rect); zones[i] = zone; found = true; break; } } if (!found) { QPainterPath zone; zone.addRect(item.rect); zones << zone; } } } // Phase #2: Order the zones by (column, y, x) const int Span = Width / Columns; QMultiMap<Key, QPainterPath> zonesForColumn; foreach (const QPainterPath &zone, zones) { const QRect &rect = zone.boundingRect().toRect(); const int Column = ((Columns == 1) ? 0 : (rect.width() > Span) ? Columns : rect.right() / Span); const int y = normalizedY(static_cast<int>(rect.y()), ToleranceY); zonesForColumn.insertMulti(Key(Column, y, rect.x()), zone); } return zonesForColumn.values(); }
void TwoDModelScene::worldWallDragged(items::WallItem *wall, const QPainterPath &shape, const QRectF &oldPos) { bool isNeedStop = false; for (RobotItem * const robotItem : mRobots.values()) { if (shape.intersects(robotItem->realBoundingRect())) { isNeedStop = true; break; } } wall->onOverlappedWithRobot(isNeedStop); if (wall->isDragged() && ((mDrawingAction == none) || (mDrawingAction == TwoDModelScene::wall && mCurrentWall == wall))) { wall->setFlag(QGraphicsItem::ItemIsMovable, !isNeedStop); if (isNeedStop) { wall->setCoordinates(oldPos); } } }
/*! \internal Checks if item collides with the path and mode, but also checks that if it doesn't collide, maybe its frame rect will. */ bool QGraphicsSceneIndexPrivate::itemCollidesWithPath(const QGraphicsItem *item, const QPainterPath &path, Qt::ItemSelectionMode mode) { if (item->collidesWithPath(path, mode)) return true; if (item->isWidget()) { // Check if this is a window, and if its frame rect collides. const QGraphicsWidget *widget = static_cast<const QGraphicsWidget *>(item); if (widget->isWindow()) { QRectF frameRect = widget->windowFrameRect(); QPainterPath framePath; framePath.addRect(frameRect); bool intersects = path.intersects(frameRect); if (mode == Qt::IntersectsItemShape || mode == Qt::IntersectsItemBoundingRect) return intersects || path.contains(frameRect.topLeft()) || framePath.contains(path.elementAt(0)); return !intersects && path.contains(frameRect.topLeft()); } } return false; }
void EditorArea::paintNodes(QPainter &painter) { bool firstTime = true; qreal radius = size2screen(6); qreal width = radius * 2; qreal height = radius * 2; QVector<int> nodesIds = workspace->getNodesIds(); for (int i=0; i < nodesIds.size(); i++) { QPointF screenXY = graph2screen(workspace->getNodePosition(nodesIds[i])); if (workspace->getNodeMov(nodesIds[i])) { painter.setPen(Qt::NoPen); } else { painter.setPen(QPen(Qt::darkRed, size2screen(3), Qt::SolidLine, Qt::RoundCap, Qt::RoundJoin)); } QPainterPath path; path.arcTo(QRectF(-radius, -radius, width, height), 0, 360); path.translate(screenXY); painter.drawPath(path); QPainterPath mousePath; mousePath.arcTo(QRectF(-5, -5, 10, 10), 0, 360); mousePath.translate(mouseCurrentPos); if (path.intersects(mousePath)) { if (firstTime) { firstTime = false; hitElements.clear(); } QPoint temp(1, nodesIds[i]); hitElements.append(temp); } } }
bool Geometry::intersects(QLineF const &line, QPainterPath const &path) { QPainterPath linePath(line.p1()); linePath.lineTo(line.p2()); return path.intersects(linePath); }
void EditorArea::paintMeshEls(QPainter& painter) { QVector<int> nodesIds = workspace->getNodesIds(); QVector<int> edgesIds = workspace->getEdgesIds(); bool showMesh = workspace->getShowMeshStatus(); int selectedTool = workspace->getSelectedTool(); bool firstTime = true; bool firstTimeNode = true; qreal radius = size2screen(9); float fontSize = size2screen(12); qreal width = radius * 2; qreal height = radius * 2; painter.setFont(QFont("Arial", fontSize)); for (int i = 0; i < nodesIds.size(); i++) { QString nodeMTypeString = workspace->getNodeMType(nodesIds[i]); QString elementType; elementType.clear(); if (!nodeMTypeString.isEmpty()) { if (nodeMTypeString == "Anastomosis") { elementType = "a"; } else if (nodeMTypeString == "Windkessel") { elementType = "w"; } else if (nodeMTypeString == "Resistance") { elementType = "r"; } else if (nodeMTypeString == "WavePropagation") elementType = "p"; } if (!nodeMTypeString.isNull()) { QPointF nodePos = graph2screen(workspace->getNodePosition(nodesIds[i])); int nodeMElementId = workspace->getNodeMElementId(nodesIds[i]); meshElsPos.insert(nodeMElementId, nodePos); meshElsType.insert(nodeMElementId, elementType); meshId2GraphId.insert(nodeMElementId, QPoint(1, nodesIds[i])); QPainterPath path; QPainterPath text; path.arcTo(QRectF(-radius*1.2, -radius*1.2, width*1.2, height*1.2), 0, 360); text.addText(-radius / 2.0, radius / 2.0, QFont("Arial", fontSize), elementType); path.translate(nodePos); text.translate(nodePos); if (showMesh) { painter.setPen(Qt::NoPen); painter.setBrush(Qt::gray); painter.drawPath(path); painter.setPen(Qt::yellow); painter.setBrush(Qt::yellow); painter.drawPath(text); } else { qreal dotR = size2screen(2); QPainterPath dotPath; painter.setPen(Qt::gray); painter.setBrush(Qt::gray); dotPath.arcTo(QRectF(-dotR, -dotR, dotR * 2, dotR * 2), 0, 360); dotPath.translate(nodePos); painter.drawPath(dotPath); } QPainterPath mousePath; mousePath.arcTo(QRectF(-1, -1, 1, 1), 0, 360); mousePath.translate(mouseCurrentPos); if (path.intersects(mousePath) && selectedTool == 7) { painter.setPen(Qt::NoPen); painter.setBrush(Qt::gray); painter.drawPath(path); painter.setPen(Qt::yellow); painter.setBrush(Qt::yellow); painter.drawPath(text); if (firstTimeNode) { firstTimeNode = false; hitMeshEls.clear(); } QPoint temp(1, nodeMElementId); hitMeshEls.append(temp); } } } for (int j = 0; j < edgesIds.size(); j++) { QVector<float> sCoord = workspace->getEdgeMs(edgesIds[j]); QVector<QString> edgeMTypes = workspace->getEdgeMTypes(edgesIds[j]); QVector<int> edgeMElementsId = workspace->getEdgeMElementsId(edgesIds[j]); for (int h = 0; h < sCoord.size(); h++) { float s; if (h == sCoord.size() - 1.0) { s = (1.0 - sCoord[h]) / 2.0 + sCoord[h]; } else { s = (sCoord[h + 1] - sCoord[h]) / 2.0 + sCoord[h]; } int t = 0; while (sOnBezier.value(edgesIds[j]).at(t) < s) { t = t + 1; } float deltaS = s - float(t - 1) / edgeDiscretization; float m = float(t - 1) / edgeDiscretization + deltaS; QString elementType; elementType.clear(); if (!edgeMTypes[h].isEmpty()) { if (edgeMTypes[h] == "Resistance") { elementType = "r"; } else if (edgeMTypes[h] == "WavePropagation") { elementType = "p"; } else if (edgeMTypes[h] == "Anastomosis") { elementType = "a"; } else if (edgeMTypes[h] == "Windkessel") { elementType = "w"; } } QPoint nodesOfEdge = workspace->getNodesOfEdge(edgesIds[j]); QPointF screenXYFirst = graph2screen(workspace->getNodePosition(nodesOfEdge.x())); QPointF screenXYSecond = graph2screen(workspace->getNodePosition(nodesOfEdge.y())); QPointF screenMidPoint = graph2screen(workspace->getThirdPointPos(edgesIds[j])); QPointF pointPos = (1 - m) * (1 - m) * screenXYFirst + 2 * (1 - m) * m * screenMidPoint + m * m * screenXYSecond; meshElsPos.insert(edgeMElementsId[h], pointPos); meshElsType.insert(edgeMElementsId[h], elementType); meshId2GraphId.insert(edgeMElementsId[h], QPoint(2, edgesIds[j])); QPainterPath path; QPainterPath text; path.arcTo(QRectF(-radius, -radius, width, height), 0, 360); text.addText(-radius / 2.0, radius / 2.0, QFont("Arial", fontSize), elementType); path.translate(pointPos); text.translate(pointPos); if (showMesh) { painter.setPen(Qt::NoPen); painter.setBrush(Qt::darkCyan); painter.drawPath(path); painter.setPen(Qt::yellow); painter.setBrush(Qt::yellow); painter.drawPath(text); } else { qreal dotR = size2screen(1); QPainterPath dotPath; painter.setPen(Qt::black); painter.setBrush(Qt::black); dotPath.arcTo(QRectF(-dotR, -dotR, dotR * 2, dotR * 2), 0, 360); dotPath.translate(pointPos); painter.drawPath(dotPath); } QPainterPath mousePath; mousePath.arcTo(QRectF(-1, -1, 1, 1), 0, 360); mousePath.translate(mouseCurrentPos); if (path.intersects(mousePath) && selectedTool == 7) { painter.setPen(Qt::NoPen); painter.setBrush(Qt::darkCyan); painter.drawPath(path); painter.setPen(Qt::yellow); painter.setBrush(Qt::yellow); painter.drawPath(text); if (firstTime) { firstTime = false; hitMeshEls.clear(); } QPoint temp(2, edgeMElementsId[h]); hitMeshEls.append(temp); } } } }