System_start_delimiter_engraver by Nested_system_start_delimiter_engraver.
* lily/nested-system-start-delimiter-engraver.cc (struct
Bracket_nesting_node): new class.
(struct Bracket_nesting_group): new class
(struct Bracket_nesting_staff): new class.
(process_music): create hierarchy of grobs. This allows separate
tuning of different SSDs.
* scm/define-grobs.scm (all-grob-descriptions): new Grob SystemStartSquare
(all-grob-descriptions): remove old NestedSystemStartDelimiter.
+2005-11-21 Han-Wen Nienhuys <hanwen@xs4all.nl>
+
+ * ly/engraver-init.ly (AncientRemoveEmptyStaffContext): replace
+ System_start_delimiter_engraver by Nested_system_start_delimiter_engraver.
+
+ * lily/nested-system-start-delimiter-engraver.cc (struct
+ Bracket_nesting_node): new class.
+ (struct Bracket_nesting_group): new class
+ (struct Bracket_nesting_staff): new class.
+ (process_music): create hierarchy of grobs. This allows separate
+ tuning of different SSDs.
+
+ * scm/define-grobs.scm (all-grob-descriptions): new Grob SystemStartSquare
+ (all-grob-descriptions): remove old NestedSystemStartDelimiter.
+
2005-11-19 Han-Wen Nienhuys <hanwen@xs4all.nl>
* lily/side-position-interface.cc (aligned_side): multiply
\consists "Nested_system_start_delimiter_engraver"
}
\relative <<
- \override StaffGroup.NestedSystemStartDelimiter #'styles = #'(line-bracket bracket line-bracket)
+ \set StaffGroup.systemStartDelimiters =
+ #'(SystemStartSquare SystemStartBracket SystemStartSquare)
+
\set StaffGroup.systemStartDelimiterHierarchy = #'((a (b)) c)
\new Staff { c1 }
\new Staff { c1 }
#include "output-def.hh"
#include "spanner.hh"
-class Nested_system_start_delimiter_engraver : public Engraver
+
+struct Bracket_nesting_node
{
public:
- TRANSLATOR_DECLARATIONS (Nested_system_start_delimiter_engraver);
+ virtual ~Bracket_nesting_node(){}
+ virtual bool add_staff (Grob *) { return false; }
+ virtual void add_support (Grob *) { }
+ virtual void set_bound (Direction, Grob *){}
+ virtual void set_nesting_support (Grob*) {}
+ virtual void create_grobs (Engraver*, SCM, SCM){}
+};
-protected:
+struct Bracket_nesting_group : public Bracket_nesting_node
+{
Spanner *delimiter_;
-
- DECLARE_ACKNOWLEDGER (system_start_delimiter);
- DECLARE_ACKNOWLEDGER (staff_symbol);
+ Link_array<Bracket_nesting_node> children_;
+
+ void from_list (SCM );
+ virtual void add_support (Grob *grob);
+ virtual bool add_staff (Grob *grob);
+ virtual void set_nesting_support (Grob*);
+ virtual void set_bound (Direction, Grob *grob);
+ virtual void create_grobs (Engraver*, SCM, SCM);
+ ~Bracket_nesting_group ();
+};
- void process_music ();
- virtual void finalize ();
+struct Bracket_nesting_staff : public Bracket_nesting_node
+{
+ Grob *staff_;
+
+ Bracket_nesting_staff (Grob *s) { staff_ = s; }
+ virtual bool add_staff (Grob *);
};
-Nested_system_start_delimiter_engraver::Nested_system_start_delimiter_engraver ()
+bool
+Bracket_nesting_staff::add_staff (Grob *g)
{
- delimiter_ = 0;
+ if (!staff_)
+ {
+ staff_ = g;
+ return true;
+ }
+ return false;
}
-bool
-add_staff_to_hierarchy (SCM hierarchy, SCM grob)
+void
+Bracket_nesting_group::create_grobs (Engraver *engraver, SCM types, SCM default_type)
+{
+ SCM type = (scm_is_pair (types) ? scm_car (types) : default_type);
+ delimiter_ = make_spanner_from_properties (engraver, type,
+ SCM_EOL, ly_symbol2string (type).to_str0 ());
+
+ for (int i = 0 ; i < children_.size (); i++)
+ {
+ children_[i]->create_grobs (engraver, (scm_is_pair (types) ? scm_cdr (types) : SCM_EOL),
+ default_type);
+ }
+}
+
+void
+Bracket_nesting_group::add_support (Grob *g)
{
- for (SCM s = hierarchy; scm_is_pair (s); s = scm_cdr (s))
+ Side_position_interface::add_support (g, delimiter_);
+ for (int i = 0 ; i < children_.size (); i++)
{
- SCM entry = scm_car (s);
+ children_[i]->add_support (g);
+ }
+}
+
+Bracket_nesting_group::~Bracket_nesting_group ()
+{
+ for (int i = 0 ; i < children_.size (); i++)
+ delete children_[i];
+}
- if (unsmob_grob (entry))
- ;
- else if (scm_is_pair (entry))
+void
+Bracket_nesting_group::set_bound (Direction d, Grob *g)
+{
+ delimiter_->set_bound (d, g);
+ for (int i = 0 ; i < children_.size (); i++)
+ {
+ children_[i]->set_bound (d, g);
+ }
+}
+
+void
+Bracket_nesting_group::set_nesting_support (Grob *parent)
+{
+ if (parent)
+ Side_position_interface::add_support (delimiter_, parent);
+
+ for (int i = 0 ; i < children_.size (); i++)
+ {
+ children_[i]->set_nesting_support (delimiter_);
+ }
+}
+
+
+void
+Bracket_nesting_group::from_list (SCM x)
+{
+ for (SCM s = x; scm_is_pair (s); s = scm_cdr (s))
+ {
+ SCM entry = scm_car (s);
+ if (scm_is_pair (entry))
{
- bool success = add_staff_to_hierarchy (entry, grob);
- if (success)
- return success;
+ Bracket_nesting_group *node = new Bracket_nesting_group;
+ node->from_list (entry);
+ children_.push (node);
}
else
{
- scm_set_car_x (s, grob);
+ children_.push (new Bracket_nesting_staff (0));
+ }
+ }
+}
+
+bool
+Bracket_nesting_group::add_staff (Grob *grob)
+{
+ for (int i = 0; i < children_.size (); i++)
+ {
+ if (children_[i]->add_staff (grob))
+ {
+ Pointer_group_interface::add_grob (delimiter_, ly_symbol2scm ("elements"), grob);
return true;
}
}
return false;
}
+
+
+
+/****************/
+
+class Nested_system_start_delimiter_engraver : public Engraver
+{
+public:
+ TRANSLATOR_DECLARATIONS (Nested_system_start_delimiter_engraver);
+
+protected:
+ Bracket_nesting_group *nesting_;
+
+ DECLARE_ACKNOWLEDGER (system_start_delimiter);
+ DECLARE_ACKNOWLEDGER (staff_symbol);
+
+ void process_music ();
+ virtual void finalize ();
+};
+
+Nested_system_start_delimiter_engraver::Nested_system_start_delimiter_engraver ()
+{
+ nesting_ = 0;
+}
+
+
+
void
Nested_system_start_delimiter_engraver::process_music ()
{
- if (!delimiter_)
+ if (!nesting_)
{
- delimiter_ = make_spanner ("NestedSystemStartDelimiter", SCM_EOL);
+ nesting_ = new Bracket_nesting_group ();
SCM hierarchy = get_property ("systemStartDelimiterHierarchy");
-
-
- delimiter_->set_object ("staff-hierarchy", ly_deep_copy (hierarchy));
- delimiter_->set_bound (LEFT, unsmob_grob (get_property ("currentCommandColumn")));
+ SCM delimiter_name = get_property ("systemStartDelimiter");
+ SCM delimiter_types = get_property ("systemStartDelimiters");
+ nesting_->from_list (hierarchy);
+ nesting_->create_grobs (this, delimiter_types,
+ delimiter_name);
+ nesting_->set_bound (LEFT, unsmob_grob (get_property ("currentCommandColumn")));
}
}
void
Nested_system_start_delimiter_engraver::finalize ()
{
- if (delimiter_)
- delimiter_->set_bound (RIGHT,
+ if (nesting_)
+ {
+ nesting_->set_bound (RIGHT,
unsmob_grob (get_property ("currentCommandColumn")));
+ nesting_->set_nesting_support (0);
+ }
}
void
Nested_system_start_delimiter_engraver::acknowledge_staff_symbol (Grob_info inf)
{
Grob *staff = inf.grob();
- SCM hier = delimiter_->get_object ("staff-hierarchy");
- bool succ = add_staff_to_hierarchy (hier, staff->self_scm ());
+ bool succ = nesting_->add_staff (staff);
if (!succ)
{
- hier = scm_append_x (scm_list_2 (hier,
- scm_list_1 (staff->self_scm ())));
-
- delimiter_->set_object ("staff-hierarchy", hier);
+ nesting_->children_.push (new Bracket_nesting_staff (0));
+ nesting_->add_staff (staff);
}
}
void
Nested_system_start_delimiter_engraver::acknowledge_system_start_delimiter (Grob_info inf)
{
- Side_position_interface::add_support (inf.grob (), delimiter_);
+ nesting_->add_support (inf.grob ());
}
#include "translator.icc"
+++ /dev/null
-/*
- system-start-delimiter.cc -- implement Nested_system_start_delimiter
-
- source file of the GNU LilyPond music typesetter
-
- (c) 2000--2005 Han-Wen Nienhuys <hanwen@xs4all.nl>
-*/
-
-#include "system-start-delimiter.hh"
-#include "spanner.hh"
-#include "axis-group-interface.hh"
-#include "output-def.hh"
-#include "font-interface.hh"
-#include "all-font-metrics.hh"
-#include "staff-symbol-referencer.hh"
-#include "lookup.hh"
-#include "item.hh"
-
-#include "pointer-group-interface.hh"
-
-
-struct Nested_system_start_delimiter
-{
-public:
- bool has_interface (Grob *);
- Stencil static make_substencil (Spanner *, Grob *, SCM, SCM, SCM);
- DECLARE_SCHEME_CALLBACK (print, (SCM));
-};
-
-Link_array<Grob>
-flatten_hierarchy (SCM hier)
-{
- Link_array<Grob> retval;
- if (unsmob_grob (hier))
- retval.push (unsmob_grob (hier));
-
- if (scm_is_pair (hier))
- {
- retval = flatten_hierarchy (scm_car (hier));
- retval.concat (flatten_hierarchy (scm_cdr (hier)));
- }
-
- return retval;
-}
-
-
-Stencil
-Nested_system_start_delimiter::make_substencil (Spanner *me,
- Grob *common,
- SCM hierarchy,
- SCM depth_styles,
- SCM default_style
- )
-{
- Interval ext;
- Link_array<Grob> elts = flatten_hierarchy (hierarchy);
-
- if (elts.is_empty ())
- return Stencil();
-
- int non_empty_count = 0;
- for (int i = elts.size (); i--;)
- {
- Spanner *sp = dynamic_cast<Spanner *> (elts[i]);
-
- if (sp
- && sp->get_bound (LEFT) == me->get_bound (LEFT))
- {
- Interval dims = sp->extent (common, Y_AXIS);
- if (!dims.is_empty ())
- {
- non_empty_count ++;
- ext.unite (dims);
- }
- }
- }
-
- SCM glyph_sym = ly_symbol2scm ("bracket");
- if (scm_is_pair (depth_styles))
- glyph_sym = scm_car (depth_styles);
-
- if (ext.is_empty ()
- || (robust_scm2double (me->get_property ("collapse-height"), 0.0) >= ext.length()))
- {
- return Stencil();
- }
-
- Stencil total;
-
- Real len = ext.length ();
- if (glyph_sym == ly_symbol2scm ("bracket"))
- total = System_start_delimiter::staff_bracket (me, len);
- else if (glyph_sym == ly_symbol2scm ("brace"))
- total = System_start_delimiter::staff_brace (me, len);
- else if (glyph_sym == ly_symbol2scm ("bar-line"))
- total = System_start_delimiter::simple_bar (me, len);
- else if (glyph_sym == ly_symbol2scm ("line-bracket"))
- total = System_start_delimiter::line_bracket (me, len);
-
- total.translate_axis (ext.center (), Y_AXIS);
-
- Real left_x = total.extent (X_AXIS)[LEFT];
- for (SCM s = hierarchy; scm_is_pair (s); s = scm_cdr (s))
- {
- SCM entry = scm_car (s);
-
- if (scm_is_pair (entry)
- && !scm_is_symbol (scm_car (entry)))
- {
- Stencil sub = make_substencil (me, common, entry,
- scm_is_pair (depth_styles)
- ? scm_cdr (depth_styles) : SCM_EOL,
- default_style);
- sub.translate_axis (left_x, X_AXIS);
- total.add_stencil (sub);
- }
- }
-
- return total;
-}
-
-MAKE_SCHEME_CALLBACK (Nested_system_start_delimiter, print, 1);
-SCM
-Nested_system_start_delimiter::print (SCM smob)
-{
- Spanner *me = unsmob_spanner (smob);
- if (!me)
- return SCM_EOL;
-
- SCM hierarchy = me->get_object ("staff-hierarchy");
- Link_array<Grob> elts = flatten_hierarchy (hierarchy);
- Grob *common = common_refpoint_of_array (elts, me, Y_AXIS);
-
- SCM default_style = me->get_property ("style");
- if (!scm_is_symbol (default_style))
- default_style = ly_symbol2scm ("line-bracket");
-
- Stencil total = make_substencil (me, common, hierarchy, me->get_property ("styles"),
- default_style);
- total.translate_axis (- me->relative_coordinate (common, Y_AXIS), Y_AXIS);
-
- return total.smobbed_copy ();
-
-}
-
-ADD_INTERFACE (Nested_system_start_delimiter,
- "nested-system-start-delimiter-interface",
-
- "The brace, bracket or bar in front of the system. By setting "
- "@code{staff-hierarchy}, eg. to @code{(a (b d) c)}, nesting for staff "
- "braces can be produced."
- ,
-
-
- /* properties */
- "collapse-height "
- "styles "
- "staff-hierarchy "
- );
m = staff_brace (me, len);
else if (glyph_sym == ly_symbol2scm ("bar-line"))
m = simple_bar (me, len);
+ else if (glyph_sym == ly_symbol2scm ("line-bracket"))
+ m = line_bracket (me, len);
m.translate_axis (ext.center (), Y_AXIS);
return m.smobbed_copy ();
\context {
\type "Engraver_group"
\name InnerChoirStaff
- \consists "System_start_delimiter_engraver"
+ \consists "Nested_system_start_delimiter_engraver"
systemStartDelimiter = #'SystemStartBracket
\accepts "Staff"
\consists "Span_bar_engraver"
\consists "Span_arpeggio_engraver"
- \consists "System_start_delimiter_engraver"
+ \consists "Nested_system_start_delimiter_engraver"
systemStartDelimiter = #'SystemStartBrace
\accepts "Staff"
\consists "Output_property_engraver"
systemStartDelimiter = #'SystemStartBracket
- \consists "System_start_delimiter_engraver"
+ \consists "Nested_system_start_delimiter_engraver"
\defaultchild "Staff"
\accepts "Staff"
\consists "Timing_translator"
\consists "Default_bar_line_engraver"
\consists "Output_property_engraver"
- \consists "System_start_delimiter_engraver"
+ \consists "Nested_system_start_delimiter_engraver"
\consists "Mark_engraver"
\consists "Metronome_mark_engraver"
\consists "Break_align_engraver"
(suggestAccidentals ,boolean? "If set, accidentals are typeset as cautionary suggestions over the note.")
(systemStartDelimiterHierarchy ,pair? "A nested list, indicating the nesting of a start delimiters.")
+
+ (systemStartDelimiters ,list? "Grobs for nested system starts
+Overrides @code{systemStartDelimiter}.")
(systemStartDelimiter ,symbol? "Which grob to make for the start of
the system/staff? Set to @code{SystemStartBrace},
@code{SystemStartBracket} or @code{SystemStartBar}.")
(interfaces . (system-interface
axis-group-interface))))))
- (NestedSystemStartDelimiter
+ (SystemStartBrace
. (
- (stencil . ,Nested_system_start_delimiter::print)
+ (style . brace)
+ (padding . 0.3)
+ (stencil . ,System_start_delimiter::print)
+ (collapse-height . 5.0)
(X-offset . ,Side_position_interface::x_aligned_side)
(direction . ,LEFT)
- (collapse-height . 1.0)
- (padding . 0.0)
(font-encoding . fetaBraces)
(Y-extent . #f)
(meta . ((class . Spanner)
side-position-interface
font-interface))))))
- (SystemStartBrace
+ (SystemStartSquare
. (
- (style . brace)
- (padding . 0.2)
- (stencil . ,System_start_delimiter::print)
- (collapse-height . 5.0)
+ (Y-extent . #f)
(X-offset . ,Side_position_interface::x_aligned_side)
(direction . ,LEFT)
- (font-encoding . fetaBraces)
- (Y-extent . #f)
+ (stencil . ,System_start_delimiter::print)
+ (style . line-bracket)
+ (thickness . 0.45)
(meta . ((class . Spanner)
- (interfaces . (system-start-delimiter-interface
+ (interfaces . (font-interface
side-position-interface
- font-interface))))))
-
+ system-start-delimiter-interface))))))
(SystemStartBracket
. (
(Y-extent . #f)