surface.cpp 10.2 KB
Newer Older
Thomas Pitiot 's avatar
Thomas Pitiot committed
1 2 3
#include "simulator.h"

//initialisation Surface
4 5
Surface::Surface(Simulator* sim,VEC3 offset):
    mapOperator(surfaceMap)
Thomas Pitiot 's avatar
Thomas Pitiot committed
6
{
7

Thomas Pitiot 's avatar
Thomas Pitiot committed
8 9 10
    r=1.0f;
    g=0.627f;
    b=0.0f;
Thomas Pitiot 's avatar
Thomas Pitiot committed
11 12 13
    sim_=sim;
    width=1.0;
    nbVertices=0;
Thomas Pitiot 's avatar
Thomas Pitiot committed
14
    nbTriangles=0;
Thomas Pitiot 's avatar
Thomas Pitiot committed
15 16
    distanceColorationMaxi=0.01f;
    distanceColorationMini=2.0f;
Thomas Pitiot 's avatar
Thomas Pitiot committed
17

pitiot's avatar
pitiot committed
18 19
    surfaceMap.initImplicitProperties();
    positionSurface = surfaceMap.addAttribute<VEC3, VERTEX, SURFACE>("positionSurface");
20 21 22
    initOperators(LERP);
    initPlane();

pitiot's avatar
pitiot committed
23
    indexParticule = surfaceMap.addAttribute<int, VERTEX, SURFACE>("indexParticule");
Thomas Pitiot 's avatar
Thomas Pitiot committed
24 25
    indexTriangle= surfaceMap.addAttribute<int, FACE, SURFACE>("indexTriangle");
    faceColor=surfaceMap.addAttribute<VEC3, FACE, SURFACE>("faceColor");
pitiot's avatar
pitiot committed
26

Thomas Pitiot 's avatar
Thomas Pitiot committed
27
    index_surface=sim->surfaces.size();
pitiot's avatar
pitiot committed
28 29


Thomas Pitiot 's avatar
Thomas Pitiot committed
30 31


pitiot's avatar
pitiot committed
32
    // initialisation des particules et des attributs de sommet
Thomas Pitiot 's avatar
Thomas Pitiot committed
33 34 35 36 37 38 39 40
    TraversorV<SURFACE> tv(surfaceMap);
    for(Dart d = tv.begin() ; d != tv.end() ; d = tv.next())
    {
        positionSurface[d]+=offset;
        indexParticule[d]=nbVertices;
        parts_.push_back(new CGoGN::Algo::Volume::MovingObjects::ParticleCell3D<PFP>(sim_->envMap_.map, sim_->envMap_.getBelongingCell(positionSurface[d]), positionSurface[d] , sim_->envMap_.position));
        nbVertices ++;
    }
pitiot's avatar
pitiot committed
41
    // initialisation tableaux de vecteurs qui vont stocker les belonging cells
Thomas Pitiot 's avatar
Thomas Pitiot committed
42 43
    TraversorE<SURFACE> tF2(surfaceMap);
    for(Dart d = tF2.begin() ; d != tF2.end() ; d = tF2.next())
pitiot's avatar
pitiot committed
44
    {
Thomas Pitiot 's avatar
Thomas Pitiot committed
45
        nbTriangles ++;
pitiot's avatar
pitiot committed
46
    }
Thomas Pitiot 's avatar
Thomas Pitiot committed
47

pitiot's avatar
pitiot committed
48

Thomas Pitiot 's avatar
Thomas Pitiot committed
49

pitiot's avatar
pitiot committed
50
    // initialisation des segments et des attributs d'edge
Thomas Pitiot 's avatar
Thomas Pitiot committed
51
    TraversorF<SURFACE> tE(surfaceMap);
Thomas Pitiot 's avatar
Thomas Pitiot committed
52 53
    for(Dart d = tE.begin() ; d != tE.end() ; d = tE.next())
    {
Thomas Pitiot 's avatar
Thomas Pitiot committed
54
        faceColor[d]=VEC3(r,g,b);
Thomas Pitiot 's avatar
Thomas Pitiot committed
55
#ifdef DEBUG_affichage
Thomas Pitiot 's avatar
Thomas Pitiot committed
56 57
        CGoGNout<<" init Segment :"<< nbTriangles ;
        CGoGNout<<" || nb_segments  :"<< triangles_.size() <<CGoGNendl;
Thomas Pitiot 's avatar
Thomas Pitiot committed
58
#endif
Thomas Pitiot 's avatar
Thomas Pitiot committed
59 60 61
        indexTriangle[d]=triangles_.size();

        VEC3 p1=positionSurface[d],p2=positionSurface[surfaceMap.phi1(d)],p3=positionSurface[surfaceMap.phi1(surfaceMap.phi1(d))];
Thomas Pitiot 's avatar
Thomas Pitiot committed
62
        Triangle* o = new Triangle(p1,p2,p3,this,d,r,g,b,indexTriangle[d]);
Thomas Pitiot 's avatar
Thomas Pitiot committed
63 64 65
        triangles_.push_back(o);

        sim_->envMap_.FirstRegistrationTriangle(o);
Thomas Pitiot 's avatar
Thomas Pitiot committed
66 67 68

    }

pitiot's avatar
pitiot committed
69 70 71


    sim_->surfaces.push_back(this);
Thomas Pitiot 's avatar
Thomas Pitiot committed
72

Thomas Pitiot 's avatar
Thomas Pitiot committed
73 74 75 76
//    for(Dart d = tE.begin() ; d != tE.end() ; d = tE.next())
//    {
//        CGoGNout<<" color face :"<<d<<" || : "<<faceColor[d]<<CGoGNendl ;
//    }
Thomas Pitiot 's avatar
Thomas Pitiot committed
77

Thomas Pitiot 's avatar
Thomas Pitiot committed
78 79 80 81
//    for(Dart d = tv.begin() ; d != tv.end() ; d = tv.next())
//    {
//        CGoGNout<<" position dart :"<<d<<" || : "<<positionSurface[d]<<CGoGNendl ;
//    }
Thomas Pitiot 's avatar
Thomas Pitiot committed
82 83 84 85 86
}

void Surface::initGL()
{
    //rendering
Thomas Pitiot 's avatar
Thomas Pitiot committed
87
    m_render_map = new Algo::Render::GL2::MapRender();
Thomas Pitiot 's avatar
Thomas Pitiot committed
88 89
    m_positionVBO = new Utils::VBO();
    m_colorVBO= new Utils::VBO();
90 91
    m_render = new Algo::Render::GL2::ColorPerFaceRender();
//
Thomas Pitiot 's avatar
Thomas Pitiot committed
92

Thomas Pitiot 's avatar
Thomas Pitiot committed
93 94 95
    m_shader= new Utils::ShaderColorPerVertex();
    m_shader->setAttributeColor(m_colorVBO);
    m_shader->setAttributePosition(m_positionVBO);
Thomas Pitiot 's avatar
Thomas Pitiot committed
96 97 98
    m_simpleColorShader = new Utils::ShaderSimpleColor();
    m_simpleColorShader->setAttributePosition(m_positionVBO);
    m_simpleColorShader->setColor(Geom::Vec4f(0.,1.,0.,0.));
Thomas Pitiot 's avatar
Thomas Pitiot committed
99

100
    m_render->updateVBO<PFPSurface,FACE>(*m_positionVBO,*m_colorVBO,surfaceMap,positionSurface,faceColor);
Thomas Pitiot 's avatar
Thomas Pitiot committed
101

Thomas Pitiot 's avatar
Thomas Pitiot committed
102
    m_render_map->initPrimitives<PFPSurface>(surfaceMap, Algo::Render::GL2::LINES) ;
103
//    m_render->initPrimitives<PFPSurface>(surfaceMap, Algo::Render::GL2::TRIANGLES) ;
Thomas Pitiot 's avatar
Thomas Pitiot committed
104 105 106 107 108
}

void Surface::draw()
{

Thomas Pitiot 's avatar
Thomas Pitiot committed
109
    m_positionVBO->updateData(positionSurface) ;
110
        glLineWidth(1.0f);
Thomas Pitiot 's avatar
Thomas Pitiot committed
111
    m_render_map->draw(m_simpleColorShader,Algo::Render::GL2::LINES);
112
//    m_colorVBO->updateData(faceColor);
Thomas Pitiot 's avatar
Thomas Pitiot committed
113
//    colorRender->updateVBO<PFPSurface,FACE>(m_positionVBO,m_colorVBO,surfaceMap,positionSurface,colorRender);
114

115
    m_render->updateVBO<PFPSurface,FACE>(*m_positionVBO,*m_colorVBO,surfaceMap,positionSurface,faceColor);
Thomas Pitiot 's avatar
Thomas Pitiot committed
116 117


Thomas Pitiot 's avatar
Thomas Pitiot committed
118
    m_simpleColorShader->setColor(Geom::Vec4f(0.0,0.0,0.0,0.));
Thomas Pitiot 's avatar
Thomas Pitiot committed
119

120
    m_render->draw(m_shader);
Thomas Pitiot 's avatar
Thomas Pitiot committed
121 122


Thomas Pitiot 's avatar
Thomas Pitiot committed
123

Thomas Pitiot 's avatar
Thomas Pitiot committed
124 125 126 127
}

void Surface::initPlane()
{
pitiot's avatar
pitiot committed
128
    CGoGNout<<" initialisation d'un plan"<< CGoGNendl ;
Thomas Pitiot 's avatar
Thomas Pitiot committed
129 130


131 132

    Algo::Surface::Tilings::Triangular::Grid<PFPSurface> prim(surfaceMap, 1,1) ;
Thomas Pitiot 's avatar
up2  
Thomas Pitiot committed
133

134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157
    prim.embedIntoGrid(positionSurface,1.0f,1.0f, 0.0f) ;


    TraversorV<SURFACE> tv(surfaceMap);
    for(Dart d = tv.begin() ; d != tv.end() ; d = tv.next())
    {
        positionSurface[d]*=4;

    }




    TraversorF<SURFACE> tF(surfaceMap);
    for(Dart d = tF.begin() ; d != tF.end() ; d = tF.next())
    {
        REAL dist = faceMaxdistance(d);
        if(dist < sim_->envMap_.maxCellRay)
        {
            sim_->envMap_.maxCellRay=dist;
        }
    }


Thomas Pitiot 's avatar
up2  
Thomas Pitiot committed
158 159 160 161 162 163
//    bool test = false;
//    while (!test)
//    {
//       test = subdiveMap();
////        CGoGNout<<"subdiv effectuée ? " <<!test<<CGoGNendl;
//    }
164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183

}

bool Surface::subdiveMap()
{
    bool res = true;
    std::vector<Dart> toCheck;
    TraversorF<SURFACE> tF(surfaceMap);
    surfaceMap.setCurrentLevel(surfaceMap.getMaxLevel()) ;
    for(Dart d = tF.begin() ; d != tF.end() ; d = tF.next())
    {

        toCheck.push_back(d);
    }

    for(Dart d : toCheck)
    {
        REAL dist = faceMaxdistance(d);
        if(dist > sim_->envMap_.maxCellRay)
        {
184
//            CGoGNout<<"ok pour subdiv face :"<<d<<CGoGNendl;
Thomas Pitiot 's avatar
Thomas Pitiot committed
185
            mapOperator.subdivideFace(d,true,true) ;
186 187 188 189

            res=false;
        }
        surfaceMap.setCurrentLevel(surfaceMap.getMaxLevel()) ;
Thomas Pitiot 's avatar
Thomas Pitiot committed
190

191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248
    }



    return res;
}


REAL Surface::faceMaxdistance(Face face)
{
    Dart d = face;

    VEC3 center = Algo::Surface::Geometry::faceCentroid<PFPSurface,VertexAttribute<VEC3,SURFACE>>(surfaceMap,face,positionSurface);

    REAL res = (positionSurface[d]-center).norm2();
    for ( Vertex vert : verticesIncidentToFace2(surfaceMap,face))
    {
        REAL size=(positionSurface[vert]-center).norm2();
        if(size>res)
        {
            res=size;
        }
    }
    return res;
}

void Surface::initOperators(SubdivisionType st)
{
    switch (st)
    {
       case LERP :
            //lerp subdiv
            mapOperator.setEdgeVertexFunctor(new Algo::MR::Primal::Masks::LerpEdgeVertexFunctor<PFPSurface>(surfaceMap,positionSurface));
            mapOperator.setVertexVertexFunctor(new Algo::MR::Primal::Masks::LerpVertexVertexFunctor<PFPSurface>(surfaceMap,positionSurface));
            mapOperator.setFaceVertexFunctor(new Algo::MR::Primal::Masks::LerpFaceVertexFunctor<PFPSurface>(surfaceMap,positionSurface));
            break;
       case LOOP :
            //loop subdiv
            mapOperator.setEdgeVertexFunctor(new Algo::MR::Primal::Masks::LoopEdgeVertexFunctor<PFPSurface>(surfaceMap,positionSurface));
            mapOperator.setVertexVertexFunctor(new Algo::MR::Primal::Masks::LoopVertexVertexFunctor<PFPSurface>(surfaceMap,positionSurface));
            break;
       case CATC :
            //catmull subdiv
            mapOperator.setEdgeVertexFunctor(new Algo::MR::Primal::Masks::CCEdgeVertexFunctor<PFPSurface>(surfaceMap,positionSurface));
            mapOperator.setVertexVertexFunctor(new Algo::MR::Primal::Masks::CCVertexVertexFunctor<PFPSurface>(surfaceMap,positionSurface));
            mapOperator.setFaceVertexFunctor(new Algo::MR::Primal::Masks::CCFaceVertexFunctor<PFPSurface>(surfaceMap,positionSurface));
            break;
       case SQRT3:
            //sqrt subdiv
            mapOperator.setVertexVertexFunctor(new Algo::MR::Primal::Masks::Sqrt3VertexVertexFunctor<PFPSurface>(surfaceMap,positionSurface));
            mapOperator.setFaceVertexFunctor(new Algo::MR::Primal::Masks::Sqrt3FaceVertexFunctor<PFPSurface>(surfaceMap,positionSurface));
        break;
       default : CGoGNerr<<" subdivtype inconnu "<<__FILE__<<__LINE__<<CGoGNendl;


    }
}

Thomas Pitiot 's avatar
Thomas Pitiot committed
249
void Surface::changeColor(Triangle *t , float distance)
250 251 252 253 254 255 256
{
    if(distance >=0)
    {
        if(distance<distanceColorationMini)
        {
            if(distance<distanceColorationMaxi)
            {
Thomas Pitiot 's avatar
Thomas Pitiot committed
257 258 259
                t->r=1.0f;
                t->g=0.0f;
                t->b=0.0f;
260 261 262 263
            }
            else
            {
                float factor = (distanceColorationMini-distance)/(distanceColorationMini-distanceColorationMaxi);
Thomas Pitiot 's avatar
Thomas Pitiot committed
264 265 266
                t->r= r+(1.0f- r)*factor;
                t->g= g- g*factor;
                t->b= b- b*factor;
267 268 269 270 271 272
            }

        }
    }
    else
    {
Thomas Pitiot 's avatar
Thomas Pitiot committed
273 274 275 276 277 278 279 280 281 282
        t->r= r;
        t->g= g;
        t->b= b;
    }

    faceColor[t->cell]=VEC3(t->r,t->g,t->b);
}



Thomas Pitiot 's avatar
up2  
Thomas Pitiot committed
283
void  Surface::addGeneralCell ( Dart d)
Thomas Pitiot 's avatar
Thomas Pitiot committed
284 285
{
    bool added = false;
Etienne Schmitt's avatar
Etienne Schmitt committed
286
    for(std::pair<Dart,int>& pere : general_belonging)
Thomas Pitiot 's avatar
Thomas Pitiot committed
287
    {
288 289
//        if(sim_->envMap_.map.sameVolume(pere.first,d))
        if(pere.first==d)
Thomas Pitiot 's avatar
Thomas Pitiot committed
290
        {
Thomas Pitiot 's avatar
up2  
Thomas Pitiot committed
291
            pere.second ++;
Thomas Pitiot 's avatar
Thomas Pitiot committed
292 293 294 295
            added= true;
            break;
        }

Thomas Pitiot 's avatar
up2  
Thomas Pitiot committed
296
    }
Thomas Pitiot 's avatar
Thomas Pitiot committed
297 298 299
    if (!added)
    {
        general_belonging.push_back(std::make_pair(d,1));
300
    }
Thomas Pitiot 's avatar
Thomas Pitiot committed
301
}
Thomas Pitiot 's avatar
Thomas Pitiot committed
302 303 304
/*removeGeneralCell
 * removes cell d to general belonging decreases the number of instance of the cell, if the number is 0 the celle is removed *forever*
 */
Thomas Pitiot 's avatar
up2  
Thomas Pitiot committed
305
bool  Surface::removeGeneralCell (Dart d)
Thomas Pitiot 's avatar
Thomas Pitiot committed
306
{
Etienne Schmitt's avatar
Etienne Schmitt committed
307
    for(std::pair<Dart,int>& pere : general_belonging)
Thomas Pitiot 's avatar
Thomas Pitiot committed
308
    {
309 310
//        if(sim_->envMap_.map.sameVolume(pere.first,d))
        if(pere.first==d)
Thomas Pitiot 's avatar
Thomas Pitiot committed
311
        {
Thomas Pitiot 's avatar
up2  
Thomas Pitiot committed
312 313
            pere.second--;
            if(pere.second==0)
Thomas Pitiot 's avatar
Thomas Pitiot committed
314
            {
Thomas Pitiot 's avatar
up2  
Thomas Pitiot committed
315
                pere=general_belonging.back() ;
Thomas Pitiot 's avatar
Thomas Pitiot committed
316 317 318 319
                general_belonging.pop_back() ;
            }
            return true;
        }
Thomas Pitiot 's avatar
up2  
Thomas Pitiot committed
320 321 322 323 324 325 326 327 328


    };
    return false;
}

void  Surface::addGeneralNeighbor ( Dart d)
{
    bool added = false;
Etienne Schmitt's avatar
Etienne Schmitt committed
329
    for(std::pair<Dart,int>& pere : general_neighbors)
Thomas Pitiot 's avatar
up2  
Thomas Pitiot committed
330
    {
331 332
//        if(sim_->envMap_.map.sameVolume(pere.first,d))
        if(pere.first==d)
Thomas Pitiot 's avatar
up2  
Thomas Pitiot committed
333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349
        {
            pere.second ++;
            added= true;
            break;
        }

    }
    if (!added)
    {
        general_neighbors.push_back(std::make_pair(d,1));
    }
}
/*removeGeneralCell
 * removes cell d to general belonging decreases the number of instance of the cell, if the number is 0 the celle is removed *forever*
 */
bool  Surface::removeGeneralNeighbor (Dart d)
{
Etienne Schmitt's avatar
Etienne Schmitt committed
350
    for(std::pair<Dart,int>& pere : general_neighbors)
Thomas Pitiot 's avatar
up2  
Thomas Pitiot committed
351
    {
352 353
//        if(sim_->envMap_.map.sameVolume(pere.first,d))
        if(pere.first==d)
Thomas Pitiot 's avatar
up2  
Thomas Pitiot committed
354 355 356 357 358 359 360 361 362 363
        {
            pere.second--;
            if(pere.second==0)
            {
                pere=general_neighbors.back() ;
                general_neighbors.pop_back() ;
            }
            return true;
        }

Thomas Pitiot 's avatar
Thomas Pitiot committed
364 365 366 367 368 369 370 371 372 373 374 375

    };
    return false;
}


VEC3 Surface::getPosition(int index)
{
    return parts_[index]->getPosition();
}