X-Git-Url: https://git.donarmstrong.com/?a=blobdiff_plain;f=lily%2Fspaceable-grob.cc;h=96313acf4abd4629f8806a6d87f9ee9f9a94e553;hb=4b5d14fc3b5ea19d4cf71d2222ddb3964122eeb2;hp=bb6afc11e6721cbceed36953f7b7be0ea5933a24;hpb=27c10914b6b29e751a97d0e73be86f101e7069a7;p=lilypond.git diff --git a/lily/spaceable-grob.cc b/lily/spaceable-grob.cc index bb6afc11e6..96313acf4a 100644 --- a/lily/spaceable-grob.cc +++ b/lily/spaceable-grob.cc @@ -1,90 +1,133 @@ -/* - spaceable-grob.cc -- implement Spaceable_grob - +/* + spaceable-grob.cc -- implement Spaceable_grob + source file of the GNU LilyPond music typesetter - - (c) 2000--2002 Han-Wen Nienhuys - - */ + + (c) 2000--2006 Han-Wen Nienhuys +*/ #include "spaceable-grob.hh" -#include "grob.hh" + +#include + #include "warn.hh" #include "spring.hh" -#include "group-interface.hh" +#include "pointer-group-interface.hh" +#include "grob.hh" +#include "paper-column.hh" SCM -Spaceable_grob::get_minimum_distances (Grob*me) +Spaceable_grob::get_minimum_distances (Grob *me) { - return me->get_grob_property ("minimum-distances"); + return me->get_object ("minimum-distances"); } /*todo: merge code of spring & rod? */ void -Spaceable_grob::add_rod (Grob *me , Grob * p, Real d) +Spaceable_grob::add_rod (Grob *me, Grob *p, Real d) { + // printf ("rod %lf\n", d); + if (d < 0) + return; + + if (isinf (d)) + programming_error ("infinite rod"); + SCM mins = get_minimum_distances (me); - SCM newdist = gh_double2scm (d); - for (SCM s = mins; gh_pair_p (s); s = ly_cdr (s)) + SCM newdist = scm_from_double (d); + for (SCM s = mins; scm_is_pair (s); s = scm_cdr (s)) { - SCM dist = ly_car (s); - if (ly_car (dist) == p->self_scm ()) + SCM dist = scm_car (s); + if (scm_car (dist) == p->self_scm ()) { - gh_set_cdr_x (dist, scm_max (ly_cdr (dist), - newdist)); - return ; + scm_set_cdr_x (dist, scm_max (scm_cdr (dist), + newdist)); + return; } } - mins = gh_cons (gh_cons (p->self_scm (), newdist), mins); - me->set_grob_property ("minimum-distances", mins); + if (Paper_column::get_rank (p) < Paper_column::get_rank (me)) + programming_error ("Adding reverse rod"); + + mins = scm_cons (scm_cons (p->self_scm (), newdist), mins); + me->set_object ("minimum-distances", mins); } void -Spaceable_grob::add_spring (Grob*me, Grob * p, Real d, Real strength, bool expand_only) +Spaceable_grob::add_spring (Grob *me, Grob *other, + Real distance, Real inverse_strength) { - if (d < 0.0 || strength <= 0.0) + if (distance <= 0.0 || inverse_strength < 0.0) + { + programming_error ("adding reverse spring, setting to unit"); + distance = 1.0; + inverse_strength = 1.0; + } + + if (isinf (distance) || isnan (distance) + || isnan (inverse_strength)) { - programming_error ("Adding reverse spring! Setting to unit spring"); - d = 1.0; - strength = 1.0; + /* strength == INF is possible. It means fixed distance. */ + programming_error ("insane distance found"); + distance = 1.0; + inverse_strength = 1.0; } - + #ifndef NDEBUG - SCM mins = me->get_grob_property ("ideal-distances"); - for (SCM s = mins; gh_pair_p (s); s = ly_cdr (s)) + SCM mins = me->get_object ("ideal-distances"); + for (SCM s = mins; scm_is_pair (s); s = scm_cdr (s)) { - Spring_smob * sp = unsmob_spring(ly_car (s)); - if (sp->other_ == p) + Spring_smob *sp = unsmob_spring (scm_car (s)); + if (sp->other_ == other) { programming_error ("already have that spring"); - return ; + return; } } #endif - + Spring_smob spring; - spring.strength_f_ = strength; - spring.distance_f_ = d; - spring.expand_only_b_ = expand_only; - spring.other_ = p; - - Group_interface::add_thing (me, ly_symbol2scm ("ideal-distances"), spring.smobbed_copy ()); -} + spring.inverse_strength_ = inverse_strength; + spring.distance_ = distance; + spring.other_ = other; + SCM ideal = me->get_object ("ideal-distances"); + ideal = scm_cons (spring.smobbed_copy (), ideal); + me->set_object ("ideal-distances", ideal); +} void -Spaceable_grob::remove_interface (Grob*me) +Spaceable_grob::get_spring (Grob *me, Grob *other, Real *dist, Real *inv_strength) { - me->remove_grob_property ("minimum-distances"); - me->remove_grob_property ("ideal-distances"); + for (SCM s = me->get_object ("ideal-distances"); + scm_is_pair (s); s = scm_cdr (s)) + { + Spring_smob *spring = unsmob_spring (scm_car (s)); + if (spring && spring->other_ == other) + { + *dist = spring->distance_; + *inv_strength = spring->inverse_strength_; + } + } } +void +Spaceable_grob::remove_interface (Grob *me) +{ + me->set_object ("minimum-distances", SCM_EOL); + me->set_object ("spacing-wishes", SCM_EOL); + me->set_object ("ideal-distances", SCM_EOL); +} -ADD_INTERFACE (Spaceable,"spaceable-grob-interface", - "An grob (a Paper_column) that takes part in the -spacing problem. ", - "measure-length penalty minimum-distances ideal-distances -left-neighbors right-neighbors"); +ADD_INTERFACE (Spaceable_grob, "spaceable-grob-interface", + "A layout object that takes part in the spacing problem. ", + /* properties */ + "ideal-distances " + "keep-inside-line " + "left-neighbors " + "measure-length " + "minimum-distances " + "right-neighbors " + "spacing-wishes");