]> git.donarmstrong.com Git - lilypond.git/blob - lily/easy-notation.cc
merge
[lilypond.git] / lily / easy-notation.cc
1 /*
2   easy-notation.cc --  implement easy notation heads
3
4   source file of the GNU LilyPond music typesetter
5
6   (c) 2005--2006 Han-Wen Nienhuys <hanwen@xs4all.nl>
7 */
8
9 #include "note-head.hh"
10
11 #include <cctype>
12 using namespace std;
13
14 #include "font-interface.hh"
15 #include "grob.hh"
16 #include "music.hh"
17 #include "output-def.hh"
18 #include "pitch.hh"
19 #include "staff-symbol-referencer.hh"
20 #include "stem.hh"
21 #include "stream-event.hh"
22 #include "text-interface.hh"
23
24 /*
25
26 TODO: move to scheme
27
28 */
29 MAKE_SCHEME_CALLBACK (Note_head, brew_ez_stencil, 1);
30 SCM
31 Note_head::brew_ez_stencil (SCM smob)
32 {
33   Grob *me = unsmob_grob (smob);
34   int log = Note_head::get_balltype (me);
35
36   SCM cause = me->get_property ("cause");
37   SCM spitch = unsmob_stream_event (cause)->get_property ("pitch");
38   Pitch *pit = unsmob_pitch (spitch);
39
40   SCM idx = scm_from_int (pit->get_notename ());
41   SCM names = me->get_property ("note-names");
42   SCM charstr = SCM_EOL;
43   if (scm_is_vector (names))
44     charstr = scm_vector_ref (names, idx);
45   else
46     {
47       char s[2] = "a";
48       s[0] = (pit->get_notename () + 2) % 7 + 'a';
49       s[0] = toupper (s[0]);
50       charstr = scm_makfrom0str (s);
51     }
52
53   SCM letter
54     = Text_interface::interpret_string (me->layout ()->self_scm (),
55                                         Font_interface::text_font_alist_chain (me),
56                                         charstr);
57
58   Stencil l (*unsmob_stencil (letter));
59   l.align_to (X_AXIS, CENTER);
60   l.align_to (Y_AXIS, CENTER);
61
62   l = Stencil (Box (), l.expr ());
63   Real ss = Staff_symbol_referencer::staff_space (me);
64   Real lt = Staff_symbol_referencer::line_thickness (me);
65
66   Real radius = (ss + lt) / 2.0;
67   Real stem_thick = 1.3 * lt;
68   if (Grob *stem = unsmob_grob (me->get_object ("stem")))
69     stem_thick = Stem::thickness (stem);
70
71   int black = (log >= 2);
72
73   Stencil head;
74   Box extent (Interval (-radius, radius),
75               Interval (-radius, radius));
76
77   Stencil black_head (extent,
78                       scm_list_4 (ly_symbol2scm ("circle"),
79                                   scm_from_double (radius),
80                                   scm_from_double (0.0),
81                                   SCM_BOOL_T));
82   Stencil white_head;
83   if (black)
84     l = l.in_color (1, 1, 1);
85   else
86     {
87       white_head = Stencil (extent,
88                             scm_list_4 (ly_symbol2scm ("circle"),
89                                         scm_from_double (radius - stem_thick),
90                                         scm_from_double (0.0),
91                                         SCM_BOOL_T));
92
93       white_head = white_head.in_color (1, 1, 1);
94     }
95
96   Stencil total;
97   total.add_stencil (l);
98   total.add_stencil (white_head);
99   total.add_stencil (black_head);
100   total.translate_axis (radius, X_AXIS);
101
102   return total.smobbed_copy ();
103 }
104