]> git.donarmstrong.com Git - lilypond.git/blob - lily/timing-translator.cc
release: 1.3.131
[lilypond.git] / lily / timing-translator.cc
1 /*
2   timing-translator.cc -- implement Timing_translator
3
4
5   source file of the GNU LilyPond music typesetter
6
7   (c)  1997--2001 Han-Wen Nienhuys <hanwen@cs.uu.nl>
8 */
9
10 #include "debug.hh"
11 #include "timing-translator.hh"
12 #include "command-request.hh"
13 #include "translator-group.hh"
14 #include "global-translator.hh"
15 #include "multi-measure-rest.hh"
16
17 /*
18   TODO: change the rest of lily, so communication with
19   Timing_translator is only done through properties.  This means the
20   class declaration can go here.  */
21
22 bool
23 Timing_translator::try_music (Music*r)
24 {
25   if (dynamic_cast<Barcheck_req*> (r))
26     {
27       check_ = r;
28       return true;
29     }
30   return false;
31 }
32
33 void
34 Timing_translator::process_music()
35 {
36   if (check_ && measure_position ())
37     {
38       check_->origin ()->warning (_f ("barcheck failed at: %s", 
39                                       measure_position ().str ()));
40       Moment zero; 
41       
42       if (!to_boolean (get_property ("barCheckNoSynchronize")))
43         daddy_trans_l_->set_property("measurePosition", zero.smobbed_copy ());
44     }
45
46   SCM fr = get_property ("timeSignatureFraction");
47   
48   if (scm_equal_p (fr, last_time_sig_) == SCM_BOOL_F)
49     {
50       last_time_sig_ = fr;
51       set_time_signature ();
52     }
53 }
54
55
56 void
57 Timing_translator::stop_translation_timestep()
58 {
59   check_ = 0;
60   
61   Translator *t = this;
62   Global_translator *global_l =0;
63   do
64     {
65       t = t->daddy_trans_l_ ;
66       global_l = dynamic_cast<Global_translator*> (t);
67     }
68   while (!global_l);
69
70   /* allbars == ! skipbars */
71   SCM sb = get_property ("skipBars");
72   bool allbars = !to_boolean (sb);
73
74   // urg: multi bar rests: should always process whole of first bar?
75   SCM tim = get_property ("timing");
76   bool timb = to_boolean (tim);
77   if (timb && allbars)
78     {
79       Moment barleft = (measure_length () - measure_position ());
80
81       if (barleft > Moment (0))
82         global_l->add_moment_to_process (now_mom () + barleft);
83     }
84 }
85
86
87 ADD_THIS_TRANSLATOR(Timing_translator);
88
89 void
90 Timing_translator::initialize()
91 {
92   Moment m;
93   daddy_trans_l_->set_property ("timing" , SCM_BOOL_T);  
94   daddy_trans_l_->set_property ("currentBarNumber" , gh_int2scm (1));
95   daddy_trans_l_->set_property ("measurePosition", m.smobbed_copy ());
96   daddy_trans_l_->set_property ("timeSignatureFraction",
97                                 gh_cons (gh_int2scm (4), gh_int2scm (4)));
98
99   set_time_signature ();
100 }
101
102 Moment
103 Timing_translator::measure_length () const
104 {
105   SCM l = get_property("measureLength");
106   if (unsmob_moment(l))
107     return *unsmob_moment (l);
108   else
109     return Moment (1);
110 }
111
112
113 void
114 Timing_translator::set_time_signature ()
115 {
116   SCM fr = get_property ("timeSignatureFraction");
117   int l = gh_scm2int (gh_car (fr));
118   int o = gh_scm2int (gh_cdr (fr));
119   
120   Moment one_beat = Moment (1)/Moment (o);
121   Moment len = Moment (l) * one_beat;
122
123   daddy_trans_l_->set_property ("measureLength", len.smobbed_copy ());
124   daddy_trans_l_->set_property ("beatLength", one_beat.smobbed_copy ());
125 }
126
127 Timing_translator::Timing_translator()
128 {
129
130   last_time_sig_ = SCM_BOOL_F;
131
132 }
133
134
135 Moment
136 Timing_translator::measure_position () const
137 {
138   SCM sm = get_property ("measurePosition");
139   
140   Moment m   =0;
141   if (unsmob_moment (sm))
142     {
143       m = *unsmob_moment(sm);
144       while (m < Moment (0))
145         m += measure_length ();
146     }
147   
148   return m;
149 }
150
151 void
152 Timing_translator::start_translation_timestep()
153 {
154         check_ =00;
155   Translator *t = this;
156   Global_translator *global_l =0;
157   do
158     {
159       t = t->daddy_trans_l_ ;
160       global_l = dynamic_cast<Global_translator*> (t);
161     }
162   while (!global_l);
163
164   Moment dt = global_l->now_mom_  - global_l -> prev_mom_;
165   if (dt < Moment (0))
166     {
167       programming_error ("Moving backwards in time");
168       dt = 0;
169     }
170   
171   if (!dt)
172     return;
173
174   Moment measposp;
175
176   SCM s = get_property ("measurePosition");
177   if (unsmob_moment (s))
178     {
179       measposp = *unsmob_moment(s);
180     }
181   else
182     {
183       daddy_trans_l_->set_property ("measurePosition", measposp.smobbed_copy());
184     }
185   
186   measposp += dt;
187   
188   SCM barn = get_property ("currentBarNumber");
189   int b = 0;
190   if (gh_number_p(barn))
191     {
192       b = gh_scm2int (barn);
193     }
194
195   SCM cad = get_property ("timing");
196   bool c= to_boolean (cad );
197
198   Moment len = measure_length ();
199   while (c && measposp >= len)
200     {
201       measposp -= len;
202       b ++;
203     }
204
205   daddy_trans_l_->set_property ("currentBarNumber", gh_int2scm (b));
206   daddy_trans_l_->set_property ("measurePosition", measposp.smobbed_copy());
207 }
208