]> git.donarmstrong.com Git - lilypond.git/blob - lily/nested-property.cc
Merge branch 'master' of git+ssh://jneem@git.sv.gnu.org/srv/git/lilypond into jneeman
[lilypond.git] / lily / nested-property.cc
1 #include "context.hh"
2 #include "grob.hh"
3
4 SCM
5 evict_from_alist (SCM symbol,
6                   SCM alist,
7                   SCM alist_end)
8 {
9   SCM new_alist = SCM_EOL;
10   SCM *tail = &new_alist;
11
12   while (alist != alist_end)
13     {
14       if (ly_is_equal (scm_caar (alist), symbol))
15         {
16           alist = scm_cdr (alist);
17           break;
18         }
19
20       *tail = scm_cons (scm_car (alist), SCM_EOL);
21       tail = SCM_CDRLOC (*tail);
22       alist = scm_cdr (alist);
23     }
24
25   *tail = alist;
26   return new_alist;
27 }
28
29 /*
30   PROP_PATH should be big-to-small ordering
31  */
32 SCM 
33 nested_property_alist (SCM alist, SCM prop_path, SCM value)
34 {
35   SCM new_value = SCM_BOOL_F;
36   if (scm_is_pair (scm_cdr (prop_path)))
37     {
38       SCM sub_alist = ly_assoc_get (scm_car (prop_path), alist, SCM_EOL);
39       new_value = nested_property_alist (sub_alist, scm_cdr (prop_path), value);
40     }
41   else
42     {
43         new_value = value;
44     }
45
46   return scm_acons (scm_car (prop_path), new_value, alist);
47 }
48
49 SCM 
50 nested_property_revert_alist (SCM alist, SCM prop_path)
51 {
52   SCM new_sub_alist = SCM_EOL;
53   SCM sym = scm_car (prop_path);
54   if (scm_is_pair (scm_cdr (prop_path)))
55     {
56       SCM sub_alist = ly_assoc_get (sym, alist, SCM_EOL);
57       new_sub_alist = nested_property_revert_alist (sub_alist, scm_cdr (prop_path));
58     }
59   else
60     {
61       new_sub_alist = evict_from_alist (sym, alist, SCM_EOL);
62     }
63
64   return scm_acons (sym, new_sub_alist, alist);
65 }
66
67
68 void
69 set_nested_property (Grob *me, SCM big_to_small, SCM value)
70 {
71   SCM alist = me->get_property (scm_car (big_to_small));
72
73   alist = nested_property_alist (alist, scm_cdr (big_to_small), value);
74   
75   me->set_property (scm_car (big_to_small),
76                     alist);
77 }
78