2014-02-14 6 views
2

나는 사용자가 물건을 그리거나 이동하기를 원하는 QGraphicsScene을 가지고 있습니다. 현재는 원하는 모든 도형 (채워지지 않은 사각형과 타원, 선 및 3 차원 베 지어 곡선)을 그릴 수 있으며, 이는 QGraphics*Item입니다.QGraphicsScene의 시각적 픽셀 완벽한 선택

나는 또한 이러한 항목에 대한 선택을 얻을 수 있지만 일종의을 선택하고 싶습니다. 예를 들어, 마우스가 실제 선에 있지 않더라도 커브가있는 곳 옆에있는 곡선을 클릭하여 선택할 수 있습니다. 빈 직사각형이나 타원에 대해서도 마찬가지입니다. 중간에있는 구멍을 클릭하여 선택하십시오.

이것은 contains의 작동 방식 때문입니다. 내 요구에 맞지 않습니다. 기본적으로 포인트가 경계 사각형에 있는지 확인합니다. setBoundingRegionGranularity(1)은 아무 것도 해결하지 못합니다.

포인트가 내 항목의 QPainterPath에 포함되어 있는지 직접 확인해 보았지만 동일한 결과가 나옵니다.

어떻게 시각적으로 도형을 선택할 수 있습니까?

현재 내가보고있는 유일한 해결책은 내가 갖고있는 모든 모양에 대해 내 함수를 다시 구현하는 것이지만 이것은 매우 복잡 할 수 있으며 가능한 경우 Qt를 통해 수행해야합니다.

저는 파이썬 3.3과 PyQt 5 (.1.1 IIRC)를 사용하고 있습니다.하지만 이것은 언어/바인딩보다 Qt 프레임 워크와 더 관련이 있으며 C++의 답변도 좋습니다.

답변

1

QGraphicsPathItem::shape에는 내부 영역을 포함하여 표시되는 경로가 포함되어 있습니다. 기대하는 동작은 QGraphicsPixmapItem과 같습니다. shapeModeQGraphicsPixmapItem::MaskShape (기본값)이면 모양에 불투명 한 점만 포함됩니다. 픽스맵에 커브를 그리고 픽스맵을 장면에 표시하고 기본 동작을 즐기기를 원할 수 있습니다. QGraphicsPathItem::shape을 다시 정의하고이 동작을 구현할 수도 있습니다. , C++은 (쉽게 파이썬 적용 할 수 있습니다) 사용 예 :

class MyGraphicsPathItem : public QGraphicsPathItem { 
public: 
    MyGraphicsPathItem() {} 
    QPainterPath shape() const { 
    QRectF rect = path().boundingRect(); 
    QImage canvas(rect.size().toSize(), QImage::Format_ARGB32); 
    canvas.fill(qRgba(0, 0, 0, 0)); 
    QPainter painter(&canvas); 
    painter.setPen(pen()); 
    painter.drawPath(path().translated(-rect.topLeft())); 
    painter.end(); 
    QPainterPath result; 
    result.addRegion(QPixmap::fromImage(canvas).mask()); 
    return result.translated(rect.topLeft()); 
    } 
}; 

사용법 :이 구현은 매우 느린 것을

MyGraphicsPathItem* item = new MyGraphicsPathItem(); 
item->setPath(path); 
item->setFlag(QGraphicsItem::ItemIsSelectable); 
item->setPen(QPen(Qt::green, 3)); 
scene->addItem(item); 

참고. 주의해서 사용하십시오.

+0

답변 해 주셔서 감사합니다. 그러나 Pixmaps를 사용하면 도형에 앤티 앨리어싱이 적용되지 않습니까? –

+0

pixmap을 만들 때 사용하는 화가에서'QPainter :: Antialiasing' 힌트를 활성화해야합니다. 픽스맵 스케일링을 사용한다면'QGraphicsPixmapItem :: setTransformationMode (Qt :: SmoothTransformation)'도 설정해야합니다. –