LOCAL void EnforceFlowSpecifedStates2d( Front *fr) { INTERFACE *intfc; CURVE **c; POINT *p; HYPER_SURF *hs; BOND *b; Locstate sl, sr; if ((fr==NULL) || (Fsr_list(fr)==NULL) || (fr->rect_grid->dim!=2)) return; intfc = fr->interf; for (c = intfc->curves; c && *c; ++c) { hs = Hyper_surf(*c); if (is_subdomain_boundary(hs) || is_passive_boundary(hs)) continue; if (BothSidesActive(hs,fr) == NO) { b = (*c)->first; p = b->start; slsr(p,Hyper_surf_element(b),hs,&sl,&sr); (void) RegionIsFlowSpecified(sl,NULL,Coords(p), negative_component(hs),NO_COMP,fr); (void) RegionIsFlowSpecified(sr,NULL,Coords(p), positive_component(hs),NO_COMP,fr); for (; b != NULL; b = b->next) { p = b->end; slsr(p,Hyper_surf_element(b),hs,&sl,&sr); (void) RegionIsFlowSpecified(sl,NULL,Coords(p), negative_component(hs),NO_COMP,fr); (void) RegionIsFlowSpecified(sr,NULL,Coords(p), positive_component(hs),NO_COMP,fr); } } } } /*end EnforceFlowSpecifedStates2d*/
LOCAL void add_neighbors_of_landing_tri( TRI ***tri_list, int *num_tri, SURFACE *s, int *max_num_tri, TRI *tri) { HYPER_SURF_ELEMENT *hse = Hyper_surf_element(tri); HYPER_SURF *hs = Hyper_surf(s); TRI *nbtris[20]; int i,num_nbtri; TriAndFirstRing(hse,hs,&num_nbtri,nbtris); for (i = 0; i < num_nbtri; ++i) check_add_tri(tri_list,nbtris[i],num_tri,max_num_tri); } /* add_neighbors_of_landing_tri */
/*ARGSUSED*/ LIB_LOCAL bool long_nearest_interface_point1d( float *coords, COMPONENT comp, INTERFACE *intfc, USE_BOUNDARIES bdry, HYPER_SURF *hs, float *ans, float *t, HYPER_SURF_ELEMENT **phse, HYPER_SURF **phs) { const COMPONENT *eq_comps; int n_eq; POINT **p; POINT *p_closest; /* Find Closest Point on Front: */ if (hs) { p_closest = Point_of_hs(hs); } else { float distance; /* Distance from (x) to a point */ float min_distance; /* Distance to Nearest point */ eq_comps = equivalent_components_list(comp,&n_eq,intfc); min_distance = HUGE_VAL; p_closest = NULL; for (p = intfc->points; p && (*p); ++p) { if (!comp_is_on_point(*p,eq_comps,n_eq)) continue; if (skip_boundary_hs(Hyper_surf(*p),bdry)) continue; distance = sqr(coords[0] - Coords(*p)[0]); if (distance < min_distance) { min_distance = distance; p_closest = *p; } } if (p_closest == NULL) { static int first = YES; (void) printf("WARNING in long_nearest_interface_point1d(), " "p_closest == NULL\n" "coords = (%g), comp = %d, bdry = %d, " "hs = %p\n",coords[0],comp,bdry,hs); (void) printf("Topological grid of interface\n"); print_rectangular_grid(&topological_grid(intfc)); if (first == YES) { (void) printf("Interface into " "long_nearest_interface_point1d()\n"); print_interface(intfc); } first = NO; return NO; } } *phs = Hyper_surf(p_closest); *phse = Hyper_surf_element(p_closest); ans[0] = Coords(p_closest)[0]; t[0] = 0.0; return YES; } /*end long_nearest_interface_point1d*/
LIB_LOCAL bool nearest_interface_point1d( float *coords, COMPONENT comp, INTERFACE *intfc, USE_BOUNDARIES bdry, HYPER_SURF *hs, float *ans, float *t, HYPER_SURF_ELEMENT **phse, HYPER_SURF **phs) { const COMPONENT *eq_comps; int n_eq; POINT **p; POINT *p_closest; int ix; /* Grid square containing x */ int icoords[MAXD]; int ix1,ix2; int k; struct Table *T = intfc->table; if (intfc->modified || T->new_grid) { if (make_point_comp_lists(intfc) == FUNCTION_FAILED) { static bool first = YES; (void) printf("WARNING in nearest_interface_point1d(), " "make_point_comp_lists() failed\n" "coords = (%g), comp = %d, bdry = %d, hs = %p\n", coords[0],comp,bdry,hs); (void) printf("Topological grid of interface\n"); print_rectangular_grid(&topological_grid(intfc)); if (first == YES) { (void) printf("Interface into "); (void) printf("nearest_interface_point1d()\n"); print_interface(intfc); } first = NO; return NO; } } if ((!rect_in_which(coords,icoords,&T->rect_grid)) || (T->compon1d[icoords[0]] != ONFRONT)) /* Off Front: */ return long_nearest_interface_point1d(coords,comp,intfc, bdry,hs,ans,t,phse,phs); /* On Front: */ /* Find Closest Point on Front: */ eq_comps = equivalent_components_list(comp,&n_eq,intfc); if (hs) { p_closest = Point_of_hs(hs); } else { float distance; /* Distance from (x) to a Point */ float min_distance; /* Distance to the nearest Point */ ix = icoords[0]; min_distance = HUGE_VAL; p_closest = NULL; p = T->pts_in_zone[ix]; /* Check center block first for existence of allowed */ /* closest point */ for (k = 0; k < T->num_of_points[ix]; ++k,++p) { if (!comp_is_on_point(*p,eq_comps,n_eq)) continue; if (skip_boundary_hs(Hyper_surf(*p),bdry)) continue; distance = sqr(coords[0] - Coords(*p)[0]); if (distance < min_distance) { min_distance = distance; p_closest = *p; } } if (p_closest == NULL) return long_nearest_interface_point1d(coords,comp,intfc,bdry, hs,ans,t,phse,phs); ix1 = ix-1; if (ix1 < 0) ix1=ix; ix2 = ix+1; if (ix2 == T->rect_grid.gmax[0]) ix2 = ix; for(ix = ix1; ix <= ix2; ++ix) { if ((ix == icoords[0]) || (T->compon1d[ix] != ONFRONT)) continue; p = T->pts_in_zone[ix]; for (k = 0; k < T->num_of_points[ix]; ++k,++p) { if (!comp_is_on_point(*p,eq_comps,n_eq)) continue; if (skip_boundary_hs(Hyper_surf(*p),bdry)) continue; distance = sqr(coords[0] - Coords(*p)[0]); if (distance < min_distance) { min_distance = distance; p_closest = *p; } } } if (p_closest == NULL) return long_nearest_interface_point1d(coords,comp, intfc,bdry,hs,ans,t,phse,phs); } *phs = Hyper_surf(p_closest); *phse = Hyper_surf_element(p_closest); ans[0] = Coords(p_closest)[0]; t[0] = 0.0; return YES; } /*end nearest_interface_point1d*/
/* ARGSUSED */ EXPORT void f_tan_curve_propagate( Front *fr, Front *newfr, INTERFACE *tempintfc, CURVE *tempc, CURVE *newc, double dt) { BOND *tempb, *newb; Locstate ansl, ansr; boolean curveIsClosed; double *h = fr->rect_grid->h; double tngt[MAXD], ds, sbl; int i, dim = fr->rect_grid->dim; static int nrad = 0; static Tan_stencil *sten = NULL; debug_print("f_tan_prop","Entered f_tan_curve_propagate()\n"); if (debugging("f_tan_prop")) { (void) printf("tempc %llu newc %llu\n",(long long unsigned int)curve_number(tempc), (long long unsigned int)curve_number(newc)); (void) printf("tempc\n"); print_curve(tempc); (void) printf("\nnewc\n"); print_curve(newc); } if (sten == NULL) { nrad = fr->npts_tan_sten/2; sten = alloc_tan_stencil(fr,nrad); } switch (wave_type(tempc)) { case PASSIVE_BOUNDARY: case SUBDOMAIN_BOUNDARY: return; default: break; } curveIsClosed = (is_closed_node(newc->end)) ? YES : NO; tempb = tempc->first; newb = newc->first; /* Check if zero length curve */ if (tempc->first == tempc->last) { sbl = scaled_bond_length(tempc->first,h,dim); if (sbl < MIN_SC_SEP(tempintfc)) { debug_print("f_tan_prop","Left f_tan_curve_propagate()\n"); return; } } for (; newb; tempb = tempb->next, newb = newb->next) { if (t_pt_propagated(newb->end)) continue; /* stop at tempc->last if no continuation */ if ((tempb == tempc->last) && !curveIsClosed && !is_fixed_node(newc->end)) { break; } /* calculate tangential displacement */ /* * TODO: the upgrade of this function * to 3 dimensions is non-trivial. * There will need to be either two * operator splitting sweeps, or one * unsplit solver. There is arbitrary * choice of tangent directions and this * will have to be resolved. */ tangent(newb->end,newb,newc,tngt,newfr); ds = grid_size_in_direction(tngt,h,dim); /* find the stencil states */ states_at_distance_along_curve(tempb->end,tempb,tempc, NEGATIVE_ORIENTATION,ds,nrad, sten->leftst-1,sten->rightst-1, sten->hs-1,sten->hse-1,sten->t-1, sten->p-1,newfr); if (tempb->next != NULL) { ansl = left_state(newb->end); ansr = right_state(newb->end); } else { ansl = left_end_state(newc); ansr = right_end_state(newc); } states_at_distance_along_curve(tempb->end,tempb,tempc, POSITIVE_ORIENTATION,ds,nrad, sten->leftst+1,sten->rightst+1, sten->hs+1,sten->hse+1,sten->t+1, sten->p+1,newfr); sten->p[0] = tempb->end; sten->hse[0] = Hyper_surf_element(tempb); sten->hs[0] = Hyper_surf(tempc); sten->t[0] = 1.0; sten->curvature = mean_curvature_at_point(sten->p[0],sten->hse[0], sten->hs[0],fr); if (debugging("f_tan_prop")) { int j; static const char *xyz[3] = { "x", "y", "z" }; (void) printf("state locations\n"); (void) printf("%-8s"," "); for (i = 0; i < dim; ++i) (void) printf("%-14s",xyz[i]); (void) printf("\n"); for (j = -nrad; j <= nrad; ++j) { for (i = 0; i < dim; ++i) (void) printf("%-14g",Coords(sten->p[j])[i]); (void) printf("\n"); } (void) printf("\n"); (void) printf("State values\n"); for (j = -nrad; j <= nrad; ++j) { (void) printf("left state[%d] at ",j); print_general_vector("",Coords(sten->p[j]),dim,"\n"); (*fr->print_state)( left_state_at_point_on_curve(sten->p[j], Bond_of_hse(sten->hse[j]), Curve_of_hs(sten->hs[j]))); (void) printf("right state[%d] at ",j); print_general_vector("",Coords(sten->p[j]),dim,"\n"); (*fr->print_state)( right_state_at_point_on_curve(sten->p[j], Bond_of_hse(sten->hse[j]), Curve_of_hs(sten->hs[j]))); (void) printf("\n"); } } /* update using n-point stencil tangential op */ sten->newhs = Hyper_surf(newc); sten->dir = tngt; npt_tang_solver(ds,dt,sten,ansl,ansr,fr); if (fr->parab == YES) npt_parab_tan_solver2d(ds,dt,sten,ansl,ansr,fr); t_pt_propagated(newb->end) = YES; if (debugging("f_tan_prop")) { (void) printf("answers: left right\n"); (*newfr->print_state)(ansl); (*newfr->print_state)(ansr); (void) printf("\n"); } } if (curveIsClosed) { /* assign start states to end states */ ft_assign(left_start_state(newc),left_end_state(newc),fr->sizest); ft_assign(right_start_state(newc),right_end_state(newc),fr->sizest); } debug_print("f_tan_prop","Left f_tan_curve_propagate()\n"); } /*end f_tan_curve_propagate*/
LOCAL void f_second_order_intfc_propagate2d( Front *fr, POINTER wave, INTERFACE *old_intfc, INTERFACE *new_intfc, double dt) { INTERFACE *tmp_intfc; HYPER_SURF *oldhs, *tmphs, *newhs; HYPER_SURF_ELEMENT *oldhse, *tmphse, *newhse; CURVE **oldc, **tmpc, **newc; BOND *oldb, *tmpb, *newb; POINT *oldp, *tmpp, *newp; int i; double V[MAXD]; set_copy_intfc_states(NO); tmp_intfc = pp_copy_interface(fr->interf); /* Compute v(x^n, t^n) */ for (oldc = old_intfc->curves, tmpc = tmp_intfc->curves; oldc && *oldc; ++oldc, ++tmpc) { for (oldb = (*oldc)->first, tmpb = (*tmpc)->first; oldb != NULL; oldb = oldb->next, tmpb = tmpb->next) { if (oldb == (*oldc)->last && !is_closed_node((*oldc)->end)) continue; oldp = oldb->end; tmpp = tmpb->end; oldhse = Hyper_surf_element(oldb); oldhs = Hyper_surf(*oldc); point_propagate(fr,wave,oldp,tmpp,oldhse,oldhs,dt,V); } } /* Compute v(x^(n+1), t^(n+1)) */ for (newc = new_intfc->curves, tmpc = tmp_intfc->curves; newc && *newc; ++newc, ++tmpc) { for (newb = (*newc)->first, tmpb = (*tmpc)->first; newb != NULL; newb = newb->next, tmpb = tmpb->next) { tmpp = tmpb->end; newp = newb->end; tmphse = Hyper_surf_element(tmpb); tmphs = Hyper_surf(*tmpc); point_propagate(fr,wave,tmpp,newp,tmphse,tmphs,dt,V); } } /* Compute x^(n+1) = x^n + 0.5*dt*(v(x^n,t^n) + v(x^(n+1), t^(n+1)) */ for (oldc = old_intfc->curves, tmpc = tmp_intfc->curves, newc = new_intfc->curves; oldc && *oldc; ++oldc, ++tmpc, ++newc) { for (oldb = (*oldc)->first, tmpb = (*tmpc)->first, newb = (*newc)->first; oldb != NULL; oldb = oldb->next, tmpb = tmpb->next, newb = newb->next) { oldp = oldb->end; tmpp = tmpb->end; newp = newb->end; for (i = 0; i < 2; ++i) Coords(newp)[i] = Coords(oldp)[i] + 0.5*(oldp->vel[i] + tmpp->vel[i])*dt; if (newb == (*newc)->last && is_closed_node((*newc)->end)) { propagation_status((*newc)->end) = PROPAGATED_NODE; set_bond_length((*newc)->first,2); set_bond_length((*newc)->last,2); } else set_bond_length(newb,2); } } delete_interface(tmp_intfc); } /* end f_second_order_intfc_propagate2d */
EXPORT void f_curve_propagate2d( Front *fr, POINTER wave, CURVE *oldc, CURVE *newc, double dt) { BOND *oldb = oldc->first; BOND *newb = newc->first; double V[MAXD]; int dim = fr->interf->dim; double L[MAXD],U[MAXD]; /* propagation boundary */ debug_print("f_curve_propagate","Entered f_curve_propagate2d\n"); if ((fr->_point_propagate == NULL) || (oldc == NULL) || (newc == NULL) || (correspond_curve(oldc) != newc) || (correspond_curve(newc) != oldc)) return; set_propagation_bounds(fr,L,U); while (oldb) { if ((oldb != oldc->last) && (!n_pt_propagated(newb->end))) { n_pt_propagated(newb->end) = YES; if (out_of_bound(oldb->end,L,U,dim) && wave_type(oldc) != MOVABLE_BODY_BOUNDARY && wave_type(oldc) != ICE_PARTICLE_BOUNDARY) { Locstate newsl,newsr; Locstate oldsl,oldsr; slsr(newb->end,Hyper_surf_element(newb),Hyper_surf(newc), &newsl,&newsr); slsr(oldb->end,Hyper_surf_element(oldb),Hyper_surf(oldc), &oldsl,&oldsr); ft_assign(newsl,oldsl,fr->sizest); ft_assign(newsr,oldsr,fr->sizest); continue; } point_propagate(fr,wave,oldb->end,newb->end,oldb->next, oldc,dt,V); } if (fr->bond_propagate != NULL) (*fr->bond_propagate)(fr,wave,oldb,newb,oldc,dt); else set_bond_length(newb,dim); /* Update new bond length */ if (oldb == oldc->last) break; oldb = oldb->next; newb = newb->next; } if (wave_type(oldc) == MOVABLE_BODY_BOUNDARY || wave_type(oldc) == ICE_PARTICLE_BOUNDARY) { /* Propagate center of mass */ /* int i,dim; dim = fr->rect_grid->dim; for (i = 0; i < dim; ++i) { center_of_mass_velo(newc)[i] = center_of_mass_velo(oldc)[i]; center_of_mass(newc)[i] = center_of_mass(oldc)[i] + dt*center_of_mass_velo(oldc)[i]; } angular_velo(newc) = angular_velo(oldc); spherical_radius(newc) = spherical_radius(oldc);*/ } debug_print("f_curve_propagate","Leaving f_curve_propagate2d\n"); } /*end f_curve_propagate2d*/
LOCAL void add_intfc_blk_pcs3d( int num_tris, TRI **tris, SURFACE **surfs, BLK_EL0 *blk_el0, P_LINK *hash_table, int h_size) { POINT_COMP_ST *pcs = blk_el0_pcs_els(blk_el0); TRI *t, *tri; SURFACE *s; BOND *b; BOND_TRI **btris; POINT *p; int i,j,k, npcs; TG_PT *tp; Locstate sl,sr; /* reset points in block tris */ for (i = 0; i < num_tris; ++i) { t = tris[i]; for (k = 0; k < 3; ++k) sorted(Point_of_tri(t)[k]) = NO; } //see count_num_pcs3d for alloc //#bjet2 add points in the boundary of the surfaces for (i = 0; i < num_tris; ++i) { t = tris[i]; for (k = 0; k < 3; ++k) { if(!is_side_bdry(t, k)) continue; b = Bond_on_side(t, k); for(j = 0; j < 2; j++) { p = Point_of_tri(t)[(k+j)%3]; //two points on side k if(sorted(p)) continue; sorted(p) = YES; tp = (TG_PT*)find_from_hash_table((POINTER)p, hash_table, h_size); for(btris = Btris(b); btris && *btris; btris++) { tri = (*btris)->tri; s = (*btris)->surface; slsr(p,Hyper_surf_element(tri),Hyper_surf(s),&sl,&sr); npcs = num_pcs_els_in_blk(blk_el0); pcs[npcs].p = tp; pcs[npcs].comp[0] = negative_component(s); pcs[npcs].comp[1] = positive_component(s); pcs[npcs].s[0] = sl; pcs[npcs].s[1] = sr; ++num_pcs_els_in_blk(blk_el0); if(debugging("pcs_cell")) { printf("npcsc %d comp %d %d\n", npcs, pcs[npcs].comp[0], pcs[npcs].comp[1]); print_general_vector("p ", Coords(tp), 3, "\n"); } } //for btris } // for j, two points for a side } // for k, sides for t } // add points in the interior of the surface for (i = 0; i < num_tris; ++i) { t = tris[i]; s = surfs[i]; for (k = 0; k < 3; ++k) { p = Point_of_tri(t)[k]; if (sorted(p) == YES) continue; sorted(p) = YES; tp = (TG_PT*)find_from_hash_table((POINTER)p,hash_table, h_size); slsr(p,Hyper_surf_element(t),Hyper_surf(s),&sl,&sr); npcs = num_pcs_els_in_blk(blk_el0); pcs[npcs].p = tp; pcs[npcs].comp[0] = negative_component(s); pcs[npcs].comp[1] = positive_component(s); pcs[npcs].s[0] = sl; pcs[npcs].s[1] = sr; ++num_pcs_els_in_blk(blk_el0); if(debugging("pcs_cell")) { printf("npcs %d comp %d %d\n", npcs, pcs[npcs].comp[0], pcs[npcs].comp[1]); print_general_vector("p ", Coords(tp), 3, "\n"); } } } } /* end add_intfc_blk_pcs3d */
LOCAL void add_intfc_blk_pcs2d( int num_bonds, BOND **bond, CURVE **curve, BLK_EL0 *blk_el0, P_LINK *hash_table, int h_size) { BOND *b; CURVE *c; POINT *p; int i; TG_PT *tp; POINT_COMP_ST *pcs = blk_el0_pcs_els(blk_el0); Locstate sl,sr; /* reset points in block bonds */ for (i = 0; i < num_bonds; ++i) { b = bond[i]; sorted(b->start) = NO; sorted(b->end) = NO; } /* add interface points inside cell */ for (i = 0; i < num_bonds; ++i) { b = bond[i]; c = curve[i]; p = b->start; if (sorted(p) == NO) { sorted(p) = YES; tp = (TG_PT*)find_from_hash_table((POINTER)p,hash_table, h_size); slsr(p,Hyper_surf_element(b),Hyper_surf(c),&sl,&sr); pcs[num_pcs_els_in_blk(blk_el0)].p = tp; pcs[num_pcs_els_in_blk(blk_el0)].comp[0] = negative_component(c); pcs[num_pcs_els_in_blk(blk_el0)].comp[1] = positive_component(c); pcs[num_pcs_els_in_blk(blk_el0)].s[0] = sl; pcs[num_pcs_els_in_blk(blk_el0)].s[1] = sr; ++num_pcs_els_in_blk(blk_el0); } p = b->end; if (sorted(p)==NO) { sorted(p) = YES; tp = (TG_PT*)find_from_hash_table((POINTER)p,hash_table, h_size); slsr(p,Hyper_surf_element(b),Hyper_surf(c),&sl,&sr); pcs[num_pcs_els_in_blk(blk_el0)].p = tp; pcs[num_pcs_els_in_blk(blk_el0)].comp[0] = negative_component(c); pcs[num_pcs_els_in_blk(blk_el0)].comp[1] = positive_component(c); pcs[num_pcs_els_in_blk(blk_el0)].s[0] = sl; pcs[num_pcs_els_in_blk(blk_el0)].s[1] = sr; ++num_pcs_els_in_blk(blk_el0); } } if (debugging("add_intfc_blk_pcs2d")) { int i; (void) printf("\nblk_el0 %llu\n", ptr2ull(blk_el0)); (void) printf("\t num_pcs_els_in_blk = %d\n", num_pcs_els_in_blk(blk_el0)); for (i=0; i< num_pcs_els_in_blk(blk_el0);++i) { (void) printf("%d: (%g,%g),", i, Coords(pcs[i].p)[0],Coords(pcs[i].p)[1]); (void) printf("comp = (%d,%d)\n", pcs[i].comp[0],pcs[i].comp[1]); } } } /* end add_intfc_blk_pcs2d */