コード例 #1
0
void GMExperiment6_1::smoothenData()
{
    smoothData = ::smoothenData(rawData, gauss_support);

    curvature = computeCurvature(smoothData);
    curvature = ::smoothenData(curvature, curv_support);
}
コード例 #2
0
void Surface_DifferentialProperties_Plugin::computeCurvatureFromDialog()
{
	QList<QListWidgetItem*> currentItems = m_computeCurvatureDialog->list_maps->selectedItems();
	if(!currentItems.empty())
	{
		const QString& mapName = currentItems[0]->text();

		QString positionName = m_computeCurvatureDialog->combo_positionAttribute->currentText();
		QString normalName = m_computeCurvatureDialog->combo_normalAttribute->currentText();

		QString KmaxName;
		if(m_computeCurvatureDialog->KmaxAttributeName->text().isEmpty())
			KmaxName = m_computeCurvatureDialog->combo_KmaxAttribute->currentText();
		else
			KmaxName = m_computeCurvatureDialog->KmaxAttributeName->text();

		QString kmaxName;
		if(m_computeCurvatureDialog->kmaxAttributeName->text().isEmpty())
			kmaxName = m_computeCurvatureDialog->combo_kmaxAttribute->currentText();
		else
			kmaxName = m_computeCurvatureDialog->kmaxAttributeName->text();

		QString KminName;
		if(m_computeCurvatureDialog->KminAttributeName->text().isEmpty())
			KminName = m_computeCurvatureDialog->combo_KminAttribute->currentText();
		else
			KminName = m_computeCurvatureDialog->KminAttributeName->text();

		QString kminName;
		if(m_computeCurvatureDialog->kminAttributeName->text().isEmpty())
			kminName = m_computeCurvatureDialog->combo_kminAttribute->currentText();
		else
			kminName = m_computeCurvatureDialog->kminAttributeName->text();

		QString KnormalName;
		if(m_computeCurvatureDialog->KnormalAttributeName->text().isEmpty())
			KnormalName = m_computeCurvatureDialog->combo_KnormalAttribute->currentText();
		else
			KnormalName = m_computeCurvatureDialog->KnormalAttributeName->text();

		bool compute_kmean = (m_computeCurvatureDialog->check_computeKmean->checkState() == Qt::Checked);
		bool compute_kgaussian = (m_computeCurvatureDialog->check_computeKgaussian->checkState() == Qt::Checked);
		bool autoUpdate = (currentItems[0]->checkState() == Qt::Checked);

		computeCurvature(
			mapName,
			positionName, normalName,
			KmaxName, kmaxName, KminName, kminName, KnormalName,
			compute_kmean, compute_kgaussian,
			autoUpdate
		);
	}
}
コード例 #3
0
Spline::InterpolatedPTCW LoopingCubicHermiteSpline::getWiggle(double x) const
{
    //use modular arithmetic to bring x into an acceptable range
    x = fmod(x, numSegments);
    if(x < 0)
        x += numSegments;

    InterpolationData segment = segmentData.at(getSegmentIndex(x));
    double t = (x - segment.t0) * segment.tDistanceInverse;

    return InterpolatedPTCW(
                computePosition(t, segment),
                computeTangent(t, segment),
                computeCurvature(t, segment),
                computeWiggle(segment)
                );
}
コード例 #4
0
void Smoother::iteration()
{
  computeCurvature();
  for (int i = 1; i < (_nbVertices - 1); ++i) {
    real motionNormal = _factorCurvature * _curvature[i] *
                        edgeStopping(_curvature[i], _anisoNormal);

    real diffC1 = _curvature[i] - _curvature[i - 1];
    real diffC2 = _curvature[i] - _curvature[i + 1];
    real motionCurvature = edgeStopping(diffC1, _anisoCurvature) * diffC1 +
                           edgeStopping(diffC2, _anisoCurvature) *
                               diffC2;  //_factorCurvatureDifference;
    motionCurvature *= _factorCurvatureDifference;
    // motionCurvature = _factorCurvatureDifference * (diffC1 + diffC2);
    if (_safeTest)
      _vertex[i] = Vec2r(_vertex[i] + (motionNormal + motionCurvature) * _normal[i]);
    Vec2r v1(_vertex[i - 1] - _vertex[i]);
    Vec2r v2(_vertex[i + 1] - _vertex[i]);
    real d1 = v1.norm();
    real d2 = v2.norm();
    _vertex[i] = Vec2r(
        _vertex[i] + _factorPoint * edgeStopping(d2, _anisoPoint) * (_vertex[i - 1] - _vertex[i]) +
        _factorPoint * edgeStopping(d1, _anisoPoint) * (_vertex[i + 1] - _vertex[i]));
  }

  if (_isClosedCurve) {
    real motionNormal = _factorCurvature * _curvature[0] *
                        edgeStopping(_curvature[0], _anisoNormal);

    real diffC1 = _curvature[0] - _curvature[_nbVertices - 2];
    real diffC2 = _curvature[0] - _curvature[1];
    real motionCurvature = edgeStopping(diffC1, _anisoCurvature) * diffC1 +
                           edgeStopping(diffC2, _anisoCurvature) *
                               diffC2;  //_factorCurvatureDifference;
    motionCurvature *= _factorCurvatureDifference;
    // motionCurvature = _factorCurvatureDifference * (diffC1 + diffC2);
    _vertex[0] = Vec2r(_vertex[0] + (motionNormal + motionCurvature) * _normal[0]);
    _vertex[_nbVertices - 1] = _vertex[0];
  }
}
コード例 #5
0
ファイル: surf3.cpp プロジェクト: wenderen/btp
void surf3::buildSurface(const fluid3 *fluidSolver, const levelset3 *fluid, const levelset3 *solid, bool enclose ) {
	tick(); dump(">>> Building surfaces started...\n");
	if( fluidSolver->getBCCMesh() ) {
		surf = &bccsurf;
		bccsurf.setBCC(*fluidSolver->getBCCMesh());
		bccsurf.buildSurface(vertices,normals,faces,fluid,solid,enclose);
	} else if( fluidSolver->getMesh() ) {
		surf = &meshsurf;
		mesh = *fluidSolver->getMesh();
		meshsurf.setReference(&mesh);
		meshsurf.buildSurface(vertices,normals,faces,fluid,solid,enclose);
	} else {
		surf = &cellsurf;
		cellsurf.buildSurface(vertices,normals,faces,fluid,solid,enclose);
	}
	
	// Build ANN
	tick(); dump("Building ANN structure for mesh vertices...");
	ann.sort(vertices);
	dump("Done. Took %s.\n", stock("surf_ANN"));
	
	// Compute vertices to face info
	v2f.clear();
	v2f.resize(vertices.size());
	for( uint n=0; n<faces.size(); n++ ) {
		for( uint m=0; m<DIM; m++ ) {
			v2f[faces[n][m]].push_back(n);
		}
	}
	
	dump("<<< Done. Took %s.\n",stock("surf_build"));
	
	tick(); dump("Computing mesh-based curvature (%d vertices %d faces)...", vertices.size(), faces.size());
	computeCurvature(solid);
	dump("Done. Took %s.\n", stock("surf_curvature"));
	
	// Write some info
	writeNumber("surf_vertex_num", vertices.size());
	writeNumber("surf_face_num", faces.size());
}
コード例 #6
0
ファイル: main.cpp プロジェクト: yixin26/Mesh-Segmentation
void readTrimesh(MeshSegment*& meshSeg, const char* fileName)
{
	std::vector<AML::double3> points;
	std::vector<std::vector<unsigned> > faces;

	TriMesh *triMesh = TriMesh::read(fileName);

	int vNum = triMesh->vertices.size();
	points.reserve(vNum);
	for (int i = 0; i < vNum; i++)
	{
		points.push_back(AML::double3(triMesh->vertices[i][0], triMesh->vertices[i][1], triMesh->vertices[i][2]));
	}
	int fNum = triMesh->faces.size();
	faces.reserve(fNum);
	std::vector<unsigned> tf(3);
	for (int i = 0; i < fNum; i++)
	{
		tf[0] = triMesh->faces[i][0]; tf[1] = triMesh->faces[i][1]; tf[2] = triMesh->faces[i][2];
		faces.push_back(tf);
	}

	rescaleMesh(points);
	for (int i = 0; i < vNum; i++)
	{
		for (int j = 0; j < 3; j++)
		{
			triMesh->vertices[i][j] = points[i][j];
		}
	}

	triMesh->need_normals();

	MyMesh* tmesh = new MyMesh;
	tmesh->initialize(points, faces);
	*(meshSeg->getMyMesh()) = tmesh;

	computeCurvature(triMesh, meshSeg->getMyMesh());
}
コード例 #7
0
void Surface_DifferentialProperties_Plugin::attributeModified(unsigned int orbit, QString nameAttr)
{
	if(orbit == VERTEX)
	{
		MapHandlerGen* map = static_cast<MapHandlerGen*>(QObject::sender());
		if(computeNormalLastParameters.contains(map->getName()))
		{
			ComputeNormalParameters& params = computeNormalLastParameters[map->getName()];
			if(params.autoUpdate && params.positionName == nameAttr)
				computeNormal(map->getName(), params.positionName, params.normalName, true);
		}
		if(computeCurvatureLastParameters.contains(map->getName()))
		{
			ComputeCurvatureParameters& params = computeCurvatureLastParameters[map->getName()];
			if(params.autoUpdate && (params.positionName == nameAttr || params.normalName == nameAttr))
				computeCurvature(
					map->getName(),
					params.positionName, params.normalName,
					params.KmaxName, params.kmaxName, params.KminName, params.kminName, params.KnormalName,
					true
				);
		}
	}
}
コード例 #8
0
ファイル: mricurv.c プロジェクト: guo2004131/freesurfer
static float computeLocalCurvature(int *ref_tab,int connectivity)
{
    int number_of_vertices;
    VerTex vertex[MAX_VERTICES];
    int number_of_faces,reference,refdst;
    FaCe face[MAX_FACES];
    int kept_vertex_table[6],kvt_nbr,save_vertex_indice[30];
    int *Case,vt[12],vind[12],fnbr,n,m,l;
    float x,y,z,xtmp[6],ytmp[6],ztmp[6],curvature[6],maxcurv;

    number_of_vertices=0;
    number_of_faces=0;
    memset(save_vertex_indice,-1,sizeof(int)*30);

    kvt_nbr=0;
    //first deal with the cube #1
    reference=ref_tab[0];
    if (reference&&reference!=255)
    {
        //position in the cube 3*3*3
        x=y=z=0;

        switch (connectivity)
        {
        case 1:
            Case=MC6p[reference];
            break;
        case 2:
            Case=MC18[reference];
            break;
        case 3:
            Case=MC6[reference];
            break;
        case 4:
            Case=MC26[reference];
            break;
        default:
            Case=MC6p[reference];
            break;
        }
        //number of faces
        fnbr=0;
        while (Case[3*fnbr]>=0)
            fnbr++;
        memset(vt,0,12*sizeof(int));
        memset(vind,-1,sizeof(int));
        for (n=0; n<3*fnbr; n++)
            vt[Case[n]]++;
        //allocate all vertex
        for (n=0; n<12; n++)
            if (vt[n])
            {
                vertex[number_of_vertices].x=x+fx[n];
                vertex[number_of_vertices].y=y+fy[n];
                vertex[number_of_vertices].z=z+fz[n];
                vertex[number_of_vertices].fnum=0;
                vind[n]=number_of_vertices++;
            }
        //save kept vertices
        if (vt[7]) kept_vertex_table[kvt_nbr++]=vind[7];
        if (vt[10]) kept_vertex_table[kvt_nbr++]=vind[10];
        if (vt[11]) kept_vertex_table[kvt_nbr++]=vind[11];
        //save vertices
        if (vt[2]) save_vertex_indice[0]=vind[2];
        if (vt[3]) save_vertex_indice[10]=vind[3];
        if (vt[5]) save_vertex_indice[20]=vind[5];
        if (vt[6]) save_vertex_indice[22]=vind[6];
        if (vt[7]) save_vertex_indice[24]=vind[7];
        if (vt[8]) save_vertex_indice[2]=vind[8];
        if (vt[9]) save_vertex_indice[12]=vind[9];
        if (vt[10]) save_vertex_indice[4]=vind[10];
        if (vt[11]) save_vertex_indice[14]=vind[11];
        //allocate faces
        for (n=0; n<fnbr; n++)
        {
            face[number_of_faces].v[0]=vind[Case[3*n]];
            face[number_of_faces].v[1]=vind[Case[3*n+1]];
            face[number_of_faces++].v[2]=vind[Case[3*n+2]];
        }
    }

    //cube #2
    reference=(ref_tab[1]);
    if (reference&&reference!=255)
    {
        //position in the cube 3*3*3
        x=1;
        y=z=0;

        switch (connectivity)
        {
        case 1:
            Case=MC6p[reference];
            break;
        case 2:
            Case=MC18[reference];
            break;
        case 3:
            Case=MC6[reference];
            break;
        case 4:
            Case=MC26[reference];
            break;
        default:
            Case=MC6p[reference];
            break;
        }
        //number of faces
        fnbr=0;
        while (Case[3*fnbr]>=0)
            fnbr++;
        memset(vt,0,12*sizeof(int));
        memset(vind,-1,sizeof(int));
        for (n=0; n<3*fnbr; n++)
            vt[Case[n]]++;

        //find and allocate vertex
        for (n=0; n<12; n++)
            if (vt[n])
            {
                if (n==1)
                {
                    vind[n]=save_vertex_indice[10];
                    continue;
                }
                if (n==4)
                {
                    vind[n]=save_vertex_indice[20];
                    continue;
                }
                if (n==6)
                {
                    vind[n]=save_vertex_indice[24];
                    continue;
                }
                if (n==9)
                {
                    vind[n]=save_vertex_indice[14];
                    continue;
                }

                vertex[number_of_vertices].x=x+fx[n];
                vertex[number_of_vertices].y=y+fy[n];
                vertex[number_of_vertices].z=z+fz[n];
                vertex[number_of_vertices].fnum=0;
                vind[n]=number_of_vertices++;
            }
        //save kept vertices
        if (vt[10]) kept_vertex_table[kvt_nbr++]=vind[10];
        //save vertices
        if (vt[2]) save_vertex_indice[1]=vind[2];
        if (vt[7]) save_vertex_indice[26]=vind[7];
        if (vt[8]) save_vertex_indice[3]=vind[8];
        if (vt[10]) save_vertex_indice[5]=vind[10];
        if (vt[11]) save_vertex_indice[16]=vind[11];
        //allocate faces
        for (n=0; n<fnbr; n++)
        {
            face[number_of_faces].v[0]=vind[Case[3*n]];
            face[number_of_faces].v[1]=vind[Case[3*n+1]];
            face[number_of_faces++].v[2]=vind[Case[3*n+2]];
        }
    }

    //cube #3
    reference=(ref_tab[2]);
    if (reference&&reference!=255)
    {
        //position in the cube 3*3*3
        x=0;
        y=1;
        z=0;

        switch (connectivity)
        {
        case 1:
            Case=MC6p[reference];
            break;
        case 2:
            Case=MC18[reference];
            break;
        case 3:
            Case=MC6[reference];
            break;
        case 4:
            Case=MC26[reference];
            break;
        default:
            Case=MC6p[reference];
            break;
        }
        //number of faces
        fnbr=0;
        while (Case[3*fnbr]>=0)
            fnbr++;
        memset(vt,0,12*sizeof(int));
        memset(vind,-1,sizeof(int));
        for (n=0; n<3*fnbr; n++)
            vt[Case[n]]++;

        //find and allocate vertex
        for (n=0; n<12; n++)
            if (vt[n])
            {
                if (n==0)
                {
                    vind[n]=save_vertex_indice[0];
                    continue;
                }
                if (n==4)
                {
                    vind[n]=save_vertex_indice[22];
                    continue;
                }
                if (n==5)
                {
                    vind[n]=save_vertex_indice[24];
                    continue;
                }
                if (n==8)
                {
                    vind[n]=save_vertex_indice[4];
                    continue;
                }

                vertex[number_of_vertices].x=x+fx[n];
                vertex[number_of_vertices].y=y+fy[n];
                vertex[number_of_vertices].z=z+fz[n];
                vertex[number_of_vertices].fnum=0;
                vind[n]=number_of_vertices++;
            }
        //save kept vertices
        if (vt[11]) kept_vertex_table[kvt_nbr++]=vind[11];
        //save vertices
        if (vt[3]) save_vertex_indice[11]=vind[3];
        if (vt[7]) save_vertex_indice[28]=vind[7];
        if (vt[9]) save_vertex_indice[13]=vind[9];
        if (vt[10]) save_vertex_indice[6]=vind[10];
        if (vt[11]) save_vertex_indice[15]=vind[11];
        //allocate faces
        for (n=0; n<fnbr; n++)
        {
            face[number_of_faces].v[0]=vind[Case[3*n]];
            face[number_of_faces].v[1]=vind[Case[3*n+1]];
            face[number_of_faces++].v[2]=vind[Case[3*n+2]];
        }
    }

    //cube #4
    reference=(ref_tab[3]);
    if (reference&&reference!=255)
    {
        //position in the cube 3*3*3
        x=1;
        y=1;
        z=0;

        switch (connectivity)
        {
        case 1:
            Case=MC6p[reference];
            break;
        case 2:
            Case=MC18[reference];
            break;
        case 3:
            Case=MC6[reference];
            break;
        case 4:
            Case=MC26[reference];
            break;
        default:
            Case=MC6p[reference];
            break;
        }
        //number of faces
        fnbr=0;
        while (Case[3*fnbr]>=0)
            fnbr++;
        memset(vt,0,12*sizeof(int));
        memset(vind,-1,sizeof(int));
        for (n=0; n<3*fnbr; n++)
            vt[Case[n]]++;

        //find and allocate vertex
        for (n=0; n<12; n++)
            if (vt[n])
            {
                if (n==0)
                {
                    vind[n]=save_vertex_indice[1];
                    continue;
                }
                if (n==1)
                {
                    vind[n]=save_vertex_indice[11];
                    continue;
                }
                if (n==4)
                {
                    vind[n]=save_vertex_indice[24];
                    continue;
                }
                if (n==5)
                {
                    vind[n]=save_vertex_indice[26];
                    continue;
                }
                if (n==6)
                {
                    vind[n]=save_vertex_indice[28];
                    continue;
                }
                if (n==8)
                {
                    vind[n]=save_vertex_indice[5];
                    continue;
                }
                if (n==9)
                {
                    vind[n]=save_vertex_indice[15];
                    continue;
                }

                vertex[number_of_vertices].x=x+fx[n];
                vertex[number_of_vertices].y=y+fy[n];
                vertex[number_of_vertices].z=z+fz[n];
                vertex[number_of_vertices].fnum=0;
                vind[n]=number_of_vertices++;
            }
        //save kept vertices
        //none
        //save vertices
        if (vt[10]) save_vertex_indice[7]=vind[10];
        if (vt[11]) save_vertex_indice[17]=vind[11];
        //allocate faces
        for (n=0; n<fnbr; n++)
        {
            face[number_of_faces].v[0]=vind[Case[3*n]];
            face[number_of_faces].v[1]=vind[Case[3*n+1]];
            face[number_of_faces++].v[2]=vind[Case[3*n+2]];
        }
    }

    //cube #5
    reference=(ref_tab[4]);
    if (reference&&reference!=255)
    {
        //position in the cube 3*3*3
        x=0;
        y=0;
        z=1;

        switch (connectivity)
        {
        case 1:
            Case=MC6p[reference];
            break;
        case 2:
            Case=MC18[reference];
            break;
        case 3:
            Case=MC6[reference];
            break;
        case 4:
            Case=MC26[reference];
            break;
        default:
            Case=MC6p[reference];
            break;
        }
        //number of faces
        fnbr=0;
        while (Case[3*fnbr]>=0)
            fnbr++;
        memset(vt,0,12*sizeof(int));
        memset(vind,-1,sizeof(int));
        for (n=0; n<3*fnbr; n++)
            vt[Case[n]]++;

        //find and allocate vertex
        for (n=0; n<12; n++)
            if (vt[n])
            {
                if (n==0)
                {
                    vind[n]=save_vertex_indice[2];
                    continue;
                }
                if (n==1)
                {
                    vind[n]=save_vertex_indice[12];
                    continue;
                }
                if (n==2)
                {
                    vind[n]=save_vertex_indice[4];
                    continue;
                }
                if (n==3)
                {
                    vind[n]=save_vertex_indice[14];
                    continue;
                }

                vertex[number_of_vertices].x=x+fx[n];
                vertex[number_of_vertices].y=y+fy[n];
                vertex[number_of_vertices].z=z+fz[n];
                vertex[number_of_vertices].fnum=0;
                vind[n]=number_of_vertices++;
            }
        //save kept vertices
        if (vt[7]) kept_vertex_table[kvt_nbr++]=vind[7];
        //save vertices
        if (vt[5]) save_vertex_indice[21]=vind[5];
        if (vt[6]) save_vertex_indice[23]=vind[6];
        if (vt[7]) save_vertex_indice[25]=vind[7];
        if (vt[10]) save_vertex_indice[8]=vind[10];
        if (vt[11]) save_vertex_indice[18]=vind[11];
        //allocate faces
        for (n=0; n<fnbr; n++)
        {
            face[number_of_faces].v[0]=vind[Case[3*n]];
            face[number_of_faces].v[1]=vind[Case[3*n+1]];
            face[number_of_faces++].v[2]=vind[Case[3*n+2]];
        }
    }

    //cube #6
    reference=(ref_tab[5]);
    if (reference&&reference!=255)
    {
        //position in the cube 3*3*3
        x=1;
        y=0;
        z=1;

        switch (connectivity)
        {
        case 1:
            Case=MC6p[reference];
            break;
        case 2:
            Case=MC18[reference];
            break;
        case 3:
            Case=MC6[reference];
            break;
        case 4:
            Case=MC26[reference];
            break;
        default:
            Case=MC6p[reference];
            break;
        }
        //number of faces
        fnbr=0;
        while (Case[3*fnbr]>=0)
            fnbr++;
        memset(vt,0,12*sizeof(int));
        memset(vind,-1,sizeof(int));
        for (n=0; n<3*fnbr; n++)
            vt[Case[n]]++;

        //find and allocate vertex
        for (n=0; n<12; n++)
            if (vt[n])
            {
                if (n==0)
                {
                    vind[n]=save_vertex_indice[3];
                    continue;
                }
                if (n==1)
                {
                    vind[n]=save_vertex_indice[14];
                    continue;
                }
                if (n==2)
                {
                    vind[n]=save_vertex_indice[5];
                    continue;
                }
                if (n==3)
                {
                    vind[n]=save_vertex_indice[16];
                    continue;
                }
                if (n==4)
                {
                    vind[n]=save_vertex_indice[21];
                    continue;
                }
                if (n==6)
                {
                    vind[n]=save_vertex_indice[25];
                    continue;
                }
                if (n==9)
                {
                    vind[n]=save_vertex_indice[18];
                    continue;
                }

                vertex[number_of_vertices].x=x+fx[n];
                vertex[number_of_vertices].y=y+fy[n];
                vertex[number_of_vertices].z=z+fz[n];
                vertex[number_of_vertices].fnum=0;
                vind[n]=number_of_vertices++;
            }
        //save kept vertices
        //none
        //save vertices
        if (vt[7]) save_vertex_indice[27]=vind[7];
        if (vt[10]) save_vertex_indice[9]=vind[10];
        //allocate faces
        for (n=0; n<fnbr; n++)
        {
            face[number_of_faces].v[0]=vind[Case[3*n]];
            face[number_of_faces].v[1]=vind[Case[3*n+1]];
            face[number_of_faces++].v[2]=vind[Case[3*n+2]];
        }
    }

    //cube #7
    reference=(ref_tab[6]);
    if (reference&&reference!=255)
    {
        //position in the cube 3*3*3
        x=0;
        y=1;
        z=1;

        switch (connectivity)
        {
        case 1:
            Case=MC6p[reference];
            break;
        case 2:
            Case=MC18[reference];
            break;
        case 3:
            Case=MC6[reference];
            break;
        case 4:
            Case=MC26[reference];
            break;
        default:
            Case=MC6p[reference];
            break;
        }
        //number of faces
        fnbr=0;
        while (Case[3*fnbr]>=0)
            fnbr++;
        memset(vt,0,12*sizeof(int));
        memset(vind,-1,sizeof(int));
        for (n=0; n<3*fnbr; n++)
            vt[Case[n]]++;

        //find and allocate vertex
        for (n=0; n<12; n++)
            if (vt[n])
            {
                if (n==0)
                {
                    vind[n]=save_vertex_indice[4];
                    continue;
                }
                if (n==1)
                {
                    vind[n]=save_vertex_indice[13];
                    continue;
                }
                if (n==2)
                {
                    vind[n]=save_vertex_indice[6];
                    continue;
                }
                if (n==3)
                {
                    vind[n]=save_vertex_indice[15];
                    continue;
                }
                if (n==4)
                {
                    vind[n]=save_vertex_indice[23];
                    continue;
                }
                if (n==5)
                {
                    vind[n]=save_vertex_indice[25];
                    continue;
                }
                if (n==8)
                {
                    vind[n]=save_vertex_indice[8];
                    continue;
                }

                vertex[number_of_vertices].x=x+fx[n];
                vertex[number_of_vertices].y=y+fy[n];
                vertex[number_of_vertices].z=z+fz[n];
                vertex[number_of_vertices].fnum=0;
                vind[n]=number_of_vertices++;
            }
        //save kept vertices
        //none
        //save vertices
        if (vt[7]) save_vertex_indice[29]=vind[7];
        if (vt[11]) save_vertex_indice[19]=vind[11];
        //allocate faces
        for (n=0; n<fnbr; n++)
        {
            face[number_of_faces].v[0]=vind[Case[3*n]];
            face[number_of_faces].v[1]=vind[Case[3*n+1]];
            face[number_of_faces++].v[2]=vind[Case[3*n+2]];
        }
    }

    //cube #8
    reference=(ref_tab[7]);
    if (reference&&reference!=255)
    {
        //position in the cube 3*3*3
        x=1;
        y=1;
        z=1;

        switch (connectivity)
        {
        case 1:
            Case=MC6p[reference];
            break;
        case 2:
            Case=MC18[reference];
            break;
        case 3:
            Case=MC6[reference];
            break;
        case 4:
            Case=MC26[reference];
            break;
        default:
            Case=MC6p[reference];
            break;
        }
        //number of faces
        fnbr=0;
        while (Case[3*fnbr]>=0)
            fnbr++;

        memset(vt,0,12*sizeof(int));
        memset(vind,-1,sizeof(int));
        for (n=0; n<3*fnbr; n++)
            vt[Case[n]]++;

        //find and allocate vertex
        for (n=0; n<12; n++)
            if (vt[n])
            {
                if (n==0)
                {
                    vind[n]=save_vertex_indice[5];
                    continue;
                }
                if (n==1)
                {
                    vind[n]=save_vertex_indice[15];
                    continue;
                }
                if (n==2)
                {
                    vind[n]=save_vertex_indice[7];
                    continue;
                }
                if (n==3)
                {
                    vind[n]=save_vertex_indice[17];
                    continue;
                }
                if (n==4)
                {
                    vind[n]=save_vertex_indice[25];
                    continue;
                }
                if (n==5)
                {
                    vind[n]=save_vertex_indice[27];
                    continue;
                }
                if (n==6)
                {
                    vind[n]=save_vertex_indice[29];
                    continue;
                }
                if (n==8)
                {
                    vind[n]=save_vertex_indice[9];
                    continue;
                }
                if (n==9)
                {
                    vind[n]=save_vertex_indice[19];
                    continue;
                }

                vertex[number_of_vertices].x=x+fx[n];
                vertex[number_of_vertices].y=y+fy[n];
                vertex[number_of_vertices].z=z+fz[n];
                vertex[number_of_vertices].fnum=0;
                vind[n]=number_of_vertices++;
            }
        //save kept vertices
        //none
        //save vertices
        //none
        //allocate faces
        for (n=0; n<fnbr; n++)
        {
            face[number_of_faces].v[0]=vind[Case[3*n]];
            face[number_of_faces].v[1]=vind[Case[3*n+1]];
            face[number_of_faces++].v[2]=vind[Case[3*n+2]];
        }
    }
    if (kvt_nbr==0)
        return 0;

    //now allocate face neighbors
    for (n=0; n<number_of_faces; n++)
    {
        for (m=0; m<3; m++)
            vertex[face[n].v[m]].f[vertex[face[n].v[m]].fnum++]=n;
    }

    //now allocate vertex neighbors for the kept vertices only
    for (m=0; m<number_of_vertices; m++)
        vertex[m].vnum=0;
    for (n=0; n<kvt_nbr; n++)
    {
        for (m=0; m<number_of_vertices; m++)
            vertex[m].marked=0;

        reference=kept_vertex_table[n];
        vertex[reference].marked=1;
        for (m=0; m<vertex[reference].fnum; m++)
            for (l=0; l<3; l++)
            {
                refdst=face[vertex[reference].f[m]].v[l];
                if (vertex[refdst].marked==0)
                {
                    vertex[reference].v[vertex[reference].vnum++]=refdst;
                    vertex[refdst].marked=1;
                }
            }
    }

#if 1
    //now smooth the surface (only the kept vertices)
    l=NITERSMOOTH;
    while (l)
    {
        for (n=0; n<kvt_nbr; n++)
        {
            reference=kept_vertex_table[n];
            xtmp[n]=ytmp[n]=ztmp[n]=0;
            for (m=0; m<vertex[reference].vnum; m++)
            {
                xtmp[n]+=vertex[vertex[reference].v[m]].x;
                ytmp[n]+=vertex[vertex[reference].v[m]].y;
                ztmp[n]+=vertex[vertex[reference].v[m]].z;
            }
            xtmp[n]/=(float)vertex[reference].vnum;
            ytmp[n]/=(float)vertex[reference].vnum;
            ztmp[n]/=(float)vertex[reference].vnum;
        }
        //update
        for (n=0; n<kvt_nbr; n++)
        {
            reference=kept_vertex_table[n];
            vertex[reference].x=vertex[reference].x+SMOOTH_MMT*(xtmp[n]-vertex[reference].x);
            vertex[reference].y=vertex[reference].y+SMOOTH_MMT*(ytmp[n]-vertex[reference].y);
            vertex[reference].z=vertex[reference].z+SMOOTH_MMT*(ztmp[n]-vertex[reference].z);
        }
        l--;
    }
#endif

#if 0
    fprintf(stderr,"\nWE HAVE:");
    fprintf(stderr," %d vertices and %d faces ",number_of_vertices,number_of_faces);
    for (n=0; n<number_of_faces; n++)
    {
        fprintf(stderr,"\nface %d (%d,%d,%d):",n,face[n].v[0],
                face[n].v[1],face[n].v[2]);
    }

    for (n=0; n<number_of_vertices; n++)
    {
        fprintf(stderr,"\nvertex %d (%3.2f,%3.2f,%3.2f) -> %d,%d: ",n,vertex[n].x,
                vertex[n].y,vertex[n].z,vertex[n].fnum,vertex[n].vnum);
        for (m=0; m<vertex[n].fnum; m++)
            fprintf(stderr,"f#%d ",vertex[n].f[m]);
        for (m=0; m<vertex[n].vnum; m++)
            fprintf(stderr,"\n     ->v%d (%3.2f,%3.2f,%3.2f)",vertex[n].v[m],vertex[vertex[n].v[m]].x
                    ,vertex[vertex[n].v[m]].y,vertex[vertex[n].v[m]].z);
    }
    fprintf(stderr,"\n %d: ",kvt_nbr);
    for (n=0; n<kvt_nbr; n++)
        fprintf(stderr," %d ",kept_vertex_table[n]);
    fprintf(stderr,"\n");
#endif


    //now compute the n(<6) curvatures
    computeFaceProperties(vertex,number_of_vertices,face,number_of_faces);
#if 0
    for (n=0; n<number_of_faces; n++)
    {
        fprintf(stderr,"\nface #%d, %f %f, %f, %f ",n,face[n].area,face[n].nx,
                face[n].ny,face[n].nz);
        if (isnan(face[n].nx)||isnan(face[n].ny)||isnan(face[n].nz)||isnan(face[n].area))
            pause();
    }
#endif

    computeCurvature(vertex,number_of_vertices,face,number_of_faces,kept_vertex_table,kvt_nbr,curvature);

    if (MODE==AVERAGE_CURV)
    {
        maxcurv=0;
        for (n=0; n<kvt_nbr; n++)
            maxcurv+=curvature[n];
        maxcurv/=(float)kvt_nbr;
    }
    else
    {
        maxcurv=0;
        m=0;
        for (n=0; n<kvt_nbr; n++)
            if (fabs(curvature[n])>maxcurv)
            {
                maxcurv=fabs(curvature[n]);
                m=n;
            }
    }
    return curvature[m];
}