diff --git a/Graphics/Post.cpp b/Graphics/Post.cpp index 6e0a6bda62fae9e94babc0d35d7f36fcc2cab246..892e0a843209b6fce33df63143ba907dcee8af91 100644 --- a/Graphics/Post.cpp +++ b/Graphics/Post.cpp @@ -1,4 +1,4 @@ -// $Id: Post.cpp,v 1.120 2007-08-27 22:05:42 geuzaine Exp $ +// $Id: Post.cpp,v 1.121 2007-08-27 23:33:28 geuzaine Exp $ // // Copyright (C) 1997-2007 C. Geuzaine, J.-F. Remacle // @@ -71,16 +71,51 @@ double normValue(int numComp, double val[9]) return 0.; } -bool getExternalValues(PView *p, int index, int iele, int nbnod, - int nbcomp, double val[NMAX][9], - int &nbcomp2, double val2[NMAX][9]) +void getLineNormal(PView *p, double x[2], double y[2], double z[2], + double *v, SVector3 n[2], bool computeNormal) +{ + PViewOptions *opt = p->getOptions(); + + if(opt->LineType > 0){ + if(v){ + // if we draw tapered cylinders, we'll use the normalized values + // (between 0 and 1) stored in the first component of the + // normals to modulate the width of the cylinder + double d = opt->TmpMax - opt->TmpMin; + n[0][0] = (v[0] - opt->TmpMin) / (d ? d : 1.); + n[1][0] = (v[1] - opt->TmpMin) / (d ? d : 1.); + } + else{ + // when we don't have values we use maximum width cylinders + n[0][0] = n[1][0] = 1.; + } + } + else if(computeNormal){ + // if we don't have a normal, we compute one + SVector3 t(x[1] - x[0], y[1] - y[0], z[1] - z[0]); + SVector3 ex(0., 0., 0.); + if(t[0] == 0.) + ex[0] = 1.; + else if(t[1] == 0.) + ex[1] = 1.; + else + ex[2] = 1.; + n[0] = crossprod(t, ex); + n[0].normalize(); + n[1] = n[0]; + } +} + +bool getExternalValues(PView *p, int index, int iele, int numNodes, + int numComp, double val[NMAX][9], + int &numComp2, double val2[NMAX][9]) { PViewOptions *opt = p->getOptions(); // use self by default - nbcomp2 = nbcomp; - for(int i = 0; i < nbnod; i++) - for(int j = 0; j < nbcomp; j++) + numComp2 = numComp; + for(int i = 0; i < numNodes; i++) + for(int j = 0; j < numComp; j++) val2[i][j] = val[i][j]; opt->ExternalMin = opt->TmpMin; opt->ExternalMax = opt->TmpMax; @@ -91,10 +126,10 @@ bool getExternalValues(PView *p, int index, int iele, int nbnod, PViewData *data2 = p2->getData(); if(opt->TimeStep < data2->getNumTimeSteps() && iele < data2->getNumElements()){ - if(data2->getNumNodes(iele) == nbnod){ - nbcomp2 = data2->getNumComponents(iele); - for(int i = 0; i < nbnod; i++) - for(int j = 0; j < nbcomp2; j++) + if(data2->getNumNodes(iele) == numNodes){ + numComp2 = data2->getNumComponents(iele); + for(int i = 0; i < numNodes; i++) + for(int j = 0; j < numComp2; j++) data2->getValue(iele, i, j, opt->TimeStep, val2[i][j]); if(opt->RangeType == PViewOptions::Custom){ opt->ExternalMin = opt->CustomMin; @@ -142,19 +177,19 @@ void applyGeneralRaise(PView *p, int numNodes, int numComp, } } -void changeCoordinates(PView *p, int iele, int nbnod, int nbcomp, +void changeCoordinates(PView *p, int iele, int numNodes, int numComp, double xyz[NMAX][3], double val[NMAX][9]) { PViewOptions *opt = p->getOptions(); if(opt->Explode != 1.) { double barycenter[3] = {0., 0., 0.}; - for(int i = 0; i < nbnod; i++) + for(int i = 0; i < numNodes; i++) for(int j = 0; j < 3; j++) barycenter[j] += xyz[i][j]; for(int j = 0; j < 3; j++) - barycenter[j] /= (double)nbnod; - for(int i = 0; i < nbnod; i++) + barycenter[j] /= (double)numNodes; + for(int i = 0; i < numNodes; i++) for(int j = 0; j < 3; j++) xyz[i][j] = barycenter[j] + opt->Explode * (xyz[i][j] - barycenter[j]); } @@ -164,7 +199,7 @@ void changeCoordinates(PView *p, int iele, int nbnod, int nbcomp, opt->Transform[1][1] != 1. || opt->Transform[1][2] != 0. || opt->Transform[2][0] != 0. || opt->Transform[2][1] != 0. || opt->Transform[2][2] != 1.){ - for(int i = 0; i < nbnod; i++) { + for(int i = 0; i < numNodes; i++) { double old[3] = {xyz[i][0], xyz[i][1], xyz[i][2]}; for(int j = 0; j < 3; j++){ xyz[i][j] = 0.; @@ -175,32 +210,32 @@ void changeCoordinates(PView *p, int iele, int nbnod, int nbcomp, } if(opt->Offset[0] || opt->Offset[1] || opt->Offset[2]){ - for(int i = 0; i < nbnod; i++) + for(int i = 0; i < numNodes; i++) for(int j = 0; j < 3; j++) xyz[i][j] += opt->Offset[j]; } if(opt->Raise[0] || opt->Raise[1] || opt->Raise[2]){ - for(int i = 0; i < nbnod; i++){ - double norm = normValue(nbcomp, val[i]); + for(int i = 0; i < numNodes; i++){ + double norm = normValue(numComp, val[i]); for(int j = 0; j < 3; j++) xyz[i][j] += opt->Raise[j] * norm; } } - if(nbcomp == 3 && opt->VectorType == PViewOptions::Displacement){ - for(int i = 0; i < nbnod; i++){ + if(numComp == 3 && opt->VectorType == PViewOptions::Displacement){ + for(int i = 0; i < numNodes; i++){ for(int j = 0; j < 3; j++) xyz[i][j] += opt->DisplacementFactor * val[i][j]; } } if(opt->UseGenRaise){ - int nbcomp2; + int numComp2; double val2[NMAX][9]; - getExternalValues(p, opt->ViewIndexForGenRaise, iele, nbnod, - nbcomp, val, nbcomp2, val2); - applyGeneralRaise(p, nbnod, nbcomp2, val2, xyz); + getExternalValues(p, opt->ViewIndexForGenRaise, iele, numNodes, + numComp, val, numComp2, val2); + applyGeneralRaise(p, numNodes, numComp2, val2, xyz); } } @@ -235,7 +270,9 @@ void addOutlineLine(PView *p, double xyz[NMAX][3], unsigned int color, x[i] = xyz[in[i]][0]; y[i] = xyz[in[i]][1]; z[i] = xyz[in[i]][2]; col[i] = color; } - p->va_lines->add(x, y, z, 0, col, 0, true); + SVector3 n[2]; + getLineNormal(p, x, y, z, 0, n, true); + p->va_lines->add(x, y, z, n, col, 0, true); } void addScalarLine(PView *p, double xyz[NMAX][3], double val[NMAX][9], @@ -258,6 +295,9 @@ void addScalarLine(PView *p, double xyz[NMAX][3], double val[NMAX][9], double z[2] = {xyz[i0][2], xyz[i1][2]}; double v[2] = {val[i0][0], val[i1][0]}; + SVector3 n[2]; + getLineNormal(p, x, y, z, v, n, true); + double vmin = opt->TmpMin, vmax = opt->TmpMax; if(opt->SaturateValues) saturate(2, val, vmin, vmax, i0, i1); @@ -268,7 +308,7 @@ void addScalarLine(PView *p, double xyz[NMAX][3], double val[NMAX][9], unsigned int col[2]; for(int i = 0; i < 2; i++) col[i] = opt->getColor(v[i], vmin, vmax); - p->va_lines->add(x, y, z, 0, col, 0, unique); + p->va_lines->add(x, y, z, n, col, 0, unique); } else{ double x2[2], y2[2], z2[2], v2[2]; @@ -277,7 +317,7 @@ void addScalarLine(PView *p, double xyz[NMAX][3], double val[NMAX][9], unsigned int col[2]; for(int i = 0; i < 2; i++) col[i] = opt->getColor(v2[i], vmin, vmax); - p->va_lines->add(x2, y2, z2, 0, col, 0, unique); + p->va_lines->add(x2, y2, z2, n, col, 0, unique); } } } @@ -292,7 +332,7 @@ void addScalarLine(PView *p, double xyz[NMAX][3], double val[NMAX][9], if(nb == 2){ unsigned color = opt->getColor(k, opt->NbIso); unsigned int col[2] = {color, color}; - p->va_lines->add(x2, y2, z2, 0, col, 0, unique); + p->va_lines->add(x2, y2, z2, n, col, 0, unique); } if(vmin == vmax) break; } @@ -334,6 +374,7 @@ void addOutlineTriangle(PView *p, double xyz[NMAX][3], unsigned int color, else p->normals->get(x[j], y[j], z[j], n[j][0], n[j][1], n[j][2]); } } + getLineNormal(p, x, y, z, 0, n, false); if(!pre) p->va_lines->add(x, y, z, n, col, 0, true); } } @@ -447,6 +488,8 @@ void addScalarTriangle(PView *p, double xyz[NMAX][3], double val[NMAX][9], else p->normals->get(x2[i], y2[i], z2[i], n[i][0], n[i][1], n[i][2]); } } + double v[2] = {iso, iso}; + getLineNormal(p, x, y, z, v, n, false); if(!pre) p->va_lines->add(x2, y2, z2, n, col, 0, unique); } if(vmin == vmax) break; @@ -475,6 +518,7 @@ void addOutlineQuadrangle(PView *p, double xyz[NMAX][3], unsigned int color, else p->normals->get(x[j], y[j], z[j], n[j][0], n[j][1], n[j][2]); } } + getLineNormal(p, x, y, z, 0, n, false); if(!pre) p->va_lines->add(x, y, z, n, col, 0, true); } } @@ -725,17 +769,20 @@ void addVectorElement(PView *p, int iele, int numNodes, int numEdges, data->getValue(iele, 0, j, ts + 1, dxyz[j][1]); } unsigned int col[2]; + double norm[2]; for(int i = 0; i < 2; i++){ - double norm = sqrt(dxyz[0][i] * dxyz[0][i] + - dxyz[1][i] * dxyz[1][i] + - dxyz[2][i] * dxyz[2][i]); - col[i] = opt->getColor(norm, opt->TmpMin, opt->TmpMax); + norm[i] = sqrt(dxyz[0][i] * dxyz[0][i] + + dxyz[1][i] * dxyz[1][i] + + dxyz[2][i] * dxyz[2][i]); + col[i] = opt->getColor(norm[i], opt->TmpMin, opt->TmpMax); } for(int j = 0; j < 3; j++){ dxyz[j][0] = xyz0[j] + dxyz[j][0] * opt->DisplacementFactor; dxyz[j][1] = xyz0[j] + dxyz[j][1] * opt->DisplacementFactor; } - p->va_lines->add(dxyz[0], dxyz[1], dxyz[2], 0, col, 0); + SVector3 n[2]; + getLineNormal(p, dxyz[0], dxyz[1], dxyz[2], norm, n, true); + p->va_lines->add(dxyz[0], dxyz[1], dxyz[2], n, col, 0, false); } } return; @@ -881,7 +928,14 @@ void drawArrays(PView *p, VertexArray *va, GLint type, bool useNormalArray) float *p1 = va->getVertexArray(3 * (i + 1)); double x[2] = {p0[0], p1[0]}, y[2] = {p0[1], p1[1]}, z[2] = {p0[2], p1[2]}; glColor4ubv((GLubyte *)va->getColorArray(4 * i)); - Draw_Cylinder(opt->LineWidth, x, y, z, opt->Light); + if(opt->LineType == 1) + Draw_Cylinder(opt->LineWidth, x, y, z, opt->Light); + else{ + char *n0 = va->getNormalArray(3 * i); + char *n1 = va->getNormalArray(3 * (i + 1)); + double v0 = char2float(*n0), v1 = char2float(*n1); + Draw_TapCylinder(opt->LineWidth, v0, v1, 0., 1., x, y, z, opt->Light); + } } } else{ @@ -1151,6 +1205,10 @@ class initPView { if(opt->SmoothNormals) addElementsInArrays(p, true); addElementsInArrays(p); + Msg(INFO, "Rendering %d vertices", p->va_points->getNumVertices() + + p->va_lines->getNumVertices() + p->va_triangles->getNumVertices() + + p->va_vectors->getNumVertices()); + p->setChanged(false); } };