]> git.donarmstrong.com Git - lilypond.git/blob - src/stembeamreg.cc
506bde34239cbc0ba0255f440aa934838fbbf55d
[lilypond.git] / src / stembeamreg.cc
1 /*
2   stembeamreg.cc -- part of LilyPond
3
4   (c) 1997 Han-Wen Nienhuys <hanwen@stack.nl>
5 */
6
7 #include "stembeamreg.hh"
8 #include "beam.hh"
9 #include "stem.hh"
10 #include "grouping.hh"
11 #include "textspanner.hh"
12 #include "complexwalker.hh"
13 #include "complexstaff.hh"
14 #include "debug.hh"
15
16 Stem_beam_register::Stem_beam_register(Complex_walker*w)
17     :Request_register(w)
18 {
19     do_post_move_process();
20     current_grouping = 0;
21     beam_p_ = 0;
22     set_dir(0);
23     start_req_l_ = 0;
24 }
25
26 bool
27 Stem_beam_register::try_request(Request*req_l)
28 {
29     if ( req_l->beam() ) {
30         if (bool(beam_p_ ) == bool(req_l->beam()->spantype == Span_req::START))
31             return false;
32         
33         if (beam_req_l_ && Beam_req::compare(*beam_req_l_ , *req_l->beam()))
34             return false;
35         
36         beam_req_l_ = req_l->beam();
37         return true;
38     }
39     
40     if ( req_l->stem() ) {
41         if (current_grouping && !current_grouping->child_fit_query(
42             walk_l_->col()->tdescription_->whole_in_measure))
43             return false;
44
45         if (stem_req_l_ && Stem_req::compare(*stem_req_l_, *req_l->stem()))
46             return false;
47
48         stem_req_l_ = req_l->stem();
49         return true;
50     }
51     return false;
52 }
53
54 void
55 Stem_beam_register::process_request()
56 {
57     if (beam_req_l_) {
58         if (beam_req_l_->spantype == Span_req::STOP) {
59             end_beam_b_ = true;
60             start_req_l_ = 0;
61         } else {
62             beam_p_ = new Beam;
63             start_req_l_ = beam_req_l_;
64
65             current_grouping = new Rhythmic_grouping;
66             if (beam_req_l_->nplet) {
67                 Text_spanner* t = new Text_spanner();
68                 t->set_support(beam_p_);
69                 t->spec.align_i_ = 0;
70                 t->spec.text_str_ = beam_req_l_->nplet;
71                 typeset_element(t);
72             }
73              
74         }
75     }
76
77     if (stem_req_l_) {
78         stem_p_ = new Stem(4);
79         if (current_grouping)
80             current_grouping->add_child(
81                 walk_l_->col()->tdescription_->whole_in_measure,
82                 stem_req_l_->duration());
83
84         stem_p_->flag = stem_req_l_->balltype;
85
86         if (beam_p_) {
87             if (stem_req_l_->balltype<= 4)
88                 warning( "stem doesn't fit in Beam",
89                          stem_req_l_->defined_ch_c_l_m);
90             else
91                 beam_p_->add(stem_p_);
92             stem_p_->print_flag = false;
93         } else {
94             stem_p_->print_flag = true;
95         }
96         
97         announce_element(Staff_elem_info(stem_p_,
98                                                   stem_req_l_,  this));
99     }
100 }
101
102 void
103 Stem_beam_register::acknowledge_element(Staff_elem_info info)
104 {
105     if (!stem_p_)
106         return;
107
108     if (info.elem_p_->name() == String("Notehead") &&
109         stem_req_l_->duration() == info.req_l_->rhythmic()->duration())
110         
111         stem_p_->add((Notehead*)info.elem_p_);
112 }
113
114 void
115 Stem_beam_register::do_pre_move_process()
116 {
117     if (stem_p_) {
118         if (default_dir_i_)
119             stem_p_->dir = default_dir_i_;
120         
121         typeset_element(stem_p_);
122         stem_p_ = 0;
123     }
124     if (beam_p_ && end_beam_b_) {
125         walk_l_->default_grouping.extend(current_grouping->interval());
126         beam_p_->set_grouping(walk_l_->default_grouping, *current_grouping);
127         typeset_element(beam_p_);
128         delete current_grouping;
129         current_grouping = 0;
130         beam_p_ = 0;
131     }
132     end_beam_b_ = false;
133 }
134 void
135 Stem_beam_register::do_post_move_process()
136 {
137     stem_p_ = 0;
138     beam_req_l_ = 0;
139     stem_req_l_ = 0;
140     end_beam_b_ = false;
141 }
142
143 Stem_beam_register::~Stem_beam_register()
144 {
145     if (beam_p_)
146         warning("unterminated beam", start_req_l_->defined_ch_c_l_m);
147 }
148
149 void
150 Stem_beam_register::set_dir(int i)
151 {
152     default_dir_i_ = i;
153 }