2 // mudela-score.cc -- implement Mudela_score
4 // copyright 1997 Jan Nieuwenhuizen <janneke@gnu.org>
9 #include "duration-convert.hh"
10 #include "mi2mu-global.hh"
11 #include "mudela-column.hh"
12 #include "mudela-item.hh"
13 #include "mudela-score.hh"
14 #include "mudela-staff.hh"
15 #include "mudela-stream.hh"
17 // ugh, cygnus' b19 gcc
21 //static Mudela_key key_c (0, 0);
22 static Mudela_time_signature time_sig_4 (4, 2, 24, 8);
23 // useconds per 4: 250000 === 60 4 per minute
24 static Mudela_tempo tempo_60 (1000000);
26 Mudela_score::Mudela_score (int format_i, int tracks_i, int tempo_i)
31 column_l_array_.push (new Mudela_column (this, Moment (0)));
32 // mudela_key_l_ = &key_c;
34 mudela_time_signature_l_ = &time_sig_4;
35 mudela_tempo_l_ = &tempo_60;
38 Mudela_score::~Mudela_score()
43 Mudela_score::add_item (Mudela_item* mudela_item_p)
45 mudela_staff_p_list_.bottom()->add_item (mudela_item_p);
49 Mudela_score::add_staff (Mudela_staff* mudela_staff_p)
51 mudela_staff_p_list_.bottom().add (mudela_staff_p);
55 Mudela_score::find_column_l (Moment mom)
58 // should do binary search
59 for (int i = 0; i < column_l_array_.size (); i++ )
60 if ( column_l_array_[i]->at_mom () == mom )
61 return column_l_array_[i];
64 int upper_i = max (0, column_l_array_.size () - 1);
69 Moment i_mom = column_l_array_ [i]->at_mom ();
71 return column_l_array_ [i];
76 if ((upper_i == lower_i) || (i == column_l_array_.size () - 1))
78 // we don't do inserts
80 Mudela_column* col_p = new Mudela_column (this, mom);
81 column_l_array_.push (col_p);
84 i = (upper_i + lower_i + 1 ) / 2;
92 Mudela_score::get_column_l (Moment mom)
96 for (i=column_l_array_.size() - 1; !c && i >=0; i--)
98 if (column_l_array_ [i]->at_mom () == mom )
99 c = column_l_array_[i];
100 else if (column_l_array_[i]->at_mom () < mom)
105 c = new Mudela_column (this, mom);
106 column_l_array_.insert (c, i+1);
109 assert (c->at_mom () == mom);
115 Mudela_score::output (String filename_str)
117 LOGOUT(NORMAL_ver) << _f ("Lily output to %s...", filename_str) << endl;
119 // ugh, ugly midi type 1 fix
120 if ( (mudela_staff_p_list_.size() == 1) && !mudela_staff_p_list_.top()->number_i_)
121 mudela_staff_p_list_.top()->number_i_ = 1;
124 Mudela_stream mudela_stream (filename_str);
125 for (PCursor<Mudela_staff*> i (mudela_staff_p_list_); i.ok(); i++)
127 LOGOUT(NORMAL_ver) << _ ("track ") << track_i++ << ": " << flush;
128 i->output (mudela_stream);
129 mudela_stream << '\n';
130 LOGOUT(NORMAL_ver) << endl;
133 mudela_stream << "\\score{\n";
134 if (mudela_staff_p_list_.size() > 1)
135 mudela_stream << "< \n";
136 for (PCursor<Mudela_staff*> i (mudela_staff_p_list_); i.ok(); i++)
138 if ( (mudela_staff_p_list_.size() != 1)
139 && (i == mudela_staff_p_list_.top()))
141 mudela_stream << "\\type Staff = \"" << i->id_str() << "\" ";
142 mudela_stream << String ("\\" + i->id_str ()) << "\n";
144 if (mudela_staff_p_list_.size() > 1)
145 mudela_stream << ">\n";
148 mudela_stream << "\\paper{}\n";
151 let's put some auto-beam stuff in place as long as it's optional
153 mudela_stream << "\\paper{\n";
154 mudela_stream << "\\translator{\n";
155 mudela_stream << "\\VoiceContext\n";
156 mudela_stream << "\\consists \"Auto_beam_engraver\";\n";
157 mudela_stream << "beamAuto = 1.;\n";
158 mudela_stream << "beamAutoEnd8 = \"2/4\";\n";
159 mudela_stream << "beamAutoEnd16 = \"1/4\";\n";
160 mudela_stream << "beamAutoEnd32 = \"1/4\";\n";
161 mudela_stream << "}\n";
162 mudela_stream << "}\n";
165 mudela_stream << "\\midi{\n";
166 // let's not use silly 0 track
167 mudela_staff_p_list_.bottom()->mudela_tempo_l_->output (mudela_stream);
168 mudela_stream << "}\n";
170 mudela_stream << "}\n";
174 Mudela_score::process()
176 LOGOUT(NORMAL_ver) << '\n' << _ ("Processing...") << endl;
178 LOGOUT(DEBUG_ver) << "columns\n";
179 // for (PCursor<Mudela_column*> i (mudela_column_p_list_); i.ok(); i++)
180 // LOGOUT(DEBUG_ver) << "At: " << i->at_mom() << '\n';
185 quantify_durations();
187 LOGOUT(NORMAL_ver) << '\n' << _ ("Creating voices...") << endl;
189 for (PCursor<Mudela_staff*> i (mudela_staff_p_list_); i.ok(); i++)
191 LOGOUT(NORMAL_ver) << _ ("track ") << track_i++ << ": " << flush;
193 LOGOUT(NORMAL_ver) << endl;
198 Mudela_score::filter_tempo()
200 LOGOUT(NORMAL_ver) << '\n' << _ ("NOT Filtering tempo...") << endl;
204 Mudela_score::quantify_columns()
207 if (Duration_convert::no_quantify_b_s)
209 LOGOUT(NORMAL_ver) << '\n' << _("NOT Quantifying columns...") << endl;
213 LOGOUT(NORMAL_ver) << '\n' << _("Quantifying columns...") << endl;
215 int current_bar_i = 0;
216 Moment bar_mom = mudela_time_signature_l_->bar_mom();
218 int n = 5 >? Duration_convert::no_smaller_than_i_s;
219 n = Duration_convert::type2_i (n);
220 Moment s = Moment (1, n);
221 Moment sh = Moment (1, 2 * n);
222 for (int i = 0; i < column_l_array_.size(); i++)
224 column_l_array_ [i]->at_mom_ =
225 s * Moment( (int) ( (column_l_array_ [i]->at_mom()) / s));
227 int bar_i = (int) (column_l_array_ [i]->at_mom () / bar_mom) + 1;
228 if (bar_i > current_bar_i)
230 LOGOUT (NORMAL_ver) << "[" << bar_i << "]" << flush;
231 current_bar_i = bar_i;
234 LOGOUT(NORMAL_ver) << endl;
238 Mudela_score::quantify_durations()
240 // LOGOUT(NORMAL_ver) << '\n' << "Quantifying durations..." << endl;
244 Mudela_score::settle_columns()
246 // LOGOUT(NORMAL_ver) << '\n' << "NOT Settling columns..." << endl;
248 LOGOUT(NORMAL_ver) << '\n' << _("Settling columns...") << endl;
251 assert (!column_l_array_.size());
252 int n = mudela_column_p_list_.size();
254 // column_l_array_.set_size (n);
255 for (PCursor<Mudela_column*> i (mudela_column_p_list_); i.ok(); i++)
256 column_l_array_.push (*i);
259 int n = column_l_array_.size();
263 Moment start_mom = 0;
264 Duration smallest_dur;
265 smallest_dur.durlog_i_ = 6;
266 Moment const noise_mom = Duration_convert::dur2_mom (smallest_dur)
268 for (int i = 0; i < n; i++)
273 start_mom = column_l_array_ [i]->at_mom();
277 // find all columns within noise's distance
279 && (column_l_array_ [i]->at_mom() - start_mom < noise_mom))
282 // bluntly set all to time of first in group
283 for (int j = start_i; j < end_i; j++)
284 column_l_array_ [j]->at_mom_ = start_mom;