Skip to content
  • 0 Votes
    3 Posts
    799 Views
    johngodJ

    @julienchz
    Hi
    I have created some opengl tutorials check here: https://bitbucket.org/joaodeusmorgado/opengltutorials/src/master/
    I am using QOpenGLWidget, but I use mostly raw opengl, you could easily create a abstract render class, and then reuse it to QOpenGLWidget, or any other frame work of your choice render class.
    Hope it helps

  • 0 Votes
    5 Posts
    573 Views
    B

    @JonB You’re right, Thanks, QGraphicsItemGroup did the trick. I just needed to set the transform origin point to the centre of the red rectangle. Now the desired effect is achieved by this code:

    #include "game.h" #include <QGraphicsItemGroup> QGraphicsItemGroup* g = new QGraphicsItemGroup; Game::Game() { player = new QGraphicsRectItem(); rectItem = new QGraphicsRectItem(); m_view = new QGraphicsView(this); m_view->setSceneRect(QRectF(0,0,800,600)); this->setBackgroundBrush(Qt::black); m_view->setScene(this); m_view->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff); m_view->setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff); m_view->setRenderHints(QPainter::Antialiasing | QPainter::SmoothPixmapTransform); m_view->setViewportUpdateMode(QGraphicsView::NoViewportUpdate); m_view->show(); player->setRect(0,0,100,100); player->setBrush(Qt::red); player->setPos(400,300); player->setFocus(); rectItem->setRect(0,0,100,100); rectItem->setBrush(Qt::green); rectItem->setPos(400,330); this->addItem(g); player->setZValue(10); rectItem->setZValue(1); g->addToGroup(player); g->addToGroup(rectItem); g->setTransformOriginPoint(player->pos().x() + player->boundingRect().width()/2 ,player->pos().y() + player->boundingRect().height()/2); } void Game::advance() { } void Game::keyPressEvent(QKeyEvent *event) { switch(event->key()) { case Qt::Key_Left : g->moveBy(-5,0); break; case Qt::Key_Right : g->moveBy(5,0); break; case Qt::Key_Up : g->moveBy(0,-5); break; case Qt::Key_Down : g->moveBy(0,5); break; case Qt::Key_Q : g->setRotation(g->rotation()- 3); break; case Qt::Key_W : g->setRotation(g->rotation() +3); break; } update(); }
  • 0 Votes
    2 Posts
    528 Views
    jeanmilostJ

    So as nobody answered this question, I found a workaround which seems to resolve my issue. I changed the stroke width from 1 to 1.5. However this unfortunately doesn't explain what happened here, and why the ShapePath object behaves this way. I have my own idea about that: I think it's a kind of pen alignment, as in GDI+ (https://docs.microsoft.com/en-us/windows/win32/api/gdiplusenums/ne-gdiplusenums-penalignment), however I found absolutely no way to configure that.

    So below is my solution, which works correctly in all situations on my side:

    import QtQuick 2.15 import QtQuick.Window 2.15 import QtQuick.Controls 2.15 import QtQuick.Shapes 1.15 import QtGraphicalEffects 1.15 import QtQuick.Templates 2.15 as T /** * Dashed border *@author JMR */ T.Control { // advanced properties property real m_StrokeWidth: 1.5 property int m_Radius: 5 property string m_FillColor: "transparent" property string m_StrokeColor: "#bac1db" /** * Background rectangle */ Rectangle { // common properties anchors.fill: parent color: m_FillColor radius: m_Radius /** * Dashed outline shape */ Shape { // common properties id: shDashedBorder anchors.fill: parent anchors.margins: 0 //layer.enabled: true //layer.samples: 8 smooth: true clip: true /** * Dashed outline shape path */ ShapePath { // common properties fillColor: "transparent" strokeColor: m_StrokeColor strokeWidth: m_StrokeWidth strokeStyle: ShapePath.DashLine dashPattern: [5, 5] startX: m_Radius startY: 0 // path commands PathLine {x: shDashedBorder.width - m_Radius; y: 0;} PathQuad {x: shDashedBorder.width; y: m_Radius; controlX: shDashedBorder.width; controlY: 0;} PathLine {x: shDashedBorder.width; y: shDashedBorder.height - m_Radius;} PathQuad {x: shDashedBorder.width - m_Radius; y: shDashedBorder.height; controlX: shDashedBorder.width; controlY: shDashedBorder.height;} PathLine {x: m_Radius; y: shDashedBorder.height;} PathQuad {x: 0; y: shDashedBorder.height - m_Radius; controlX: 0; controlY: shDashedBorder.height;} PathLine {x: 0; y: m_Radius;} PathQuad {x: m_Radius; y: 0; controlX: 0; controlY: 0;} } } } }
  • 0 Votes
    3 Posts
    1k Views
    D

    @Jakob-Weiss
    Is there any QT 3d Volume Rendering exmple in Qt? We are also trying to get Texture3d work in shader. Up to now, thanks to your tip, we made Texture2d work. We did the same in Texture3d, but it just didn't work and always shows black. Thanks if there is any tip.

    QML is like: parameters: [ Parameter { id: mainTex name: "mainTex" value: m_mainTexture }, Parameter { id: myTex3D name: "myTex3D" value: m_mainTex3D } ] frag Shader is like: layout(std140, binding = auto) uniform custom_uniforms { vec3 maincolor; }; layout(binding = auto) uniform sampler2D mainTex; layout(binding = auto) uniform sampler3D myTex3D; layout(location = 0) in vec3 worldPosition; layout(location = 1) in vec2 v_texcoord; layout(location = 0) out vec4 fragColor; void main() { //vec4 txtColor = texture(mainTex, v_texcoord); vec4 txtColor = texture(myTex3D, vec3(v_texcoord.x,v_texcoord.y,0.5)); float value_3D = txtColor.r * 100; fragColor = vec4(value_3D,value_3D,value_3D,1.0); } C++ is like: m_texture3D = new Qt3DRender::QTexture3D(); m_texture3D->setSize(128,128,128); m_texture3D->setFormat(Qt3DRender::QTexture3D::R8_UNorm); m_texture3D->setLayers(1); m_texture3D->setGenerateMipMaps(false); Qt3DRender::QTextureWrapMode wm(Qt3DRender::QTextureWrapMode::ClampToBorder); m_texture3D->setWrapMode(wm); //m_texture3D->setMinificationFilter(Qt3DRender::QTexture3D::Linear); //m_texture3D->setMagnificationFilter(Qt3DRender::QTexture3D::Linear); rawPixelData3D.resize(128 * 128 * 128 * sizeof(uchar)); uchar *pixels3D = reinterpret_cast<uchar *>(rawPixelData3D.data()); std::memset(pixels3D, 60, 128 * 128 * 128 * sizeof(uchar)); Qt3DRender::QTextureImageDataPtr imageData3D = Qt3DRender::QTextureImageDataPtr::create(); imageData3D->setFormat(QOpenGLTexture::TextureFormat::R8_UNorm); imageData3D->setWidth(128); imageData3D->setHeight(128); imageData3D->setDepth(128); imageData3D->setMipLevels(1); imageData3D->setLayers(1); imageData3D->setPixelFormat(QOpenGLTexture::PixelFormat::Red); imageData3D->setPixelType(QOpenGLTexture::PixelType::UInt8); imageData3D->setData(rawPixelData3D, 1, false); Qt3DRender::QTextureDataUpdate update3D; update3D.setX(0); update3D.setY(0); update3D.setData(imageData3D); m_texture3D->updateData(update3D);
  • 0 Votes
    4 Posts
    709 Views
    J

    We could not figure out how to achieve this without pure QtQuick3D without major modifications.. In the end, for this we opted to go with Qt3D instead of QtQuick3D. it seems that Qt3D is more geared towards customizable rendering while QtQuick3D just covers the standard cases and little else.

  • 0 Votes
    4 Posts
    2k Views
    E

    @SGaist
    Thank you so much! Your response was much helpful!

  • Grafica di base

    Solved Italian
    6
    0 Votes
    6 Posts
    3k Views
    B

    @VRonin said in Grafica di base:

    In realta' usando QML puoi andare oltre QGraphicView/Scene, viene spiegato in questo blog: http://blog.qt.io/blog/2017/01/19/should-you-be-using-qgraphicsview/

    Grazie per la risposta.
    E' bastato approfondire il link per capire tutte le potenzialità, veramente notevoli.
    Saluti

  • 0 Votes
    8 Posts
    2k Views
    mrjjM

    @GhostWolf
    Sounds like it crash.
    Does the samples also crash ?

  • 0 Votes
    2 Posts
    3k Views
    VagabondV

    Okay, I have come up with a solution. I have setup a better handling for the hittest evaluation. I first check which side of the intersected boundingbox the moved item is closest to. Then I set the x, or y coordinate accordingly. I added some helper functions for this, to compute point-line distance and closest side of a rect to a point. They are all included in the snippet below.

    NOTE: the collision test will also evaluate and prohibit the item to exceed the scene bounds. It will also only solve, overlapping one other item. If the border test results in another overlap I simply set the position back to where it was prior to mouse move. Works a lot nicer than my initial implementation though.

    enum CustomGraphicsItem::BOX_SIDE { LEFT, RIGHT, UPPER, LOWER }; void CustomGraphicsItem::mouseMoveEvent(QGraphicsSceneMouseEvent* e) { if(mode_ == MOVE) { QPointF p = pos(); QGraphicsItem::mouseMoveEvent(e); QPointF p_new = pos(); QList<QGraphicsItem*> col_it = collidingItems(Qt::IntersectsItemBoundingRect); if(col_it.size() > 0) { qreal x_min = col_it[0]->pos().x() - boundingRect().width(); qreal x_max = col_it[0]->pos().x() + col_it[0]->boundingRect().width(); qreal y_min = col_it[0]->pos().y() - boundingRect().height(); qreal y_max = col_it[0]->pos().y() + col_it[0]->boundingRect().height(); QRectF rect(QPointF(x_min, y_min), QPointF(x_max, y_max)); switch(closestSide(p_new, rect)) { case LEFT: p_new.setX(x_min); break; case RIGHT: p_new.setX(x_max); break; case UPPER: p_new.setY(y_min); break; case LOWER: p_new.setY(y_max); break; } setPos(p_new); } // check if item in scene bounds qreal max_x = scene()->width() - boundingRect().width(); qreal max_y = scene()->height() - boundingRect().height(); if (x() < 0) setPos(0, y()); else if (x() > max_x) setPos(max_x, y()); if (y() < 0) setPos(x(), 0); else if (y() > max_y) setPos(x(), max_y); // if still colliding set pos back to start col_it = collidingItems(Qt::IntersectsItemBoundingRect); if(col_it.size() > 0) setPos(p); } } qreal CustomGraphicsItem::distance(const QPointF &p, const QLineF &l) { QPointF p1 = l.p1(); QPointF p2 = l.p2(); qreal x = p.x() - p1.x(); qreal y = p.y() - p1.y(); qreal x2 = p2.x() - p1.x(); qreal y2 = p2.y() - p1.y(); // if line is a point, return distance between point and one line node qreal norm = sqrt(x2*x2 + y2*y2); if (norm <= std::numeric_limits<int>::epsilon()) return sqrt(x*x + y*y); // distance return fabs(x*y2 - y*x2) / norm; } CustomGraphicsItem::BOX_SIDE CustomGraphicsItem::closestSide(const QPointF &p, const QRectF &rect) { qreal x_min = rect.x(); qreal x_max = rect.x() + rect.width(); qreal y_min = rect.y(); qreal y_max = rect.y() + rect.height(); qreal temp_dist = 0; // left QLineF l(QPointF(x_min, y_min), QPointF(x_min, y_max)); qreal min_dist = distance(p,l); BOX_SIDE side = LEFT; // right l.setPoints(QPointF(x_max,y_min), QPointF(x_max, y_max)); temp_dist = distance(p,l); if(temp_dist < min_dist) { min_dist = temp_dist; side = RIGHT; } // upper l.setPoints(QPointF(x_min, y_min), QPointF(x_max, y_min)); temp_dist = distance(p,l); if(temp_dist < min_dist) { min_dist = temp_dist; side = UPPER; } // lower l.setPoints(QPointF(x_min, y_max), QPointF(x_max, y_max)); temp_dist = distance(p,l); if(temp_dist < min_dist) { min_dist = temp_dist; side = LOWER; } return side; }
  • 0 Votes
    3 Posts
    930 Views
    Stefan Monov76S

    @sierdzio : Thanks. I got a similar comment at my SO crosspost. I've posted there what I could gather from the docs.

  • 0 Votes
    7 Posts
    3k Views
    0

    @raven-worx I mean drawing part is quite simple, but there is a stuff QGraphicsPathItem doesn't provide, so I had to implement my own class. I will make some experiments with QGraphicsPathItem later, but for now viewportUpdateMode solves an issue.

  • 0 Votes
    1 Posts
    770 Views
    No one has replied
  • 0 Votes
    1 Posts
    789 Views
    No one has replied
  • 0 Votes
    3 Posts
    2k Views
    S

    Hi and thanks for hints. We were thinking also about local coordinates of arc being drawn. But considering that when drawing arc in its local space using global scene coordinates and then adding arc into scene at 0.0 would be the same as drawing arc in its local coords at 0.0 and then placing it at some position.
    Considering we don't rotate which we don't at this time...

    Will try to draw at 0.0 and translate in scene afterward. lets see if that'll make a difference.

  • 0 Votes
    1 Posts
    799 Views
    No one has replied