-}
-
-int Track::traverse(unsigned i, unsigned route) const
-{
- const vector<Endpoint> &eps=type.get_endpoints();
- if(i>=eps.size())
- throw InvalidParameterValue("Endpoint index out of range");
-
- const Endpoint &ep=eps[i];
-
- if(ep.routes&(1<<route))
- {
- // Find the other endpoint for this route
- for(unsigned j=0; j<eps.size(); ++j)
- if((eps[j].routes&(1<<route)) && j!=i)
- return j;
- }
- else
- {
- // Find an endpoint that's connected to this one and has the requested route
- for(unsigned j=0; j<eps.size(); ++j)
- if((eps[j].routes&(1<<route)) && (eps[j].routes&ep.routes))
- return j;
- }
-
- return -1;
-}
-
-Point Track::get_point(unsigned epi, unsigned route, float d) const
-{
- const vector<Endpoint> &eps=type.get_endpoints();
- if(epi>=eps.size())
- throw InvalidParameterValue("Endpoint index out of range");
-
- float x=eps[epi].pos.x;
- float y=eps[epi].pos.y;
-
- const vector<TrackPart> &parts=type.get_parts();
- const TrackPart *last_part=0;
- while(1)
- {
- for(vector<TrackPart>::const_iterator i=parts.begin(); i!=parts.end(); ++i)
- {
- if((eps[epi].routes&(1<<route)) && i->route!=route)
- continue;
- if(&*i==last_part)
- continue;
-
- vector<Endpoint> part_eps;
- i->collect_endpoints(part_eps);
- for(unsigned j=0; j<part_eps.size(); ++j)
- {
- float dx=part_eps[j].pos.x-x;
- float dy=part_eps[j].pos.y-y;
- if(dx*dx+dy*dy<1e-6)
- {
- float plen=i->length;
- if(i->radius)
- plen*=abs(i->radius);
- if(d<plen)
- {
- if(j==1)
- d=plen-d;
- Point p=i->get_point(d);
- float c=cos(rot);
- float s=sin(rot);
- return Point(pos.x+c*p.x-s*p.y, pos.y+c*p.y+s*p.x);
- }
- else if(part_eps.size()>1)
- {
- d-=plen;
- x=part_eps[1-j].pos.x;
- y=part_eps[1-j].pos.y;
- last_part=&*i;
- i=parts.begin();
- break;
- }
- else
- return pos;
- }
- }
- }