예제 #1
0
static real edge_compatibility(pedge e1, pedge e2){
  /* two edges are u1->v1, u2->v2.
     return 1 if two edges are exactly the same, 0 if they are very different.
   */
  real *u1, *v1, *u2, *v2, *u, dist1, dist2, len1, len2;
  int dim = e1->dim, flipped = FALSE;

  u1 = e1->x;
  v1 = (e1->x)+(e1->npoints)*dim-dim;
  u2 = e2->x;
  v2 = (e2->x)+(e2->npoints)*dim-dim;
  dist1 = sqr_dist(dim, u1, u2) + sqr_dist(dim, v1, v2);
  dist2 =  sqr_dist(dim, u1, v2) + sqr_dist(dim, v1, u2);
  if (dist1 > dist2){
    u = u2;
    u2 = v2;
    v2 = u;
    dist1 = dist2;
    flipped = TRUE;
  }
  len1 = dist(dim, u1, v1);
  len2 = dist(dim, u2, v2);
  //dist1 = MAX(0.1, dist1/(len1+len2+dist1));
  dist1 = MAX(0.1, dist1/(len1+len2+0.0001*dist1));
  if (flipped){
    return -1/dist1; 
  } else {
    return 1/dist1; 
  }
}
예제 #2
0
static real edge_compatibility_full(pedge e1, pedge e2){
  /* two edges are u1->v1, u2->v2.
     return 1 if two edges are exactly the same, 0 if they are very different.
     This is based on Holten and van Wijk's paper
   */
  real *u1, *v1, *u2, *v2, *u, dist1, dist2, len1, len2, len;
  real tmp, ca, cp, cs;
  int dim = e1->dim, flipped = FALSE, i;

  u1 = e1->x;
  v1 = (e1->x)+(e1->npoints)*dim-dim;
  u2 = e2->x;
  v2 = (e2->x)+(e2->npoints)*dim-dim;
  dist1 = sqr_dist(dim, u1, u2) + sqr_dist(dim, v1, v2);
  dist2 =  sqr_dist(dim, u1, v2) + sqr_dist(dim, v1, u2);
  if (dist1 > dist2){
    u = u2;
    u2 = v2;
    v2 = u;
    dist1 = dist2;
    flipped = TRUE;
  }
  len1 = MAX(dist(dim, u1, v1), SMALL);
  len2 = MAX(dist(dim, u2, v2), SMALL);
  len = 0.5*(len1+len2);

  /* angle compatibility */
  ca = 0;
  for (i = 0; i < dim; i++) 
    ca += (v1[i]-u1[i])*(v2[i]-u2[i]);
  ca = ABS(ca/(len1*len2));
  assert(ca > -0.001);

  /* scale compatibility */
  //cs = 2/(len1/len2+len2/len1);
  cs = 2/(MAX(len1,len2)/len + len/MIN(len1, len2));
  assert(cs > -0.001 && cs < 1.001);
 
  /* position compatibility */
  cp = 0;
  for (i = 0; i < dim; i++) {
    tmp = .5*(v1[i]+u1[i])-.5*(v2[i]+u2[i]);
    cp += tmp*tmp;
  }
  cp = sqrt(cp);
  cp = len/(len + cp);
  assert(cp > -0.001 && cp < 1.001);

  /* visibility compatibility */

  //dist1 = MAX(0.1, dist1/(len1+len2+dist1));
  dist1 = cp*ca*cs;
  if (flipped){
    return -dist1; 
  } else {
    return dist1; 
  }
}
예제 #3
0
static void  edge_attraction_force(real similarity, pedge e1, pedge e2, real *force){
  /* attrractive force from x2 applied to x1 */
  real *x1 = e1->x, *x2 = e2->x;
  int dim = e1->dim;
  int np = e1->npoints;
  int i, j;
  real dist, s, ss;
  real edge_length = e1->edge_length;


  assert(e1->npoints == e2->npoints);

  /* attractive force = 1/d where d = D/||e1|| is the relative distance, D is the distance between e1 and e2.
   so the force is norminal and unitless
  */
  if (similarity > 0){
    s = edge_length;
    s = similarity*edge_length;
    for (i = 1; i <= np - 2; i++){
      dist = sqr_dist(dim, &(x1[i*dim]), &(x2[i*dim]));
      if (dist < SMALL) dist = SMALL;
      ss = s/(dist+0.1*edge_length*sqrt(dist));
      for (j = 0; j < dim; j++) force[i*dim + j] += ss*(x2[i*dim + j] - x1[i*dim + j]);
    }
  } else {/* clip e2 */
    s = -edge_length;
    s = -similarity*edge_length; 
    for (i = 1; i <= np - 2; i++){
      dist = sqr_dist(dim, &(x1[i*dim]), &(x2[(np - 1 - i)*dim]));
      if (dist < SMALL) dist = SMALL;
      ss = s/(dist+0.1*edge_length*sqrt(dist));
      for (j = 0; j < dim; j++) force[i*dim + j] += ss*(x2[(np - 1 - i)*dim + j] - x1[i*dim + j]);
    }
  }

}
예제 #4
0
double  MSLPoint3d::distance(const MSLPoint3d& q) const 
{ return sqrt(sqr_dist(q)); }
예제 #5
0
static real dist(int dim, real *x, real *y){
  return sqrt(sqr_dist(dim,x,y));
}