function.
+2004-02-06 Han-Wen Nienhuys <hanwen@xs4all.nl>
+
+ * scripts/lilypond-book.py (simple_toplevel_snippets): new
+ function.
+
+2004-02-05 Han-Wen Nienhuys <hanwen@xs4all.nl>
+
+ * scripts/lilypond-book.py (outname): fix typo
+
2004-02-05 Jan Nieuwenhuizen <janneke@gnu.org>
* Documentation/topdocs/NEWS.texi: Add item about lilypond-book.
2004-02-05 Han-Wen Nienhuys <hanwen@xs4all.nl>
+ * lily/rest-collision-engraver.cc (process_acknowledged_grobs):
+ make rest-collision only.
+
+ * lily/break-substitution.cc (substitute_one_mutable_property):
+ clear all-elements using scm_assq_remove_x().
+
+ * lily/rest-collision.cc (do_shift): shift single rests
+
+ * flower/include/array.hh (class Array): rename to is_empty ()
+
* lily/drum-note-performer.cc: new file: perform drum notes.
* VERSION (PACKAGE_NAME): release 2.1.19.
/// remove and return last entry
T pop ()
{
- assert (!empty ());
+ assert (!is_empty ());
T l = top (0);
set_size (size ()-1);
return l;
(*this)[i]= (*this)[j];
(*this)[j]=t;
}
- bool empty () const
+ bool is_empty () const
{ return !size_; }
void insert (T k, int j);
Array<void*>::size;
Array<void*>::clear;
Array<void*>::set_size;
- Array<void*>::empty;
+ Array<void*>::is_empty;
Array<void*>::reverse;
Array<void*>::tighten_maxsize;
--- /dev/null
+\header {
+
+ texidoc = "In polyphonic situations, rests are moved down
+even if there is no opposite note or rest. The amount is two
+staff-spaces. "
+
+ }
+
+
+\version "2.1.15"
+
+\score {
+ \new Staff \notes \relative c' {
+ << { r8 g''4 g8 r g4 g8 } \\
+ { d,4 r d r } >>
+ }
+
+}
see below.
*/
if (sym == ly_symbol2scm ("all-elements"))
- sc->set_grob_property ("all-elements", SCM_EOL);
-
+ sc->mutable_property_alist_
+ = scm_assq_remove_x (sc->mutable_property_alist_,
+ ly_symbol2scm ("all-elements"));
+
sc->mutable_property_alist_ = scm_acons (sym, newval,
sc->mutable_property_alist_);
}
(hwn 4/2/04)
*/
if (sym == ly_symbol2scm ("all-elements"))
- sc->set_grob_property ("all-elements", SCM_EOL);
+ sc->mutable_property_alist_
+ = scm_assq_remove_x (sc->mutable_property_alist_,
+ ly_symbol2scm ("all-elements"));
sc->mutable_property_alist_ = scm_cons (scm_cons (sym, newval),
sc->mutable_property_alist_);
if (Note_column::has_interface (i.grob_))
{
/*should check Y axis? */
- if (Note_column::rest_b (i.grob_) || i.grob_->get_parent (X_AXIS))
+ if (Note_column::has_rests (i.grob_) || i.grob_->get_parent (X_AXIS))
return ;
note_columns_.push (i.grob_);
#ifdef HAVE_FLEXLEXER_YY_CURRENT_BUFFER
yy_current_buffer = 0;
#endif
- if (state_stack_.empty ())
+ if (state_stack_.is_empty ())
{
#ifdef HAVE_FLEXLEXER_YY_CURRENT_BUFFER
yy_current_buffer = 0;
char const*
Includable_lexer::here_str0 () const
{
- if (include_stack_.empty ())
+ if (include_stack_.is_empty ())
return 0;
return include_stack_.top ()->to_str0 () + char_count_stack_.top ();
}
Includable_lexer::~Includable_lexer ()
{
- while (!include_stack_.empty ())
+ while (!include_stack_.is_empty ())
{
close_input ();
}
Source_file*
Includable_lexer::get_source_file () const
{
- if (include_stack_.empty ())
+ if (include_stack_.is_empty ())
return 0;
else
return include_stack_.top ();
static void set_stem (Grob*me,Grob*);
static void set_dotcol (Grob*me,Grob*);
static void add_head (Grob*me,Grob*);
- static bool rest_b (Grob*me);
+ static bool has_rests (Grob*me);
static bool has_interface (Grob*);
static Item *get_stem (Grob*);
void
My_lily_lexer::LexerError (char const *s)
{
- if (include_stack_.empty ())
+ if (include_stack_.is_empty ())
{
progress_indication (_f ("error at EOF: %s", s)+ String ("\n"));
}
progress_indication ("\n");
- if (!define_spots_.empty ())
+ if (!define_spots_.is_empty ())
{
define_spots_.top ().warning (_ ("Braces don't match"));
error_level_ = 1;
#include "accidental-placement.hh"
bool
-Note_column::rest_b (Grob*me)
+Note_column::has_rests (Grob*me)
{
return unsmob_grob (me->get_grob_property ("rest"));
}
for (int i=0; i < sc->defs_.size (); i++)
default_rendering (sc->music_, sc->defs_[i]->self_scm(),head, outname);
- if (sc->defs_.empty ())
+ if (sc->defs_.is_empty ())
{
Music_output_def *id =
unsmob_music_output_def (THIS->lexer_->lookup_identifier
{
Link_array<Music> eventses_;
Link_array<Music> new_phrasing_slur_evs_;
- Link_array<Grob> phrasing_slur_l_stack_;
+ Link_array<Grob> phrasing_slurs_;
Link_array<Grob> end_phrasing_slurs_;
Moment last_start_;
if (Note_column::has_interface (info.grob_))
{
Grob *e =info.grob_;
- for (int i = 0; i < phrasing_slur_l_stack_.size (); i++)
- Slur::add_column (phrasing_slur_l_stack_[i], e);
+ for (int i = 0; i < phrasing_slurs_.size (); i++)
+ Slur::add_column (phrasing_slurs_[i], e);
for (int i = 0; i < end_phrasing_slurs_.size (); i++)
Slur::add_column (end_phrasing_slurs_[i], e);
}
void
Phrasing_slur_engraver::finalize ()
{
- for (int i = 0; i < phrasing_slur_l_stack_.size (); i++)
+ for (int i = 0; i < phrasing_slurs_.size (); i++)
{
/*
Let's not typeset unterminated stuff
*/
- phrasing_slur_l_stack_[i]->suicide ();
+ phrasing_slurs_[i]->suicide ();
}
- phrasing_slur_l_stack_.clear ();
+ phrasing_slurs_.clear ();
for (int i=0; i < eventses_.size (); i++)
{
if (d == STOP)
{
- if (phrasing_slur_l_stack_.empty ())
+ if (phrasing_slurs_.is_empty ())
phrasing_slur_ev->origin ()->warning (_f ("can't find start of phrasing slur"));
else
{
- Grob* phrasing_slur = phrasing_slur_l_stack_.pop ();
+ Grob* phrasing_slur = phrasing_slurs_.pop ();
end_phrasing_slurs_.push (phrasing_slur);
eventses_.pop ();
}
}
}
for (int i=0; i < start_phrasing_slurs.size (); i++)
- phrasing_slur_l_stack_.push (start_phrasing_slurs[i]);
+ phrasing_slurs_.push (start_phrasing_slurs[i]);
new_phrasing_slur_evs_.clear ();
}
class Rest_collision_engraver : public Engraver
{
Item* rest_collision_;
-
+ int rest_count_;
Link_array<Grob> note_columns_;
protected:
virtual void acknowledge_grob (Grob_info);
Rest_collision_engraver::Rest_collision_engraver ()
{
rest_collision_ =0;
+ rest_count_ = 0;
}
void
Rest_collision_engraver::process_acknowledged_grobs ()
{
- if (rest_collision_ || note_columns_.size () < 2)
+ if (rest_collision_
+ || note_columns_.is_empty ()
+ || !rest_count_)
return;
rest_collision_ = make_item ("RestCollision");
announce_grob(rest_collision_, SCM_EOL);
- for (int i=0; i< note_columns_.size (); i++)
+ for (int i=0; i < note_columns_.size (); i++)
Rest_collision::add_column (rest_collision_,note_columns_[i]);
}
Rest_collision_engraver::acknowledge_grob (Grob_info i)
{
if (Note_column::has_interface (i.grob_))
- note_columns_.push (i.grob_);
+ {
+ note_columns_.push (i.grob_);
+ if (Note_column::has_rests (i.grob_))
+ rest_count_ ++;
+ }
}
void
rest_collision_ = 0;
}
note_columns_.clear ();
+ rest_count_ = 0;
}
+
ENTER_DESCRIPTION(Rest_collision_engraver,
/* descr */ "Handles collisions of rests.",
/* creats*/ "RestCollision",
// no partners to collide with
if (rests.size () + notes.size () < 2)
- return SCM_UNSPECIFIED;
-
+ {
+ if (rests.size () == 1
+ && Note_column::dir (rests[0]))
+ {
+ Note_column::translate_rests (rests[0],
+ 4 * Note_column::dir (rests[0]));
+ }
+ }
// meisjes met meisjes
if (!notes.size ())
{
staff_spacing_ = 0;
}
- bool empty( )const
+ bool is_empty () const
{
return !staff_spacing_ && !note_spacings_.size ();
}
}
- if (!current_spacings_.empty ())
+ if (!current_spacings_.is_empty ())
{
last_spacings_ = current_spacings_;
}
Direction d = to_dir (slur_ev->get_mus_property ("span-direction"));
if (d== STOP)
{
- if (slur_stack_.empty ())
+ if (slur_stack_.is_empty ())
/* How to shut up this warning, when Voice_devnull_engraver has
eaten start event? */
slur_ev->origin ()->warning (_f ("can't find start of slur"));
Use outer non-rest columns to determine slope
*/
int l = 0;
- while (l <columns.size () && Note_column::rest_b (columns[l]))
+ while (l <columns.size () && Note_column::has_rests (columns[l]))
l ++;
int r = columns.size ()- 1;
- while (r >= l && Note_column::rest_b (columns[r]))
+ while (r >= l && Note_column::has_rests (columns[r]))
r--;
if (l < r)
@example
@@lilypond[fragment,verbatim,center]
r1 r1*3 R1*3 \\\\property Score.skipBars= ##t r1*3 R1*3
-
@@end lilypond
@end example
help with debugging large scores.")
(translator-property-description 'slurMelismaBusy boolean? "Signal if a slur is present.")
(translator-property-description 'solo boolean? "set if solo is detected by the part combiner.")
-(translator-property-description 'soloADue boolean? "set Solo/A due texts in the part combiner?.")
+(translator-property-description 'soloADue boolean? "set Solo/A due texts in the part combiner?")
(translator-property-description 'soloIIText string? "text for begin of solo for voice ``two'' when part-combining.")
(translator-property-description 'soloText string? "text for begin of solo when part-combining.")
(translator-property-description 'sparseTies boolean? "only create one tie per chord.")
(translator-property-description 'tupletSpannerDuration ly:moment? "
Normally a tuplet bracket is as wide as the
-@code{ imes} expression that gave rise to it. By setting this
+@code{\\times} expression that gave rise to it. By setting this
property, you can make brackets last shorter. Example
@example
@@lilypond[verbatim,fragment]
-context Voice imes 2/3 @{
+context Voice \\times 2/3 @{
property Voice.tupletSpannerDuration = #(ly:make-moment 1 4)
c-[8 c c-] c-[ c c-]
@}
example, this sets the sizes of a staff to 10 (5+5) staffspaces high.
@example
-property Staff.verticalExtent = #(-5.0 . 5.0)
+property Staff.verticalExtent = #'(-5.0 . 5.0)
@end example
VerticalExtent, MinimumVerticalExtent and ExtraVerticalExtent are
according to values of @code{defaultBarType}, @code{barAlways},
@code{barNonAuto} and @code{measurePosition}.
-Valid values are described in @ref{(lilypond-internals)bar-line-interface}.
-
-.")
+Valid values are described in @ref{bar-line-interface}.
+")
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
HTML: {
'include': no_match,
'lilypond' : '(?m)(?P<match><lilypond((?P<options>[^:]*):)(?P<code>.*?)/>)',
- 'lilypond-block': r'''(?ms)(?P<match><lilypond(?P<options>[^>]+)?>(?P<code>.*?)</lilypond>)''',
- 'lilypond-file': r'(?m)(?P<match><lilypondfile(?P<options>[^>]+)?>\s*(?P<filename>[^<]+)\s*</lilypondfile>)',
- 'multiline-comment': r"(?sm)\s*(?!@c\s+)(?P<code><!--\s.*?!-->)\s",
- 'singleline-comment': no_match,
+ 'lilypond_block': r'''(?ms)(?P<match><lilypond(?P<options>[^>]+)?>(?P<code>.*?)</lilypond>)''',
+ 'lilypond_file': r'(?m)(?P<match><lilypondfile(?P<options>[^>]+)?>\s*(?P<filename>[^<]+)\s*</lilypondfile>)',
+ 'multiline_comment': r"(?sm)\s*(?!@c\s+)(?P<code><!--\s.*?!-->)\s",
+ 'singleline_comment': no_match,
'verb': r'''(?P<code><pre>.*?</pre>)''',
'verbatim': r'''(?s)(?P<code><pre>\s.*?</pre>\s)''',
},
LATEX: {
'include': r'(?m)^[^%\n]*?(?P<match>\\input{(?P<filename>[^}]+)})',
'lilypond' : r'(?m)^[^%\n]*?(?P<match>\\lilypond\s*(\[(?P<options>.*?)\])?\s*{(?P<code>.*?)})',
- 'lilypond-block': r"(?sm)^[^%\n]*?(?P<match>\\begin\s*(\[(?P<options>.*?)\])?\s*{lilypond}(?P<code>.*?)\\end{lilypond})",
- 'lilypond-file': r'(?m)^[^%\n]*?(?P<match>\\lilypondfile\s*(\[(?P<options>.*?)\])?\s*\{(?P<filename>.+)})',
- 'multiline-comment': no_match,
- 'singleline-comment': r"(?m)^.*?(?P<match>(?P<code>^%.*$\n+))",
+ 'lilypond_block': r"(?sm)^[^%\n]*?(?P<match>\\begin\s*(\[(?P<options>.*?)\])?\s*{lilypond}(?P<code>.*?)\\end{lilypond})",
+ 'lilypond_file': r'(?m)^[^%\n]*?(?P<match>\\lilypondfile\s*(\[(?P<options>.*?)\])?\s*\{(?P<filename>.+)})',
+ 'multiline_comment': no_match,
+ 'singleline_comment': r"(?m)^.*?(?P<match>(?P<code>^%.*$\n+))",
'verb': r"(?P<code>\\verb(?P<del>.).*?(?P=del))",
'verbatim': r"(?s)(?P<code>\\begin\s*{verbatim}.*?\\end{verbatim})",
},
TEXINFO: {
'include': '(?m)^[^%\n]*?(?P<match>@include\s+(?P<filename>\S*))',
'lilypond' : '(?m)^(?P<match>@lilypond(\[(?P<options>[^]]*)\])?{(?P<code>.*?)})',
- 'lilypond-block': r'''(?ms)^(?P<match>@lilypond(\[(?P<options>[^]]*)\])?\s(?P<code>.*?)@end lilypond)\s''',
- 'lilypond-file': '(?m)^(?P<match>@lilypondfile(\[(?P<options>[^]]*)\])?{(?P<filename>[^}]+)})',
- 'multiline-comment': r"(?sm)^\s*(?!@c\s+)(?P<code>@ignore\s.*?@end ignore)\s",
- 'singleline-comment': r"(?m)^.*?(?P<match>(?P<code>@c([ \t][^\n]*|)\n))",
+ 'lilypond_block': r'''(?ms)^(?P<match>@lilypond(\[(?P<options>[^]]*)\])?\s(?P<code>.*?)@end lilypond)\s''',
+ 'lilypond_file': '(?m)^(?P<match>@lilypondfile(\[(?P<options>[^]]*)\])?{(?P<filename>[^}]+)})',
+ 'multiline_comment': r"(?sm)^\s*(?!@c\s+)(?P<code>@ignore\s.*?@end ignore)\s",
+ 'singleline_comment': r"(?m)^.*?(?P<match>(?P<code>@c([ \t][^\n]*|)\n))",
'verb': r'''(?P<code>@code{.*?})''',
'verbatim': r'''(?s)(?P<code>@example\s.*?@end example\s)''',
},
index = 0
class Snippet:
+
+ ## huh? index is redundant? --hwn
def __init__ (self, type, source, index, match):
self.type = type
self.source = source
def ly (self):
s = ''
- if self.type == 'lilypond-block' or self.type == 'lilypond':
+ if self.type == 'lilypond_block' or self.type == 'lilypond':
s = self.substring ('code')
- elif self.type == 'lilypond-file':
+ elif self.type == 'lilypond_file':
name = self.substring ('filename')
s = open (find_file (name)).read ()
return s
raise 'to be done'
def write_ly (self):
- if self.type == 'lilypond-block' or self.type == 'lilypond'\
- or self.type == 'lilypond-file':
+ if self.type == 'lilypond_block' or self.type == 'lilypond'\
+ or self.type == 'lilypond_file':
h = open (self.basename () + '.ly', 'w')
h.write (self.full_ly ())
h.write ('\n@end html\n')
def outdated_p (self):
- if self.type != 'lilypond-block' and self.type != 'lilypond'\
- and self.type != 'lilypond-file':
+ if self.type != 'lilypond_block' and self.type != 'lilypond'\
+ and self.type != 'lilypond_file':
return None
base = self.basename ()
if os.path.exists (base + '.ly') \
# Hmm, why is verbatim's group called 'code'; rename to 'verb'?
#if snippet.match.group ('code'):
# urg
- if self.type == 'lilypond' or self.type == 'lilypond-block':
+ if self.type == 'lilypond' or self.type == 'lilypond_block':
h.write (self.source[index:self.start ('code')])
h.write (run_filter (self.substring ('code')))
h.write (self.source[self.end ('code'):self.end (0)])
# if snippet.match.group ('code'):
# urg
if self.type == 'lilypond' \
- or self.type == 'lilypond-block'\
- or self.type == 'lilypond-file':
+ or self.type == 'lilypond_block'\
+ or self.type == 'lilypond_file':
h.write (self.source[index:self.start (0)])
snippet_output = eval ("Snippet.output_" + format)
snippet_output (self)
h.write (self.source[index:self.end (0)])
index = self.end (0)
+
+# this isn't working - <params> are doubly used.
+# a solution is to strip P<> from the regexes,
+# and redo the match with the original in notice_snippet
+def other_toplevel_snippets (str, types):
+ res = ['(?P<regex%s>%s)' % (t, snippet_res[format][t])
+ for t in types]
+
+ big_re = re.compile (string.join (res, '|'))
+ snippets = []
+
+ def notice_snippet (match, snips = snippets, types = types):
+ snip = None
+ for t in types:
+ try:
+ key = 'regex' + t
+ gr = match.group (key)
+ snip =Snippet (t, str, match.start (key), match)
+ break
+ except IndexError:
+ pass
+ if snip:
+ snips.append (snip)
+ else:
+ raise "Huh?"
+
+ return match.group (0)
+
+ str = big_re.sub (notice_snippet, str)
+
+ return snippets
+
+def simple_toplevel_snippets (str, types):
+ snippets = []
+ for t in types:
+ regex = re.compile (snippet_res[format][t])
+
+ # ugh, this can be done nicer in python 2.x
+ def notice_snippet (match, snippets = snippets,
+ t = t, str = str):
+ s = Snippet (t, str, 0, match)
+ snippets.append (s)
+ return ''
+
+ regex.sub (notice_snippet, str)
+ return snippets
+
def find_toplevel_snippets (s, types):
res = {}
for i in types:
ly.progress (_ ("Dissecting..."))
#snippets = find_toplevel_snippets (source, snippet_res[format].keys ())
snippet_types = (
- 'lilypond-block',
+ 'lilypond_block',
'verb',
'verbatim',
- 'singleline-comment',
- 'multiline-comment',
- 'lilypond-file',
+ 'singleline_comment',
+ 'multiline_comment',
+ 'lilypond_file',
'include',
'lilypond', )
- snippets = find_toplevel_snippets (source, snippet_types)
+ snippets = simple_toplevel_snippets (source, snippet_types)
ly.progress ('\n')
global h