vec3& mesh_parametric_cloth::force(int const ku,int const kv)
{
    ASSERT_CPE(ku >= 0 , "Value ku ("+std::to_string(ku)+") should be >=0 ");
    ASSERT_CPE(ku < size_u() , "Value ku ("+std::to_string(ku)+") should be < size_u ("+std::to_string(size_u())+")");
    ASSERT_CPE(kv >= 0 , "Value kv ("+std::to_string(kv)+") should be >=0 ");
    ASSERT_CPE(kv < size_v() , "Value kv ("+std::to_string(kv)+") should be < size_v ("+std::to_string(size_v())+")");

    int const offset = ku + size_u()*kv;

    ASSERT_CPE(offset < static_cast<int>(force_data.size()),"Internal error");

    return force_data[offset];
}
void mesh_parametric_cloth::set_plane_xy_unit(int const size_u_param,int const size_v_param)
{
    mesh_parametric::set_plane_xy_unit(size_u_param,size_v_param);

    int const N = size_u()*size_v();
    speed_data.resize(N);
    force_data.resize(N);
}
示例#3
0
vec3 mesh_parametric::normal(int const ku,int const kv) const
{
    ASSERT_CPE(ku >= 0 , "Value ku ("+std::to_string(ku)+") should be >=0 ");
    ASSERT_CPE(ku < size_u() , "Value ku ("+std::to_string(ku)+") should be < size_u ("+std::to_string(size_u())+")");
    ASSERT_CPE(ku >= 0 , "Value kv ("+std::to_string(kv)+") should be >=0 ");
    ASSERT_CPE(ku < size_v() , "Value kv ("+std::to_string(kv)+") should be < size_v ("+std::to_string(size_v())+")");

    int const offset = ku+size_u_data*kv;
    return mesh_basic::normal(offset);
}
void mesh_parametric_cloth::integration_step(float const dt)
{
    ASSERT_CPE(speed_data.size() == force_data.size(),"Incorrect size");
    ASSERT_CPE(static_cast<int>(speed_data.size()) == size_vertex(),"Incorrect size");


    int const Nu = size_u();//nombre de ressort
    int const Nv = size_v();//nombre de ressort
    //*************************************************************//
    // TO DO: Calculer l'integration numerique des positions au cours de l'intervalle de temps dt.
    //*************************************************************//

    //security check (throw exception if divergence is detected)
    static float const LIMIT=30.0f;
 for(int ku=0 ; ku<Nu; ++ku)
    {
        for(int kv=0; kv<Nv; ++kv)
        {
            vec3 & p = vertex(ku,kv);
            speed(ku,kv)=(1-mu*dt)*speed(ku,kv)+ dt*force(ku,kv);//gg c'est beau
            p = p + dt*speed(ku,kv);

            // collision avec le sol
            if (p.z() < -1.101f)// hauteur du sol
            {
                p.z()= -1.100f;
                force(ku,kv).z() = 0.0f;
                speed(ku,kv).z() = 0.0f;
            }
            // collision avec la sphere
            vec3 centre_sphere = {0.5f,0.05f,-1.1f};
            vec3 normale= p-centre_sphere;
            float rayon =0.4f;
            if (norm(normale)<rayon) {

                p= centre_sphere + normale/norm(normale) * rayon;
                //on annule la composante normale de la force  et de la vitesse

                speed(ku,kv) -= dot (speed(ku,kv),normale/norm(normale)) * normale;
                force(ku,kv) -= dot (force(ku,kv),normale/norm(normale)) * normale;




                //on annule la composante normale de la force  et de la vitesse

            }

        }
    }

}
示例#5
0
bool mesh_parametric::valid_mesh() const
{
    int const total_size=size_u()*size_v();

    if(size_vertex()!=total_size ||
            size_color()!=total_size ||
            size_texture_coord()!=total_size ||
            size_normal()!=total_size )
    {
        std::cout<<"mesh parametric has incorrect data size"<<std::endl;
        return false;
    }

    return mesh_basic::valid_mesh();
}
void mesh_parametric_cloth::update_force()
{

    int const Nu = size_u();
    int const Nv = size_v();
    int const N_total = Nu*Nv;
    ASSERT_CPE(static_cast<int>(force_data.size()) == Nu*Nv , "Error of size");
    //wind direction
    vec3 uw=vec3( x_wind,y_wind,z_wind);
    uw= normalized(uw);

    //Gravity and wind
    static vec3 const g (0.0f,0.0f,-9.81f);
    vec3 const g_normalized = g/N_total;
    for(int ku=0 ; ku<Nu ; ++ku)
    {
        for(int kv=0 ; kv<Nv ; ++kv)
        {

            force(ku,kv) = g_normalized;


            vec3 n=this->normal(ku,kv);
            force(ku,kv) += Kw*dot(n,uw)*n;
        }
    }

    //*************************************************************//
    // TO DO, Calculer les forces s'appliquant sur chaque sommet
    //*************************************************************//
    //*************************************************************//
    float L01= 1.0f/(Nu-1);
    float L02= sqrt(2)/(Nu-1);
    float L03= 2.0f/(Nu-1);

    for(int ku=0 ; ku<Nu; ++ku)
    {
        for(int kv=0 ; kv<Nv; ++kv)
        {

            vec3 const& p = vertex(ku,kv);
            std::vector<vec3> pvd;
            std::vector<vec3> pvdiag;
            std::vector<vec3> pvb;

            /** cas general **/
            //voisin directs
            if( kv < Nv-1) {
                pvd.push_back(vertex(ku,kv+1));
            }
            if( kv > 0) {
                pvd.push_back(vertex(ku,kv-1));
            }
            if( ku < Nu-1) {
                pvd.push_back(vertex(ku+1,kv));
            }
            if( ku > 0) {
                pvd.push_back(vertex(ku-1,kv));
            }
            //voisin diagonale
            if( ku< Nu -1 && kv < Nv-1 ) {
                pvdiag.push_back(vertex(ku+1,kv+1));
            }
            if( ku < Nu-1 && kv >0 ) {
                pvdiag.push_back(vertex(ku+1,kv-1));
            }
            if( ku > 0 && kv > 0 ) {
                pvdiag.push_back(vertex(ku-1,kv-1));
            }
            if( ku>0 && kv< Nu -1) {
                pvdiag.push_back(vertex(ku-1,kv+1));
            }

            //voisin bend
            if( ku < Nu -2) {
                pvb.push_back(vertex(ku+2,kv));
            }
            if( ku >1 ) {
                pvb.push_back(vertex(ku-2,kv));

            }
            if( kv < Nv -2) {
                pvb.push_back(vertex(ku,kv+2));
            }
            if( kv >1 ) {
                pvb.push_back(vertex(ku,kv-2));
            }



            for (int i=0; i<int(pvd.size());i++) {
                vec3 u=p-pvd[i];
                force(ku,kv)  += (Kdirect *(L01 - norm(u)) *u) /norm(u);
            }
            for (int i=0; i<int (pvdiag.size());i++) {
                vec3 u=p-pvdiag[i];
                force(ku,kv)  +=( Kdiag *(L02 - norm(u))*u) /norm(u);
            }
            for (int i=0; i<int (pvb.size());i++) {
                vec3 u=p-pvb[i];
                force(ku,kv)  +=( Kdouble *(L03 - norm(u))*u) /norm(u);
            }


            // on bloque les angles
           if ((ku == 0 && kv == 0 ) || (ku == 0 && kv == Nv -1)) {
            //if ((ku == Nu-1 && kv == Nv-1 )||(ku == Nu-1 && kv == 0 )||(ku == 0 && kv == 0 ) || (ku == 0 && kv == Nv -1)) {

                force(ku,kv) = vec3(0.0f,0.0f, 0.0f);
            }
        }
    }

}