]> git.donarmstrong.com Git - lilypond.git/blob - lily/item.cc
patch::: 1.3.54.hwn2
[lilypond.git] / lily / item.cc
1 /*
2   item.cc -- implement Item
3
4   source file of the GNU LilyPond music typesetter
5
6   (c)  1997--2000 Han-Wen Nienhuys <hanwen@cs.uu.nl>
7 */
8
9 #include "dimension-cache.hh"
10 #include "paper-score.hh"
11 #include "debug.hh"
12 #include "item.hh"
13 #include "paper-column.hh"
14 #include "spanner.hh"
15 #include "lily-guile.hh"
16 #include "line-of-score.hh"
17
18 Item::Item ()
19 {
20   broken_to_drul_[LEFT] = broken_to_drul_[RIGHT]=0;
21 }
22
23 /**
24    Item copy ctor.  Copy nothing: everything should be a elt property
25    or a special purpose pointer (such as broken_to_drul_[]) */
26 Item::Item (Item const &s)
27   : Score_element (s)
28 {
29   broken_to_drul_[LEFT] = broken_to_drul_[RIGHT] =0;
30 }
31
32
33
34 bool
35 Item::breakable_b () const
36 {
37   if (original_l_ )
38     return false;
39   
40   Item * i  =dynamic_cast<Item*> (parent_l (X_AXIS));
41   return (i) ?  i->breakable_b () : to_boolean (get_elt_property ("breakable"));
42 }
43
44 Line_of_score *
45 Item::line_l() const
46 {
47   Score_element *g = parent_l (X_AXIS);
48   return g ?  g->line_l () : 0;
49 }
50
51
52 void
53 Item::copy_breakable_items()
54 {
55   Drul_array<Item *> new_copies;
56   Direction  i=LEFT;
57   do 
58     {
59       Score_element * dolly = clone();
60       Item * item_p = dynamic_cast<Item*>(dolly);
61       pscore_l_->line_l_->typeset_element (item_p);
62       new_copies[i] =item_p;
63     }
64   while (flip(&i) != LEFT);
65   broken_to_drul_= new_copies;
66 }
67
68
69 bool
70 Item::broken_b () const
71 {
72   return broken_to_drul_[LEFT] || broken_to_drul_[RIGHT];
73 }
74
75
76 /*
77   Generate items for begin and end-of line.
78  */
79 void
80 Item::discretionary_processing()
81 {
82   if (broken_b ())
83     return;
84
85   if (breakable_b ())
86     copy_breakable_items();
87 }
88
89 Score_element*
90 Item::find_broken_piece (Line_of_score*l) const
91 {
92   if (line_l() == l) 
93     return (Item*)(this);
94
95   Direction d = LEFT;
96   do {
97     Score_element *s = broken_to_drul_[d];
98     if (s && s->line_l () == l)
99       return s;
100   }
101   while (flip (&d) != LEFT);
102
103   return 0;
104 }
105
106
107 Item*
108 Item::find_prebroken_piece (Direction d) const
109 {
110   Item * me = (Item *) (this);  
111   if (!d)
112     return me;
113   return dynamic_cast<Item*> (broken_to_drul_[d]);
114 }
115
116 Paper_column *
117 Item::column_l () const
118 {
119   return dynamic_cast<Item*> (parent_l (X_AXIS))->column_l ();
120 }
121
122 Direction
123 Item::break_status_dir () const
124 {
125   if (original_l_)
126     {
127       Item * i = dynamic_cast<Item*> (original_l_);
128
129       return (i->broken_to_drul_[LEFT] == this) ? LEFT : RIGHT;
130     }
131   else
132     return CENTER;
133 }
134
135 void
136 Item::handle_prebroken_dependencies ()
137 {
138   if (original_l_)
139     {
140       pointer_alist_
141         = handle_broken_smobs (original_l_->pointer_alist_,
142                                gh_int2scm (break_status_dir ()));
143     }
144   
145   /*
146     Can't do this earlier, because try_visibility_lambda () might set
147     the elt property transparent, which would then be copied.
148   */
149   SCM vis = get_elt_property ("visibility-lambda");
150   if (gh_procedure_p (vis))
151     {
152       SCM args = scm_listify (gh_int2scm (break_status_dir ()), SCM_UNDEFINED);
153       SCM result = gh_apply (vis, args);
154       bool trans = gh_scm2bool (gh_car (result));
155       bool empty = gh_scm2bool (gh_cdr (result));
156
157       if (empty)
158         {
159           set_extent_callback (0, X_AXIS);
160           set_extent_callback (0,  Y_AXIS);
161         }
162       if (trans)
163         set_elt_property ("transparent", SCM_BOOL_T);
164     }
165 }