
Fri, 01/17/2014 - 02:40
Hi,
I am using OCCT660 to convert an IGES format to OpenSceneGraph Format. I am having troubles calculating normals for each triangle.
here is the code that I am using to calculate normals of triangle.
Handle (Poly_Triangulation) triangulation = BRep_Tool::Triangulation(face, location);
if (!triangulation.IsNull())
{
int noOfNodes = triangulation->NbNodes();
// Store vertices. Build vertex array here
for(int j = 1; j NbNodes(); j++)
{
// populate vertex list
// Ref: http://www.opencascade.org/org/forum/thread_16694/?forum=3
gp_Pnt pt = (triangulation->Nodes())(j).Transformed(transformation * location.Transformation());
vertexList->push_back(osg::Vec3(pt.X(), pt.Y(), pt.Z()));
// calculate normal method 1
gp_Pnt2d uv;
gp_Vec normal;
gp_Pnt pos;
uv = (triangulation->UVNodes())(j);
faceProperty.Normal(uv.X(), uv.Y(), pos, normal);
// normal.Normalize();
normalList->push_back(osg::Vec3(normal.X(), normal.Y(), normal.Z()));
// populate color list
colorList->push_back(geomColor);
}
....
....
}
Here most of the time i get normal as (0,0,0) resulting in a crash in normalization. I am attaching the result for your reference.
Thank You
-Abhishek
Fri, 01/17/2014 - 12:22
I tried solution given in following thread but that also is not working for me..
http://www.opencascade.org/org/forum/thread_12568/?forum=3
Fri, 01/17/2014 - 13:43
I tried to use code from Ling's question from following thread
http://www.opencascade.org/org/forum/thread_9004/?forum=3
I changed my code.. here it is..
Handle (Poly_Triangulation) triangulation = BRep_Tool::Triangulation(face, location);
if (!triangulation.IsNull())
{
int noOfNodes = triangulation->NbNodes();
// Store vertices. Build vertex array here
for(int j = 1; j <= triangulation->NbNodes(); j++)
{
// populate vertex list
// Ref: http://www.opencascade.org/org/forum/thread_16694/?forum=3
gp_Pnt pt = (triangulation->Nodes())(j).Transformed(transformation * location.Transformation());
vertexList->push_back(osg::Vec3(pt.X(), pt.Y(), pt.Z()));
// populate color list
colorList->push_back(geomColor);
}
/// now we need to get face indices for triangles
// get list of triangle first
const Poly_Array1OfTriangle& triangles = triangulation->Triangles();
//No of triangles in this triangulation
noOfTriangles = triangulation->NbTriangles();
Standard_Integer v1, v2, v3;
for (unsigned int j = 1; j <= noOfTriangles; j++)
{
bool flip = false;
/// If face direction is reversed then we add verticews in reverse order
/// order of vertices is important for normal calculation later
if (face.Orientation() == TopAbs_REVERSED)
{
triangles(j).Get(v1, v3, v2);
flip = true;
}
else
{
triangles(j).Get(v1, v2, v3);
}
triangleStrip->push_back(index + v1 - 1);
triangleStrip->push_back(index + v2 - 1);
triangleStrip->push_back(index + v3 - 1);
Poly_Triangle triangle = (triangulation -> Triangles())(j);
for(int k=1; k<=3; k++)
{
gp_Pnt2d uv;
gp_Vec nn;
uv = (triangulation -> UVNodes())(triangle(k));
prop.SetParameters (uv.X(), uv.Y());
if (prop.IsNormalDefined())
nn = prop.Normal();
else
{
osg::Vec3 op1 = vertexList->at(index + v1 - 1);
osg::Vec3 op2 = vertexList->at(index + v2 - 1);
osg::Vec3 op3 = vertexList->at(index + v3 - 1);
osg::Vec3 n1 = op2-op1;
osg::Vec3 n2 = op3-op2;
osg::Vec3 normal = n1^n2;
nn.SetX(0);
nn.SetY(0);
nn.SetZ(0);
}
if (face.Orientation() == TopAbs_REVERSED)
nn *= -1;
normalList->push_back(osg::Vec3(nn.X(),nn.Y(),nn.Z()));
normalList->push_back(osg::Vec3(nn.X(),nn.Y(),nn.Z()));
normalList->push_back(osg::Vec3(nn.X(),nn.Y(),nn.Z()));
}
}
index = index + noOfNodes;
}
}
The normals are again wrong. I have attached image for your reference.
Sun, 01/19/2014 - 15:07
Hi,
If you want to access to vertexes formals, you can use Poly_Triangulation::Normals method, C.f. documentation.
Then if you really want to use the triangle face normal, the cross product of the 2 vectors composed by the triangle vertexes is should do the trick.
Mon, 01/20/2014 - 15:19
Hi,
Thanks for youe reply !
Poly_Triangulation HasNormals() method always return false for me. I checked with multiple models.
Thank You
Abhishek
Mon, 02/03/2014 - 13:45
Have a look to Poly::ComputeNormals(const Handle(Poly_Triangulation)&Tri)
Tue, 02/11/2014 - 18:59
Have a look StlTransfer.cxx,
There is a function: Normal() to calculate the normals for the triangualtion.
Wed, 02/26/2014 - 16:35
Hi Abhishek,
I met the same problem when i tried to visulization the model in OSG using Triangulation. Have you found a solution to it? I am attaching my result for your reference.
Thank you!
-Junjie Xue
Mon, 01/28/2019 - 16:10
Hi,
I know this thread is old, but for anyone is still experiencing this issue: Flipping the normal in case the face is reversed does the job:
gp_Dir normal = triangulation->Normal(i);
normal.Transform(transformation);
if (face.Orientation() == TopAbs_REVERSED)
{
normal = normal.Reversed();
}
Best,
-Jan