Example #1
0
/*
 * Retrieve constants of motion (as if) in 2-body problem.
 * Returns j, e, a, omega in vectors/fields provided.
 */
void get_constants( double x[3], double v[3], double m_central,
                    double j[3], double e[3], double *a, double *omega)
{
    _enter_function(_UL_KEPLER, _UL_KEPLER_GET_CONSTANTS);
    int i;

    vec_prod(x, v, j);
    vec_prod (v, j, e);
    double r = sqrt(scal_prod(x, x));
    for(i = 0; i < DIMENSIONS; i++)
        e[i] = e[i]/m_central - x[i]/r;
    *a = scal_prod(j, j) / m_central / fabs(1 - scal_prod(e, e));
    *omega = sqrt(m_central / pow(*a, 3.0));

    _exit_function();
}
Example #2
0
float vol_p_side_lgth(int i, int j,int k, ls  lss[MAX_LS_AMOUNT] ){
  /* calculate volume of the parallelepiped defined by the loudspeaker
     direction vectors and divide it with total length of the triangle sides. 
     This is used when removing too narrow triangles. */

  float volper, lgth;
  cart_vec xprod;
  cross_prod(lss[i].coords, lss[j].coords, &xprod);
  volper = fabsf(vec_prod(xprod, lss[k].coords));
  lgth = (fabsf(vec_angle(lss[i].coords,lss[j].coords)) 
	  + fabsf(vec_angle(lss[i].coords,lss[k].coords)) 
	  + fabsf(vec_angle(lss[j].coords,lss[k].coords)));
  if(lgth>0.00001)
    return volper / lgth;
  else
    return 0.0;
}
Example #3
0
/*
 * Calculate Kepler position and velocity for given timestep _dt_
 * for particle no. _pos_.
 * _xp_ and _vp_ will be updated.
 */
void step_kepler_1(struct particle parts[], int pcount, int pos, double dt,
                   double *out_a, double *out_a_, double *out_a_2, double *out_a_3,
                   double *curr_a, double *curr_e)
{
    _enter_function(_UL_KEPLER, _UL_KEPLER_STEP_KEPLER_1);
    int i;
    struct particle *p0 = parts, *p1 = parts + pos;
    double r_[3], v_[3], j_[3], ecc_[3], a_[3], b_[3], _1_r2, afact, v_r_, v_v_, r_a_, v_a_, r_a__;
    double ecc, a, r, v, b, omega, e, mean, cosp, sinp;
    double m_c=p0->m, _cosp_ecc, e2, _1_ecc, _cosp_1, de_dt;//+p1->m;

    // get relative position / motion
    for(i = 0; i < 3; i++)
    {
        r_[i] = p1->xp[i] - p0->xp[i];
        v_[i] = p1->vp[i] - p0->vp[i];
    }

    // calculate ellipse constants
    get_constants(r_, v_, m_c, j_, ecc_, &a, &omega);
    //printf("#  [%d]:\t%e\t%e\t%e\n", pos, v_abs(ecc_), a, omega);

    ecc = v_abs(ecc_);
    // b_ = a * sqrt(|1-e²|) * (j_ x e_) / |j_ x e_|
    vec_prod(j_, ecc_, b_);
    b = a * sqrt(fabs(1-ecc*ecc)) / v_abs(b_);
    for(i = 0; i < 3; i++)
    {
        a_[i]  = a*ecc_[i]/ecc;            // semi major vector
        b_[i] *= b;                        // semi minor vector
    }

    if(curr_a != NULL) *curr_a = a;
    if(curr_e != NULL) *curr_e = ecc;

    if(ecc < 1)
    // elliptical orbit
    {
        if(!p1->is_elliptical)
        {
            fprintf(get_file(FILE_WARNING),
                    "#### [t=%1.12e] Particle #%d captured onto elliptical orbit with e=%e ####\n",
                    t_total(p1->t), pos, ecc);
                    p1->is_elliptical = 1;
        }
        // calculate eccentric anomaly e at t+dt
        e = (a - v_abs(r_)) / (ecc * a);
        if(e >= 1.0) e = .0;
        else if(e <= -1.0) e = M_PI;
        else e = acos(e);
        if(scal_prod(r_, b_) < 0)
            e = 2*M_PI - e;
        mean = (e - ecc*sin(e)) + dt * omega;
        while(mean >= 2. * M_PI)
            mean -= 2. * M_PI;

        e = solve_kepler(mean, ecc);

        cosp = cos(e);
        sinp = sin(e);
        _cosp_ecc = cosp - ecc;
        de_dt = omega / (1. - ecc * cosp);
        if(ecc > .99)
        {
            e2 = (e > 2. * M_PI - 1e-3) ? e - 2. * M_PI : e;
            if(e2 < 1e-3)
            {
                e2 *= e2;
                _1_ecc    = scal_prod(j_, j_)/(p0->m*a*(1+ecc));
                _cosp_1   =  - .5 * e2 * (1 - e2 / 12. * (1 - e2 / 30.));
                _cosp_ecc = _1_ecc + _cosp_1;
                de_dt     = omega / (_1_ecc - ecc * _cosp_1);
            }
        }
        for(i = 0; i < DIMENSIONS; i++)
        {
            r_[i] =   a_[i] * _cosp_ecc + b_[i] * sinp ;  // new location
            v_[i] = (-a_[i] * sinp      + b_[i] * cosp) * de_dt;   // direction of v only
        }
    }
    else
    // hyperbolic orbit  // parabolic?
    {
        if(p1->is_elliptical)
        {
            fprintf(get_file(FILE_WARNING), "#### [t=%1.12e+%1.12e] Particle #%d thrown onto hyperbolic orbit with e=%e (E=%e, a=%e) ####\n",
                    t_total(p1->t), convert_time(dt, 0), pos, ecc, p1->energy, convert_length(a, 0));
            p1->is_elliptical = 0;
        }
        if(ecc == 1)
            fprintf(get_file(FILE_WARNING), "# # # %e\tParabolic orbit of m%d treated as hyperbolic: e=%e\t(x=%e)\n",
                    t_total(p1->t), pos, ecc, convert_length(v_abs(p1->xp), 0));

        // calculate eccentric anomaly e at t+dt
        e = (a + v_abs(r_)) / (ecc * a);
        if(e < 1.0) e = .0;
        else if(scal_prod(r_, v_) < 0) e = -acosh(e);
        else e = acosh(e);

        e = kepler(ecc, ecc * sinh(e) - e + dt * omega);
        cosp = cosh(e);
        sinp = sinh(e);
        de_dt = omega / (ecc * cosp - 1.);
        for(i = 0; i < DIMENSIONS; i++)
        {
            r_[i] =   a_[i] * (ecc - cosp)  + b_[i] * sinp;  // new location
            v_[i] = (-a_[i] * sinp          + b_[i] * cosp) * de_dt;  // direction of v only
        }
    }

    // get |v_| from j_ = r_ x v_
    v = v_abs(v_);
    r = v_abs(r_);
    v = v_abs(j_) / (r * v * sin(acos(scal_prod(r_, v_)/ (r * v))));

    for(i = 0; i < DIMENSIONS; i++)
    {
        //v_[i] *= v;
        // total motion relative to fix central mass
        p1->xp[i] = p0->xp[i] + r_[i];
        p1->vp[i] = p0->vp[i] + v_[i];
    }

    if(out_a != NULL)
    {
        _1_r2 = 1. / scal_prod(r_, r_);
        afact = - m_c * _1_r2 * sqrt(_1_r2);
        //printf("4  %e %e %e\n", *(out_a), *(out_a+1), *(out_a+2));
        for(i = 0; i < DIMENSIONS; i++)
            out_a[i] = afact * r_[i];
            if(out_a_ != NULL)
            {
                v_r_ = scal_prod(v_, r_);
                for(i = 0; i < DIMENSIONS; i++)
                    out_a_[i] = afact * (v_[i] - 3 * _1_r2 * v_r_ * r_[i]);
                    if(out_a_2 != NULL)
                    {
                        v_v_ = scal_prod(v_, v_);
                        r_a_ = scal_prod(r_, out_a);
                        for(i = 0; i < DIMENSIONS; i++)
                            out_a_2[i] = afact * (out_a[i] - 3. * _1_r2 * (v_r_ * (2. * v_[i] - 5. * v_r_ * r_[i] * _1_r2)
                                         + (v_v_ + r_a_) * r_[i]));
                        if(out_a_3 != NULL)
                        {
                            v_a_  = scal_prod(v_, out_a);
                            r_a__  = scal_prod(r_, out_a_);
                            for(i = 0; i < DIMENSIONS; i++)
                                out_a_3[i] = afact * (out_a_[i]
                                            - 3. * _1_r2 * (3. * v_r_ * out_a[i]
                                            + 3. * (v_v_ + r_a_)
                                            * (v_[i] - 5. * v_r_ * _1_r2 * r_[i])
                                            + (3. * v_a_ + r_a__) * r_[i]
                                            + v_r_ * v_r_ * _1_r2
                                            * (-15. * v_[i] + 35. * v_r_ * _1_r2 * r_[i])));
                        }
                    }
            }
    }

    _exit_function();
}