6 #include "leastsquares.hh"
23 Stem_info(const Stem*);
25 Stem_info::Stem_info(const Stem*s)
29 idealy = MAX(dir*s->top, dir*s->bot);
30 miny = MAX(dir*s->minnote, dir*s-> maxnote);
31 assert(miny <= idealy);
47 stems.bottom().add(s);
48 s->print_flag = false;
52 Beam::set_default_dir()
55 dirs[0]=0; dirs[1] =0;
56 for (PCursor<Stem*> sc(stems); sc.ok(); sc++) {
57 sc->set_default_dir();
58 dirs[(sc->dir+1)/2] ++;
60 dir = (dirs[0] > dirs[1]) ? -1 : 1;
61 for (PCursor<Stem*> sc(stems); sc.ok(); sc++) {
67 should use minimum energy formulation (cf linespacing)
72 svec<Stem_info> sinfo;
73 for (PCursor<Stem* >sc(stems); sc.ok(); sc++) {
74 sc->set_default_extents();
78 Real leftx = sinfo[0].x;
80 for (int i=0; i < sinfo.sz(); i++) {
82 l.input.add(Offset(sinfo[i].x, sinfo[i].idealy));
85 l.minimise(slope, left_pos);
87 for (int i=0; i < sinfo.sz(); i++) {
88 Real y = sinfo[i].x * slope + left_pos;
89 Real my = sinfo[i].miny;
103 PCursor<Stem*> s(stems);
105 for (; s.ok() ; s++) {
106 Real x = s->hpos()-x0;
107 s->set_stemend(left_pos + slope * x);
114 assert(stems.size()>1);
127 for (PCursor<Stem*> i(stems); i.ok(); i++)
128 i->beams_left = i->beams_right = intlog2(ABS(i->flag)) - 2;
130 stems.top()->beams_left = 0;
131 stems.bottom()->beams_right = 0;
140 Beam::broken_at(const PCol *, const PCol *) const
142 return new Beam(*this);
148 left = (*stems.top()) ->pcol_;
149 right = (*stems.bottom())->pcol_;
155 return output->extent().y;
161 Beam * me = (Beam*) this; // ugh
162 return Interval( (*me->stems.top()) ->hpos(),
163 (*me->stems.bottom()) ->hpos() );
166 beams to go with one stem.
169 Beam::stem_beams(Stem *here, Stem *next, Stem *prev)
171 assert( !next || next->hpos() > here->hpos() );
172 assert( !prev || prev->hpos() < here->hpos() );
173 Real dy=paper()->internote()*2;
174 Real stemdx = paper()->rule_thickness();
175 Real sl = slope*paper()->internote();
179 /* half beams extending to the left. */
181 int lhalfs= lhalfs = here->beams_left - prev->beams_right ;
182 int lwholebeams= here->beams_left <? prev->beams_right ;
183 Real w = (here->hpos() - prev->hpos())/4;
184 Atom a = paper()->lookup_->beam(sl, w);
185 a.translate(Offset (-w, -w * sl));
186 for (int j = 0; j < lhalfs; j++) {
188 b.translate(Offset(0, -dir * dy * (lwholebeams+j)));
194 int rhalfs = here->beams_right - next->beams_left;
195 int rwholebeams = here->beams_right <? next->beams_left; // g++
197 Real w = next->hpos() - here->hpos();
198 Atom a = paper()->lookup_->beam(sl, w + stemdx);
201 for (; j < rwholebeams; j++) {
203 b.translate(Offset(0, -dir * dy * j));
207 a = paper()->lookup_->beam(sl, w);
209 for (; j < rwholebeams + rhalfs; j++) {
211 b.translate(Offset(0, -dir * dy * j));
216 leftbeams.add(rightbeams);
222 Beam::brew_molecule()
224 assert(left->line == right->line);
225 Real inter=paper()->internote();
226 Real sl = slope*inter;
228 output = new Molecule;
230 Real x0 = stems.top()->hpos();
232 for (PCursor<Stem*> i(stems); i.ok(); i++) {
233 PCursor<Stem*> p(i-1);
234 PCursor<Stem*> n(i+1);
235 Stem * prev = p.ok() ? p.ptr() : 0;
236 Stem * next = n.ok() ? n.ptr() : 0;
238 Molecule sb = stem_beams(i, next, prev);
239 Real x = i->hpos()-x0;
240 sb.translate(Offset(x, (x * slope + left_pos)* inter));
243 output->translate(Offset(x0 - left->hpos,0));
250 mtor << "{ slope " <<slope << "left ypos " << left_pos;