]> git.donarmstrong.com Git - lilypond.git/commitdiff
Issue 4609/2: Add Grob_property_info::temporary_{override,revert} functions
authorDavid Kastrup <dak@gnu.org>
Tue, 15 Sep 2015 15:16:36 +0000 (17:16 +0200)
committerDavid Kastrup <dak@gnu.org>
Sun, 20 Sep 2015 13:09:38 +0000 (15:09 +0200)
lily/context-property.cc
lily/include/context.hh
lily/include/grob-properties.hh

index 446306cd5d0ec3e6b65f4a816374fbff80d9bc57..87bfbc5b9d842d9fe0771da958b0054c85e4a4d4 100644 (file)
@@ -238,6 +238,59 @@ Grob_property_info::push (SCM grob_property_path, SCM new_value)
   return SCM_EOL;
 }
 
+// Used for \once \override, returns a token for matched_pop
+SCM
+Grob_property_info::temporary_override (SCM grob_property_path, SCM new_value)
+{
+  SCM cell = push (grob_property_path, new_value);
+  if (!scm_is_pair (cell))
+    return cell;
+  if (scm_is_symbol (scm_car (cell)))
+    props_->nested_++;
+  cell = scm_cons (SCM_BOOL_T, cell);
+  props_->alist_ = scm_cons (cell, scm_cdr (props_->alist_));
+  return cell;
+}
+
+// Used for \once \revert, returns a token for matched_pop
+SCM
+Grob_property_info::temporary_revert (SCM grob_property_path)
+{
+  if (!check ())
+    return SCM_EOL;
+
+  SCM current_alist = props_->alist_;
+  SCM daddy = props_->based_on_;
+  SCM tail = SCM_EOL;
+
+  if (!scm_is_pair (grob_property_path)
+      || !scm_is_symbol (scm_car (grob_property_path)))
+    {
+      programming_error ("Grob property path should be list of symbols.");
+      return SCM_EOL;
+    }
+
+  if (scm_is_pair (scm_cdr (grob_property_path)))
+    {
+      tail = assoc_tail (grob_property_path, current_alist, daddy);
+      if (scm_is_false (tail))
+        return SCM_EOL;
+    }
+  else
+    {
+      tail = assq_tail (scm_car (grob_property_path), current_alist, daddy);
+      if (scm_is_false (tail))
+        return SCM_EOL;
+      ++props_->nested_;
+    }
+
+  SCM cell = scm_cons (SCM_BOOL_F, scm_car (tail));
+  props_->alist_ = partial_list_copy (current_alist, tail,
+                                      scm_cons (cell, scm_cdr (tail)));
+  return cell;
+}
+
+
 void
 Grob_property_info::matched_pop (SCM cell)
 {
@@ -251,6 +304,17 @@ Grob_property_info::matched_pop (SCM cell)
     {
       if (scm_is_eq (scm_car (p), cell))
         {
+          SCM key = scm_car (cell);
+          if (scm_is_false (key))
+            {
+              // temporary revert, reactivate
+              cell = scm_cdr (cell);
+              if (scm_is_symbol (scm_car (cell)))
+                props_->nested_--;
+              props_->alist_ = partial_list_copy (current_alist, p,
+                                                  scm_cons (cell, scm_cdr (p)));
+              return;
+            }
           if (!scm_is_symbol (key))
             props_->nested_--;
           props_->alist_ = partial_list_copy (current_alist, p, scm_cdr (p));
@@ -341,7 +405,7 @@ apply_property_operations (Context *tg, SCM pre_init_ops)
       else if (scm_is_eq (type, ly_symbol2scm ("assign")))
         tg->set_property (scm_car (entry), scm_cadr (entry));
       else if (scm_is_eq (type, ly_symbol2scm ("apply")))
-       scm_apply_1 (scm_car (entry), tg->self_scm (), scm_cdr (entry));
+        scm_apply_1 (scm_car (entry), tg->self_scm (), scm_cdr (entry));
       else if (scm_is_eq (type, ly_symbol2scm ("unset")))
         tg->unset_property (scm_car (entry));
     }
index 28e80fd2db070b32001b82ceaf508a11869f3977..546152035082b302a887667aedc2018ba58f86f7 100644 (file)
@@ -195,6 +195,8 @@ void set_context_property_on_children (Context *trans, SCM sym, SCM val);
 SCM nested_property_alist (SCM alist, SCM prop_path, SCM value);
 SCM nested_create_alist (SCM prop_path, SCM value);
 SCM partial_list_copy (SCM alist, SCM tail, SCM newtail);
+SCM assq_tail (SCM key, SCM alist, SCM alist_end);
+SCM assoc_tail (SCM key, SCM alist, SCM alist_end);
 SCM evict_from_alist (SCM, SCM, SCM);
 SCM nalist_to_alist (SCM nalist, int nested);
 
index 7b128353b80bcc734d77c0770de874c35759f680..5822dd01fb915e5ecda1b4247468ad66c37e87e7 100644 (file)
@@ -48,6 +48,8 @@ public:
   bool create ();
   SCM updated ();
   SCM push (SCM path, SCM value);
+  SCM temporary_override (SCM path, SCM value);
+  SCM temporary_revert (SCM path);
   void matched_pop (SCM);
   void pop (SCM path);
   void pushpop (SCM path, SCM value)