// hotHandle: 绘新图时,起始步骤为-1,后续步骤>0;拖动一个或多个整体图形时为-1,拖动顶点时>=0 Point2d MgCmdManagerImpl::snapPoint(const MgMotion* sender, const Point2d& orignPt, const MgShape* shape, int hotHandle, int ignoreHandle, const int* ignoreids) { int ignoreids_tmp[2] = { shape ? shape->getID() : 0, 0 }; if (!ignoreids) ignoreids = ignoreids_tmp; if (!shape || hotHandle >= shape->shapec()->getHandleCount()) { hotHandle = -1; // 对hotHandle进行越界检查 } _ptSnap = orignPt; // 默认结果为当前触点位置 SnapItem arr[3] = { // 设置捕捉容差和捕捉初值 SnapItem(_ptSnap, _ptSnap, displayMmToModel(3.f, sender)), // XY点捕捉 SnapItem(_ptSnap, _ptSnap, displayMmToModel(1.f, sender)), // X分量捕捉,竖直线 SnapItem(_ptSnap, _ptSnap, displayMmToModel(1.f, sender)), // Y分量捕捉,水平线 }; if (shape && shape->getID() == 0 && hotHandle > 0 // 绘图命令中的临时图形 && !shape->shapec()->isCurve() && !shape->shapec()->isKindOf(MgBaseRect::Type())) { // 不是矩形或椭圆 Point2d pt (orignPt); snapHV(shape->shapec()->getPoint(hotHandle - 1), pt, arr); // 和上一个点对齐 } Point2d pnt(-1e10f, -1e10f); // 当前图形的某一个顶点匹配到其他顶点pnt bool matchpt = (shape && shape->getID() != 0 // 拖动整个图形 && (hotHandle < 0 || (ignoreHandle >= 0 && ignoreHandle != hotHandle))); snapPoints(sender, orignPt, shape, ignoreHandle, ignoreids, arr, matchpt ? &pnt : NULL); // 在所有图形中捕捉 checkResult(arr); return matchpt && pnt.x > -1e8f ? pnt : _ptSnap; // 顶点匹配优先于用触点捕捉结果 }
void EditArea::mouseReleaseEvent(QMouseEvent *) { if (mode == drawMode) //drew "add line" line { snapPoints(startPos, lastPos); } else if (mode == deleteMode) //drew "delete" line { QLineF line(startPos, lastPos); QVector<QVector<QPointF> > newdata; QVector<QPointF> st; QPointF trash; for (int i = 0; i < map.size(); i++) { if (map[i].size() >= 1) st.push_back(map[i][0]); for (int j = 0; j < map[i].size() - 1; j++) { QLineF tmpline(map[i][j], map[i][j + 1]); if (line.intersect(tmpline, &trash) == QLineF::BoundedIntersection) { emit mapChanged(); if (st.size() >= 2) newdata.push_back(st); st.clear(); } st.push_back(map[i][j + 1]); } if (st.size() >= 2) newdata.push_back(st); st.clear(); } map = newdata; } mode = noMode; update(); }