1 #include "libr2c2/track.h"
8 SlopeTool::SlopeTool(Designer &d, 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");
20 for(set<Object *>::const_iterator i=objects.begin(); (!track && i!=objects.end()); ++i)
21 if(Track *t = dynamic_cast<Track *>(*i))
23 unsigned nls = t->get_n_link_slots();
24 for(unsigned j=0; (!track && j<nls); ++j)
25 if(!objects.count((*i)->get_link(j)))
26 track = TrackIter(t, j);
30 while(track && objects.count(track.track()))
32 tracks.push_back(track);
33 total_length += track->get_type().get_path_length(0);
38 void SlopeTool::even_slope(bool smooth)
40 float start_z = tracks.front()->get_snap_node(tracks.front().entry()).position.z;
41 float end_z = tracks.back()->get_snap_node(tracks.back().reverse().entry()).position.z;
43 float length = total_length;
46 float dir = (end_z>start_z)?1:-1;
48 while((end_z-start_z)*dir/length>cur_slope+0.025 && tracks.size()>2)
51 Angle tilt = Geometry::atan(cur_slope);
53 set_slope(tracks.front(), start_z, tilt);
54 start_z += tracks.front()->get_type().get_path_length(0)*dir*cur_slope;
55 length -= tracks.front()->get_type().get_path_length(0);
58 end_z -= tracks.back()->get_type().get_path_length(0)*dir*cur_slope;
59 set_slope(tracks.back(), end_z, tilt);
60 length -= tracks.back()->get_type().get_path_length(0);
65 float cur_z = start_z;
66 Angle tilt = Geometry::atan((end_z-start_z)/length);
67 for(list<TrackIter>::iterator i=tracks.begin(); i!=tracks.end(); ++i)
69 set_slope(*i, cur_z, tilt);
70 cur_z += (*i)->get_type().get_path_length(0)*(end_z-start_z)/length;
74 void SlopeTool::flatten()
77 for(list<TrackIter>::iterator i=tracks.begin(); i!=tracks.end(); ++i)
79 unsigned nsn = (*i)->get_n_snap_nodes();
80 for(unsigned j=0; j<nsn; ++j)
81 z += (*i)->get_snap_node(j).position.z/nsn;
83 z /= static_cast<int>(tracks.size());
85 for(list<TrackIter>::iterator i=tracks.begin(); i!=tracks.end(); ++i)
87 Vector p = (*i)->get_position();
88 (*i)->set_position(Vector(p.x, p.y, z));
89 (*i)->set_tilt(Angle::zero());
93 void SlopeTool::set_slope(const TrackIter &track, float z, const Angle &tilt)
95 const Vector &p = track->get_position();
96 float dz = tan(tilt)*track->get_type().get_path_length(0);
99 track->set_position(Vector(p.x, p.y, z+dz));
100 track->set_tilt(-tilt);
104 track->set_position(Vector(p.x, p.y, z));
105 track->set_tilt(tilt);