changeset 8061:f819e8992367

Auto-generate base_properties
author John W. Eaton <jwe@octave.org>
date Tue, 26 Aug 2008 13:32:52 -0400
parents 09f32aac8fbc
children e04a4beeb283
files src/ChangeLog src/genprops.awk src/graphics.cc src/graphics.h.in
diffstat 4 files changed, 237 insertions(+), 468 deletions(-) [+]
line wrap: on
line diff
--- a/src/ChangeLog	Tue Aug 26 13:26:05 2008 -0400
+++ b/src/ChangeLog	Tue Aug 26 13:32:52 2008 -0400
@@ -1,5 +1,51 @@
 2008-08-26  Michael Goffioul  <michael.goffioul@gmail.com>
 
+	* genprops.awk (emit_declarations, emit_source): Change code emission
+	when emitting base_properties code (base is 1).
+	(BEGIN): Initialize pcount to 0.
+	(BEGIN_PROPERTIES): Initialize base to 0.
+	(BEGIN_BASE_PROPERTIES): New statement.
+	(main): Add support for 'f' modifier. Add support for non xxx_property
+	typed properties.
+	* graphics.h.in (base_properties::base_properties): Remove
+	implementation.
+	(base_properties::get_tag, base_properties::get_parent,
+	base_properties::get_type, base_properties::get___myhandle__,
+	base_properties::get_busyaction, base_properties::get_buttondownfcn,
+	base_properties::is_clipping, base_properties::get_clipping,
+	base_properties::execute_createfcn, base_properties::get_createfcn,
+	base_properties::execute_deletefcn, base_properties::get_deletefcn,
+	base_properties::get_handlevisibility, base_properties::is_hittest,
+	base_properties::get_hittest, base_properties::is_interruptible,
+	base_properties::get_interruptible, base_properties::is_selected,
+	base_properties::get_selected, base_properties::is_selectionhighlight,
+	base_properties::get_selectionhighlight,
+	base_properties::get_uicontextmenu, base_properties::get_userdata,
+	base_properties::is_visible, base_properties::get_visible,
+	base_properties::is_beingdeleted, base_properties::get_beingdeleted,
+	base_properties::set_busyaction, base_properties::set_buttondownfcn,
+	base_properties::set_clipping, base_properties::set_createfcn,
+	base_properties::set_deletefcn, base_properties::set_handlevisibility,
+	base_properties::set_hittest, base_properties::set_interruptible,
+	base_properties::set_selected,
+	base_properties::set_selectionhighlight,
+	base_properties::set_uicontextmenu, base_properties::set_userdata,
+	base_properties::set_visible, base_properties::set_beingdeleted,
+	base_properties::get_children): Remove (now auto-generated).
+	(base_properties::enum): Likewise.
+	(base_properties::is_modified): Call is___modified__.
+	(base_properties::set_modified): Call set___modified__.
+	(base_properties::set_children): Add.
+	(base_properties::set_dynamic, base_properties::get_dynamic,
+	base_properties::get_property_dynamic): New methods.
+	(class base_properties): Surround properties declaration with
+	BEGIN_BASE_PROPERTIES/END_PROPERTIES pair.
+	* graphics.cc (base_properties::get, base_properties::set,
+	base_properties::get_property): Remove (now auto-generated).
+	(base_properties::set_dynamic, base_properties::get_dynamic,
+	base_properties::get_property_dynamic): New methods.
+	(base_properties::set_children): Likewise.
+
 	* DLD_FUNCTIONS/fltk_backend.cc (F__fltk_redraw__): Make static.
 	(F__init_fltk__): Protect from mutliple invocations.
 	(F__remove_fltk__): Likewise.
--- a/src/genprops.awk	Tue Aug 26 13:26:05 2008 -0400
+++ b/src/genprops.awk	Tue Aug 26 13:32:52 2008 -0400
@@ -112,8 +112,8 @@
 ##       settable from the global set (caseless_str, octave_value)
 ##       method, but still has set_X accessor.
 ##
-##   u:  The property has an updater method. This effectively add
-##       the line
+##   u:  The property has an inline updater method. This effectively
+##       add the line
 ##
 ##         update_NAME ();
 ##
@@ -121,6 +121,11 @@
 ##       any other update call (like those added by the 'l' or 'm'
 ##       modifiers.
 ##
+##   U:  Like 'u' modifier except that the updater is not inline.
+##       A declaration for the updater function will be emitted.
+##
+##   f:  The property does not have any factory default value.
+##
 ## The 'o' and 'O' qualifiers are only useful when the the property type
 ## is something other than octave_value.
 
@@ -249,11 +254,11 @@
 
 function emit_declarations ()
 {
-  if (class_name)
+  if (class_name && ! base)
     emit_common_declarations();
 
   if (idx > 0)
-    print "private:\n";
+    print (base ? "protected:\n" : "private:\n");
 
   for (i = 1; i <= idx; i++)
     printf ("  %s%s %s;\n", mutable[i] ? "mutable " : "", type[i], name[i]);
@@ -377,12 +382,20 @@
 
     ## constructor
 
-    printf ("%s::properties::properties (const graphics_handle& mh, const graphics_handle& p)\n", class_name) >> filename;
-    printf ("  : base_properties (go_name, mh, p),\n") >> filename;
+    if (base)
+      printf ("base_properties::base_properties (const std::string& ty, const graphics_handle& mh, const graphics_handle& p)\n  : ") >> filename;
+    else
+    {
+      printf ("%s::properties::properties (const graphics_handle& mh, const graphics_handle& p)\n", class_name) >> filename;
+      printf ("  : base_properties (go_name, mh, p),\n") >> filename;
+    }
 
     for (i = 1; i <= idx; i++)
     {
-      printf ("    %s (\"%s\", mh, %s)", name[i], name[i], defval[i]) >> filename;
+      if (ptype[i])
+        printf ("    %s (\"%s\", mh, %s)", name[i], name[i], defval[i]) >> filename;
+      else
+        printf ("    %s (%s)", name[i], defval[i]) >> filename;
       if (i < idx)
         printf (",") >> filename;
       printf ("\n") >> filename;
@@ -393,17 +406,23 @@
     for (i = 1; i <= idx; i++)
     {
 ##    printf ("  insert_static_property (\"%s\", %s);\n", name[i], name[i]) >> filename;
-      printf ("  %s.set_id (%s);\n", name[i], toupper(name[i])) >> filename;
-      if (hidden[i])
-        printf ("  %s.set_hidden (true);\n", name[i]) >> filename;
+      if (ptype[i])
+      {
+        printf ("  %s.set_id (%s);\n", name[i], toupper(name[i])) >> filename;
+        if (hidden[i])
+          printf ("  %s.set_hidden (true);\n", name[i]) >> filename;
+      }
     }
 
     printf ("  init ();\n}\n\n") >> filename;
 
     ## set method
 
-    printf ("void\n%s::properties::set (const caseless_str& pname, const octave_value& val)\n{\n",
-            class_name) >> filename;
+    if (base)
+      printf ("void\nbase_properties::set (const caseless_str& pname, const octave_value& val)\n{\n") >> filename;
+    else
+      printf ("void\n%s::properties::set (const caseless_str& pname, const octave_value& val)\n{\n",
+              class_name) >> filename;
 
     first = 1;
 
@@ -417,29 +436,43 @@
       }
     }
 
-    printf ("  else\n    base_properties::set (pname, val);\n}\n\n") >> filename;
+    if (base)
+      printf ("  else\n    set_dynamic (pname, val);\n}\n\n") >> filename;
+    else
+      printf ("  else\n    base_properties::set (pname, val);\n}\n\n") >> filename;
 
     ## get "all" method
 
-    printf ("octave_value\n%s::properties::get (bool all) const\n{\n", class_name) >> filename;
-    printf ("  Octave_map m = base_properties::get (all).map_value ();\n\n") >> filename;
+    if (base)
+    {
+      printf ("octave_value\nbase_properties::get (bool all) const\n{\n") >> filename;
+      printf ("  Octave_map m = get_dynamic (all).map_value ();\n\n") >> filename;
+    }
+    else
+    {
+      printf ("octave_value\n%s::properties::get (bool all) const\n{\n", class_name) >> filename;
+      printf ("  Octave_map m = base_properties::get (all).map_value ();\n\n") >> filename;
+    }
 
     for (i = 1; i <= idx; i++)
     {
       if (hidden[i])
         printf ("  if (all)\n    m.assign (\"%s\", get_%s ()%s);\n", name[i], name[i],
-                (type[i] == "handle_property" ? ".as_octave_value ()" : "")) >> filename;
+                (type[i] == "handle_property" || type[i] == "graphics_handle" ? ".as_octave_value ()" : "")) >> filename;
       else
         printf ("  m.assign (\"%s\", get_%s ()%s);\n", name[i], name[i],
-                (type[i] == "handle_property" ? ".as_octave_value ()" : "")) >> filename;
+                (type[i] == "handle_property" || type[i] == "graphics_handle" ? ".as_octave_value ()" : "")) >> filename;
     }
 
     printf ("\n  return m;\n}\n\n") >> filename;
     
     ## get "one" method
 
-    printf ("octave_value\n%s::properties::get (const caseless_str& pname) const\n{\n",
-            class_name) >> filename;
+    if (base)
+      printf ("octave_value\nbase_properties::get (const caseless_str& pname) const\n{\n") >> filename;
+    else
+      printf ("octave_value\n%s::properties::get (const caseless_str& pname) const\n{\n",
+              class_name) >> filename;
     printf ("  octave_value retval;\n\n") >> filename;
 
     for (i = 1; i<= idx; i++)
@@ -447,58 +480,82 @@
       printf ("  %sif (pname.compare (\"%s\"))\n",
               (i > 1 ? "else " : ""), name[i]) >> filename;
       printf ("    retval = get_%s ()%s;\n", name[i],
-              (type[i] == "handle_property" ? ".as_octave_value ()" : "")) >> filename;
+              (type[i] == "handle_property" || type[i] == "graphics_handle" ? ".as_octave_value ()" : "")) >> filename;
     }
 
-    printf ("  else\n    retval = base_properties::get (pname);\n\n") >> filename;
+    if (base)
+      printf ("  else\n    retval = get_dynamic (pname);\n\n") >> filename;
+    else
+      printf ("  else\n    retval = base_properties::get (pname);\n\n") >> filename;
     printf ("  return retval;\n}\n\n") >> filename;
 
     ## get_property method
 
-    printf ("property\n%s::properties::get_property (const caseless_str& pname)\n{\n",
-            class_name) >> filename;
+    if (base)
+      printf ("property\nbase_properties::get_property (const caseless_str& pname)\n{\n") >> filename;
+    else
+      printf ("property\n%s::properties::get_property (const caseless_str& pname)\n{\n",
+              class_name) >> filename;
 
     for (i = 1; i<= idx; i++)
     {
-      printf ("  %sif (pname.compare (\"%s\"))\n",
-              (i > 1 ? "else " : ""), name[i]) >> filename;
-      printf ("    return property (&%s, true);\n", name[i]) >> filename;
+      if (ptype[i])
+      {
+        printf ("  %sif (pname.compare (\"%s\"))\n",
+                (i > 1 ? "else " : ""), name[i]) >> filename;
+        printf ("    return property (&%s, true);\n", name[i]) >> filename;
+      }
     }
 
-    printf ("  else\n    return base_properties::get_property (pname);\n") >> filename;
+    if (base)
+      printf ("  else\n    return get_property_dynamic (pname);\n") >> filename;
+    else
+      printf ("  else\n    return base_properties::get_property (pname);\n") >> filename;
     printf ("}\n\n") >> filename;
 
 
     ## factory defaults method
 
-    printf ("property_list::pval_map_type\n%s::properties::factory_defaults (void)\n{\n",
-            class_name) >> filename;
-    printf ("  property_list::pval_map_type m;\n\n") >> filename;
+    if (base)
+    {
+      printf ("property_list::pval_map_type\nbase_properties::factory_defaults (void)\n{\n") >> filename;
+      printf ("  property_list::pval_map_type m;\n\n") >> filename;
+    }
+    else
+    {
+      printf ("property_list::pval_map_type\n%s::properties::factory_defaults (void)\n{\n",
+              class_name) >> filename;
+      printf ("  property_list::pval_map_type m = base_properties::factory_defaults ();\n\n") >> filename;
+    }
 
     for (i = 1; i <= idx; i++)
     {
-      dval = defval[i];
-      if (type[i] == "radio_property" || type[i] == "color_property")
-	{
-	  k = index (dval, "{");
-	  dval = substr (dval, k+1);
-	  l = index (dval, "}");
-	  if (k > 0 && l > 0)
-	    dval = "\"" + substr (dval, 1, l-1) +  "\"";
-	  else
-	    dval = "octave_value ()";
-	}
+      if (factory[i])
+      {
+        dval = defval[i];
+        if (type[i] == "radio_property" || type[i] == "color_property")
+      	{
+      	  k = index (dval, "{");
+    	    dval = substr (dval, k+1);
+  	      l = index (dval, "}");
+      	  if (k > 0 && l > 0)
+	          dval = "\"" + substr (dval, 1, l-1) +  "\"";
+    	    else
+  	        dval = "octave_value ()";
+      	}
 
-      printf ("  m[\"%s\"] = %s%s;\n", name[i], dval,
-		 (type[i] == "handle_property" ? ".as_octave_value ()" : "")) >> filename;
+        printf ("  m[\"%s\"] = %s%s;\n", name[i], dval,
+                (type[i] == "handle_property" || type[i] == "graphics_handle" ? ".as_octave_value ()" : "")) >> filename;
+      }
     }
 
     printf ("\n  return m;\n}\n\n") >> filename;
 
     ## go_name static field
 
-    printf ("std::string %s::properties::go_name (\"%s\");\n\n",
-            class_name, class_name) >> filename;
+    if (! base)
+      printf ("std::string %s::properties::go_name (\"%s\");\n\n",
+              class_name, class_name) >> filename;
   }
 }
 
@@ -506,7 +563,7 @@
   filename = "graphics-props.cc";
   printf ("// DO NOT EDIT!  Generated automatically by genprops.awk.\n\n");
   printf ("// DO NOT EDIT!  Generated automatically by genprops.awk.\n\n") > filename;
-  pcount = 1000;
+  pcount = 0;
 }
 
 /BEGIN_PROPERTIES\(.*\)/ {
@@ -517,6 +574,7 @@
   str = substr (str, k + 17);
   l = index (str, ")");
   class_name = substr (str, 1, l-1);
+  base = 0;
   next;
 }
 
@@ -524,6 +582,15 @@
   gather = 1;
   idx = 0;
   class_name = "";
+  base = 0;
+  next;
+}
+
+/BEGIN_BASE_PROPERTIES/ {
+  gather = 1;
+  idx = 0;
+  class_name = "base";
+  base = 1;
   next;
 }
 
@@ -553,6 +620,7 @@
       mutable[idx] = 0;
 
     type[idx] = $(field++);
+    ptype[idx] = (type[idx] ~ /^.*_property$/);
     name[idx] = $(field++);
 
     limits[idx] = 0;
@@ -563,6 +631,7 @@
     emit_set[idx] = "definition";
     defval[idx] = "";
     updater[idx] = "";
+    factory[idx] = 1;
 ##    if (type[idx] == "octave_value")
 ##      emit_ov_set[idx] = "";
 ##    else
@@ -618,6 +687,10 @@
         if (index (quals, "U"))
           updater[idx] = "extern";
 
+	## There is not factory default value
+        if (index (quals, "f"))
+          factory[idx] = 0;
+
 ##        ## emmit an asignment set function
 ##        if (index (quals, "a"))
 ##          emit_ov_set[idx] = "assignment";
--- a/src/graphics.cc	Tue Aug 26 13:26:05 2008 -0400
+++ b/src/graphics.cc	Tue Aug 26 13:32:52 2008 -0400
@@ -1447,63 +1447,22 @@
 }
 
 octave_value
-base_properties::get (const caseless_str& name) const
+base_properties::get_dynamic (const caseless_str& name) const
 {
   octave_value retval;
 
-  if (name.compare ("tag"))
-    retval = get_tag ();
-  else if (name.compare ("type"))
-    retval = get_type ();
-  else if (name.compare ("__modified__"))
-    retval = is_modified ();
-  else if (name.compare ("parent"))
-    retval = get_parent ().as_octave_value ();
-  else if (name.compare ("children"))
-    retval = children;
-  else if (name.compare ("busyaction"))
-    retval = get_busyaction ();
-  else if (name.compare ("buttondownfcn"))
-    retval = get_buttondownfcn ();
-  else if (name.compare ("clipping"))
-    retval = get_clipping ();
-  else if (name.compare ("createfcn"))
-    retval = get_createfcn ();
-  else if (name.compare ("deletefcn"))
-    retval = get_deletefcn ();
-  else if (name.compare ("handlevisibility"))
-    retval = get_handlevisibility ();
-  else if (name.compare ("hittest"))
-    retval = get_hittest ();
-  else if (name.compare ("interruptible"))
-    retval = get_interruptible ();
-  else if (name.compare ("selected"))
-    retval = get_selected ();
-  else if (name.compare ("selectionhighlight"))
-    retval = get_selectionhighlight ();
-  else if (name.compare ("uicontextmenu"))
-    retval = get_uicontextmenu ();
-  else if (name.compare ("userdata"))
-    retval = get_userdata ();
-  else if (name.compare ("visible"))
-    retval = get_visible ();
-  else if (name.compare ("beingdeleted"))
-    retval = get_beingdeleted ();
+  std::map<caseless_str, property>::const_iterator it = all_props.find (name);
+
+  if (it != all_props.end ())
+    retval = it->second.get ();
   else
-  {
-    std::map<caseless_str, property>::const_iterator it = all_props.find (name);
-
-    if (it != all_props.end ())
-      retval = it->second.get ();
-    else
-      error ("get: unknown property \"%s\"", name.c_str ());
-  }
+    error ("get: unknown property \"%s\"", name.c_str ());
 
   return retval;
 }
 
 octave_value
-base_properties::get (bool all) const
+base_properties::get_dynamic (bool all) const
 {
   Octave_map m;
 
@@ -1512,130 +1471,35 @@
     if (all || ! it->second.is_hidden ())
       m.assign (it->second.get_name (), it->second.get ());
 
-  m.assign ("tag", get_tag ());
-  m.assign ("type", get_type ());
-  if (all)
-    m.assign ("__modified__", is_modified ());
-  m.assign ("parent", get_parent ().as_octave_value ());
-  m.assign ("children", children);
-  m.assign ("busyaction", get_busyaction ());
-  m.assign ("buttondownfcn", get_buttondownfcn ());
-  m.assign ("clipping", get_clipping ());
-  m.assign ("createfcn", get_createfcn ());
-  m.assign ("deletefcn", get_deletefcn ());
-  m.assign ("handlevisibility", get_handlevisibility ());
-  m.assign ("hittest", get_hittest ());
-  m.assign ("interruptible", get_interruptible ());
-  m.assign ("selected", get_selected ());
-  m.assign ("selectionhighlight", get_selectionhighlight ());
-  m.assign ("uicontextmenu", get_uicontextmenu ());
-  m.assign ("userdata", get_userdata ());
-  m.assign ("visible", get_visible ());
-  m.assign ("beingdeleted", get_beingdeleted ());
-
   return m;
 }
 
 void
-base_properties::set (const caseless_str& name, const octave_value& val)
+base_properties::set_dynamic (const caseless_str& name, const octave_value& val)
 {
-  if (name.compare ("tag"))
-    set_tag (val);
-  else if (name.compare ("__modified__"))
-    __modified__ = val;
-  else if (name.compare ("parent"))
-    set_parent (val);
-  else if (name.compare ("children"))
-    maybe_set_children (children, val);
-  else if (name.compare ("busyaction"))
-    set_busyaction (val);
-  else if (name.compare ("buttondownfcn"))
-    set_buttondownfcn (val);
-  else if (name.compare ("clipping"))
-    set_clipping (val);
-  else if (name.compare ("createfcn"))
-    set_createfcn (val);
-  else if (name.compare ("deletefcn"))
-    set_deletefcn (val);
-  else if (name.compare ("handlevisibility"))
-    set_handlevisibility (val);
-  else if (name.compare ("hittest"))
-    set_hittest (val);
-  else if (name.compare ("interruptible"))
-    set_interruptible (val);
-  else if (name.compare ("selected"))
-    set_selected (val);
-  else if (name.compare ("selectionhighlight"))
-    set_selectionhighlight (val);
-  else if (name.compare ("uicontextmenu"))
-    set_uicontextmenu (val);
-  else if (name.compare ("userdata"))
-    set_userdata (val);
-  else if (name.compare ("visible"))
-    set_visible (val);
+  std::map<caseless_str, property>::iterator it = all_props.find (name);
+
+  if (it != all_props.end ())
+    it->second.set (val);
   else
-  {
-    std::map<caseless_str, property>::iterator it = all_props.find (name);
-
-    if (it != all_props.end ())
-      it->second.set (val);
-    else
-      error ("set: unknown property \"%s\"", name.c_str ());
-  }
-
-  if (! error_state && ! name.compare ("__modified__"))
+    error ("set: unknown property \"%s\"", name.c_str ());
+
+  if (! error_state)
     mark_modified ();
 }
 
 property
-base_properties::get_property (const caseless_str& name)
+base_properties::get_property_dynamic (const caseless_str& name)
 {
-  if (name.compare ("beingdeleted"))
-    return property (&beingdeleted, true);
-  else if (name.compare ("busyaction"))
-    return property (&busyaction, true);
-  else if (name.compare ("buttondownfcn"))
-    return property (&buttondownfcn, true);
-  else if (name.compare ("clipping"))
-    return property (&clipping, true);
-  else if (name.compare ("createfcn"))
-    return property (&createfcn, true);
-  else if (name.compare ("deletefcn"))
-    return property (&deletefcn, true);
-  else if (name.compare ("handlevisibility"))
-    return property (&handlevisibility, true);
-  else if (name.compare ("hittest"))
-    return property (&hittest, true);
-  else if (name.compare ("interruptible"))
-    return property (&interruptible, true);
-  else if (name.compare ("parent"))
-    return property (&parent, true);
-  else if (name.compare ("selected"))
-    return property (&selected, true);
-  else if (name.compare ("selectionhighlight"))
-    return property (&selectionhighlight, true);
-  else if (name.compare ("tag"))
-    return property (&tag, true);
-  else if (name.compare ("type"))
-    return property (&userdata, true);
-  else if (name.compare ("userdata"))
-    return property (&visible, true);
-  else if (name.compare ("visible"))
-    return property (&visible, true);
-  else if (name.compare ("__modified__"))
-    return property (&__modified__, true);
+  std::map<caseless_str, property>::const_iterator it = all_props.find (name);
+
+  if (it == all_props.end ())
+    {
+      error ("get_property: unknown property \"%s\"", name.c_str ());
+      return property ();
+    }
   else
-    {
-      std::map<caseless_str, property>::const_iterator it = all_props.find (name);
-
-      if (it == all_props.end ())
-	{
-	  error ("get_property: unknown property \"%s\"", name.c_str ());
-	  return property ();
-	}
-      else
-	return it->second;
-    }
+    return it->second;
 }
 
 bool
@@ -1714,6 +1578,12 @@
 }
 
 void
+base_properties::set_children (const octave_value& val)
+{
+  children = maybe_set_children (children, val);
+}
+
+void
 base_properties::mark_modified (void)
 {
   __modified__ = "on";
--- a/src/graphics.h.in	Tue Aug 26 13:26:05 2008 -0400
+++ b/src/graphics.h.in	Tue Aug 26 13:32:52 2008 -0400
@@ -1516,44 +1516,7 @@
 public:
   base_properties (const std::string& ty = "unknown",
                    const graphics_handle& mh = graphics_handle (),
-                   const graphics_handle& p = graphics_handle ())
-    : beingdeleted ("beingdeleted", mh, false),
-      busyaction ("parent", mh, "{queue}|cancel"),
-      buttondownfcn ("buttondownfcn", mh, Matrix ()),
-      children (),
-      clipping ("clipping", mh, true),
-      createfcn ("createfcn", mh, Matrix ()),
-      deletefcn ("deletefcn", mh, Matrix ()),
-      handlevisibility ("handlevisibility", mh, "{on}|callback|off"),
-      hittest ("hittest", mh, true),
-      interruptible ("interruptible", mh, true),
-      parent ("parent", mh, p), 
-      selected ("selected", mh, false),
-      selectionhighlight ("selectionhighlight", mh, true),
-      tag ("tag", mh),
-      type ("type", mh, ty),
-      userdata ("userdata", mh, Matrix ()),
-      visible ("visible", mh, true),
-      __modified__ ("__modified__", mh, true),
-      __myhandle__ (mh),
-      uicontextmenu ("uicontextmenu", mh, graphics_handle ())
-    {
-      beingdeleted.set_id (BEINGDELETED);
-      busyaction.set_id (BUSYACTION);
-      buttondownfcn.set_id (BUTTONDOWNFCN);
-      clipping.set_id (CLIPPING);
-      createfcn.set_id (CREATEFCN);
-      deletefcn.set_id (DELETEFCN);
-      handlevisibility.set_id (HANDLEVISIBILITY);
-      hittest.set_id (HITTEST);
-      interruptible.set_id (INTERRUPTIBLE);
-      parent.set_id (PARENT);
-      selected.set_id (SELECTED);
-      selectionhighlight.set_id (SELECTIONHIGHLIGHT);
-      tag.set_id (TAG);
-      userdata.set_id (USERDATA);
-      visible.set_id (VISIBLE);
-    }
+                   const graphics_handle& p = graphics_handle ());
 
   virtual ~base_properties (void) { }
 
@@ -1585,57 +1548,8 @@
 
   bool has_property (const caseless_str&);
 
-  std::string get_tag (void) const { return tag.string_value (); }
-
-  graphics_handle get_parent (void) const { return parent.handle_value (); }
-
-  std::string get_type (void) const { return type.string_value (); }
-
-  bool is_modified (void) const { return __modified__.is_on (); }
+  bool is_modified (void) const { return is___modified__ (); }
  
-  graphics_handle get___myhandle__ (void) const { return __myhandle__; }
-  
-  std::string get_busyaction (void) const { return busyaction.current_value (); }
-
-  octave_value get_buttondownfcn (void) const { return buttondownfcn.get (); }
-
-  bool is_clipping (void) const { return clipping.is_on (); }
-  std::string get_clipping (void) const { return clipping.current_value (); }
-
-  void execute_createfcn (const octave_value& data = octave_value ()) const
-    { createfcn.execute (data); }
-
-  octave_value get_createfcn (void) const { return createfcn.get (); }
-
-  void execute_deletefcn (const octave_value& data = octave_value ()) const
-    { deletefcn.execute (data); }
-
-  octave_value get_deletefcn (void) const { return deletefcn.get (); }
-
-  std::string get_handlevisibility (void) const { return handlevisibility.current_value (); }
-
-  bool is_hittest (void) const { return hittest.is_on (); }
-  std::string get_hittest (void) const { return hittest.current_value (); }
-
-  bool is_interruptible (void) const { return interruptible.is_on (); }
-  std::string get_interruptible (void) const { return interruptible.current_value (); }
-
-  bool is_selected (void) const { return selected.is_on (); }
-  std::string get_selected (void) const { return selected.current_value (); }
-
-  bool is_selectionhighlight (void) const { return selectionhighlight.is_on (); }
-  std::string get_selectionhighlight (void) const { return selectionhighlight.current_value (); }
-  
-  octave_value get_uicontextmenu (void) const { return uicontextmenu.get (); }
-
-  octave_value get_userdata (void) const { return userdata.get (); }
- 
-  bool is_visible (void) const { return visible.is_on (); }
-  std::string get_visible (void) const { return visible.current_value (); }
-
-  bool is_beingdeleted (void) const { return beingdeleted.is_on (); }
-  std::string get_beingdeleted (void) const { return beingdeleted.current_value (); }
-
   virtual void remove_child (const graphics_handle& h);
 
   virtual void adopt (const graphics_handle& h)
@@ -1660,135 +1574,11 @@
 
   void set_parent (const octave_value& val);
 
-  void set_modified (const octave_value& val) { __modified__ = val; }
-
-  void set_busyaction (const octave_value& val)
-  {
-    if (! error_state)
-      {
-        busyaction = val;
-        mark_modified ();
-      }
-  }
-
-  void set_buttondownfcn (const octave_value& val)
-  {
-    if (! error_state)
-      {
-        buttondownfcn = val;
-        mark_modified ();
-      }
-  }
-
-  void set_clipping (const octave_value& val)
-  {
-    if (! error_state)
-      {
-        clipping = val;
-        mark_modified ();
-      }
-  }
-
-  void set_createfcn (const octave_value& val)
-  {
-    if (! error_state)
-      {
-        createfcn = val;
-        mark_modified ();
-      }
-  }
-
-  void set_deletefcn (const octave_value& val)
-  {
-    if (! error_state)
-      {
-        deletefcn = val;
-        mark_modified ();
-      }
-  }
-
-  void set_handlevisibility (const octave_value& val)
-  {
-    if (! error_state)
-      {
-        handlevisibility = val;
-        mark_modified ();
-      }
-  }
-
-  void set_hittest (const octave_value& val)
-  {
-    if (! error_state)
-      {
-        hittest = val;
-        mark_modified ();
-      }
-  }
-
-  void set_interruptible (const octave_value& val)
-  {
-    if (! error_state)
-      {
-        interruptible = val;
-        mark_modified ();
-      }
-  }
-
-  void set_selected (const octave_value& val)
-  {
-    if (! error_state)
-      {
-        selected = val;
-        mark_modified ();
-      }
-  }
-
-  void set_selectionhighlight (const octave_value& val)
-  {
-    if (! error_state)
-      {
-        selectionhighlight = val;
-        mark_modified ();
-      }
-  }
-
-  void set_uicontextmenu (const octave_value& val)
-  {
-    if (! error_state)
-      {
-        uicontextmenu = val;
-        mark_modified ();
-      }
-  }
-
-  void set_userdata (const octave_value& val)
-  {
-    if (! error_state)
-      {
-        userdata = val;
-        mark_modified ();
-      }
-  }
-
-  virtual void set_visible (const octave_value& val)
-  {
-    if (! error_state)
-      {
-        visible = val;
-        mark_modified ();
-      }
-  }
-
-  void set_beingdeleted (const octave_value& val)
-  {
-    if (! error_state)
-      {
-	beingdeleted = val;
-	mark_modified ();
-      }
-  }
-
-
+  void set_children (const octave_value& val);
+
+  void set_modified (const octave_value& val) { set___modified__ (val); }
+
+  void set___modified__ (const octave_value& val) { __modified__ = val; }
 
   void reparent (const graphics_handle& new_parent) { parent = new_parent; }
 
@@ -1799,7 +1589,7 @@
 
   virtual void delete_children (void);
 
-  Matrix get_children (void) const { return children; }
+  static property_list::pval_map_type factory_defaults (void);
 
   // FIXME -- these functions should be generated automatically by the
   // genprops.awk script.
@@ -1818,51 +1608,41 @@
   virtual bool is_climinclude (void) const { return false; }
   virtual bool is_aliminclude (void) const { return false; }
  
-  enum
-    {
-      BEINGDELETED = 0,
-      BUSYACTION,
-      BUTTONDOWNFCN,
-      // CHILDREN,
-      CLIPPING,
-      CREATEFCN,
-      DELETEFCN,
-      HANDLEVISIBILITY,
-      HITTEST,
-      INTERRUPTIBLE,
-      PARENT,
-      SELECTED,
-      SELECTIONHIGHLIGHT,
-      TAG,
-      USERDATA,
-      VISIBLE
-    };
-
 protected:
-  // properties common to all objects
-  bool_property beingdeleted;
-  radio_property busyaction;
-  callback_property buttondownfcn;
-  // FIXME: use a property class for children
-  Matrix children;
-  bool_property clipping;
-  callback_property createfcn;
-  callback_property deletefcn;
-  radio_property handlevisibility;
-  bool_property hittest;
-  bool_property interruptible;
-  handle_property parent;
-  bool_property selected;
-  bool_property selectionhighlight;
-  string_property tag;
-  string_property type;
-  any_property userdata;
-  bool_property visible;
-  // additional (octave-specific) properties
-  bool_property __modified__;
-  graphics_handle __myhandle__;
-  // FIXME: should this really be here?
-  handle_property uicontextmenu;
+  void set_dynamic (const caseless_str&, const octave_value&);
+
+  octave_value get_dynamic (const caseless_str&) const;
+
+  octave_value get_dynamic (bool all = false) const;
+
+  property get_property_dynamic (const caseless_str&);
+
+  BEGIN_BASE_PROPERTIES
+    // properties common to all objects
+    bool_property beingdeleted , "off"
+    radio_property busyaction , "{queue}|cancel"
+    callback_property buttondownfcn , Matrix ()
+    // FIXME: use a property class for children
+    Matrix children fs , Matrix ()
+    bool_property clipping , "on"
+    callback_property createfcn , Matrix ()
+    callback_property deletefcn , Matrix ()
+    radio_property handlevisibility , "{on}|callback|off"
+    bool_property hittest , "on"
+    bool_property interruptible , "on"
+    handle_property parent fs , p
+    bool_property selected , "off"
+    bool_property selectionhighlight , "on"
+    string_property tag s , ""
+    string_property type frs , ty
+    any_property userdata , Matrix ()
+    bool_property visible , "on"
+    // additional (octave-specific) properties
+    bool_property __modified__ s , "on"
+    graphics_handle __myhandle__ fhrs , mh
+    // FIXME: should this really be here?
+    handle_property uicontextmenu , graphics_handle ()
+  END_PROPERTIES
 
 protected:
   struct cmp_caseless_str