2002-04-21 Han-Wen <hanwen@cs.uu.nl>
+ * scm/lily.scm (ly-load): use primitive-load for loading.
+
+ * lily/misc.cc: remove quantise_iv()
+
+ * lily/*.cc: pass read-only arrays by reference.
+
+ * lily/grob.cc (common_refpoint_of_array): new function. Try to
+ use common_refpoint_of_{array, list} when possible.
+
* lily/include/accidental-placement.hh: new file.
* lily/accidental-placement.cc (alignment_callback): position
@section Accidentals
-Accidentals are currently in a development stage.
@lilypondfile[printfilename]{accidental.ly}
+@lilypondfile[printfilename]{accidental-placement.ly}
+
@lilypondfile[printfilename]{accidental-single-double.ly}
@lilypondfile[printfilename]{accidentals.ly}
--- /dev/null
+\header {
+ texidoc ="Accidentals are placed as closely as possible.
+Accidentals in corresponding octaves are aligned."
+}
+
+
+\score { \notes \context Voice \relative c' {
+ cis4
+ <cis4 d es fis gis ases bes ces d dis >
+ <bes'! fis!>
+ <bes! cis!>
+ <c! es ges beses>
+}
+\paper { linewidth = -1. }
+ }
tie_break_reminder);
Side_position_interface::add_support (key_item_p_, support_l);
- support_l->set_grob_property ("accidentals-grob", key_item_p_->self_scm ());
+ support_l->set_grob_property ("accidental-grob", key_item_p_->self_scm ());
}
*/
-
+#include <math.h>
+#include <libc-extension.hh>
#include "item.hh"
#include "skyline.hh"
#include "music.hh"
#include "accidental-placement.hh"
+MAKE_SCHEME_CALLBACK(Accidental_placement,extent_callback, 2);
+SCM
+Accidental_placement::extent_callback(SCM s, SCM axis)
+{
+ Grob * me =unsmob_grob (s);
+ Axis a = Axis (gh_scm2int (axis));
+
+ assert (a == X_AXIS);
+
+ SCM w = position_accidentals (me);
+ return w;
+}
+
MAKE_SCHEME_CALLBACK(Accidental_placement,alignment_callback, 2);
SCM
Accidental_placement::alignment_callback(SCM s, SCM )
Grob * me =unsmob_grob (s);
Grob * par = me->get_parent (X_AXIS);
- if (!to_boolean (par->get_grob_property ("done")))
- {
- par->set_grob_property ("done", SCM_BOOL_T);
- position_accidentals (par);
- }
-
+ if (!to_boolean (par->get_grob_property ("alignment-done")))
+ {
+ par->set_grob_property ("alignment-done", SCM_BOOL_T);
+ position_accidentals (par);
+ }
return gh_int2scm (0);
}
+
+
void
Accidental_placement::add_accidental (Grob* me, Grob* a)
{
me->set_grob_property ("accidentals", accs);
}
-
struct Accidental_placement_entry
{
Array<Skyline_entry> left_skyline_;
Interval vertical_extent_;
Array<Box> extents_;
Link_array<Grob> grobs_;
+ Real offset_;
int notename_;
+ Accidental_placement_entry()
+ {
+ offset_ =0.0;
+ notename_ = -1;
+ }
};
+
int ape_compare (Accidental_placement_entry *const &a,
Accidental_placement_entry *const &b)
{
return sign (a->vertical_extent_.length () - b->vertical_extent_.length());
}
-void
+/*
+ Return: width as SCM interval.
+
+
+ This routine computes placements of accidentals. During
+ add_accidental(), accidentals are already grouped by note, so that
+ octaves are placed above each other; they form columns. Then the
+ columns are sorted: the biggest columns go closest to the note.
+ Then the columns are spaced as closely as possible (using skyline
+ spacing).
+
+
+ TODO: more advanced placement. Typically, the accs should be placed
+ to form a C shape, like this
+
+
+ ##
+ b b
+ # #
+ b
+ b b
+
+ The naturals should be left of the C as well; they should
+ be separate accs.
+
+ TODO: Try to combine Apes before sorting them: this will allow a
+ better placement.
+
+ Note that this placement problem is almost certainly NP hard, so we
+ just use a simple strategy, not an optimal choice.
+*/
+
+SCM
Accidental_placement::position_accidentals (Grob * me)
{
SCM accs = me->get_grob_property ("accidentals");
Grob *commony =0 ;
for (int i= apes.size (); i--;)
- for (int j = apes[i]->grobs_.size(); j--;)
- {
- Grob * a = apes[i]->grobs_[j];
-
- if (commony)
- commony =commony->common_refpoint (a, Y_AXIS);
- else
- commony =a;
- }
+ commony = common_refpoint_of_array (apes[i]->grobs_, commony, Y_AXIS);
+ Link_array<Grob> heads;
for (int i= apes.size (); i--;)
{
- Interval y ;
-
+ Accidental_placement_entry * ape = apes[i];
+ ape->left_skyline_ = empty_skyline ( LEFT);
+ ape->right_skyline_ = empty_skyline ( RIGHT);
+
for (int j = apes[i]->grobs_.size(); j--;)
{
Grob * a = apes[i]->grobs_[j];
b[X_AXIS] = a->extent (me, X_AXIS);
b[Y_AXIS] = a->extent (commony, Y_AXIS);
- y.unite (b[Y_AXIS]);
- apes[i]->extents_.push (b);
+ Grob *head = a->get_parent (Y_AXIS);
+ heads.push (head);
+ commony = commony->common_refpoint (head, Y_AXIS);
+
+ ape->extents_.push (b);
+
+
+ /*
+ TODO: replace the extents of a flat by combination of two
+ bboxes, so that we use the shape of the flat better.
+ */
+ insert_extent_into_skyline (&ape->left_skyline_, b, Y_AXIS, LEFT);
+ insert_extent_into_skyline (&ape->right_skyline_ , b,Y_AXIS, RIGHT);
}
+ }
+ for (int i = apes.size(); i--;)
+ {
+ Interval y ;
+
+ for (int j = apes[i]->extents_.size(); j--;)
+ {
+ y.unite (apes[i]->extents_[j][Y_AXIS]);
+ }
apes[i]->vertical_extent_ = y;
}
- for (int i= apes.size (); i--;)
+ apes.sort (&ape_compare);
+
+ Accidental_placement_entry * head_ape = new Accidental_placement_entry;
+ Grob *commonx = common_refpoint_of_array (heads, me, X_AXIS);
+ Array<Skyline_entry> head_skyline (empty_skyline (LEFT));
+ Array<Box> head_extents;
+ for (int i = heads.size(); i--;)
{
- Accidental_placement_entry * ape = apes[i];
- ape->left_skyline_ = extents_to_skyline (apes[i]->extents_, Y_AXIS, LEFT);
- ape->right_skyline_ = extents_to_skyline (apes[i]->extents_, Y_AXIS, RIGHT);
+ Box b(heads[i]->extent (commonx, X_AXIS),
+ heads[i]->extent (commony, Y_AXIS));
+
+ insert_extent_into_skyline (&head_skyline, b , Y_AXIS, LEFT);
}
- apes.sort (&ape_compare);
+ head_ape-> left_skyline_ = head_skyline;
+ head_ape->offset_ = 0.0;
- for (int i= apes.size ()-1; i-- > 0;)
+ SCM rs = me->get_grob_property ("right-padding");
+ if (gh_number_p (rs))
+ head_ape->offset_ -= gh_scm2double (rs);
+
+ Real padding = 0.1;
+ apes.push (head_ape);
+ for (int i= apes.size () -1 ; i-- > 0;)
{
Accidental_placement_entry *ape = apes[i];
- Real here = 0.0;
-
- Real d = skyline_meshing_distance (ape->right_skyline_, apes[i+1]->left_skyline_);
+ Real d = 0.0;
+ /*
+ confusing naming: left_skyline is a skyline pointing to the
+ left. It is on the right of the curent entry.
+ */
+
+ int j = i+1;
+ do {
+ Array<Skyline_entry> const *right_sky =
+ (j < apes.size())
+ ? &apes[j]->left_skyline_
+ : &head_skyline;
+
+ d = - skyline_meshing_distance (ape->right_skyline_,
+ *right_sky);
+
+ if (!isinf(d)
+ || j + 1 == apes.size())
+ break;
+
+ j = j+ 1;
+ } while (1);
+
+ if (isinf(d))
+ d = 0.0;
+
+ d -= padding;
+ ape->offset_ += apes[j]->offset_ + d;
+ }
- here += d;
+ apes.pop();
+ for (int i = apes.size(); i--;)
+ {
+ Accidental_placement_entry* ape = apes[i];
for (int j = ape->grobs_.size(); j--;)
{
- ape->grobs_[j]->translate_axis (here, X_AXIS);
+ ape->grobs_[j]->translate_axis (ape->offset_, X_AXIS);
}
}
+
+ Interval left_extent, right_extent;
+ Accidental_placement_entry *ape = apes[0];
+
+ for (int i = ape->extents_.size(); i--;)
+ left_extent.unite (ape->offset_ + ape->extents_[i][X_AXIS]);
+
+ ape = apes.top();
+ for (int i = ape->extents_.size(); i--;)
+ right_extent.unite (ape->offset_ + ape->extents_[i][X_AXIS]);
+
+ SCM ls = me->get_grob_property ("left-padding");
+ if (gh_number_p (rs))
+ left_extent[LEFT] -= gh_scm2double (ls);
+
+
+ Interval width(left_extent[LEFT], right_extent[RIGHT]);
+
+ SCM scm_width = ly_interval2scm (width);
+ me->set_extent (scm_width, X_AXIS);
+
for (int i = apes.size(); i--;)
delete apes[i];
+
+ return scm_width;
}
ADD_INTERFACE(Accidental_placement,
"accidental-placement-interface",
"Take care of complex accidental collisions.",
- "accidentals done")
+ "left-padding right-padding accidentals alignment-done")
#include "item.hh"
#include "molecule.hh"
+/*
+ TODO: insert support for smaller cautionaries, tie-break-reminders.
+ Either here or in new-accidental-engraver.
+
+ 'accidentals should go, for a single 'accidental property -- see
+ accidental-placement.cc
+
+*/
class Accidental_interface
{
public:
style +
to_str (gh_scm2int(entry))));
- mol.add_at_edge (X_AXIS, RIGHT, acc, 0.0);
+ mol.add_at_edge (X_AXIS, RIGHT, acc, 0.1);
}
+#if 0
+ // TODO.
if (to_boolean (me->get_grob_property ("parenthesize")))
mol = parenthesize (me, mol);
-
+#endif
return mol.smobbed_copy();
}
ADD_INTERFACE(Accidental_interface, "accidental-interface",
"a single accidental",
- "accidentals parenthesize");
+ "style accidentals");
if (gh_pair_p (dims) && gh_number_p (ly_car (dims))
&& gh_number_p (ly_cdr (dims)))
{
- staffline_p_->set_extent_callback (Grob::preset_extent_proc, Y_AXIS);
+ staffline_p_->set_extent (Grob::preset_extent_proc, Y_AXIS);
staffline_p_->set_grob_property ("extent-Y", dims);
}
Grob *me = unsmob_grob (element_smob);
Axis a = (Axis) gh_scm2int (scm_axis);
- Grob * common = (Grob*) me;
-
- for (SCM s = me->get_grob_property ("elements"); gh_pair_p (s); s = ly_cdr (s))
- {
- Grob * se = unsmob_grob (ly_car (s));
- common = se->common_refpoint (common, a);
- }
+ Grob * common = common_refpoint_of_list (me->get_grob_property ("elements"), me, a);
Real my_coord = me->relative_coordinate (common, a);
Interval r (relative_group_extent (a, common, me->get_grob_property ("elements")));
}
if (a1 != X_AXIS && a2 != X_AXIS)
- me->set_extent_callback (SCM_EOL, X_AXIS);
+ me->set_extent (SCM_EOL, X_AXIS);
if (a1 != Y_AXIS && a2 != Y_AXIS)
- me->set_extent_callback (SCM_EOL, Y_AXIS);
+ me->set_extent (SCM_EOL, Y_AXIS);
/*
why so convoluted ? (fixme/documentme?)
*/
if (me->has_extent_callback_b (Grob::molecule_extent_proc, a1))
- me->set_extent_callback (Axis_group_interface::group_extent_callback_proc,a1);
+ me->set_extent (Axis_group_interface::group_extent_callback_proc,a1);
if (me->has_extent_callback_b (Grob::molecule_extent_proc, a2))
- me->set_extent_callback (Axis_group_interface::group_extent_callback_proc,a2);
+ me->set_extent (Axis_group_interface::group_extent_callback_proc,a2);
}
Link_array<Grob>
if (!gh_string_p (g))
{
me->set_grob_property ("molecule-callback", SCM_EOL);
- me->set_extent_callback (SCM_EOL, X_AXIS);
+ me->set_extent (SCM_EOL, X_AXIS);
// leave y_extent for spanbar?
}
Simple_spacer*
-Break_algorithm::generate_spacing_problem (Link_array<Grob> curline, Interval line) const
+Break_algorithm::generate_spacing_problem (Link_array<Grob> const &curline,
+ Interval line) const
{
Simple_spacer * sp = new Simple_spacer;
mutable_property_alist_ = SCM_EOL;
immutable_property_alist_ = SCM_EOL;
- set_extent_callback (SCM_EOL, Y_AXIS);
- set_extent_callback (SCM_EOL, X_AXIS);
+ set_extent (SCM_EOL, Y_AXIS);
+ set_extent (SCM_EOL, X_AXIS);
for (int a= X_AXIS; a <= Y_AXIS; a++)
{
Grob *
-Grob::common_refpoint (SCM elist, Axis a) const
+common_refpoint_of_list (SCM elist, Grob *common, Axis a)
{
- Grob * common = (Grob*) this;
for (; gh_pair_p (elist); elist = ly_cdr (elist))
{
Grob * s = unsmob_grob (ly_car (elist));
- if (s)
+ if (!s)
+ continue;
+ if (common)
+ common = common->common_refpoint (s, a);
+ else
+ common = s;
+ }
+
+ return common;
+}
+
+
+
+Grob *
+common_refpoint_of_array (Link_array<Grob> const &arr, Grob *common, Axis a)
+{
+ for (int i = arr.size() ; i--; )
+ {
+ Grob * s = arr[i];
+ if (!s)
+ continue;
+
+ if (common)
common = common->common_refpoint (s, a);
+ else
+ common = s;
}
return common;
}
-bool
-Grob::has_extent_callback_b (Axis a) const
-{
- return gh_procedure_p (dim_cache_[a].dimension_);
-}
-
bool
Grob::has_offset_callback_b (SCM cb, Axis a)const
{
}
void
-Grob::set_extent_callback (SCM dc, Axis a)
+Grob::set_extent (SCM dc, Axis a)
{
dim_cache_[a].dimension_ =dc;
}
{
public:
DECLARE_SCHEME_CALLBACK (alignment_callback, (SCM element, SCM axis));
+ DECLARE_SCHEME_CALLBACK (extent_callback, (SCM element, SCM axis));
static void add_accidental (Grob *,Grob* );
- static void position_accidentals (Grob* );
+ static SCM position_accidentals (Grob* );
static bool has_interface (Grob*);
};
#endif /* ACCIDENTAL_PLACEMENT_HH */
void solve_line (Column_x_positions*) const;
/// does curline fit on the paper?
- bool feasible (Link_array<Grob>) const;
+ bool feasible (Link_array<Grob> const &) const;
- Simple_spacer* generate_spacing_problem (Link_array<Grob>, Interval) const;
+ Simple_spacer* generate_spacing_problem (Link_array<Grob> const &, Interval) const;
virtual Array<Column_x_positions> do_solve () const=0;
#include "compare.hh"
INSTANTIATE_COMPARE (Duration, Duration::compare);
DECLARE_UNSMOB(Duration,duration);
-// int compare (Array<Duration>*, Array<Duration>*);
+
#endif // DURATION_HH
Dimension_cache dim_cache_[NO_AXES];
public:
+
bool empty_b (Axis a) const;
Interval extent (Grob * refpoint, Axis) const;
Find the group-element which has both #this# and #s#
*/
Grob*common_refpoint (Grob const* s, Axis a) const;
- Grob*common_refpoint (SCM elt_list, Axis a) const;
+
// duh. slim down interface here. (todo)
bool has_offset_callback_b (SCM callback, Axis)const;
void add_offset_callback (SCM callback, Axis);
bool has_extent_callback_b (SCM, Axis)const;
- void set_extent_callback (SCM , Axis);
- bool has_extent_callback_b (Axis) const;
+ void set_extent (SCM , Axis);
/**
Spanner* unsmob_spanner (SCM );
Item* unsmob_item (SCM );
+Grob*common_refpoint_of_list (SCM elt_list, Grob * , Axis a);
+Grob*common_refpoint_of_array (Link_array<Grob> const&, Grob * , Axis a);
#endif // STAFFELEM_HH
/**
Least squares minimisation in 2 variables.
*/
-void minimise_least_squares (Real * coef, Real * offset, Array<Offset>);
+void minimise_least_squares (Real * coef, Real * offset, Array<Offset> const &);
#endif // LEASTSQUARE_HH
else return 0;
}
-Interval quantise_iv (Array<Real> positions, Real x);
+
#endif
Simple_spacer ();
void solve (Column_x_positions *, bool) const;
- void add_columns (Link_array<Grob>);
+ void add_columns (Link_array<Grob>const &);
void my_solve_linelen ();
void my_solve_natural_len ();
Real active_springs_stiffness () const;
Skyline_entry (Interval, Real);
};
-void
-insert_extent_into_skyline (Array<Skyline_entry> *line, Box b, Axis line_axis,
- Direction d);
+
+void insert_extent_into_skyline (Array<Skyline_entry> *line, Box b, Axis line_axis,
+ Direction d);
Array<Skyline_entry>
-extents_to_skyline (Array<Box> extents, Axis a, Direction d);
+extents_to_skyline (Array<Box> const & extents, Axis a, Direction d);
+Array<Skyline_entry> empty_skyline (Direction d);
Real
-skyline_meshing_distance (Array<Skyline_entry> buildings,
- Array<Skyline_entry> clouds);
+skyline_meshing_distance (Array<Skyline_entry> const &buildings,
+ Array<Skyline_entry> const &clouds);
#endif /* SKYLINE_HH */
static void add_column (Grob*me,Item*);
static void add_beam (Grob*me,Grob*);
- static Grob *parallel_beam (Grob *me, Link_array<Grob> cols, bool *equally_long);
+ static Grob *parallel_beam (Grob *me, Link_array<Grob> const&cols, bool *equally_long);
static void calc_dy (Grob*,Real *) ;
static void calc_position_and_height (Grob*,Real*,Real *dy);
suicide ();
else if (empty)
{
- set_extent_callback (SCM_EOL, X_AXIS);
- set_extent_callback (SCM_EOL, Y_AXIS);
+ set_extent (SCM_EOL, X_AXIS);
+ set_extent (SCM_EOL, Y_AXIS);
}
else if (trans)
set_grob_property ("molecule-callback", SCM_EOL);
void
minimise_least_squares (Real * coef, Real * offset,
- Array<Offset> input)
+ Array<Offset> const &input)
{
Real sx = 0.0;
Real sy = 0.0;
int i=0;
while ((d != 1))
{
- d/= 2;
+ d /= 2;
i++;
}
return log (x) /log (2.0);
}
-
-static int
-comp (Real const &a, Real const &b)
-{
- return sign (a-b);
-}
-
-Interval
-quantise_iv (Array<Real> positions, Real x)
-{
- positions.sort (comp);
- Real period = positions.top () - positions[0];
-
- int n = int ((x - positions[0]) / period);
- Real frac = (x - positions[0]) - n * period;
-
- while (frac < 0)
- {
- frac += period;
- n --;
- }
-
- Real px = frac + positions[0];
- assert (positions[0] <= px && px <= positions.top ());
- int i=0;
- for (; i < positions.size () - 1; i++)
- {
- if (positions[i] <= px && px <= positions[i+1])
- break;
- }
-
- return Interval (positions[i] , positions[i+1]) + period * n;
-}
}
Accidental_placement::add_accidental (accidental_placement_, a);
-
- Side_position_interface::add_support (a, support_l);
announce_grob (a, SCM_EOL);
- // todo: add cautionary option
+
SCM accs = gh_cons (gh_int2scm (pitch->alteration_i_), SCM_EOL);
if (num == 2 && extra_natural_b)
accs = gh_cons (gh_int2scm (0), accs);
+ /* TODO:
+
+ add cautionary option in accidental.
+ */
+
if (tie_break_reminder)
; // TODO.
- support_l->set_grob_property ("accidentals-grob", a->self_scm ());
+
+ support_l->set_grob_property ("accidental-grob", a->self_scm ());
a->set_grob_property ("accidentals", accs);
accidental_arr_[i].accidental_ = a;
#include "staff-symbol-referencer.hh"
#include "rest.hh"
#include "note-head.hh"
+#include "accidental-placement.hh"
bool
Note_column::rest_b (Grob*me)
Note_column::accidentals (Grob *me)
{
SCM heads = me->get_grob_property ("note-heads");
+ Grob * acc = 0;
for (;gh_pair_p (heads); heads =gh_cdr (heads))
{
Grob * h = unsmob_grob (gh_car (heads));
- Grob *a = h ? unsmob_grob(h->get_grob_property ("accidentals-grob")) : 0;
- if (a)
- return a;
+ acc = h ? unsmob_grob (h->get_grob_property ("accidental-grob")) : 0;
+ if (acc)
+ break;
}
- return 0;
+ if (!acc)
+ return 0;
+
+ if (Accidental_placement::has_interface (acc->get_parent (X_AXIS)))
+ return acc->get_parent (X_AXIS);
+
+ /* compatibility. */
+ return acc;
}
Real left_ledger_protusion = hd.length ()/4;
Real right_ledger_protusion = left_ledger_protusion;
- if (unsmob_grob(me->get_grob_property ("accidentals-grob")))
+ if (unsmob_grob(me->get_grob_property ("accidental-grob")))
{
/*
make a little room for accidentals.
ADD_INTERFACE (Note_head,"note-head-interface",
"Note head",
- "accidentals-grob style stem-attachment-function");
+ "accidental-grob style stem-attachment-function");
*/
Link_array<Grob> rests;
Link_array<Grob> notes;
- Grob * commony = 0;
+
for (SCM s = elts; gh_pair_p (s); s = ly_cdr (s))
{
-
Grob * e = unsmob_grob (ly_car (s));
- if (!e)
- continue;
-
- if (!commony)
- commony = e;
- else
- commony= commony->common_refpoint (e, Y_AXIS);
-
if (unsmob_grob (e->get_grob_property ("rest")))
rests.push (e);
else
Real minimum_dist = gh_scm2double (me->get_grob_property ("minimum-distance")) * staff_space;
- Grob *common = rcol;
- for (int i = 0; i < notes.size (); i++)
- common = common->common_refpoint (notes[i], Y_AXIS);
+ Grob *common = common_refpoint_of_array (notes, rcol, Y_AXIS);
Interval notedim;
for (int i = 0; i < notes.size (); i++)
SCM
Side_position_interface::general_side_position (Grob * me, Axis a, bool use_extents)
{
- Grob *common = me->get_parent (a);
+
/*
As this is only used as a callback, this is called only once. We
*/
SCM support = me->get_grob_property ("side-support-elements");
- // me->remove_grob_property ("side-support-elements");
- for (SCM s = support; s != SCM_EOL; s = ly_cdr (s))
- {
- Grob * e = unsmob_grob (ly_car (s));
- if (e)
- common = common->common_refpoint (e, a);
- }
+ Grob *common = common_refpoint_of_list (support, me->get_parent (a), a);
Interval dim;
for (SCM s = support; s != SCM_EOL; s = ly_cdr (s))
}
void
-Simple_spacer::add_columns (Link_array<Grob> cols)
+Simple_spacer::add_columns (Link_array<Grob> const &icols)
{
+ Link_array<Grob> cols(icols);
+
for (int i = cols.size (); i--;)
if (gh_pair_p (cols[i]->get_grob_property ("between-cols")))
{
#include "skyline.hh"
+
+/*
+ A skyline is a shape of the form:
+
+
+ ----
+ | |
+ ---------| |
+ | |
+ | |
+ | |______
+ --------| |___
+
+
+
+ This file deals with building such skyline structure, and computing
+ the minimum distance between two opposing skylines.
+
+
+ Invariants for a skyline:
+
+ skyline[...].width_ forms a partition of the real interval, where
+ the segments are adjacent, and ascending. Hence we have
+
+ skyline.top().width_[RIGHT] = inf
+ skyline[0].width_[LEFT] = -inf
+
+ */
+
+
+/*
+ TODO: avoid unnecessary fragmentation.
+
+ This is O(n^2), searching and insertion. Could be O(n log n) with
+ binsearch.
+*/
void
insert_extent_into_skyline (Array<Skyline_entry> *line, Box b, Axis line_axis,
Direction d)
}
}
+
Array<Skyline_entry>
-extents_to_skyline (Array<Box> extents, Axis a, Direction d)
+empty_skyline (Direction d)
{
Array<Skyline_entry> skyline;
e.width_ = i;
e.height_ = -d * infinity_f;
skyline.push (e);
+ return skyline;
+}
+
+Array<Skyline_entry>
+extents_to_skyline (Array<Box> const &extents, Axis a, Direction d)
+{
+
+ Array<Skyline_entry> skyline = empty_skyline(d);
/*
- This makes a quadratic algorithm -- we could do better (n log (n) ) but that
- seems overkill for now.
+ This makes a cubic algorithm (array insertion is O(n),
+ searching the array dumbly is O(n), and for n items, we get O(n^3).)
+
+ We could do a lot better (n log (n), using a balanced tree) but
+ that seems overkill for now.
*/
for (int j = extents.size(); j--; )
insert_extent_into_skyline (&skyline, extents[j], a, d);
/*
minimum distance that can be achieved between baselines. "Clouds" is
a skyline pointing down.
+
+ This is an O(n) algorithm.
*/
Real
-skyline_meshing_distance (Array<Skyline_entry> buildings,
- Array<Skyline_entry> clouds)
+skyline_meshing_distance (Array<Skyline_entry> const &buildings,
+ Array<Skyline_entry> const &clouds)
{
int i = buildings.size () -1;
int j = clouds.size() -1;
{
Spanner*sp = dynamic_cast<Spanner*> (me);
SCM eltlist = me->get_grob_property ("note-columns");
- Grob *common[] = {me->common_refpoint (eltlist, X_AXIS),
- me->common_refpoint (eltlist, Y_AXIS)};
+ Grob *common[] = {common_refpoint_of_list (eltlist, me, X_AXIS),
+ common_refpoint_of_list (eltlist, me, Y_AXIS)};
common[X_AXIS] = common[X_AXIS]->common_refpoint (sp->get_bound (RIGHT), X_AXIS);
Grob*
-Tuplet_bracket::parallel_beam (Grob *me, Link_array<Grob> cols, bool *equally_long)
+Tuplet_bracket::parallel_beam (Grob *me, Link_array<Grob> const &cols, bool *equally_long)
{
/*
ugh: code dup.
Pointer_group_interface__extract_grobs (me, (Grob*)0, "note-columns");
- Grob * commony = me->common_refpoint (me->get_grob_property ("note-columns"), Y_AXIS);
- Grob * commonx = me->common_refpoint (me->get_grob_property ("note-columns"), X_AXIS);
+ SCM cols = me->get_grob_property ("note-columns");
+ Grob * commony = common_refpoint_of_list (cols, me, Y_AXIS);
+ Grob * commonx = common_refpoint_of_list (cols, me, X_AXIS);
Direction dir = Directional_element_interface::get (me);
(if (not (defined? 'standalone))
(begin
- (debug-enable 'backtrace)
+; (debug-enable 'backtrace)
(load "standalone.scm")
))
;(write (map car interface-description-alist) (current-error-port))
-;(display (lookup-interface 'volta-bracket-interface))
+;(display (lookup-interface 'accidental-placement-interface))
+;(display (document-all-grobs "OO" ))
(define (document-all-interfaces name)
(string-append
-
-;;; generate-interface-doc.scm -- Generate list of all intefaces, for refman
-;;;
-;;; source file of the GNU LilyPond music typesetter
-;;;
-;;; (c) 2000--2001 Han-Wen Nienhuys <hanwen@cs.uu.nl>
-;;; Jan Nieuwenhuizen <janneke@gnu.org>
-
-;;; File entry point for generated documentation
-
-;;; Running LilyPond on this file generates the documentation
-
-
-
-;; We use ly-gulp because these files live in
-;;
-;; PATH=$LILYPONDPREFIX/scm:<datadir>/scm
-;;
-(eval-string (ly-gulp-file "documentation-lib.scm"))
-(eval-string (ly-gulp-file "engraver-documentation-lib.scm"))
-(eval-string (ly-gulp-file "backend-documentation-lib.scm"))
-
-;;(define no-copies #t) ; from 490 to 410K, but doesn't look nice yet
-;;
-;; Also, copies of interfaces use up lots more space, but that's
-;; functional because the default property values of the interfaces
-;; are described...
-(define no-copies #f)
-
-(let* ((doc (string-append
- (document-all-interfaces "Full Grob interface list")
- )
- )
- (name "interfaces")
- (outname (string-append name ".itexi"))
- (out (open-output-file outname)))
-
- (writing-wip outname)
- (display
- (string-append
- ;;(itexi-file-head
- ;;
- ;; ;; we can't use (dir) and top if we're included by lilypond.tely
- ;; "Grob interfaces" name ""
- ;; '(
- ;; ("Grob interfaces" . "Grob Interfaces")
- ;; ))
- doc
- "\n")
- out))
-
-(newline (current-error-port))
(Accidental
. (
(molecule-callback . ,Accidental_interface::brew_molecule)
- (X-offset-callbacks . (,Side_position_interface::aligned_side))
-; (after-line-breaking-callback . ,Local_key_item::after_line_breaking)
- (direction . -1)
- (left-padding . 0.2)
- (right-padding . 0.5)
- (paren-cautionaries . #t)
(font-family . music)
- (meta . ((interfaces . (accidental-interface staff-symbol-referencer-interface font-interface side-position-interface))))
+ (meta . ((interfaces . (accidental-interface font-interface))))
))
(AccidentalPlacement
. (
- (X-extent-callback . ,Axis_group_interface::group_extent_callback)
-; (after-line-breaking-callback . ,Local_key_item::after_line_breaking)
+ (X-extent-callback . ,Accidental_placement::extent_callback)
+ (left-padding . 0.2)
+ (right-padding . 0.5)
(meta . ((interfaces . (accidental-placement-interface))))
))
(grob-property-description 'Y-offset-callbacks list? "see @code{X-offset-callbacks}.")
(grob-property-description 'accidentals list? "Alist with (PITCH
. OPTION-LIST) entries. OPTION-LIST can contain 'cautionary, 'natural
-and 'tie-break-reminder ")
+and 'tie-break-reminder
+
+FIXME: outdated.
+")
(grob-property-description 'add-stem boolean? "Add stem to porrectus?.")
(grob-property-description 'adjust-if-on-staffline boolean? "If this grob is on a staff line, adjust its appearance, so that it better fits into the staff. E.g., if set true on stem grobs, flares of mensural flags will always be aligned with the staff lines, regardless if the associated note head is printed on a staff line or inbetween.")
(grob-property-description 'after-line-breaking-callback procedure? "Procedure taking a grob as argument.
(grob-property-description 'old-accidentals list? "list of (pitch, accidental) pairs.")
(grob-property-description 'padding number? "add this much extra space between objects that are next to each other.")
(grob-property-description 'paren-cautionaries boolean? "Whether to add parenthesis around cautionary accidentals.")
+
(grob-property-description 'pedal-type symbol? "Style of piano pedal: text, bracket or mixed.")
(grob-property-description 'penalty number? "Penalty for breaking at
this column. 10000 or more means forbid linebreak, -10000 or less
(grob-property-description 'staff-support boolean? " JUNKME.")
(grob-property-description 'script-molecule pair? "index code for script.")
-(grob-property-description 'accidentals-grob ly-grob? "accidentals for this note.")
+(grob-property-description 'accidental-grob ly-grob? "Accidental for this note.")
(grob-property-description 'causes list? "list of cause objects.")
(grob-property-description 'flag-count number? "")
-(debug-enable 'backtrace)
+;(debug-enable 'backtrace)
(define point-and-click #f)
(symbol->string (car y))))
-(define (ly-load x) (eval-string (ly-gulp-file x)))
+(define (ly-load x)
+ (primitive-load (%search-load-path x))
+
+ )
(ly-load "output-lib.scm")