Mercurial > octave
comparison src/graphics.h.in @ 11175:c0a95a5c6d25
Address the speed of plotting large hggroup groups and in particular
contours (bug #31305). Changes to address this include
- Use __go_patch__ in __contour__ rather than patch so that
the cost of setting up the callback functions is avoided.
The contourgroup callback handles the updating of properties.
- Add children_property class to store children in a list so
that adding and deleting children is a low cost operation.
- Create a new version of update_axis_limits code that doesn't
force the recalculation of all of the objects children.
Patch also allows unclosed patch contours with the FLTK backend.
author | David Bateman <dbateman@free.fr> |
---|---|
date | Tue, 02 Nov 2010 00:47:31 +0100 |
parents | 51ac3a08e53c |
children | 29b1f7d68665 |
comparison
equal
deleted
inserted
replaced
11174:2114867f2a50 | 11175:c0a95a5c6d25 |
---|---|
1366 octave_value data; | 1366 octave_value data; |
1367 }; | 1367 }; |
1368 | 1368 |
1369 // --------------------------------------------------------------------- | 1369 // --------------------------------------------------------------------- |
1370 | 1370 |
1371 class children_property : public base_property | |
1372 { | |
1373 public: | |
1374 children_property (void) | |
1375 : base_property ("", graphics_handle ()) | |
1376 { | |
1377 do_init_children (Matrix ()); | |
1378 } | |
1379 | |
1380 children_property (const std::string& nm, const graphics_handle& h, | |
1381 const Matrix &val) | |
1382 : base_property (nm, h) | |
1383 { | |
1384 do_init_children (val); | |
1385 } | |
1386 | |
1387 children_property (const children_property& p) | |
1388 : base_property (p) | |
1389 { | |
1390 do_init_children (p.children_list); | |
1391 } | |
1392 | |
1393 children_property& operator = (const octave_value& val) | |
1394 { | |
1395 set (val); | |
1396 return *this; | |
1397 } | |
1398 | |
1399 base_property* clone (void) const { return new children_property (*this); } | |
1400 | |
1401 bool remove_child (const double &val) | |
1402 { | |
1403 return do_remove_child (val); | |
1404 } | |
1405 | |
1406 void adopt (const double &val) | |
1407 { | |
1408 do_adopt_child (val); | |
1409 } | |
1410 | |
1411 Matrix get_children (void) const | |
1412 { | |
1413 return do_get_children (false); | |
1414 } | |
1415 | |
1416 Matrix get_hidden (void) const | |
1417 { | |
1418 return do_get_children (true); | |
1419 } | |
1420 | |
1421 Matrix get_all (void) const | |
1422 { | |
1423 return do_get_all_children (); | |
1424 } | |
1425 | |
1426 octave_value get (void) const | |
1427 { | |
1428 return octave_value (get_children ()); | |
1429 } | |
1430 | |
1431 void delete_children (bool clear = false) | |
1432 { | |
1433 do_delete_children (clear); | |
1434 } | |
1435 | |
1436 private: | |
1437 typedef std::list<double>::iterator children_list_iterator; | |
1438 typedef std::list<double>::const_iterator const_children_list_iterator; | |
1439 std::list<double> children_list; | |
1440 | |
1441 protected: | |
1442 bool do_set (const octave_value& val) | |
1443 { | |
1444 const Matrix new_kids = val.matrix_value (); | |
1445 | |
1446 octave_idx_type nel = new_kids.numel (); | |
1447 | |
1448 const Matrix new_kids_column = new_kids.reshape (dim_vector (nel, 1)); | |
1449 | |
1450 bool is_ok = true; | |
1451 | |
1452 if (! error_state) | |
1453 { | |
1454 const Matrix visible_kids = do_get_children (false); | |
1455 | |
1456 if (visible_kids.numel () == new_kids.numel ()) | |
1457 { | |
1458 Matrix t1 = visible_kids.sort (); | |
1459 Matrix t2 = new_kids_column.sort (); | |
1460 | |
1461 if (t1 != t2) | |
1462 is_ok = false; | |
1463 } | |
1464 else | |
1465 is_ok = false; | |
1466 | |
1467 if (! is_ok) | |
1468 error ("set: new children must be a permutation of existing children"); | |
1469 } | |
1470 else | |
1471 { | |
1472 is_ok = false; | |
1473 error ("set: expecting children to be array of graphics handles"); | |
1474 } | |
1475 | |
1476 if (is_ok) | |
1477 { | |
1478 children_list.clear (); | |
1479 do_init_children (new_kids_column.stack (get_hidden ())); | |
1480 } | |
1481 | |
1482 return is_ok; | |
1483 } | |
1484 | |
1485 private: | |
1486 void do_init_children (const Matrix &val) | |
1487 { | |
1488 children_list.clear (); | |
1489 for (octave_idx_type i = 0; i < val.numel (); i++) | |
1490 children_list.push_front (val.xelem (i)); | |
1491 } | |
1492 | |
1493 void do_init_children (const std::list<double> &val) | |
1494 { | |
1495 children_list.clear (); | |
1496 for (const_children_list_iterator p = val.begin (); p != val.end (); p++) | |
1497 children_list.push_front (*p); | |
1498 } | |
1499 | |
1500 Matrix do_get_children (bool return_hidden) const; | |
1501 | |
1502 Matrix do_get_all_children (void) const | |
1503 { | |
1504 Matrix retval (children_list.size (), 1); | |
1505 octave_idx_type i = 0; | |
1506 | |
1507 for (const_children_list_iterator p = children_list.begin (); | |
1508 p != children_list.end (); p++) | |
1509 retval(i++) = *p; | |
1510 return retval; | |
1511 } | |
1512 | |
1513 bool do_remove_child (double child) | |
1514 { | |
1515 for (children_list_iterator p = children_list.begin (); | |
1516 p != children_list.end (); p++) | |
1517 { | |
1518 if (*p == child) | |
1519 { | |
1520 children_list.erase (p); | |
1521 return true; | |
1522 } | |
1523 } | |
1524 return false; | |
1525 } | |
1526 | |
1527 void do_adopt_child (const double &val) | |
1528 { | |
1529 children_list.push_front (val); | |
1530 } | |
1531 | |
1532 void do_delete_children (bool clear); | |
1533 }; | |
1534 | |
1535 | |
1536 | |
1537 // --------------------------------------------------------------------- | |
1538 | |
1371 class callback_property : public base_property | 1539 class callback_property : public base_property |
1372 { | 1540 { |
1373 public: | 1541 public: |
1374 callback_property (const std::string& nm, const graphics_handle& h, | 1542 callback_property (const std::string& nm, const graphics_handle& h, |
1375 const octave_value& m) | 1543 const octave_value& m) |
1846 return false; | 2014 return false; |
1847 } | 2015 } |
1848 | 2016 |
1849 bool is_modified (void) const { return is___modified__ (); } | 2017 bool is_modified (void) const { return is___modified__ (); } |
1850 | 2018 |
1851 virtual void remove_child (const graphics_handle& h); | 2019 virtual void remove_child (const graphics_handle& h) |
2020 { | |
2021 if (children.remove_child (h.value ())) | |
2022 mark_modified (); | |
2023 } | |
1852 | 2024 |
1853 virtual void adopt (const graphics_handle& h) | 2025 virtual void adopt (const graphics_handle& h) |
1854 { | 2026 { |
1855 octave_idx_type n = children.numel (); | 2027 children.adopt (h.value ()); |
1856 children.resize (n+1, 1); | |
1857 for (octave_idx_type i = n; i > 0; i--) | |
1858 children(i) = children(i-1); | |
1859 children(0) = h.value (); | |
1860 mark_modified (); | 2028 mark_modified (); |
1861 } | 2029 } |
1862 | 2030 |
1863 virtual graphics_backend get_backend (void) const; | 2031 virtual graphics_backend get_backend (void) const; |
1864 | 2032 |
1875 | 2043 |
1876 void set_tag (const octave_value& val) { tag = val; } | 2044 void set_tag (const octave_value& val) { tag = val; } |
1877 | 2045 |
1878 void set_parent (const octave_value& val); | 2046 void set_parent (const octave_value& val); |
1879 | 2047 |
1880 Matrix get_all_children (void) const { return children; } | 2048 Matrix get_children (void) const |
1881 | 2049 { |
1882 Matrix get_hidden_children (void) const; | 2050 return children.get_children (); |
1883 | 2051 } |
1884 void set_children (const octave_value& val); | 2052 |
2053 Matrix get_all_children (void) const | |
2054 { | |
2055 return children.get_all (); | |
2056 } | |
2057 | |
2058 Matrix get_hidden_children (void) const | |
2059 { | |
2060 return children.get_hidden (); | |
2061 } | |
1885 | 2062 |
1886 void set_modified (const octave_value& val) { set___modified__ (val); } | 2063 void set_modified (const octave_value& val) { set___modified__ (val); } |
1887 | 2064 |
1888 void set___modified__ (const octave_value& val) { __modified__ = val; } | 2065 void set___modified__ (const octave_value& val) { __modified__ = val; } |
1889 | 2066 |
1892 // Update data limits for AXIS_TYPE (xdata, ydata, etc.) in the parent | 2069 // Update data limits for AXIS_TYPE (xdata, ydata, etc.) in the parent |
1893 // axes object. | 2070 // axes object. |
1894 | 2071 |
1895 virtual void update_axis_limits (const std::string& axis_type) const; | 2072 virtual void update_axis_limits (const std::string& axis_type) const; |
1896 | 2073 |
1897 virtual void delete_children (void); | 2074 virtual void update_axis_limits (const std::string& axis_type, |
1898 | 2075 const graphics_handle& h) const; |
2076 | |
2077 virtual void delete_children (bool clear = false) | |
2078 { | |
2079 children.delete_children (clear); | |
2080 } | |
2081 | |
1899 static property_list::pval_map_type factory_defaults (void); | 2082 static property_list::pval_map_type factory_defaults (void); |
1900 | 2083 |
1901 // FIXME -- these functions should be generated automatically by the | 2084 // FIXME -- these functions should be generated automatically by the |
1902 // genprops.awk script. | 2085 // genprops.awk script. |
1903 // | 2086 // |
1938 BEGIN_BASE_PROPERTIES | 2121 BEGIN_BASE_PROPERTIES |
1939 // properties common to all objects | 2122 // properties common to all objects |
1940 bool_property beingdeleted , "off" | 2123 bool_property beingdeleted , "off" |
1941 radio_property busyaction , "{queue}|cancel" | 2124 radio_property busyaction , "{queue}|cancel" |
1942 callback_property buttondownfcn , Matrix () | 2125 callback_property buttondownfcn , Matrix () |
1943 // FIXME -- use a property class for children. | 2126 children_property children gf , Matrix () |
1944 Matrix children Gfs , Matrix () | |
1945 bool_property clipping , "on" | 2127 bool_property clipping , "on" |
1946 callback_property createfcn , Matrix () | 2128 callback_property createfcn , Matrix () |
1947 callback_property deletefcn , Matrix () | 2129 callback_property deletefcn , Matrix () |
1948 radio_property handlevisibility , "{on}|callback|off" | 2130 radio_property handlevisibility , "{on}|callback|off" |
1949 bool_property hittest , "on" | 2131 bool_property hittest , "on" |
1981 protected: | 2163 protected: |
1982 void insert_static_property (const std::string& name, base_property& p) | 2164 void insert_static_property (const std::string& name, base_property& p) |
1983 { insert_property (name, property (&p, true)); } | 2165 { insert_property (name, property (&p, true)); } |
1984 | 2166 |
1985 virtual void init (void) { } | 2167 virtual void init (void) { } |
1986 | |
1987 private: | |
1988 Matrix get_children_internal (bool return_hidden) const; | |
1989 }; | 2168 }; |
1990 | 2169 |
1991 class OCTINTERP_API base_graphics_object | 2170 class OCTINTERP_API base_graphics_object |
1992 { | 2171 { |
1993 public: | 2172 public: |
2149 return properties; | 2328 return properties; |
2150 } | 2329 } |
2151 | 2330 |
2152 virtual void update_axis_limits (const std::string& axis_type); | 2331 virtual void update_axis_limits (const std::string& axis_type); |
2153 | 2332 |
2333 virtual void update_axis_limits (const std::string& axis_type, | |
2334 const graphics_handle& h); | |
2335 | |
2154 virtual bool valid_object (void) const { return false; } | 2336 virtual bool valid_object (void) const { return false; } |
2155 | 2337 |
2156 virtual std::string type (void) const | 2338 virtual std::string type (void) const |
2157 { | 2339 { |
2158 return (valid_object () ? get_properties ().graphics_object_name () | 2340 return (valid_object () ? get_properties ().graphics_object_name () |
2332 } | 2514 } |
2333 | 2515 |
2334 void update_axis_limits (const std::string& axis_type) | 2516 void update_axis_limits (const std::string& axis_type) |
2335 { | 2517 { |
2336 rep->update_axis_limits (axis_type); | 2518 rep->update_axis_limits (axis_type); |
2519 } | |
2520 | |
2521 void update_axis_limits (const std::string& axis_type, | |
2522 const graphics_handle& h) | |
2523 { | |
2524 rep->update_axis_limits (axis_type, h); | |
2337 } | 2525 } |
2338 | 2526 |
2339 bool valid_object (void) const { return rep->valid_object (); } | 2527 bool valid_object (void) const { return rep->valid_object (); } |
2340 | 2528 |
2341 std::string type (void) const { return rep->type (); } | 2529 std::string type (void) const { return rep->type (); } |
3193 | 3381 |
3194 const base_properties& get_properties (void) const { return xproperties; } | 3382 const base_properties& get_properties (void) const { return xproperties; } |
3195 | 3383 |
3196 void update_axis_limits (const std::string& axis_type); | 3384 void update_axis_limits (const std::string& axis_type); |
3197 | 3385 |
3386 void update_axis_limits (const std::string& axis_type, | |
3387 const graphics_handle& h); | |
3388 | |
3198 bool valid_object (void) const { return true; } | 3389 bool valid_object (void) const { return true; } |
3199 | 3390 |
3200 void reset_default_properties (void); | 3391 void reset_default_properties (void); |
3201 | 3392 |
3202 private: | 3393 private: |
3798 update_limits (); | 3989 update_limits (); |
3799 } | 3990 } |
3800 | 3991 |
3801 void adopt (const graphics_handle& h) | 3992 void adopt (const graphics_handle& h) |
3802 { | 3993 { |
3994 | |
3803 base_properties::adopt (h); | 3995 base_properties::adopt (h); |
3804 update_limits (); | 3996 update_limits (h); |
3805 } | 3997 } |
3806 | 3998 |
3807 // See the genprops.awk script for an explanation of the | 3999 // See the genprops.awk script for an explanation of the |
3808 // properties declarations. | 4000 // properties declarations. |
3809 | 4001 |
3820 bool_property climinclude h , "on" | 4012 bool_property climinclude h , "on" |
3821 bool_property aliminclude h , "on" | 4013 bool_property aliminclude h , "on" |
3822 END_PROPERTIES | 4014 END_PROPERTIES |
3823 | 4015 |
3824 private: | 4016 private: |
3825 void update_limits (void) | 4017 void update_limits (void) const; |
3826 { | 4018 |
3827 update_axis_limits ("xlim"); | 4019 void update_limits (const graphics_handle& h) const; |
3828 update_axis_limits ("ylim"); | |
3829 update_axis_limits ("zlim"); | |
3830 update_axis_limits ("clim"); | |
3831 update_axis_limits ("alim"); | |
3832 } | |
3833 | 4020 |
3834 protected: | 4021 protected: |
3835 void init (void) | 4022 void init (void) |
3836 { } | 4023 { } |
4024 | |
3837 }; | 4025 }; |
3838 | 4026 |
3839 private: | 4027 private: |
3840 properties xproperties; | 4028 properties xproperties; |
3841 | 4029 |
3851 base_properties& get_properties (void) { return xproperties; } | 4039 base_properties& get_properties (void) { return xproperties; } |
3852 | 4040 |
3853 const base_properties& get_properties (void) const { return xproperties; } | 4041 const base_properties& get_properties (void) const { return xproperties; } |
3854 | 4042 |
3855 bool valid_object (void) const { return true; } | 4043 bool valid_object (void) const { return true; } |
3856 | 4044 |
3857 void update_axis_limits (const std::string& axis_type); | 4045 void update_axis_limits (const std::string& axis_type); |
4046 | |
4047 void update_axis_limits (const std::string& axis_type, | |
4048 const graphics_handle& h); | |
4049 | |
3858 }; | 4050 }; |
3859 | 4051 |
3860 // --------------------------------------------------------------------- | 4052 // --------------------------------------------------------------------- |
3861 | 4053 |
3862 class OCTINTERP_API uimenu : public base_graphics_object | 4054 class OCTINTERP_API uimenu : public base_graphics_object |