void GLC_CuttingPlane::create3DviewInstance() { Q_ASSERT(GLC_3DWidget::isEmpty()); // The cutting plane material GLC_Material* pMaterial= new GLC_Material(m_Color); pMaterial->setOpacity(m_Opacity); // Cutting plane 3Dview instance GLC_3DViewInstance cuttingPlaneInstance= GLC_Factory::instance()->createCuttingPlane(m_Center, m_Normal, m_L1, m_L2, pMaterial); GLC_3DWidget::add3DViewInstance(cuttingPlaneInstance); // Normal arrow geometry GLC_Arrow* pArrow= new GLC_Arrow(GLC_Point3d(), -glc::Z_AXIS, GLC_3DWidget::widgetManagerHandle()->cameraHandle()->forward().normalize()); pArrow->setLineWidth(4.5); pArrow->setHeadLength(0.15); QColor arrowColor(Qt::red); arrowColor.setAlphaF(0.4); pArrow->setWireColor(arrowColor); //Base arrow disc pMaterial= new GLC_Material(Qt::red); pMaterial->setOpacity(m_Opacity); GLC_Disc* pDisc= new GLC_Disc(0.3); pDisc->replaceMasterMaterial(pMaterial); // Normal arrow + base instance GLC_3DRep normalLine(pArrow); normalLine.addGeom(pDisc); GLC_3DWidget::add3DViewInstance(GLC_3DViewInstance(normalLine)); GLC_3DWidget::set3DViewInstanceVisibility(1, false); // Rotation manipulator const double initRadius= 1; // Arrond X axis pDisc= new GLC_Disc(initRadius); pMaterial= new GLC_Material(Qt::red); pMaterial->setOpacity(m_Opacity); pDisc->replaceMasterMaterial(pMaterial); pDisc->setAngle(glc::PI); GLC_3DWidget::add3DViewInstance(GLC_3DViewInstance(pDisc)); GLC_3DWidget::set3DViewInstanceVisibility(2, false); // Arround Y axis pDisc= new GLC_Disc(initRadius); pMaterial= new GLC_Material(Qt::green); pMaterial->setOpacity(m_Opacity); pDisc->replaceMasterMaterial(pMaterial); pDisc->setAngle(glc::PI); GLC_3DWidget::add3DViewInstance(GLC_3DViewInstance(pDisc)); GLC_3DWidget::set3DViewInstanceVisibility(3, false); // Arround Z axis pDisc= new GLC_Disc(initRadius); pMaterial= new GLC_Material(Qt::blue); pMaterial->setOpacity(m_Opacity); pDisc->replaceMasterMaterial(pMaterial); //pDisc->setAngle(glc::PI / 2.0); GLC_3DWidget::add3DViewInstance(GLC_3DViewInstance(pDisc)); GLC_3DWidget::set3DViewInstanceVisibility(4, false); }
// Triangulate a no convex polygon void glc::triangulatePolygon(QList<GLuint>* pIndexList, const QList<float>& bulkList) { int size= pIndexList->size(); if (polygonIsConvex(pIndexList, bulkList)) { QList<GLuint> indexList(*pIndexList); pIndexList->clear(); for (int i= 0; i < size - 2; ++i) { pIndexList->append(indexList.at(0)); pIndexList->append(indexList.at(i + 1)); pIndexList->append(indexList.at(i + 2)); } } else { // Get the polygon vertice QList<GLC_Point3d> originPoints; QHash<int, int> indexMap; QList<int> face; GLC_Point3d currentPoint; int delta= 0; for (int i= 0; i < size; ++i) { const int currentIndex= pIndexList->at(i); currentPoint= GLC_Point3d(bulkList.at(currentIndex * 3), bulkList.at(currentIndex * 3 + 1), bulkList.at(currentIndex * 3 + 2)); if (!originPoints.contains(currentPoint)) { originPoints.append(GLC_Point3d(bulkList.at(currentIndex * 3), bulkList.at(currentIndex * 3 + 1), bulkList.at(currentIndex * 3 + 2))); indexMap.insert(i - delta, currentIndex); face.append(i - delta); } else { qDebug() << "Multi points"; ++delta; } } // Values of PindexList must be reset pIndexList->clear(); // Update size size= size - delta; // Check new size if (size < 3) return; //-------------- Change frame to mach polygon plane // Compute face normal const GLC_Point3d point1(originPoints[0]); const GLC_Point3d point2(originPoints[1]); const GLC_Point3d point3(originPoints[2]); const GLC_Vector3d edge1(point2 - point1); const GLC_Vector3d edge2(point3 - point2); GLC_Vector3d polygonPlaneNormal(edge1 ^ edge2); polygonPlaneNormal.normalize(); // Create the transformation matrix GLC_Matrix4x4 transformation; GLC_Vector3d rotationAxis(polygonPlaneNormal ^ Z_AXIS); if (!rotationAxis.isNull()) { const double angle= acos(polygonPlaneNormal * Z_AXIS); transformation.setMatRot(rotationAxis, angle); } QList<GLC_Point2d> polygon; // Transform polygon vertexs for (int i=0; i < size; ++i) { originPoints[i]= transformation * originPoints[i]; // Create 2d vector polygon << originPoints[i].toVector2d(Z_AXIS); } // Create the index QList<int> index= face; const bool faceIsCounterclockwise= isCounterclockwiseOrdered(polygon); if(!faceIsCounterclockwise) { //qDebug() << "face Is Not Counterclockwise"; const int max= size / 2; for (int i= 0; i < max; ++i) { polygon.swap(i, size - 1 -i); int temp= face[i]; face[i]= face[size - 1 - i]; face[size - 1 - i]= temp; } } QList<int> tList; triangulate(polygon, index, tList); size= tList.size(); for (int i= 0; i < size; i+= 3) { // Avoid normal problem if (faceIsCounterclockwise) { pIndexList->append(indexMap.value(face[tList[i]])); pIndexList->append(indexMap.value(face[tList[i + 1]])); pIndexList->append(indexMap.value(face[tList[i + 2]])); } else { pIndexList->append(indexMap.value(face[tList[i + 2]])); pIndexList->append(indexMap.value(face[tList[i + 1]])); pIndexList->append(indexMap.value(face[tList[i]])); } } Q_ASSERT(size == pIndexList->size()); } }
// Move the camera bool GLC_TsrMover::move(const GLC_UserInput& userInput) { if (!(userInput.normalyzeXTouchCenter() < 0.0) && !(userInput.normalyzeYTouchCenter() < 0.0)) { m_PreviousVector= GLC_Point3d(userInput.normalyzeXTouchCenter(), userInput.normalyzeYTouchCenter(), 0.0); } else { qDebug() << "Pas cool"; if (!userInput.translation().isNull()) { m_PreviousVector= GLC_Vector3d(userInput.translation().getX(), userInput.translation().getY(), 0.0) + m_PreviousVector; } } const double x= m_PreviousVector.x(); const double y= m_PreviousVector.y(); //GLC_Point3d center2= m_pViewport->unProject(x * m_pViewport->viewHSize(), y * m_pViewport->viewVSize()); //qDebug() << "touch center= " << x << " , " << y; if (!qFuzzyCompare(userInput.scaleFactor(), 0)) { GLC_Point dummy(m_pViewport->cameraHandle()->target()); m_pViewport->setDistMinAndMax(dummy.boundingBox()); GLC_Point2d nPos= m_pViewport->mapNormalyzeToOpenGLScreen(x, y); GLC_Point3d nPos3D(nPos.getX(), nPos.getY(), 1.0); GLC_Point3d projected= m_pViewport->compositionMatrix().inverted() * nPos3D; m_pViewport->cameraHandle()->zoom(userInput.scaleFactor()); m_pViewport->setDistMinAndMax(dummy.boundingBox()); GLC_Point3d projected2= m_pViewport->compositionMatrix().inverted() * nPos3D; GLC_Vector3d delta= projected - projected2; m_pViewport->cameraHandle()->translate(delta); } if (!qFuzzyCompare(userInput.rotationAngle(), 0)) { GLC_Point dummy(m_pViewport->cameraHandle()->target()); m_pViewport->setDistMinAndMax(dummy.boundingBox()); GLC_Point2d nPos= m_pViewport->mapNormalyzeToOpenGLScreen(x, y); GLC_Point3d nPos3D(nPos.getX(), nPos.getY(), 1.0); GLC_Point3d center= m_pViewport->compositionMatrix().inverted() * nPos3D; GLC_Vector3d axis= m_pViewport->cameraHandle()->forward(); m_pViewport->cameraHandle()->rotateAround(axis, userInput.rotationAngle(), center); } if (!userInput.translation().isNull()) { double transX= userInput.translation().getX() * m_pViewport->viewHSize(); double transY= userInput.translation().getY() * m_pViewport->viewVSize(); GLC_Vector3d mappedTranslation(-transX, -transY, 0.0); // Compute the length of camera's field of view const double ChampsVision = m_pViewport->cameraHandle()->distEyeTarget() * m_pViewport->viewTangent(); // the side of camera's square is mapped on Vertical length of window // Ratio OpenGL/Pixel = dimend GL / dimens Pixel const double Ratio= ChampsVision / static_cast<double>(m_pViewport->viewVSize()); mappedTranslation= mappedTranslation * Ratio; m_pViewport->cameraHandle()->pan(mappedTranslation); } return true; }
// Initialized the mover void GLC_TsrMover::init(const GLC_UserInput& userInput) { m_PreviousVector= GLC_Point3d(userInput.normalyzeXTouchCenter(), userInput.normalyzeYTouchCenter(), 0.0); }