1 #include "libr2c2/track.h"
8 SlopeTool::SlopeTool(Designer &d, Input::Keyboard &k, Input::Mouse &m, const set<Object *> &objects):
12 for(set<Object *>::const_iterator i=objects.begin(); i!=objects.end(); ++i)
13 if(!dynamic_cast<Track *>(*i) || (*i)->get_n_link_slots()!=2)
15 set_status("Must have linear tracks only");
21 for(set<Object *>::const_iterator i=objects.begin(); (!track && i!=objects.end()); ++i)
22 if(Track *t = dynamic_cast<Track *>(*i))
24 unsigned nls = t->get_n_link_slots();
25 for(unsigned j=0; (!track && j<nls); ++j)
26 if(!objects.count((*i)->get_link(j)))
27 track = TrackIter(t, j);
31 while(track && objects.count(track.track()))
33 tracks.push_back(track);
34 total_length += track->get_type().get_path_length(0);
39 void SlopeTool::even_slope(bool smooth)
41 float start_z = tracks.front()->get_snap_node(tracks.front().entry()).position.z;
42 float end_z = tracks.back()->get_snap_node(tracks.back().reverse().entry()).position.z;
44 float length = total_length;
47 float dir = (end_z>start_z)?1:-1;
49 while((end_z-start_z)*dir/length>cur_slope+0.025 && tracks.size()>2)
52 Angle tilt = Geometry::atan(cur_slope);
54 set_slope(tracks.front(), start_z, tilt);
55 start_z += tracks.front()->get_type().get_path_length(0)*dir*cur_slope;
56 length -= tracks.front()->get_type().get_path_length(0);
59 end_z -= tracks.back()->get_type().get_path_length(0)*dir*cur_slope;
60 set_slope(tracks.back(), end_z, tilt);
61 length -= tracks.back()->get_type().get_path_length(0);
66 float cur_z = start_z;
67 Angle tilt = Geometry::atan((end_z-start_z)/length);
68 for(list<TrackIter>::iterator i=tracks.begin(); i!=tracks.end(); ++i)
70 set_slope(*i, cur_z, tilt);
71 cur_z += (*i)->get_type().get_path_length(0)*(end_z-start_z)/length;
75 void SlopeTool::flatten()
78 for(list<TrackIter>::iterator i=tracks.begin(); i!=tracks.end(); ++i)
80 unsigned nsn = (*i)->get_n_snap_nodes();
81 for(unsigned j=0; j<nsn; ++j)
82 z += (*i)->get_snap_node(j).position.z/nsn;
84 z /= static_cast<int>(tracks.size());
86 for(list<TrackIter>::iterator i=tracks.begin(); i!=tracks.end(); ++i)
88 Vector p = (*i)->get_position();
89 (*i)->set_position(Vector(p.x, p.y, z));
90 (*i)->set_tilt(Angle::zero());
94 void SlopeTool::set_slope(const TrackIter &track, float z, const Angle &tilt)
96 const Vector &p = track->get_position();
97 float dz = tan(tilt)*track->get_type().get_path_length(0);
100 track->set_position(Vector(p.x, p.y, z+dz));
101 track->set_tilt(-tilt);
105 track->set_position(Vector(p.x, p.y, z));
106 track->set_tilt(tilt);