2 complexwalker.cc -- implement Complex_walker
4 source file of the LilyPond music typesetter
6 (c) 1997 Han-Wen Nienhuys <hanwen@stack.nl>
9 #include "associter.hh"
11 #include "musicalrequest.hh"
14 #include "complexstaff.hh"
16 #include "voicegroup.hh"
17 #include "complexwalker.hh"
19 #include "commandrequest.hh"
21 #include "localkeyreg.hh"
23 #include "meterreg.hh"
28 Complex_walker::announce_element(Staff_elem_info info)
30 info.group_regs_l_ = find_voice_group((Voice*)info.voice_l_);
31 announce_info_arr_.push(info);
35 Complex_walker::do_announces()
38 for (int i = 0; i < announce_info_arr_.size(); i++){
39 Staff_elem_info info = announce_info_arr_[i];
41 info.req_l_ = &dummy_req;
43 for (iter_top(voice_reg_list_,j); j.ok(); j++) {
44 j->acknowledge_element(info);
46 for (iter_top ( group_reg_list_, j); j.ok(); j++) {
47 j->acknowledge_element(info);
49 bar_reg_p_->acknowledge_element(info);
50 clef_reg_p_->acknowledge_element(info);
51 key_reg_p_->acknowledge_element(info);
52 meter_reg_p_->acknowledge_element(info);
54 local_key_reg_p_->acknowledge_element(info);
59 Complex_walker::find_voice_reg(Voice*v_l)const
61 for (iter_top(voice_reg_list_, i); i.ok(); i++) {
62 if (i->voice_l_ == v_l)
69 Complex_walker::get_voice_reg(Voice*v_l)
71 Voice_registers *regs_p=find_voice_reg(v_l);
75 regs_p = new Voice_registers(this,v_l);
76 voice_reg_list_.bottom().add (regs_p);
80 Voice_group_registers *
81 Complex_walker::find_voice_group(Voice* v_l)const
83 if (!voice_group_map_.elt_query(v_l))
85 else return voice_group_map_[v_l];
88 Voice_group_registers *
89 Complex_walker::find_voice_group(const char *id)const
91 for (iter_top(group_reg_list_, i); i.ok(); i++)
92 if (i->group_id_str_ == id)
98 Voice_group_registers *
99 Complex_walker::get_voice_group(Voice *v_l)
101 Voice_group_registers *group_p = find_voice_group(v_l);
105 group_p = new Voice_group_registers(this);
106 group_reg_list_.bottom().add(group_p);
107 voice_group_map_[v_l] = group_p;
112 Voice_group_registers *
113 Complex_walker::get_voice_group(const char* id)
115 Voice_group_registers *group_p = find_voice_group(id);
118 group_p = new Voice_group_registers(this,id);
119 group_reg_list_.bottom().add(group_p);
124 Complex_walker::do_change_group(Voice * v, String group_id_str)
126 voice_group_map_[v] = get_voice_group(group_id_str);
130 Complex_walker::try_command_request(Nonmusical_req *req_l)
133 Voice *voice_l = (Voice*)req_l->elt_l_->voice_l_; // ugh
134 if (req_l->groupchange()){
135 do_change_group(voice_l, req_l->groupchange()->newgroup_str_);
137 } else if(req_l->groupfeature()) {
138 Voice_group_registers* reg_l = get_voice_group(voice_l);
139 b |= reg_l->try_request(req_l);
142 b |= bar_reg_p_->try_request(req_l);
143 b |= clef_reg_p_->try_request(req_l);
145 b |= key_reg_p_->try_request(req_l);
147 b |= meter_reg_p_->try_request(req_l);
153 Complex_walker::try_request(Request*req)
156 Voice *voice_l = (Voice*)req->elt_l_->voice_l_; // ahh. This sux
159 b = try_command_request(req->nonmus());
160 } else if (Voice_registers::acceptable_request(req)) {
161 Voice_registers *vregs_l = get_voice_reg(voice_l);
162 b = vregs_l->try_request(req);
163 } else if (Voice_group_registers::acceptable_request(req)){
164 Voice_group_registers* reg_l = get_voice_group(voice_l);
165 b = reg_l->try_request(req);
169 warning("junking request: " + String(req->name()),
170 req->defined_ch_c_l_);
174 Complex_walker::process_requests()
176 Complex_column*c = col();
178 for (int i=0; i < c->first_l_arr_.size(); i++) {
179 try_request(c->first_l_arr_[i]);
182 for (int i=0; i < c->second_l_arr_.size(); i++) {
183 try_request(c->second_l_arr_[i]);
186 regs_process_requests();
191 Complex_walker::regs_process_requests()
193 for (iter_top(voice_reg_list_, j); j.ok(); j++) {
194 j->process_requests();
196 for (iter_top(group_reg_list_, j); j.ok(); j++)
197 j->process_requests();
200 bar_reg_p_->process_request();
201 clef_reg_p_->process_request();
202 key_reg_p_->process_request();
203 meter_reg_p_->process_request();
204 local_key_reg_p_->process_request();
208 Complex_walker::typeset_element(Staff_elem *elem_p)
212 if (elem_p->spanner())
213 pscore_l_->typeset_spanner(elem_p->spanner(), staff()->pstaff_l_);
215 col()->typeset_musical_item(elem_p->item());
218 Complex_walker::Complex_walker(Complex_staff*s)
219 : Staff_walker(s, s->pstaff_l_->pscore_l_)
221 local_key_reg_p_= new Local_key_register(this);
222 clef_reg_p_= new Clef_register(this);
223 key_reg_p_ = new Key_register(this);
224 bar_reg_p_ = new Bar_register(this);
225 meter_reg_p_ = new Meter_register(this);
231 Complex_walker::~Complex_walker()
233 delete local_key_reg_p_;
241 Complex_walker::c0_position_i()const
243 return c0_position_i_;
247 Complex_walker::set_c0_position(int p)
253 Complex_walker::staff()
255 return (Complex_staff*) staff_l_;
259 Complex_walker::col()
261 return (Complex_column*) *(*this);
265 Complex_walker::do_pre_move()
267 for (iter_top(voice_reg_list_,i); i.ok(); i++) {
268 i->pre_move_processing();
270 for (iter_top (group_reg_list_, j); j.ok(); j++)
271 j->pre_move_processing();
272 local_key_reg_p_->pre_move_processing();
273 bar_reg_p_->pre_move_processing();
274 clef_reg_p_->pre_move_processing();
275 key_reg_p_->pre_move_processing();
276 meter_reg_p_->pre_move_processing();
278 col()->typeset_breakable_items(prebreak_item_p_arr_,
280 postbreak_item_p_arr_);
284 Complex_walker::do_post_move()
286 for (iter_top(voice_reg_list_,i); i.ok(); i++) {
287 i->post_move_processing();
289 announce_info_arr_.set_size(0);
290 for (iter_top (group_reg_list_, j); j.ok(); j++)
291 j->post_move_processing();
293 local_key_reg_p_->post_move_processing();
294 bar_reg_p_->post_move_processing();
295 clef_reg_p_->post_move_processing();
296 key_reg_p_->post_move_processing();
297 meter_reg_p_->post_move_processing();
301 Array<Voice_registers*>
302 Complex_walker::get_voice_regs(Voice_group_registers* group_regs_l) const
305 for (Assoc_iter<Voice*,Voice_group_registers*> i(voice_group_map_);
307 if (i.val() == group_regs_l)
308 l_arr.push(find_voice_reg(i.key()));
313 Complex_walker::typeset_breakable_item(Item * pre_p , Item * nobreak_p,
317 prebreak_item_p_arr_.push(pre_p);
319 nobreak_item_p_arr_.push(nobreak_p);
321 postbreak_item_p_arr_.push(post_p);