]> git.donarmstrong.com Git - lilypond.git/commitdiff
patch::: 1.3.31.jcn1
authorJan Nieuwenhuizen <janneke@gnu.org>
Thu, 9 Mar 2000 13:27:13 +0000 (14:27 +0100)
committerJan Nieuwenhuizen <janneke@gnu.org>
Thu, 9 Mar 2000 13:27:13 +0000 (14:27 +0100)
1.3.30.jcn4
===========

* Adjacent dynamic markings are now grouped on a horizontal line, but it's
  not perfect yet: they're always below the staff and no horizontal spacing
  is done.  Also, character metrics of dynamics are still not used.
  See: input/test/crescendi.ly and input/test/dyn-line.ly

* Cleaned up Span_dynamic_performer.

CHANGES
VERSION
input/test/crescendi.ly
input/test/dyn-line.ly [new file with mode: 0644]
input/test/span-dynamic.ly
lily/dynamic-engraver.cc
lily/rest-collision.cc
lily/span-dynamic-performer.cc

diff --git a/CHANGES b/CHANGES
index 9e5717579120a9f784e91c9a834b81df9b61f472..4b8dcfb1ea11e2eb1dd8e38e5cfb9cfe6a9953f2 100644 (file)
--- a/CHANGES
+++ b/CHANGES
@@ -1,3 +1,13 @@
+1.3.30.jcn4
+===========
+
+* Adjacent dynamic markings are now grouped on a horizontal line, but it's
+  not perfect yet: they're always below the staff and no horizontal spacing
+  is done.  Also, character metrics of dynamics are still not used.
+  See: input/test/crescendi.ly and input/test/dyn-line.ly
+
+* Cleaned up Span_dynamic_performer.
+
 1.3.30.mb1
 =========
 
 1.3.30.jcn3
 ===========
 
-* Span_dynamic_performer; perform crescendi/decrescendi.  Bit scrappy.
+* Lily now also performs crescendi and decrescendi in MIDI output:
+  Span_dynamic_performer (bit scrappy).
 
-* Preliminary support for crescendi/decrescendi other than `hairpins', eg:
-  `cresc. poco `a poco -- -- --'
+* Added preliminary support for crescendi/decrescendi other than `hairpins',
+  eg: `cresc. poco `a poco -- -- --'
 
-* Tie performance fix.
+* Made MIDI tie performance fix.
 
 1.3.30.jcn2
 ===========
 
-* Dynamic_performer: performs absolute dynamic requests.
+* Lily now performs absolute dynamics in MIDI output.
 
-* David's comments on opus47
+* Included David's comments on opus47 in TODO.
 
 1.3.30.jcn1
 ===========
diff --git a/VERSION b/VERSION
index 023bbc67dee1740d78ad71ab1e48dc2cf917337d..103c9b2621a5fffc3424ffdd60650ac27fa796fd 100644 (file)
--- a/VERSION
+++ b/VERSION
@@ -2,7 +2,7 @@ PACKAGE_NAME=LilyPond
 MAJOR_VERSION=1
 MINOR_VERSION=3
 PATCH_LEVEL=31
-MY_PATCH_LEVEL=
+MY_PATCH_LEVEL=jcn1
 
 # use the above to send patches: MY_PATCH_LEVEL is always empty for a
 # released version.
index 3d4774187581c5b1e91c97259b5d1728fc976652..0175ce9ccc29190652ac1572cab51b5d630b3b1f 100644 (file)
@@ -1,13 +1,11 @@
 \score{
 \notes\relative c''{
-a1\fff\< \!a
-a\> \!a
+a1\fff\> \!a\pp
+a\< \!a
 \property Voice.crescendoText = "cresc."
 \property Voice.crescendoSpanner = "dashed-line"
 a\mf\cresc \endcresc a
-%a\decresc \enddecresc a
-a1\< \!a
-a\> \!a
+a\< \!a
 }
 \paper{
 }
diff --git a/input/test/dyn-line.ly b/input/test/dyn-line.ly
new file mode 100644 (file)
index 0000000..38f023b
--- /dev/null
@@ -0,0 +1,19 @@
+\score{
+\notes\relative c''{
+a1\fff\> \!c,,\pp a'' a\p
+
+
+% We need this to test if we get two Dynamic line spanners
+a
+
+% because Dynamic_engraver::do_removal_processing ()
+% doesn't seem to do its job?
+a\f
+
+}
+\paper{
+}
+\midi{
+\tempo 1 = 60;
+}
+}
index 8c48f7d3a0342db3506039e4d8a684d855dc187f..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,17 +0,0 @@
-\score{
-\notes\relative c''{
-a1\ppp\<
-a
-a
-a
-a
-a
-a
-\!a\fff
-}
-\paper{
-}
-\midi{
-\tempo 1 = 60;
-}
-}
index 254271080f1110fef47d0575d3b998ee95a35e26..c1d91728797ef43ef948fa833bf3411d9d46b0a1 100644 (file)
@@ -1,11 +1,12 @@
 /*
-  dynamic-reg.cc -- implement Dynamic_engraver
+  dynamic-engraver.cc -- implement Dynamic_engraver
 
   source file of the GNU LilyPond music typesetter
 
   (c)  1997--2000 Han-Wen Nienhuys <hanwen@cs.uu.nl>
 */
 #include "debug.hh"
+#include "dimensions.hh"
 #include "crescendo.hh"
 #include "musical-request.hh"
 #include "lookup.hh"
 #include "stem.hh"
 #include "note-head.hh"
 #include "group-interface.hh"
+#include "directional-element-interface.hh"
+#include "staff-symbol-referencer.hh"
+
+#define DYN_LINE
+
+#ifdef DYN_LINE
+
+class Dynamic_line_spanner : public Spanner
+{
+public:
+  Dynamic_line_spanner ();
+  
+  void add_element (Score_element*);
+  void add_column (Note_column*);
+  Direction get_default_dir () const;
+
+protected:
+  virtual void do_add_processing ();
+  // URG: see Dynamic_engraver::do_removal_processing
+  friend class Dynamic_engraver;
+  virtual void do_post_processing ();
+
+private:
+  void translate_elements (Real);
+  Real get_extreme_y () const;
+};
+
+Dynamic_line_spanner::Dynamic_line_spanner ()
+{
+  set_elt_property ("transparent", SCM_BOOL_T);
+}
+
+void
+Dynamic_line_spanner::add_element (Score_element* e)
+{
+  Group_interface gi (this, "elements");
+  gi.add_element (e);
+  //?
+  Side_position_interface (e).set_axis (Y_AXIS);
+  add_dependency (e);
+}
+
+void
+Dynamic_line_spanner::add_column (Note_column* n)
+{
+  Group_interface gi (this, "note-columns");
+  gi.add_element (n);
+  add_dependency (n);
+}
+
+/*
+  Copied (urg: literally!) from slur.
+  Why not do this once, at post-processing stage?
+ */
+void
+Dynamic_line_spanner::do_add_processing ()
+{
+  Link_array<Note_column> encompass_arr =
+    Group_interface__extract_elements (this, (Note_column*)0, "note-columns");
+
+  if (encompass_arr.size ())
+    {
+      set_bounds (LEFT, encompass_arr[0]);    
+      if (encompass_arr.size () > 1)
+       set_bounds (RIGHT, encompass_arr.top ());
+    }
+}
+
+#if 0
+Molecule
+Dynamic_line_spanner::do_brew_molecule () const
+{
+  return Molecule ();
+}
+#endif
+
+void
+Dynamic_line_spanner::do_post_processing ()
+{
+  translate_elements (get_extreme_y ());
+}
+
+void
+Dynamic_line_spanner::translate_elements (Real dy)
+{
+  SCM s = get_elt_property ("elements");
+  for (; gh_pair_p (s); s = gh_cdr (s))
+    {
+      Score_element* se = unsmob_element (gh_car (s));
+      se->translate_axis (dy, Y_AXIS);
+    }
+}
+
+Direction
+Dynamic_line_spanner::get_default_dir () const
+{
+  return DOWN;
+  //Direction dir = directional_element (this).get ();
+}
+
+Real
+Dynamic_line_spanner::get_extreme_y () const
+{
+  Link_array<Note_column> encompass_arr =
+    Group_interface__extract_elements (this, (Note_column*)0, "note-columns");
+  
+  Staff_symbol_referencer_interface si (this);
+  int stafflines = si.line_count ();
+  //hurg?
+  stafflines = stafflines != 0 ? stafflines : 5;
+  Direction dir = get_default_dir ();
+
+  Real staff_space = si.staff_space ();
+  // burp?  when are these available?
+  staff_space = staff_space != 0 ? staff_space : 5 PT;
+
+  // urg: TODO: padding
+  Real y = (stafflines / 2 + 1) * staff_space;
+
+  for (int i = 0; i < encompass_arr.size (); i++)
+    {
+      Note_column* column = encompass_arr[i];
+      Stem* stem = column->stem_l ();
+      if (stem)
+       {
+         Direction stem_dir = directional_element (stem).get ();
+         if ((stem_dir == dir)
+             && !stem->extent (Y_AXIS).empty_b ())
+           {
+             y = y >? (stem->extent (Y_AXIS)[dir]) * dir;
+           }
+         else
+           {
+             y = y >? (column->extent (Y_AXIS)[dir]) * dir;
+           }
+       }
+    }
+
+  return y * dir;
+}
+
+#endif
 
 /*
   TODO:
@@ -43,6 +186,15 @@ class Dynamic_engraver : public Engraver
 
   Span_req * cresc_req_l_;
   Array<Request*> dynamic_req_l_arr_;
+
+#ifdef DYN_LINE
+  /*
+    We probably need two of these: line-up above and below staff
+   */
+  Dynamic_line_spanner* spanner_;
+  Moment last_request_mom_;
+#endif
+  
   void  typeset_all ();
 public:
   VIRTUAL_COPY_CONS(Translator);
@@ -61,6 +213,8 @@ protected:
   virtual void typeset_element (Score_element*);
 };
 
+ADD_THIS_TRANSLATOR (Dynamic_engraver);
+
 void
 Dynamic_engraver::announce_element (Score_element_info i)
 {
@@ -70,13 +224,16 @@ Dynamic_engraver::announce_element (Score_element_info i)
 }
 
 
-Dynamic_engraver::Dynamic_engraver()
+Dynamic_engraver::Dynamic_engraver ()
 {
   do_post_move_processing();
   abs_text_p_ = 0;
   cr_text_p_ = 0;
   to_end_cresc_p_ = cresc_p_ = 0;
   cresc_req_l_ = 0;
+#ifdef DYN_LINE
+  spanner_ = 0;
+#endif
 }
 
 void
@@ -85,6 +242,9 @@ Dynamic_engraver::do_post_move_processing()
   dynamic_req_l_arr_.clear();
 }
 
+/*
+  ugr
+ */
 bool
 Dynamic_engraver::do_try_music (Music * m)
 {
@@ -104,6 +264,12 @@ Dynamic_engraver::do_try_music (Music * m)
   else
     return false;
   
+#ifdef DYN_LINE
+  if (!spanner_)
+    spanner_ = new Dynamic_line_spanner;
+  last_request_mom_ = now_mom ();
+#endif
+  
   for (int i=0; i < dynamic_req_l_arr_.size (); i++)
     if (r->equal_b (dynamic_req_l_arr_[i]))
       return true;
@@ -138,8 +304,11 @@ Dynamic_engraver::do_process_requests()
          abs_text_p_->set_elt_property ("script-priority",
                                     gh_int2scm (100));
          
+#ifdef DYN_LINE
+         assert (spanner_);
+         spanner_->add_element (abs_text_p_);
+#else
          Side_position_interface (abs_text_p_).set_axis (Y_AXIS);
-
          
          if (absd->get_direction ())
            {
@@ -164,7 +333,9 @@ Dynamic_engraver::do_process_requests()
            {
              abs_text_p_->set_elt_property ("padding", prop);
            }
+#endif
          announce_element (Score_element_info (abs_text_p_, absd));
+
        }
       else if (Span_req *span_l
               = dynamic_cast <Span_req *> (dynamic_req_l_arr_[i]))
@@ -222,6 +393,12 @@ Dynamic_engraver::do_process_requests()
                      Side_position_interface (cr_text_p_).set_axis (X_AXIS);
                      Side_position_interface (cr_text_p_).add_support (abs_text_p_);
                    }
+
+#ifdef DYN_LINE
+                 assert (spanner_);
+                 spanner_->add_element (cr_text_p_);
+#endif
+
                  //Side_position_interface (cr_text_p_).set_axis (Y_AXIS);
                  announce_element (Score_element_info (cr_text_p_, span_l));
                }
@@ -232,7 +409,13 @@ Dynamic_engraver::do_process_requests()
                  new_cresc_p->set_elt_property ("spanner", s);
                }
          
+#ifdef DYN_LINE
+             assert (spanner_);
+             spanner_->add_element (new_cresc_p);
+#else
+             // what's the diff between side_position and Side_pos_iface?
              side_position (new_cresc_p).set_axis (Y_AXIS);
+#endif
              announce_element (Score_element_info (new_cresc_p, span_l));
            }
        }
@@ -262,6 +445,7 @@ Dynamic_engraver::do_process_requests()
                            RIGHT, SCM_BOOL_T);
        }
     }
+
 }
 
 void
@@ -270,10 +454,6 @@ Dynamic_engraver::do_pre_move_processing()
   typeset_all ();
 }
 
-
-
-ADD_THIS_TRANSLATOR(Dynamic_engraver);
-
 void
 Dynamic_engraver::do_removal_processing ()
 {
@@ -283,6 +463,15 @@ Dynamic_engraver::do_removal_processing ()
       cresc_req_l_->warning (_ ("unended crescendo"));
       cresc_p_ =0;
     }
+#ifdef DYN_LINE
+  if (spanner_)
+    {
+      // URG urg.  We did't get a post_processing call !?
+      spanner_->do_post_processing ();
+      typeset_element (spanner_);
+      spanner_ = 0;
+    }
+#endif
   typeset_all ();
 }
 
@@ -310,15 +499,44 @@ Dynamic_engraver::typeset_all ()
       typeset_element (cr_text_p_);
       cr_text_p_ = 0;
     }
+#ifdef DYN_LINE
+  /*
+    TODO: This should be optionised:
+      * break when group of dynamic requests ends
+      * break now 
+      * continue through piece
+   */
+  if (spanner_ && last_request_mom_ < now_mom ())
+    {
+      typeset_element (spanner_);
+      spanner_ = 0;
+    }
+#endif
 }
 
 void
 Dynamic_engraver::typeset_element (Score_element * e)
 {
+#ifndef DYN_LINE
   side_position(e).add_staff_support ();
+#endif
   Engraver::typeset_element (e);
 }
 
+#ifdef DYN_LINE
+
+void
+Dynamic_engraver::acknowledge_element (Score_element_info i)
+{
+  if (spanner_)
+    {
+      if (Note_column* n = dynamic_cast<Note_column*> (i.elem_l_))
+       spanner_->add_column (n);
+    }
+}
+
+#else
+
 void
 Dynamic_engraver::acknowledge_element (Score_element_info i)
 {
@@ -343,3 +561,4 @@ Dynamic_engraver::acknowledge_element (Score_element_info i)
     }
 }
 
+#endif
index 6bdfe4eaf2282d76f97e39bc6db0c57b3003d8b3..07ab3c764aa789991245e082ef68dec9d3e24275 100644 (file)
@@ -17,6 +17,7 @@
 #include "paper-def.hh"
 #include "rest.hh"
 #include "group-interface.hh"
+#include "staff-symbol-referencer.hh"
 
 void
 Rest_collision::add_column (Note_column *nc_l)
@@ -115,8 +116,10 @@ Rest_collision::do_pre_processing()
 
 
       // FIXME
-      int stafflines = 5; // rcol->rest_l_arr[0]->line_count;
-
+      //int stafflines = 5; // rcol->rest_l_arr[0]->line_count;
+      int stafflines = Staff_symbol_referencer_interface (this).line_count ();
+      // hurg?
+      stafflines = stafflines != 0 ? stafflines : 5;
       
       // move discretely by half spaces.
       int discrete_dist = int (ceil (dist / (0.5 *staff_space)));
index c6f115901a8bf1404d0c2d2dccb426366e1afb5e..415852f5733371276779f555a70d3e7637298823 100644 (file)
@@ -18,7 +18,7 @@ struct Audio_dynamic_tuple
 };
 
 /**
-   handle perform span-dynamics
+   perform span-dynamics
  */
 class Span_dynamic_performer : public Performer
 {
@@ -34,17 +34,11 @@ protected:
   virtual void do_pre_move_processing ();
 
 private:
+  Audio_dynamic* audio_p_;
   Drul_array<Span_req*> request_drul_;
-  Drul_array<Moment> moment_drul_;
-  Drul_array<int> volume_drul_;
   Array<Audio_dynamic_tuple> dynamic_tuple_arr_;
-
-  // BURP
-  Drul_array<Moment> done_moment_drul_;
-  Drul_array<int> done_volume_drul_;
-  Array<Audio_dynamic_tuple> done_dynamic_tuple_arr_;
-
-  Audio_dynamic* audio_p_;
+  Array<Audio_dynamic_tuple> finished_dynamic_tuple_arr_;
+  Direction finished_dir_;
 };
 
 ADD_THIS_TRANSLATOR (Span_dynamic_performer);
@@ -52,7 +46,6 @@ ADD_THIS_TRANSLATOR (Span_dynamic_performer);
 Span_dynamic_performer::Span_dynamic_performer ()
 {
   request_drul_[START] = request_drul_[STOP] = 0;
-  volume_drul_[START] = volume_drul_[STOP] = 0;
   audio_p_ = 0;
 }
 
@@ -61,59 +54,64 @@ Span_dynamic_performer::acknowledge_element (Audio_element_info i)
 {
   if (Audio_dynamic * d = dynamic_cast <Audio_dynamic*> (i.elem_l_))
     {
-      Direction dir = volume_drul_[START] ? STOP : START;
-      volume_drul_[dir] = d->volume_i_;
-      if (done_dynamic_tuple_arr_.size ())
-       done_volume_drul_[STOP] = d->volume_i_;
-#if 0
       Audio_dynamic_tuple a = { d, now_mom () };
+      if (!request_drul_[START])
+       dynamic_tuple_arr_.clear ();
       dynamic_tuple_arr_.push (a);
-#endif
+      if (finished_dynamic_tuple_arr_.size ())
+       finished_dynamic_tuple_arr_.push (a);
     }
 }
 
 void
 Span_dynamic_performer::do_process_requests ()
 {
-  if (request_drul_[START])
-    {
-      audio_p_ = new Audio_dynamic (volume_drul_[START]);
-      Audio_element_info info (audio_p_, 0);
-      announce_element (info);
-
-      Audio_dynamic_tuple a = { audio_p_, now_mom () };
-      dynamic_tuple_arr_.push (a);
-    }
-
-  if (done_dynamic_tuple_arr_.size ())
+  if (finished_dynamic_tuple_arr_.size () > 1
+     && finished_dynamic_tuple_arr_.top ().audio_l_->volume_i_)
     {
-      if (done_volume_drul_[STOP])
+      Real start_volume = finished_dynamic_tuple_arr_[0].audio_l_->volume_i_;
+      Real dv = finished_dynamic_tuple_arr_.top ().audio_l_->volume_i_
+       - start_volume;
+      if (!dv)
+       {
+         // urg.  about one volume step
+         dv = (int)finished_dir_ * 13;
+         if (!start_volume)
+           start_volume = finished_dynamic_tuple_arr_.top
+             ().audio_l_->volume_i_ - dv;
+       }
+      Moment start_mom = finished_dynamic_tuple_arr_[0].mom_;
+      Moment dt = finished_dynamic_tuple_arr_.top ().mom_ - start_mom;
+      for (int i=0; i < finished_dynamic_tuple_arr_.size (); i++)
        {
-         Real dv = done_volume_drul_[STOP] - done_volume_drul_[START];
-         Moment dt = done_moment_drul_[STOP] - done_moment_drul_[START];
-         for (int i=0; i < done_dynamic_tuple_arr_.size (); i++)
-           {
-             Real volume =
-               (done_volume_drul_[START]
-                + dv * (Real)(done_dynamic_tuple_arr_[i].mom_
-                              - done_moment_drul_[START]) / (Real)dt);
-             done_dynamic_tuple_arr_[i].audio_l_->volume_i_ = (int)volume;
-           }
+         Audio_dynamic_tuple* a = &finished_dynamic_tuple_arr_[i];
+         Real volume = start_volume + dv * (Real)(a->mom_ - start_mom)
+           / (Real)dt;
+         a->audio_l_->volume_i_ = (int)volume;
        }
-      done_dynamic_tuple_arr_.clear ();
+      finished_dynamic_tuple_arr_.clear ();
     }
 
   if (request_drul_[STOP])
     {
-      done_dynamic_tuple_arr_ = dynamic_tuple_arr_;
+      finished_dynamic_tuple_arr_ = dynamic_tuple_arr_;
+      finished_dir_ = request_drul_[STOP]->span_type_str_ == "crescendo"
+       ? RIGHT : LEFT;
       dynamic_tuple_arr_.clear ();
-      done_volume_drul_[START] = volume_drul_[START];
-      done_volume_drul_[STOP] = volume_drul_[STOP];
-      done_moment_drul_[START] = moment_drul_[START];
-      done_moment_drul_[STOP] = moment_drul_[STOP];
+      if (finished_dynamic_tuple_arr_.size ())
+       dynamic_tuple_arr_.push (finished_dynamic_tuple_arr_.top ());
       request_drul_[STOP] = 0;
-      volume_drul_[START] = volume_drul_[STOP];
-      volume_drul_[STOP] = 0;
+      request_drul_[START] = 0;
+    }
+
+  if (request_drul_[START])
+    {
+      audio_p_ = new Audio_dynamic (0);
+      Audio_element_info info (audio_p_, 0);
+      announce_element (info);
+
+      Audio_dynamic_tuple a = { audio_p_, now_mom () };
+      dynamic_tuple_arr_.push (a);
     }
 }
 
@@ -144,9 +142,6 @@ Span_dynamic_performer::do_try_music (Music* r)
          return false;
        }
       request_drul_[d] = s;
-      moment_drul_[d] = now_mom ();
-      if (d == START && volume_drul_[STOP])
-       volume_drul_[START] = volume_drul_[STOP];
       return true;
     }
   return false;