]> git.donarmstrong.com Git - lilypond.git/commitdiff
* lily/property-iterator.cc (do_quit): add finalization functions
authorHan-Wen Nienhuys <hanwen@xs4all.nl>
Thu, 12 Sep 2002 22:26:20 +0000 (22:26 +0000)
committerHan-Wen Nienhuys <hanwen@xs4all.nl>
Thu, 12 Sep 2002 22:26:20 +0000 (22:26 +0000)
to undo property settings.

* lily/parser.yy (property_def): syntax for \once \property ....

* lily/note-spacing.cc (get_spacing): don't get crazy when there
is no (live) stem.

* lily/my-lily-lexer.cc: new keyword \once

* lily/global-translator.cc (apply_finalizations): new function
(add_finalization): new function

lily/engraver.cc
lily/global-translator.cc
lily/include/global-translator.hh
lily/include/property-iterator.hh
lily/include/translator.hh
lily/my-lily-lexer.cc
lily/note-spacing.cc
lily/parser.yy
lily/property-iterator.cc
lily/score-engraver.cc
lily/sequential-iterator.cc

index 02bf0e107472a48f7a169637f9a0286333f41be8..b8cb0f493949df5cbe3c96158c75ca7a0989e79b 100644 (file)
@@ -68,17 +68,7 @@ Engraver::Engraver()
 Score_engraver* 
 Engraver::top_engraver () const
 {
-  /*
-    ugh.
-   */
-  if (dynamic_cast<Score_engraver*>((Engraver*)this))
-    return dynamic_cast<Score_engraver*> ((Engraver*)this);
-
-  if (daddy_trans_)
-    return dynamic_cast<Engraver*> (daddy_trans_)->top_engraver ();
-
-  programming_error ("No score engraver!");
-  return 0;
+  return dynamic_cast<Score_engraver*> (top_translator());
 }
 
 ENTER_DESCRIPTION(Engraver,
index 0c079c40d223d89d80c7cde2e8de5818f6ef7446..bbe997ce0b8355c2307b1ba4dee2fbb6d4e72339 100644 (file)
@@ -72,6 +72,7 @@ void
 Global_translator::one_time_step ()
 {
 }
+
 void
 Global_translator::start ()
 {
@@ -100,9 +101,6 @@ Global_translator::run_iterator_on_me (Music_iterator * iter)
       w = sneaky_insert_extra_moment (w);
       
       //      printf ("proccing %s\n ",       w.string ().to_str0 ());
-
-
-      
       if (first)
        {
          first = false;
@@ -116,3 +114,39 @@ Global_translator::run_iterator_on_me (Music_iterator * iter)
       one_time_step ();
     }
 }
+
+void
+Global_translator::apply_finalizations ()
+{
+  SCM lst = get_property ("finalizations");
+  set_property ("finalizations" , SCM_EOL); 
+  for (SCM s = lst ; gh_pair_p (s); s = gh_cdr (s))
+    {
+      scm_primitive_eval (gh_car (s));
+    }
+}
+
+/*
+   Add a function to execute before stepping to the next time step.
+ */
+void
+Global_translator::add_finalization (SCM x)
+{
+  SCM lst = get_property ("finalizations");
+  lst = scm_cons (x, lst);
+  set_property ("finalizations" ,lst); 
+}
+
+
+Global_translator *
+Translator::top_translator()const
+{
+  if (dynamic_cast<Global_translator*>((Translator*)this))
+    return dynamic_cast<Global_translator*> ((Translator*)this);
+
+  if (daddy_trans_)
+    return daddy_trans_->top_translator ();
+
+  programming_error ("No top translator!");
+  return 0;
+}
index c59cc3fb43405ed729c370ae64e425c9459d20d7..39d814747cd4e53158e93396c9d46c3a2045e1cb 100644 (file)
@@ -14,8 +14,8 @@
 #include "moment.hh"
 #include "pqueue.hh"
 
-
-class Global_translator : public virtual Translator_group{
+class Global_translator : public virtual Translator_group
+{
   PQueue<Moment> extra_mom_pq_;
 public:
   VIRTUAL_COPY_CONS (Translator);
@@ -28,6 +28,9 @@ public:
   Moment sneaky_insert_extra_moment (Moment);
   void add_moment_to_process (Moment);
   void run_iterator_on_me (Music_iterator*);
+
+  void apply_finalizations ();
+  void add_finalization (SCM);
   
   virtual Music_output *get_output ();     
   virtual void prepare (Moment);
index c7c3cc5cda38f7c8bd9d511a95d77a40d5912a30..50485ed15c1a092cd007e2a047502ee48418296a 100644 (file)
@@ -23,8 +23,10 @@ class Property_iterator : public Simple_music_iterator
 public:
   VIRTUAL_COPY_CONS (Music_iterator);
   DECLARE_SCHEME_CALLBACK(constructor, ());
-  /* construction */
+  DECLARE_SCHEME_CALLBACK(once_finalization, (SCM, SCM ));
+
 protected:
+  virtual void do_quit();
   virtual void process (Moment);
 };
 
@@ -39,7 +41,6 @@ class Property_unset_iterator : public Simple_music_iterator
 public:
   VIRTUAL_COPY_CONS (Music_iterator);
   DECLARE_SCHEME_CALLBACK(constructor, ());
-  /* construction */
 protected:
   virtual void process (Moment);
 };
@@ -49,9 +50,10 @@ class Push_property_iterator : public Simple_music_iterator
 public:
   VIRTUAL_COPY_CONS (Music_iterator);
   DECLARE_SCHEME_CALLBACK(constructor, ());  
+  DECLARE_SCHEME_CALLBACK(once_finalization, (SCM, SCM));
 protected:
-  /* construction */
   virtual void process (Moment);
+  virtual void do_quit();
 };
 
 class Pop_property_iterator : public Simple_music_iterator
@@ -60,7 +62,6 @@ public:
   DECLARE_SCHEME_CALLBACK(constructor, ());
   VIRTUAL_COPY_CONS (Music_iterator);
 protected:
-  /* construction */
   virtual void process (Moment);
 };
 
index 97784a82a980136b90e27b5bc44c2cc6e97fb407..4b27559aa91c15b246b07ffc5df937d3dc857890 100644 (file)
@@ -66,7 +66,9 @@ public:
   SCM properties_scm_;
   DECLARE_SMOBS (Translator, dummy);
 
+
 public:
+  Global_translator * top_translator () const;
   TRANSLATOR_DECLARATIONS(Translator);
     /**
     try to fit the request in this engraver
index cff5ae13e698f155b5d202334d2d4ba70eb61390..48005225d18c895bc4f3bf781d24df77ab1a55cb 100644 (file)
@@ -58,6 +58,7 @@ static Keyword_ent the_key_tab[]={
   {"lyrics", LYRICS},
   {"key", KEY},
   {"mark", MARK},
+  {"once", ONCE},
   {"pitch", PITCH},
   {"time", TIME_T},
   {"times", TIMES},
index e7256e8bbe038858ffbb6bdb2269fe9fb4e4b5cc..7964a2966e0885e25739209655da14047de8df80 100644 (file)
@@ -66,6 +66,10 @@ Note_spacing::get_spacing (Grob *me, Item* right_col,
              if (!g)
                g =  Note_column::first_head (it);
 
+             /*
+               Ugh. If Stem is switched off, we don't know what the
+               first note head will be.
+              */
              if (g)
                left_head_wid = g->extent(it_col, X_AXIS);
            }
@@ -102,7 +106,8 @@ Note_spacing::get_spacing (Grob *me, Item* right_col,
   */
   *fixed = left_head_wid.empty_b () ? increment : left_head_wid[RIGHT];
   *space = (base_space - increment) + *fixed +
-    (extents[LEFT][RIGHT] - left_head_wid[RIGHT])/ 2;
+    (extents[LEFT][RIGHT]
+     - (left_head_wid.empty_b () ? 0.0 : left_head_wid[RIGHT]))/ 2;
     ;
 
   if (*space - *fixed < 2 * ((- extents[RIGHT][LEFT]) >? 0))
@@ -233,7 +238,7 @@ Note_spacing::stem_dir_correction (Grob*me, Item * rcolumn,
          
          Grob *stem = Note_column::get_stem (it);
 
-         if (!stem)
+         if (!stem || !stem->live ())
            {
              if (d == RIGHT && Separation_item::has_interface (it))
                {
index 450fa77c5f0e35b7dc518ecba64cece2c55723d0..99ff6633534efbb7039a2bc11f6ff13e91075011 100644 (file)
@@ -210,6 +210,7 @@ yylex (YYSTYPE *s,  void * v)
 %token NAME
 %token PITCHNAMES
 %token NOTES
+%token ONCE
 %token PAPER
 %token PARTIAL
 %token PENALTY
@@ -283,7 +284,6 @@ yylex (YYSTYPE *s,  void * v)
 %type <i>      tremolo_type
 %type <i>      bare_int  bare_unsigned
 %type <i>      script_dir
-
 %type <scm>    identifier_init 
 
 %type <scm> steno_duration optional_notemode_duration multiplied_duration
@@ -302,7 +302,7 @@ yylex (YYSTYPE *s,  void * v)
 %type <scm>  embedded_scm scalar
 %type <music>  Music Sequential_music Simultaneous_music 
 %type <music>  relative_music re_rhythmed_music part_combined_music
-%type <music>  property_def translator_change
+%type <music>  property_def translator_change  simple_property_def
 %type <scm> Music_list
 %type <outputdef>  music_output_def_body
 %type <request> shorthand_command_req
@@ -1038,6 +1038,15 @@ translator_change:
        ;
 
 property_def:
+       simple_property_def
+       | ONCE simple_property_def {
+               $$ = $2;
+               SCM e = $2->get_mus_property ("element");
+               unsmob_music (e)->set_mus_property ("once", SCM_BOOL_T);
+       }
+       ;
+
+simple_property_def:
        PROPERTY STRING '.' STRING '='  scalar {
                
                Music *t = set_property_music (scm_string_to_symbol ($4), $6);
@@ -1090,7 +1099,9 @@ property_def:
 
                csm-> set_mus_property ("context-type", $2);
        }
-       | PROPERTY STRING '.' STRING OVERRIDE embedded_scm '=' embedded_scm {
+       | PROPERTY STRING '.' STRING OVERRIDE
+               embedded_scm '=' embedded_scm
+       {
                /*
                        UGH UGH UGH UGH.
                */
@@ -1118,6 +1129,7 @@ property_def:
                $$->set_spot (THIS->here_input ());
 
                csm-> set_mus_property ("context-type", $2);
+
        }
        | PROPERTY STRING '.' STRING REVERT embedded_scm {
                Music *t = new Music (SCM_EOL);
index 480b506858d7fe62b885c1cf14861351a42ec91c..cf018f4f2ab3ef7166b52f55dea59ecadf45d5a6 100644 (file)
@@ -10,6 +10,7 @@
 #include "music.hh"
 #include "translator-def.hh"
 #include "translator-group.hh"
+#include "global-translator.hh"
 
 
 bool check_grob(Music *mus, SCM sym);
@@ -44,6 +45,34 @@ Property_unset_iterator::process (Moment m)
   Simple_music_iterator::process (m);
 }
 
+MAKE_SCHEME_CALLBACK(Property_iterator,once_finalization, 2);
+SCM
+Property_iterator::once_finalization(SCM translator, SCM music )
+{
+  Music * m = unsmob_music (music);
+  Translator_group * tg
+    = dynamic_cast<Translator_group*> (unsmob_translator (translator));
+  SCM sym = m->get_mus_property ("symbol");
+
+  tg->unset_property (sym);
+  return SCM_UNSPECIFIED;
+}
+
+void
+Property_iterator::do_quit ()
+{
+  if (to_boolean (get_music ()->get_mus_property  ("once")))
+    {
+      SCM trans = report_to()->self_scm();
+      SCM music = get_music()->self_scm();
+
+      Global_translator * tg=  report_to()->top_translator ();
+
+      tg->add_finalization (scm_list_n (once_finalization_proc,
+                                       trans, music, SCM_UNDEFINED));
+    }
+}
+
 
 SCM list_p = 0;
 
@@ -75,13 +104,47 @@ Push_property_iterator::process (Moment m)
       SCM eprop = get_music ()->get_mus_property ("grob-property");
       SCM val = get_music ()->get_mus_property ("grob-value");
 
-      if (to_boolean (get_music ()->get_mus_property ("pop-first")))
+      if (to_boolean (get_music ()->get_mus_property ("pop-first"))
+         && !to_boolean (get_music ()->get_mus_property ("once"))
+         )
        Translator_def::apply_pushpop_property (report_to (),
                                                sym, eprop, SCM_UNDEFINED);
 
-      Translator_def::apply_pushpop_property (report_to (), sym, eprop, val);
+      translator_def::apply_pushpop_property (report_to (), sym, eprop, val);
+    }
+  simple_music_iterator::process (m);
+}
+
+make_scheme_callback(push_property_iterator,once_finalization, 2);
+scm
+push_property_iterator::once_finalization (scm trans, scm music)
+{
+  music * mus = unsmob_music (music);
+  translator_group *tg
+    = dynamic_cast<translator_group*> (unsmob_translator (trans));
+
+  scm sym = mus->get_mus_property ("symbol");
+  if (check_grob (mus, sym))
+    {
+      scm eprop = mus->get_mus_property ("grob-property");
+  
+      translator_def::apply_pushpop_property (tg, sym, eprop, scm_undefined);
+    }
+  return scm_unspecified;
+}
+
+void
+Push_property_iterator::do_quit ()
+{
+  if (to_boolean (get_music ()->get_mus_property  ("once")))
+    {
+      SCM trans = report_to()->self_scm();
+      SCM music = get_music ()->self_scm();
+
+      Global_translator * tg=  report_to()->top_translator ();
+      tg->add_finalization (scm_list_n (once_finalization_proc,
+                                       trans, music, SCM_UNDEFINED));
     }
-  Simple_music_iterator::process (m);
 }
 
 void
@@ -97,7 +160,9 @@ Pop_property_iterator::process (Moment m)
 }
 
 
+
 IMPLEMENT_CTOR_CALLBACK (Pop_property_iterator);
 IMPLEMENT_CTOR_CALLBACK (Push_property_iterator);
 IMPLEMENT_CTOR_CALLBACK (Property_iterator);
 IMPLEMENT_CTOR_CALLBACK (Property_unset_iterator);
+
index 693158620ba71fbc41889ffb947651fdf95b8a3c..ce13f5ec447eee430d1a684c00f92d29a064aa66 100644 (file)
@@ -55,11 +55,8 @@ Score_engraver::make_columns ()
       Grob_info i2 (musical_column_);
       i2.origin_trans_ = this;
 
-  
       announce_grob (i1);
       announce_grob (i2);
-
-      
     }
 }
 
@@ -145,6 +142,8 @@ Score_engraver::one_time_step ()
     }
   
   stop_translation_timestep ();
+  
+  apply_finalizations ();
   check_removal ();
 
 
@@ -176,7 +175,6 @@ Score_engraver::typeset_grob (Grob *elem)
   if (!elem)
     programming_error ("Score_engraver: empty elt\n");
   else
-
     elems_.push (elem);
 }
 
index edd5ab5ee80aa3d93f13dd20e221c1c75edc1fbe..7c6f6c4a4659f5f8ab7ab1036f58882d69584324 100644 (file)
@@ -52,7 +52,8 @@ Sequential_iterator::get_music_list () const
 void
 Sequential_iterator::do_quit ()
 {
-  if (iter_) iter_->quit();
+  if (iter_)
+    iter_->quit();
 }