]> git.donarmstrong.com Git - lilypond.git/blob - lily/dynamic-engraver.cc
d5419588446007feaffcf4426e6d177cae55c895
[lilypond.git] / lily / dynamic-engraver.cc
1 /*
2   dynamic-reg.cc -- implement Dynamic_engraver
3
4   source file of the GNU LilyPond music typesetter
5
6   (c)  1997--1998 Han-Wen Nienhuys <hanwen@cs.uu.nl>
7 */
8 #include "debug.hh"
9 #include "crescendo.hh"
10 #include "dynamic-engraver.hh"
11 #include "musical-request.hh"
12 #include "text-item.hh"
13 #include "lookup.hh"
14 #include "paper-def.hh"
15 #include "score-column.hh"
16 #include "staff-sym.hh"
17 #include "note-column.hh"
18
19 Dynamic_engraver::Dynamic_engraver()
20 {
21   do_post_move_processing();
22   dir_ = CENTER;
23   dynamic_p_ =0;
24   to_end_cresc_p_ = cresc_p_ = 0;
25   cresc_req_l_ = 0;
26 }
27
28 void
29 Dynamic_engraver::do_post_move_processing()
30 {
31   dynamic_req_l_arr_.clear();
32 }
33
34 bool
35 Dynamic_engraver::do_try_music (Music * r)
36 {
37   if(Dynamic_req * d = dynamic_cast <Dynamic_req *> (r))
38     {
39       for (int i=0; i < dynamic_req_l_arr_.size (); i++)
40         if (d->equal_b (dynamic_req_l_arr_[i]))
41           return true;
42       
43       dynamic_req_l_arr_.push (d);
44       return true;
45     }
46   return false;
47 }
48 void
49 Dynamic_engraver::do_process_requests()
50 {
51   Crescendo*  new_cresc_p=0;
52   for (int i=0; i < dynamic_req_l_arr_.size(); i++)
53     {
54       Dynamic_req *dreq_l = dynamic_req_l_arr_[i];
55       if (Absolute_dynamic_req *absd = dynamic_cast<Absolute_dynamic_req *> (dreq_l))
56         {
57
58           if (dynamic_p_)
59             {
60               dynamic_req_l_arr_[i]->warning (_("Got a dynamic already.  Continuing dazed and confused"));
61               continue;
62             }
63           
64           Text_def * td_p = new Text_def;
65           String loud = absd->loudness_str ();
66           td_p->text_str_ =  paper ()->lookup_l (0)->dynamic (loud).str_; // ugh
67           td_p->style_str_ = "dynamic";
68           td_p->align_dir_ = RIGHT;
69           Real nw_f = paper ()->note_width () * 0.8;
70
71           dynamic_p_ = new Text_item (td_p);
72           dynamic_p_->translate (Offset (nw_f, 0));
73
74           announce_element (Score_element_info (dynamic_p_, dreq_l));
75         }
76       else if (Span_dynamic_req *span_l = dynamic_cast <Span_dynamic_req *> (dreq_l))
77         {
78           if (span_l->spantype == Span_req::STOP)
79             {
80               if (!cresc_p_)
81                 {
82                   span_l->warning (_ ("can't find (de)crescendo to end"));
83                 }
84               else
85                 {
86                   assert (!to_end_cresc_p_);
87                   to_end_cresc_p_ =cresc_p_;
88                   cresc_p_ = 0;
89                 }
90             }
91           else if (span_l->spantype == Span_req::START)
92             {
93               cresc_req_l_ = span_l;
94               assert (!new_cresc_p);
95               new_cresc_p  = new Crescendo;
96               new_cresc_p->grow_dir_ = span_l->dynamic_dir_;
97               announce_element (Score_element_info (new_cresc_p, span_l));
98             }
99         }
100     }
101
102   if (new_cresc_p)
103     {
104       if (cresc_p_)
105         {
106           ::warning (_ ("Too many crescendi here"));
107           typeset_element (cresc_p_);
108           cresc_p_ = 0;
109         }
110       
111       cresc_p_ = new_cresc_p;
112       cresc_p_->set_bounds(LEFT,get_staff_info().musical_l ());
113       if (dynamic_p_)
114         {
115           cresc_p_->dyn_b_drul_[LEFT] = true;
116         }
117     }
118 }
119
120 void
121 Dynamic_engraver::do_pre_move_processing()
122 {
123   Staff_symbol* s_l = get_staff_info().staff_sym_l_;
124   if (to_end_cresc_p_)
125     {
126       if (dynamic_p_)
127         to_end_cresc_p_->dyn_b_drul_[RIGHT]=true;
128
129
130       Scalar prop = get_property ("dynamicdir");
131       if (prop.isnum_b ())
132        {
133          to_end_cresc_p_->dir_ = (Direction) (int) prop;
134        }
135       to_end_cresc_p_->set_bounds(RIGHT,get_staff_info().musical_l ());
136       to_end_cresc_p_->add_support (s_l);
137       typeset_element (to_end_cresc_p_);
138       to_end_cresc_p_ = 0;
139     }
140   if (dynamic_p_)
141     {
142       Scalar prop = get_property ("dynamicdir");
143       if (prop.isnum_b ())
144        {
145          dynamic_p_->dir_ = (Direction) (int) prop;
146        }
147       
148       dynamic_p_->add_support (s_l);
149       typeset_element (dynamic_p_);
150       dynamic_p_ = 0;
151     }
152 }
153
154
155
156 ADD_THIS_TRANSLATOR(Dynamic_engraver);
157
158 void
159 Dynamic_engraver::do_removal_processing ()
160 {
161   if (cresc_p_)
162     {
163       typeset_element (cresc_p_ );
164       
165       cresc_req_l_->warning (_ ("unended crescendo"));
166       cresc_p_ =0;
167     }
168   if (to_end_cresc_p_)
169     {
170       typeset_element (to_end_cresc_p_);
171       to_end_cresc_p_ =0;
172     }
173   if (dynamic_p_)
174     {
175       typeset_element (dynamic_p_);
176       dynamic_p_ =0;
177     }
178 }
179
180 void
181 Dynamic_engraver::acknowledge_element (Score_element_info i)
182 {
183   if (dynamic_cast<Note_column *> (i.elem_l_))
184     {
185       if (dynamic_p_)
186         dynamic_p_->add_support (i.elem_l_);
187
188       if (to_end_cresc_p_)
189         to_end_cresc_p_->add_support (i.elem_l_);
190
191       if (cresc_p_)
192         cresc_p_->add_support (i.elem_l_);
193     }
194 }