Index: trunk/src_plugins/rbs_routing/seq.c =================================================================== --- trunk/src_plugins/rbs_routing/seq.c (revision 38823) +++ trunk/src_plugins/rbs_routing/seq.c (revision 38824) @@ -27,28 +27,81 @@ rbsq->last_x = RBSR_G2R(start->x); rbsq->last_y = RBSR_G2R(start->y); + rbsq->path[0].dir = GRBS_ADIR_INC; + rbsq->path[0].pt = start; + rbsq->used = 1; + return 0; } +RND_INLINE int rbsr_seq_redraw(rbsr_seq_t *rbsq) +{ + grbs_t *grbs = &rbsq->map.grbs; + grbs_path_remove_2net_addrs(grbs, rbsq->tn); + grbs_snapshot_restore(rbsq->snap); +} + int rbsr_seq_consider(rbsr_seq_t *rbsq, rnd_coord_t tx, rnd_coord_t ty) { grbs_point_t *end; + rnd_coord_t ptcx, ptcy; + double l1x, l1y, l2x, l2y, px, py, side, dist2, dx, dy, cop2; + grbs_arc_dir_t dir; - rnd_trace("consider: "); + end = rbsr_find_point(&rbsq->map, tx, ty); + if (end == NULL) { + int need_redraw = 0; + if (rbsq->consider.dir != RBS_ADIR_invalid) + need_redraw = 1; - end = rbsr_find_point(&rbsq->map, tx, ty); - if (end != NULL) { - rnd_trace("found pt\n"); + rbsq->consider.dir = RBS_ADIR_invalid; + if (need_redraw) + rbsr_seq_redraw(rbsq); + return -1; } - else - rnd_trace("nope\n"); - return -1; + ptcx = RBSR_G2R(end->x); + ptcy = RBSR_G2R(end->y); + + cop2 = RBSR_G2R(end->copper); + cop2 = cop2 * cop2; + + dx = tx - ptcx; dy = ty - ptcy; + dist2 = dx*dx + dy*dy; + + if (dist2 > cop2) { + /* project target point onto the line between last end and center of the + point; if it is to the right, go ccw, if to the left go cw, if in the + center go incident */ + /* decide direction from cross product; line is rbsq->last_* -> ptc* */ + l1x = rbsq->last_x; l1y = rbsq->last_y; + l2x = ptcx, l2y = ptcy; + px = tx; py = ty; + + side = (l2x - l1x) * (py - l1y) - (l2y - l1y) * (px - l1x); + rnd_trace(" side: %f %s\n", side, (side < 0) ? "cw" : "ccw"); + dir = (side < 0) ? GRBS_ADIR_CONVEX_CW : GRBS_ADIR_CONVEX_CCW; + } + else { + rnd_trace(" incident\n"); + dir = GRBS_ADIR_INC; + } + + if ((rbsq->consider.pt == end) && (rbsq->consider.dir == dir)) + return 0; /* do not redraw if there's no change */ + + rbsq->consider.pt = end; + rbsq->consider.dir = dir; + + return rbsr_seq_redraw(rbsq); } -int rbsr_seq_accept(rbsr_seq_t *rbss) +int rbsr_seq_accept(rbsr_seq_t *rbsq) { - return -1; + rbsq->path[rbsq->used] = rbsq->consider; + rbsq->used++; +TODO("update last_x and last_y"); + return 0; } Index: trunk/src_plugins/rbs_routing/seq.h =================================================================== --- trunk/src_plugins/rbs_routing/seq.h (revision 38823) +++ trunk/src_plugins/rbs_routing/seq.h (revision 38824) @@ -7,14 +7,20 @@ #include #define RBSR_SEQ_MAX 256 +#define RBS_ADIR_invalid -42 +typedef struct rbsr_seq_addr_s { + grbs_point_t *pt; + grbs_arc_dir_t dir; +} rbsr_seq_addr_t; + typedef struct rbsr_seq_s { rbsr_map_t map; grbs_2net_t *tn; - grbs_addr_t path[RBSR_SEQ_MAX]; + rbsr_seq_addr_t consider; /* next point to route to, before click; valid if .adir != RBS_ADIR_invalid */ + rbsr_seq_addr_t path[RBSR_SEQ_MAX]; long used; /* number of path items already accepted */ - grbs_addr_t consider; rnd_coord_t last_x, last_y; /* last point coords on the path for the tool code */