From 6d5417709cda9af579e067ee91dadef8559d43bf Mon Sep 17 00:00:00 2001 From: Surinder Kumar Date: Thu, 27 Jul 2017 17:25:07 +0530 Subject: [PATCH] Moved the javascripts of different modules from 'templates' to 'static' directory. Moving the javascripts for the following modules: - About - Browser nodes - Dashboard - FileManager - Vendor/snap.svg - Preferences - Settings - Backup - Datagrid - Debugger - Sqleditor - Grant Wizard - Import & Export - Maintenance - Restore and - User Management --- .../{templates/about => static/js}/about.js | 0 web/pgadmin/browser/server_groups/__init__.py | 2 +- .../foreign_servers/__init__.py | 8 + .../js/foreign_server.js} | 0 .../foreign_servers/user_mapping/__init__.py | 8 + .../js/user_mapping.js} | 0 .../catalog_objects/columns/__init__.py | 8 + .../js/catalog_object_column.js | 0 .../schemas/foreign_tables/__init__.py | 8 +- .../static/img/coll-foreign_table.png | Bin 0 -> 492 bytes .../static/img/foreign_table.png | Bin 0 -> 563 bytes .../foreign_tables/static/js/foreign_table.js | 719 ++ .../tests/test_foreign_table_add.py | 2 +- .../tests/test_foreign_table_delete.py | 2 +- .../tests/test_foreign_table_get.py | 2 +- .../tests/test_foreign_table_put.py | 2 +- .../schemas/packages/edbfuncs/__init__.py | 16 + .../edbfunc => static}/js/edbfunc.js | 0 .../edbproc => static}/js/edbproc.js | 0 .../schemas/packages/edbvars/__init__.py | 8 + .../{templates/edbvar => static}/js/edbvar.js | 0 .../schemas/tables/column/__init__.py | 8 + .../{templates/column => static}/js/column.js | 0 .../schemas/tables/constraints/__init__.py | 8 + .../constraints/check_constraint/__init__.py | 12 +- .../js/check_constraint.js | 2 +- .../tests/test_check_constraint_add.py | 2 +- .../tests/test_check_constraint_delete.py | 2 +- .../tests/test_check_constraint_get.py | 2 +- .../tests/test_check_constraint_put.py | 2 +- .../exclusion_constraint/__init__.py | 8 + .../js/exclusion_constraint.js | 2 + .../constraints/foreign_key/__init__.py | 8 + .../foreign_key => static}/js/foreign_key.js | 2 + .../constraints/index_constraint/__init__.py | 8 + .../index_constraint/js/index_constraint.js | 569 -- .../constraints => static}/js/constraints.js | 2 +- .../schemas/tables/indexes/__init__.py | 8 + .../{templates/index => static}/js/index.js | 0 .../schemas/tables/rules/__init__.py | 8 + .../rules/js/rules.js => static/js/rule.js} | 0 .../schemas/tables/triggers/__init__.py | 8 + .../trigger => static}/js/trigger.js | 0 .../servers/resource_groups/__init__.py | 9 + .../js/resource_group.js} | 0 .../server_groups/servers/roles/__init__.py | 8 + .../{templates/role => static}/js/role.js | 0 .../server_groups/servers/static/js/server.js | 8 +- .../servers/tablespaces/__init__.py | 8 + .../js/tablespace.js} | 0 .../server_groups/static/img/server_group.png | Bin 0 -> 504 bytes .../js/{server-group.js => server_group.js} | 12 +- .../server_groups/tests/test_sg_get.py | 2 +- .../browser => static}/js/browser.js | 2 +- .../browser => static}/js/collection.js | 0 .../{templates/browser => static}/js/error.js | 0 .../{templates/browser => static}/js/node.js | 38 +- .../dashboard => static}/js/dashboard.js | 0 .../js/file_manager.js | 0 .../file_manager => static}/js/utility.js | 0 .../explain/js/explain.js | 0 .../explain/vendor/snap.svg/snap.svg-min.js | 21 - .../explain/vendor/snap.svg/snap.svg.js | 8149 ----------------- .../preferences => static/js}/preferences.js | 0 .../settings => static/js}/settings.js | 0 web/pgadmin/static/bundle/app.js | 4 +- web/pgadmin/static/bundle/browser.js | 4 +- web/pgadmin/static/bundle/codemirror.js | 2 +- web/pgadmin/static/js/url_for.js | 1 - web/pgadmin/templates/base.html | 1 - .../{templates/backup => static}/js/backup.js | 0 .../datagrid => static}/js/datagrid.js | 2 +- .../debugger => static}/js/debugger.js | 4 +- .../debugger => static}/js/debugger_ui.js | 0 .../debugger => static}/js/direct.js | 6 +- .../js/grant_wizard.js | 2 +- .../js/import_export.js | 0 .../maintenance => static}/js/maintenance.js | 0 .../restore => static}/js/restore.js | 0 .../sqleditor => static}/js/sqleditor.js | 10 +- .../js/user_management.js | 0 web/webpack.config.js | 42 +- web/webpack.shim.js | 205 +- 83 files changed, 1058 insertions(+), 8928 deletions(-) rename web/pgadmin/about/{templates/about => static/js}/about.js (100%) rename web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/{templates/foreign_servers/js/foreign_servers.js => static/js/foreign_server.js} (100%) rename web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/user_mapping/{templates/user_mappings/js/user_mappings.js => static/js/user_mapping.js} (100%) rename web/pgadmin/browser/server_groups/servers/databases/schemas/catalog_objects/columns/{templates/catalog_object_column => static}/js/catalog_object_column.js (100%) create mode 100644 web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/static/img/coll-foreign_table.png create mode 100644 web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/static/img/foreign_table.png create mode 100644 web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/static/js/foreign_table.js rename web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/{templates/edbfunc => static}/js/edbfunc.js (100%) rename web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/{templates/edbproc => static}/js/edbproc.js (100%) rename web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbvars/{templates/edbvar => static}/js/edbvar.js (100%) rename web/pgadmin/browser/server_groups/servers/databases/schemas/tables/column/{templates/column => static}/js/column.js (100%) rename web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/{templates/check_constraint => static}/js/check_constraint.js (99%) rename web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/exclusion_constraint/{templates/exclusion_constraint => static}/js/exclusion_constraint.js (99%) rename web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/foreign_key/{templates/foreign_key => static}/js/foreign_key.js (99%) delete mode 100644 web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/index_constraint/templates/index_constraint/js/index_constraint.js rename web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/{templates/constraints => static}/js/constraints.js (96%) rename web/pgadmin/browser/server_groups/servers/databases/schemas/tables/indexes/{templates/index => static}/js/index.js (100%) rename web/pgadmin/browser/server_groups/servers/databases/schemas/tables/rules/{templates/rules/js/rules.js => static/js/rule.js} (100%) rename web/pgadmin/browser/server_groups/servers/databases/schemas/tables/triggers/{templates/trigger => static}/js/trigger.js (100%) rename web/pgadmin/browser/server_groups/servers/resource_groups/{templates/resource_groups/js/resource_groups.js => static/js/resource_group.js} (100%) rename web/pgadmin/browser/server_groups/servers/roles/{templates/role => static}/js/role.js (100%) rename web/pgadmin/browser/server_groups/servers/tablespaces/{templates/tablespaces/js/tablespaces.js => static/js/tablespace.js} (100%) create mode 100644 web/pgadmin/browser/server_groups/static/img/server_group.png rename web/pgadmin/browser/server_groups/static/js/{server-group.js => server_group.js} (90%) rename web/pgadmin/browser/{templates/browser => static}/js/browser.js (99%) rename web/pgadmin/browser/{templates/browser => static}/js/collection.js (100%) rename web/pgadmin/browser/{templates/browser => static}/js/error.js (100%) rename web/pgadmin/browser/{templates/browser => static}/js/node.js (98%) rename web/pgadmin/dashboard/{templates/dashboard => static}/js/dashboard.js (100%) rename web/pgadmin/misc/file_manager/{templates/file_manager => static}/js/file_manager.js (100%) rename web/pgadmin/misc/file_manager/{templates/file_manager => static}/js/utility.js (100%) rename web/pgadmin/misc/{templates => static}/explain/js/explain.js (100%) delete mode 100644 web/pgadmin/misc/static/explain/vendor/snap.svg/snap.svg-min.js delete mode 100644 web/pgadmin/misc/static/explain/vendor/snap.svg/snap.svg.js rename web/pgadmin/preferences/{templates/preferences => static/js}/preferences.js (100%) rename web/pgadmin/settings/{templates/settings => static/js}/settings.js (100%) rename web/pgadmin/tools/backup/{templates/backup => static}/js/backup.js (100%) rename web/pgadmin/tools/datagrid/{templates/datagrid => static}/js/datagrid.js (99%) rename web/pgadmin/tools/debugger/{templates/debugger => static}/js/debugger.js (99%) rename web/pgadmin/tools/debugger/{templates/debugger => static}/js/debugger_ui.js (100%) rename web/pgadmin/tools/debugger/{templates/debugger => static}/js/direct.js (99%) rename web/pgadmin/tools/grant_wizard/{templates/grant_wizard => static}/js/grant_wizard.js (99%) rename web/pgadmin/tools/import_export/{templates/import_export => static}/js/import_export.js (100%) rename web/pgadmin/tools/maintenance/{templates/maintenance => static}/js/maintenance.js (100%) rename web/pgadmin/tools/restore/{templates/restore => static}/js/restore.js (100%) rename web/pgadmin/tools/sqleditor/{templates/sqleditor => static}/js/sqleditor.js (99%) rename web/pgadmin/tools/user_management/{templates/user_management => static}/js/user_management.js (100%) diff --git a/web/pgadmin/about/templates/about/about.js b/web/pgadmin/about/static/js/about.js similarity index 100% rename from web/pgadmin/about/templates/about/about.js rename to web/pgadmin/about/static/js/about.js diff --git a/web/pgadmin/browser/server_groups/__init__.py b/web/pgadmin/browser/server_groups/__init__.py index ab0a3ee2a..fd2b4ac99 100644 --- a/web/pgadmin/browser/server_groups/__init__.py +++ b/web/pgadmin/browser/server_groups/__init__.py @@ -26,7 +26,7 @@ from pgadmin.model import db, ServerGroup class ServerGroupModule(BrowserPluginModule): - NODE_TYPE = "server-group" + NODE_TYPE = "server_group" def get_nodes(self, *arg, **kwargs): """Return a JSON document listing the server groups for the user""" diff --git a/web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/__init__.py b/web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/__init__.py index 7b2da9932..c2512c432 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/__init__.py @@ -86,6 +86,14 @@ class ForeignServerModule(CollectionNodeModule): """ return databases.DatabaseModule.NODE_TYPE + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + blueprint = ForeignServerModule(__name__) diff --git a/web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/templates/foreign_servers/js/foreign_servers.js b/web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/static/js/foreign_server.js similarity index 100% rename from web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/templates/foreign_servers/js/foreign_servers.js rename to web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/static/js/foreign_server.js diff --git a/web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/user_mapping/__init__.py b/web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/user_mapping/__init__.py index c6a131df4..263a4ca79 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/user_mapping/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/user_mapping/__init__.py @@ -101,6 +101,14 @@ class UserMappingModule(CollectionNodeModule): return servers.ServerModule.NODE_TYPE + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + blueprint = UserMappingModule(__name__) diff --git a/web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/user_mapping/templates/user_mappings/js/user_mappings.js b/web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/user_mapping/static/js/user_mapping.js similarity index 100% rename from web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/user_mapping/templates/user_mappings/js/user_mappings.js rename to web/pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/user_mapping/static/js/user_mapping.js diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/catalog_objects/columns/__init__.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/catalog_objects/columns/__init__.py index ea2254d83..eebf05b48 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/catalog_objects/columns/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/catalog_objects/columns/__init__.py @@ -94,6 +94,14 @@ class CatalogObjectColumnsModule(CollectionNodeModule): 'show_system_objects' ) + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + blueprint = CatalogObjectColumnsModule(__name__) diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/catalog_objects/columns/templates/catalog_object_column/js/catalog_object_column.js b/web/pgadmin/browser/server_groups/servers/databases/schemas/catalog_objects/columns/static/js/catalog_object_column.js similarity index 100% rename from web/pgadmin/browser/server_groups/servers/databases/schemas/catalog_objects/columns/templates/catalog_object_column/js/catalog_object_column.js rename to web/pgadmin/browser/server_groups/servers/databases/schemas/catalog_objects/columns/static/js/catalog_object_column.js diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/__init__.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/__init__.py index 2ee6a4305..ed383942c 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/__init__.py @@ -56,7 +56,7 @@ class ForeignTableModule(SchemaChildModule): - Load the module script for Foreign Table, when schema node is initialized. """ - NODE_TYPE = 'foreign-table' + NODE_TYPE = 'foreign_table' COLLECTION_LABEL = gettext("Foreign Tables") def __init__(self, *args, **kwargs): @@ -396,7 +396,7 @@ class ForeignTableView(PGChildNodeView, DataTypeReader): row['oid'], scid, row['name'], - icon="icon-foreign-table" + icon="icon-foreign_table" )) return make_json_response( @@ -430,7 +430,7 @@ class ForeignTableView(PGChildNodeView, DataTypeReader): row['oid'], scid, row['name'], - icon="icon-foreign-table" + icon="icon-foreign_table" ), status=200 ) @@ -689,7 +689,7 @@ class ForeignTableView(PGChildNodeView, DataTypeReader): foid, scid, self.request['name'], - icon="icon-foreign-table" + icon="icon-foreign_table" ) ) except Exception as e: diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/static/img/coll-foreign_table.png b/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/static/img/coll-foreign_table.png new file mode 100644 index 0000000000000000000000000000000000000000..dc1f742bbca05980f3c4cbf3c16af0e0cf9afa41 GIT binary patch literal 492 zcmVPx#x=>71MPs@4A(iKf&i<6o`K{IR%G~PS>E7PngUkI&tMEOf?I@Y)-{0Tj;^O1u zv~3?Ck9B?(XU7>EYqwrlzK-sHm;2t*@`I>gwu{%Jb*v=j-e1 z=;-LFsj2Vp@A2{R?d|QVs;aQCu(GnUPx#)lf`SMdakzW8Cd_Exg@A$?CYb4k%>8S=_(7)bHlge;oa(gJ z?%mzp-rnBd-{0Wi;Njun;^N}tFMX^=c%cwtgNi;?CkCB?eFjJ z>gwvJr>Cf>sI9H7udlD`>+A6F@bdEV?(XiZtE;fEu(7eRva+)A@$vKX^Y!)hwY9bO z_V)Pr__nsTxVX6Y_xDt#KRo~d00DGTPE!Ct=GbNc0004EOGiWihy@);00009a7bBm z000XU000XU0RWnu7ytkO2XskIMF-mh92F=elJWmr0002WNkl -1) + return true; + + if ('coll-foreign-table' == d._type) { + //Check if we are not child of catalog + var prev_i = t.hasParent(i) ? t.parent(i) : null, + prev_d = prev_i ? t.itemData(prev_i) : null; + if( prev_d._type == 'catalog') { + return false; + } else { + return true; + } + } + i = t.hasParent(i) ? t.parent(i) : null; + d = i ? t.itemData(i) : null; + } + // by default we do not want to allow create menu + return true; + } + }); + + } + + return pgBrowser.Nodes['foreign_table']; +}); diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_add.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_add.py index d11e11c27..3dcf456c5 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_add.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_add.py @@ -30,7 +30,7 @@ class ForeignTableAddTestCase(BaseTestGenerator): scenarios = [ # Fetching default URL for foreign server node. - ('Check foreign table Node', dict(url='/browser/foreign-table/obj/')) + ('Check foreign table Node', dict(url='/browser/foreign_table/obj/')) ] def setUp(self): diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_delete.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_delete.py index 86ea0ae6a..731e32b07 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_delete.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_delete.py @@ -30,7 +30,7 @@ class ForeignTableDeleteTestCase(BaseTestGenerator): scenarios = [ # Fetching default URL for foreign table node. - ('Check foreign table Node', dict(url='/browser/foreign-table/obj/')) + ('Check foreign table Node', dict(url='/browser/foreign_table/obj/')) ] def setUp(self): diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_get.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_get.py index 7c4faf1c0..329bd34a4 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_get.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_get.py @@ -29,7 +29,7 @@ class ForeignTableGetTestCase(BaseTestGenerator): """ scenarios = [ # Fetching default URL for foreign server node. - ('Check foreign table Node', dict(url='/browser/foreign-table/obj/')) + ('Check foreign table Node', dict(url='/browser/foreign_table/obj/')) ] def setUp(self): diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_put.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_put.py index b46e18442..ee219047c 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_put.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/tests/test_foreign_table_put.py @@ -30,7 +30,7 @@ class ForeignTablePutTestCase(BaseTestGenerator): """ scenarios = [ # Fetching default URL for foreign server node. - ('Check foreign table Node', dict(url='/browser/foreign-table/obj/')) + ('Check foreign table Node', dict(url='/browser/foreign_table/obj/')) ] def setUp(self): diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/__init__.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/__init__.py index 4d34f131d..42187b0de 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/__init__.py @@ -109,6 +109,14 @@ class EdbFuncModule(CollectionNodeModule): self.SHOW_ON_BROWSER, category_label=gettext('Nodes') ) + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + blueprint = EdbFuncModule(__name__) @@ -693,6 +701,14 @@ class EdbProcModule(CollectionNodeModule): self.SHOW_ON_BROWSER, category_label=gettext('Nodes') ) + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + procedure_blueprint = EdbProcModule(__name__) diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/templates/edbfunc/js/edbfunc.js b/web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/static/js/edbfunc.js similarity index 100% rename from web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/templates/edbfunc/js/edbfunc.js rename to web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/static/js/edbfunc.js diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/templates/edbproc/js/edbproc.js b/web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/static/js/edbproc.js similarity index 100% rename from web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/templates/edbproc/js/edbproc.js rename to web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/static/js/edbproc.js diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbvars/__init__.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbvars/__init__.py index 96d789184..7a41194c7 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbvars/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbvars/__init__.py @@ -91,6 +91,14 @@ class EdbVarModule(CollectionNodeModule): """ return False + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + blueprint = EdbVarModule(__name__) diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbvars/templates/edbvar/js/edbvar.js b/web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbvars/static/js/edbvar.js similarity index 100% rename from web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbvars/templates/edbvar/js/edbvar.js rename to web/pgadmin/browser/server_groups/servers/databases/schemas/packages/edbvars/static/js/edbvar.js diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/column/__init__.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/column/__init__.py index b5b88e902..a22703c96 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/column/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/column/__init__.py @@ -92,6 +92,14 @@ class ColumnsModule(CollectionNodeModule): """ return False + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + blueprint = ColumnsModule(__name__) diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/column/templates/column/js/column.js b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/column/static/js/column.js similarity index 100% rename from web/pgadmin/browser/server_groups/servers/databases/schemas/tables/column/templates/column/js/column.js rename to web/pgadmin/browser/server_groups/servers/databases/schemas/tables/column/static/js/column.js diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/__init__.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/__init__.py index 4fda9d76b..88cbe1d6a 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/__init__.py @@ -72,6 +72,14 @@ class ConstraintsModule(CollectionNodeModule): """ return database.DatabaseModule.NODE_TYPE + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + blueprint = ConstraintsModule(__name__) diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/__init__.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/__init__.py index e3022abab..9de9d41ee 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/__init__.py @@ -46,7 +46,7 @@ class CheckConstraintModule(CollectionNodeModule): - Load the module script for the Check Constraint, when any of the Check node is initialized. """ - NODE_TYPE = 'check_constraints' + NODE_TYPE = 'check_constraint' COLLECTION_LABEL = _("Check Constraints") def __init__(self, *args, **kwargs): @@ -75,6 +75,16 @@ class CheckConstraintModule(CollectionNodeModule): """ return database.DatabaseModule.NODE_TYPE + + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + + @property def csssnippets(self): """ diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/templates/check_constraint/js/check_constraint.js b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/static/js/check_constraint.js similarity index 99% rename from web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/templates/check_constraint/js/check_constraint.js rename to web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/static/js/check_constraint.js index bd31d141b..52a197ea6 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/templates/check_constraint/js/check_constraint.js +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/static/js/check_constraint.js @@ -1,5 +1,5 @@ // Check Constraint Module: Node -define('pgadmin.node.check_constraints', [ +define('pgadmin.node.check_constraint', [ 'sources/gettext', 'sources/url_for', 'jquery', 'underscore', 'underscore.string', 'pgadmin', 'pgadmin.browser', 'alertify', 'sources/alerts/alertify_wrapper', diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_add.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_add.py index 1e28d51c4..13a12a885 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_add.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_add.py @@ -25,7 +25,7 @@ class CheckConstraintAddTestCase(BaseTestGenerator): """This class will add check constraint to existing table""" scenarios = [ ('Add check constraint to table', - dict(url='/browser/check_constraints/obj/')) + dict(url='/browser/check_constraint/obj/')) ] def setUp(self): diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_delete.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_delete.py index 0dd361dc5..ae58c9bba 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_delete.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_delete.py @@ -25,7 +25,7 @@ class CheckConstraintDeleteTestCase(BaseTestGenerator): """This class will delete check constraint to existing table""" scenarios = [ ('Delete check constraint to table', - dict(url='/browser/check_constraints/obj/')) + dict(url='/browser/check_constraint/obj/')) ] def setUp(self): diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_get.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_get.py index ee94bbc46..971570ae8 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_get.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_get.py @@ -25,7 +25,7 @@ class CheckConstraintGetTestCase(BaseTestGenerator): """This class will fetch check constraint to existing table""" scenarios = [ ('Fetch check constraint to table', - dict(url='/browser/check_constraints/obj/')) + dict(url='/browser/check_constraint/obj/')) ] def setUp(self): diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_put.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_put.py index 6192ae5a1..e016dc605 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_put.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/tests/test_check_constraint_put.py @@ -26,7 +26,7 @@ class CheckConstraintPutTestCase(BaseTestGenerator): """This class will update check constraint to existing table""" scenarios = [ ('Update check constraint to table', - dict(url='/browser/check_constraints/obj/')) + dict(url='/browser/check_constraint/obj/')) ] def setUp(self): diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/exclusion_constraint/__init__.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/exclusion_constraint/__init__.py index b86850307..24ec064b1 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/exclusion_constraint/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/exclusion_constraint/__init__.py @@ -93,6 +93,14 @@ class ExclusionConstraintModule(ConstraintTypeModule): """ return database.DatabaseModule.NODE_TYPE + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + blueprint = ExclusionConstraintModule(__name__) diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/exclusion_constraint/templates/exclusion_constraint/js/exclusion_constraint.js b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/exclusion_constraint/static/js/exclusion_constraint.js similarity index 99% rename from web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/exclusion_constraint/templates/exclusion_constraint/js/exclusion_constraint.js rename to web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/exclusion_constraint/static/js/exclusion_constraint.js index 917c329c2..065b6096d 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/exclusion_constraint/templates/exclusion_constraint/js/exclusion_constraint.js +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/exclusion_constraint/static/js/exclusion_constraint.js @@ -560,6 +560,8 @@ define('pgadmin.node.exclusion_constraint', [ newRow.addClass("new"); $(newRow).pgMakeVisible('backform-tab'); + } else { + //delete m; } return false; diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/foreign_key/__init__.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/foreign_key/__init__.py index be3061099..ef4667746 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/foreign_key/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/foreign_key/__init__.py @@ -93,6 +93,14 @@ class ForeignKeyConstraintModule(ConstraintTypeModule): """ return database.DatabaseModule.NODE_TYPE + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + @property def csssnippets(self): """ diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/foreign_key/templates/foreign_key/js/foreign_key.js b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/foreign_key/static/js/foreign_key.js similarity index 99% rename from web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/foreign_key/templates/foreign_key/js/foreign_key.js rename to web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/foreign_key/static/js/foreign_key.js index bd88eff2f..7d7426320 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/foreign_key/templates/foreign_key/js/foreign_key.js +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/foreign_key/static/js/foreign_key.js @@ -493,6 +493,8 @@ define('pgadmin.node.foreign_key', [ newRow.addClass("new"); $(newRow).pgMakeVisible('backform-tab'); + } else { + //delete m; } return false; diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/index_constraint/__init__.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/index_constraint/__init__.py index e7a12cceb..f8894cd65 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/index_constraint/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/index_constraint/__init__.py @@ -93,6 +93,14 @@ class IndexConstraintModule(ConstraintTypeModule): """ return database.DatabaseModule.NODE_TYPE + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + class PrimaryKeyConstraintModule(IndexConstraintModule): """ diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/index_constraint/templates/index_constraint/js/index_constraint.js b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/index_constraint/templates/index_constraint/js/index_constraint.js deleted file mode 100644 index 9479acd8f..000000000 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/index_constraint/templates/index_constraint/js/index_constraint.js +++ /dev/null @@ -1,569 +0,0 @@ -define('pgadmin.node.{{node_type}}', [ - 'sources/gettext', 'jquery', 'underscore', 'underscore.string', 'pgadmin', - 'pgadmin.browser', 'alertify', 'pgadmin.browser.collection' -], function(gettext, $, _, S, pgAdmin, pgBrowser, alertify) { - - // Extend the browser's node class for index constraint node - if (!pgBrowser.Nodes['{{node_type}}']) { - pgAdmin.Browser.Nodes['{{node_type}}'] = pgBrowser.Node.extend({ - getTreeNodeHierarchy: pgBrowser.tableChildTreeNodeHierarchy, - type: '{{node_type}}', - label: '{{ node_label }}', - collection_type: 'coll-constraints', - sqlAlterHelp: 'ddl-alter.html', - sqlCreateHelp: 'ddl-constraints.html', - {% if node_type == 'primary_key' %} - dialogHelp: '{{ url_for('help.static', filename='primary_key_dialog.html') }}', - {% else %} - dialogHelp: '{{ url_for('help.static', filename='unique_constraint_dialog.html') }}', - {% endif %} - hasSQL: true, - hasDepends: true, - hasStatistics: true, - statsPrettifyFields: ['Index size'], - parent_type: ['table','partition'], - canDrop: true, - canDropCascade: true, - Init: function() { - /* Avoid multiple registration of menus */ - if (this.initialized) - return; - - this.initialized = true; - - pgBrowser.add_menus([{ - name: 'create_{{node_type}}_on_coll', node: 'coll-constraints', module: this, - applies: ['object', 'context'], callback: 'show_obj_properties', - category: 'create', priority: 4, label: '{{ node_label }}', - icon: 'wcTabIcon icon-{{node_type}}', data: {action: 'create', check: true}, - enable: 'canCreate' - - } - ]); - }, - canCreate: function(itemData, item, data) { - // If check is false then , we will allow create menu - if (data && data.check == false) - return true; - - var t = pgBrowser.tree, i = item, d = itemData, parents = [], - immediate_parent_table_found = false, - is_immediate_parent_table_partitioned = false; - - // To iterate over tree to check parent node - while (i) { - // If table is partitioned table then return false - if (!immediate_parent_table_found && (d._type == 'table' || d._type == 'partition')) { - immediate_parent_table_found = true; - if ('is_partitioned' in d && d.is_partitioned) { - is_immediate_parent_table_partitioned = true; - } - } - - // If it is schema then allow user to create table - if (_.indexOf(['schema'], d._type) > -1) { - {% if node_type == 'primary_key' %} - - if (is_immediate_parent_table_partitioned) { - return false; - } - - // There should be only one primary key per table. - var children = t.children(arguments[1], false), - primary_key_found = false; - - _.each(children, function(child){ - data = pgBrowser.tree.itemData($(child)); - if (!primary_key_found && data._type == "primary_key") { - primary_key_found = true; - } - }); - return !primary_key_found; - {% else %} - return !is_immediate_parent_table_partitioned; - {% endif %} - } - parents.push(d._type); - i = t.hasParent(i) ? t.parent(i) : null; - d = i ? t.itemData(i) : null; - } - // If node is under catalog then do not allow 'create' menu - if (_.indexOf(parents, 'catalog') > -1) { - return false; - } else { - return !is_immediate_parent_table_partitioned; - } - }, - - // Define the model for index constraint node - model: pgAdmin.Browser.Node.Model.extend({ - idAttribute: 'oid', - - defaults: { - name: undefined, - oid: undefined, - comment: undefined, - spcname: undefined, - index: undefined, - fillfactor: undefined, - condeferrable: undefined, - condeferred: undefined, - columns: [] - }, - - // Define the schema for the index constraint node - schema: [{ - id: 'name', label: gettext('Name'), type: 'text', - mode: ['properties', 'create', 'edit'], editable:true, - cellHeaderClasses:'width_percent_40', - },{ - id: 'oid', label: gettext('OID'), cell: 'string', - type: 'text' , mode: ['properties'], editable: false, - cellHeaderClasses:'width_percent_20', - },{ - id: 'comment', label: gettext('Comment'), cell: 'string', - type: 'multiline', mode: ['properties', 'create', 'edit'], - deps:['name'], disabled:function(m) { - var name = m.get('name'); - if (!(name && name != '')) { - setTimeout(function(){ - if(m.get('comment') && m.get('comment') !== '') { - m.set('comment', null); - } - },10); - return true; - } else { - return false; - } - } - },{ - id: 'columns', label: gettext('Columns'), - type: 'collection', group: gettext('Definition'), - editable: false, - cell: Backgrid.StringCell.extend({ - initialize: function() { - Backgrid.StringCell.prototype.initialize.apply(this, arguments); - - var self = this, - collection = this.model.get('columns'); - - // Do not listen for any event(s) for existing constraint. - if (_.isUndefined(self.model.get('oid'))) { - var tableCols = self.model.top.get('columns'); - self.listenTo(tableCols, 'remove' , self.removeColumn); - self.listenTo(tableCols, 'change:name', self.resetColOptions); - } - - collection.on('pgadmin:multicolumn:updated', function() { - self.render.apply(self); - }); - self.listenTo(collection, "add", self.render); - self.listenTo(collection, "remove", self.render); - }, - removeColumn: function(m) { - var self = this, - removedCols = self.model.get('columns').where( - {column: m.get('name')} - ); - - self.model.get('columns').remove(removedCols); - setTimeout(function () { - self.render(); - }, 10); - - {% if node_type == 'primary_key' %} - var key = 'primary_key' - {% else %} - var key = 'unique_constraint' - {% endif %} - - setTimeout(function () { - constraints = self.model.top.get(key); - var removed = []; - constraints.each(function(constraint) { - if (constraint.get("columns").length == 0) { - removed.push(constraint); - } - }); - constraints.remove(removed); - },100); - - }, - resetColOptions : function(m) { - var self = this, - updatedCols = self.model.get('columns').where( - {column: m.previous('name')} - ); - if (updatedCols.length > 0) { - /* - * Table column name has changed so update - * column name in primary key as well. - */ - updatedCols[0].set( - {"column": m.get('name')}, - {silent: true}); - } - - setTimeout(function () { - self.render(); - }, 10); - }, - formatter: { - fromRaw: function (rawValue, model) { - return rawValue.pluck("column").toString(); - }, - toRaw: function (val, model) { - return val; - } - }, - render: function() { - return Backgrid.StringCell.prototype.render.apply(this, arguments); - }, - remove: function() { - var tableCols = this.model.top.get('columns'), - primary_key_col = this.model.get('columns'); - - if (primary_key_col) { - primary_key_col.off('pgadmin:multicolumn:updated'); - } - - this.stopListening(tableCols, 'remove' , self.removeColumn); - this.stopListening(tableCols, 'change:name' , self.resetColOptions); - - Backgrid.StringCell.prototype.remove.apply(this, arguments); - } - }), - canDelete: true, canAdd: true, - control: Backform.MultiSelectAjaxControl.extend({ - defaults: _.extend( - {}, - Backform.NodeListByNameControl.prototype.defaults, - { - select2: { - multiple: true, - allowClear: true, - width: 'style', - placeholder: gettext('Select the column(s)'), - } - } - ), - keyPathAccessor: function(obj, path) { - var res = obj; - if(_.isArray(res)) { - return _.map(res, function(o) { return o['column'] - }); - } - path = path.split('.'); - for (var i = 0; i < path.length; i++) { - if (_.isNull(res)) return null; - if (_.isEmpty(path[i])) continue; - if (!_.isUndefined(res[path[i]])) res = res[path[i]]; - } - return _.isObject(res) && !_.isArray(res) ? null : res; - }, - initialize: function() { - // Here we will decide if we need to call URL - // Or fetch the data from parent columns collection - var self = this; - if(this.model.handler) { - Backform.Select2Control.prototype.initialize.apply(this, arguments); - // Do not listen for any event(s) for existing constraint. - if (_.isUndefined(self.model.get('oid'))) { - var tableCols = self.model.top.get('columns'); - self.listenTo(tableCols, 'remove' , self.resetColOptions); - self.listenTo(tableCols, 'change:name', self.resetColOptions); - } - - self.custom_options(); - } else { - Backform.MultiSelectAjaxControl.prototype.initialize.apply(this, arguments); - } - self.model.get('columns').on('pgadmin:multicolumn:updated', function() { - self.render.apply(self); - }); - }, - resetColOptions: function(m) { - var self = this; - - setTimeout(function () { - self.custom_options(); - self.render.apply(self); - }, 50); - - }, - custom_options: function() { - // We will add all the columns entered by user in table model - var columns = this.model.top.get('columns'), - added_columns_from_tables = []; - - if (columns.length > 0) { - _.each(columns.models, function(m) { - var col = m.get('name'); - if(!_.isUndefined(col) && !_.isNull(col)) { - added_columns_from_tables.push( - {label: col, value: col, image:'icon-column'} - ); - } - }); - } - // Set the values in to options so that user can select - this.field.set('options', added_columns_from_tables); - }, - onChange: function(e) { - var self = this, - model = this.model, - $el = $(e.target), - attrArr = this.field.get("name").split('.'), - name = attrArr.shift(), - path = attrArr.join('.'), - vals = this.getValueFromDOM(), - collection = model.get(name), - removed = []; - - this.stopListening(this.model, "change:" + name, this.render); - - /* - * Iterate through all the values, and find out how many are already - * present in the collection. - */ - collection.each(function(m) { - var column = m.get('column'), - idx = _.indexOf(vals, column); - - if (idx > -1) { - vals.splice(idx, 1); - } else { - removed.push(column); - } - }); - - /* - * Adding new values - */ - - _.each(vals, function(v) { - var m = new (self.field.get('model'))( - {column: v}, { silent: true, - top: self.model.top, - collection: collection, - handler: collection - }); - - collection.add(m); - }); - - /* - * Removing unwanted! - */ - _.each(removed, function(v) { - collection.remove(collection.where({column: v})); - }); - - this.listenTo(this.model, "change:" + name, this.render); - }, - remove: function() { - if(this.model.handler) { - var self = this, - tableCols = self.model.top.get('columns'); - self.stopListening(tableCols, 'remove' , self.resetColOptions); - self.stopListening(tableCols, 'change:name' , self.resetColOptions); - self.model.get('columns').off('pgadmin:multicolumn:updated'); - - Backform.Select2Control.prototype.remove.apply(this, arguments); - - } else { - Backform.MultiSelectAjaxControl.prototype.remove.apply(this, arguments); - } - } - }), - deps: ['index'], node: 'column', - model: pgBrowser.Node.Model.extend({ - defaults: { - column: undefined - }, - validate: function() { - return null; - } - }), - transform : function(data){ - var res = []; - if (data && _.isArray(data)) { - _.each(data, function(d) { - res.push({label: d.label, value: d.label, image:'icon-column'}); - }) - } - return res; - }, - select2:{allowClear:false}, - disabled: function(m) { - // If we are in table edit mode then - if (_.has(m, 'top') && !_.isUndefined(m.top) - && !m.top.isNew()) { - // If OID is undefined then user is trying to add - // new constraint which should be allowed for Unique - return !_.isUndefined(m.get('oid')); - } - - // We can't update columns of existing index constraint. - if (!m.isNew()) { - return true; - } - // Disable if index is selected. - var index = m.get('index'); - if(_.isUndefined(index) || index == '') { - return false; - } else { - var col = m.get('columns'); - col.reset(); - return true; - } - } - },{ - id: 'spcname', label: gettext('Tablespace'), - type: 'text', group: gettext('Definition'), - control: 'node-list-by-name', node: 'tablespace', - deps: ['index'], - select2:{allowClear:false}, - filter: function(m) { - // Don't show pg_global tablespace in selection. - if (m.label == "pg_global") return false; - else return true; - }, - disabled: function(m) { - // Disable if index is selected. - m = m.top || m; - var index = m.get('index'); - if(_.isUndefined(index) || index == '') { - return false; - } else { - setTimeout(function(){ - m.set('spcname', ''); - },10); - return true; - } - } - },{ - id: 'index', label: gettext('Index'), - type: 'text', group: gettext('Definition'), - control: Backform.NodeListByNameControl.extend({ - initialize:function() { - if (_.isUndefined(this.model.top)) { - Backform.NodeListByNameControl.prototype.initialize.apply(this,arguments); - } else { - Backform.Control.prototype.initialize.apply(this,arguments); - } - } - }), - select2:{allowClear:true}, node: 'index', - disabled: function(m) { - // If we are in table edit mode then disable it - if (_.has(m, 'top') && !_.isUndefined(m.top) - && !m.top.isNew()) { - return true; - } - - // We can't update index of existing index constraint. - return !m.isNew(); - }, - // We will not show this field in Create Table mode - visible: function(m) { - return !_.isUndefined(m.top.node_info['table']); - } - },{ - id: 'fillfactor', label: gettext('Fill factor'), deps: ['index'], - type: 'int', group: gettext('Definition'), allowNull: true, - disabled: function(m) { - // Disable if index is selected. - var index = m.get('index'); - if(_.isUndefined(index) || index == '') { - return false; - } else { - setTimeout(function(){ - m.set('fillfactor', null); - },10); - return true; - } - } - },{ - id: 'condeferrable', label: gettext('Deferrable?'), - type: 'switch', group: gettext('Definition'), deps: ['index'], - disabled: function(m) { - // If we are in table edit mode then - if (_.has(m, 'top') && !_.isUndefined(m.top) - && !m.top.isNew()) { - // If OID is undefined then user is trying to add - // new constraint which should allowed for Unique - return !_.isUndefined(m.get('oid')); - } - - // We can't update condeferrable of existing index constraint. - if (!m.isNew()) { - return true; - } - // Disable if index is selected. - var index = m.get('index'); - if(_.isUndefined(index) || index == '') { - return false; - } else { - setTimeout(function(){ - if(m.get('condeferrable')) - m.set('condeferrable', false); - },10); - return true; - } - } - },{ - id: 'condeferred', label: gettext('Deferred?'), - type: 'switch', group: gettext('Definition'), - deps: ['condeferrable'], - disabled: function(m) { - // If we are in table edit mode then - if (_.has(m, 'top') && !_.isUndefined(m.top) - && !m.top.isNew()) { - // If OID is undefined then user is trying to add - // new constraint which should allowed for Unique - return !_.isUndefined(m.get('oid')); - } - - // We can't update condeferred of existing index constraint. - if (!m.isNew()) { - return true; - } - // Disable if condeferred is false or unselected. - if(m.get('condeferrable') == true) { - return false; - } else { - setTimeout(function(){ - if(m.get('condeferred')) - m.set('condeferred', false); - },10); - return true; - } - } - } - ], - validate: function() { - this.errorModel.clear(); - // Clear parent's error as well - if (_.has(this, 'top')) { - this.top.errorModel.clear(); - } - - var columns = this.get('columns'), - index = this.get('index'); - - if ((_.isUndefined(index) || String(index).replace(/^\s+|\s+$/g, '') == '') && - (_.isUndefined(columns) || _.isNull(columns) || columns.length < 1)) { - var msg = gettext('Please specify columns for %(node)s', {node: '{{ node_label }}'}); - this.errorModel.set('columns', msg); - return msg; - } - - return null; - } - }) - }); - } - - return pgBrowser.Nodes['{{node_type}}']; -}); diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/templates/constraints/js/constraints.js b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/static/js/constraints.js similarity index 96% rename from web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/templates/constraints/js/constraints.js rename to web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/static/js/constraints.js index 6c3af6ffc..dc38bbae0 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/templates/constraints/js/constraints.js +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/static/js/constraints.js @@ -1,7 +1,7 @@ define('pgadmin.node.constraints', [ 'sources/gettext', 'jquery', 'underscore', 'underscore.string', 'pgadmin', 'pgadmin.browser', 'pgadmin.browser.collection', 'pgadmin.node.unique_constraint', - 'pgadmin.node.check_constraints', 'pgadmin.node.foreign_key', + 'pgadmin.node.check_constraint', 'pgadmin.node.foreign_key', 'pgadmin.node.exclusion_constraint', 'pgadmin.node.primary_key' ], function(gettext, $, _, S, pgAdmin, pgBrowser) { diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/indexes/__init__.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/indexes/__init__.py index 13f9d8648..670dccdba 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/indexes/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/indexes/__init__.py @@ -127,6 +127,14 @@ class IndexesModule(CollectionNodeModule): """ return False + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + blueprint = IndexesModule(__name__) diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/indexes/templates/index/js/index.js b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/indexes/static/js/index.js similarity index 100% rename from web/pgadmin/browser/server_groups/servers/databases/schemas/tables/indexes/templates/index/js/index.js rename to web/pgadmin/browser/server_groups/servers/databases/schemas/tables/indexes/static/js/index.js diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/rules/__init__.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/rules/__init__.py index c318e5240..e4c89a5cf 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/rules/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/rules/__init__.py @@ -121,6 +121,14 @@ class RuleModule(CollectionNodeModule): return snippets + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + # Create blueprint of RuleModule. blueprint = RuleModule(__name__) diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/rules/templates/rules/js/rules.js b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/rules/static/js/rule.js similarity index 100% rename from web/pgadmin/browser/server_groups/servers/databases/schemas/tables/rules/templates/rules/js/rules.js rename to web/pgadmin/browser/server_groups/servers/databases/schemas/tables/rules/static/js/rule.js diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/triggers/__init__.py b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/triggers/__init__.py index 5cbcc4dbf..19dcf8af9 100644 --- a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/triggers/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/triggers/__init__.py @@ -114,6 +114,14 @@ class TriggerModule(CollectionNodeModule): """ return False + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + @property def csssnippets(self): """ diff --git a/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/triggers/templates/trigger/js/trigger.js b/web/pgadmin/browser/server_groups/servers/databases/schemas/tables/triggers/static/js/trigger.js similarity index 100% rename from web/pgadmin/browser/server_groups/servers/databases/schemas/tables/triggers/templates/trigger/js/trigger.js rename to web/pgadmin/browser/server_groups/servers/databases/schemas/tables/triggers/static/js/trigger.js diff --git a/web/pgadmin/browser/server_groups/servers/resource_groups/__init__.py b/web/pgadmin/browser/server_groups/servers/resource_groups/__init__.py index cf945b034..55eaa5316 100644 --- a/web/pgadmin/browser/server_groups/servers/resource_groups/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/resource_groups/__init__.py @@ -100,6 +100,15 @@ class ResourceGroupModule(CollectionNodeModule): return servers.ServerModule.NODE_TYPE + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + + blueprint = ResourceGroupModule(__name__) diff --git a/web/pgadmin/browser/server_groups/servers/resource_groups/templates/resource_groups/js/resource_groups.js b/web/pgadmin/browser/server_groups/servers/resource_groups/static/js/resource_group.js similarity index 100% rename from web/pgadmin/browser/server_groups/servers/resource_groups/templates/resource_groups/js/resource_groups.js rename to web/pgadmin/browser/server_groups/servers/resource_groups/static/js/resource_group.js diff --git a/web/pgadmin/browser/server_groups/servers/roles/__init__.py b/web/pgadmin/browser/server_groups/servers/roles/__init__.py index da8d06a58..a89229ea5 100644 --- a/web/pgadmin/browser/server_groups/servers/roles/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/roles/__init__.py @@ -74,6 +74,14 @@ class RoleModule(CollectionNodeModule): return snippets + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + blueprint = RoleModule(__name__) diff --git a/web/pgadmin/browser/server_groups/servers/roles/templates/role/js/role.js b/web/pgadmin/browser/server_groups/servers/roles/static/js/role.js similarity index 100% rename from web/pgadmin/browser/server_groups/servers/roles/templates/role/js/role.js rename to web/pgadmin/browser/server_groups/servers/roles/static/js/role.js diff --git a/web/pgadmin/browser/server_groups/servers/static/js/server.js b/web/pgadmin/browser/server_groups/servers/static/js/server.js index a337dfe9f..ab753f63b 100644 --- a/web/pgadmin/browser/server_groups/servers/static/js/server.js +++ b/web/pgadmin/browser/server_groups/servers/static/js/server.js @@ -42,7 +42,7 @@ define('pgadmin.node.server', [ }); pgAdmin.Browser.Nodes['server'] = pgAdmin.Browser.Node.extend({ - parent_type: 'server-group', + parent_type: 'server_group', type: 'server', dialogHelp: url_for('help.static', {'filename': 'server_dialog.html'}), label: gettext('Server'), @@ -61,7 +61,7 @@ define('pgadmin.node.server', [ this.initialized = true; pgBrowser.add_menus([{ - name: 'create_server_on_sg', node: 'server-group', module: this, + name: 'create_server_on_sg', node: 'server_group', module: this, applies: ['object', 'context'], callback: 'show_obj_properties', category: 'create', priority: 1, label: gettext('Server...'), data: {action: 'create'}, icon: 'wcTabIcon icon-server' @@ -632,7 +632,7 @@ define('pgadmin.node.server', [ var isNew = (_.size(attrs) === 0); if (isNew) { - this.set({'gid': args.node_info['server-group']._id}); + this.set({'gid': args.node_info['server_group']._id}); } pgAdmin.Browser.Node.Model.prototype.initialize.apply(this, arguments); }, @@ -643,7 +643,7 @@ define('pgadmin.node.server', [ mode: ['properties', 'edit', 'create'] },{ id: 'gid', label: gettext('Server group'), type: 'int', - control: 'node-list-by-id', node: 'server-group', + control: 'node-list-by-id', node: 'server_group', mode: ['create', 'edit'], select2: {allowClear: false} },{ id: 'server_type', label: gettext('Server type'), type: 'options', diff --git a/web/pgadmin/browser/server_groups/servers/tablespaces/__init__.py b/web/pgadmin/browser/server_groups/servers/tablespaces/__init__.py index 1535aa4bc..dd49045d3 100644 --- a/web/pgadmin/browser/server_groups/servers/tablespaces/__init__.py +++ b/web/pgadmin/browser/server_groups/servers/tablespaces/__init__.py @@ -46,6 +46,14 @@ class TablespaceModule(CollectionNodeModule): """ return servers.ServerModule.NODE_TYPE + @property + def module_use_template_javascript(self): + """ + Returns whether Jinja2 template is used for generating the javascript + module. + """ + return False + @property def node_inode(self): return False diff --git a/web/pgadmin/browser/server_groups/servers/tablespaces/templates/tablespaces/js/tablespaces.js b/web/pgadmin/browser/server_groups/servers/tablespaces/static/js/tablespace.js similarity index 100% rename from web/pgadmin/browser/server_groups/servers/tablespaces/templates/tablespaces/js/tablespaces.js rename to web/pgadmin/browser/server_groups/servers/tablespaces/static/js/tablespace.js diff --git a/web/pgadmin/browser/server_groups/static/img/server_group.png b/web/pgadmin/browser/server_groups/static/img/server_group.png new file mode 100644 index 0000000000000000000000000000000000000000..bd49bd271f9be5ddf43a180638783626895c0548 GIT binary patch literal 504 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!63?wyl`GbMfmH?j+S0LS-Q!}lx|JD8HkFMUk zdGhLoy{C_DJg|S+&d#EynQfDItl0eW{?i*Lubkg|YX6EIb6cj}zIfx+{b!G^-aWtX z)Q0IRFC0Dn>EoxLKYo7w`03ZrUmxGTe{%c&hj;J4ef{>}^7SLDw^mPC60>Am&*~lT z-@W_(_1lrvTcQ_imcMm8dE>zuHB-}DXZufI`{m=OhgWVKUbQ)T>9+Up-aoi)v3-1r7=tpgewDrdA0 zom1qxd{{$GPf=4*RkvAS!qmy(0U<$d94l6wTD>wm;}Gi>2Zv~P>6<*UCB|RAi1JQ2 zV-R8*WUQ9Z*4eUhrsXC{v1wr*QAc>z2J)u5e6nXy?d82)6r;Qx=nT~o*NBpo#FA92 zCuWneJxo!%-G4Y~O#nQ4^}4F;BA4M5c< ZRt9De4X37ut^sOb@O1TaS?83{1OPP$<_Q1* literal 0 HcmV?d00001 diff --git a/web/pgadmin/browser/server_groups/static/js/server-group.js b/web/pgadmin/browser/server_groups/static/js/server_group.js similarity index 90% rename from web/pgadmin/browser/server_groups/static/js/server-group.js rename to web/pgadmin/browser/server_groups/static/js/server_group.js index eb5512447..d09908427 100644 --- a/web/pgadmin/browser/server_groups/static/js/server-group.js +++ b/web/pgadmin/browser/server_groups/static/js/server_group.js @@ -3,10 +3,10 @@ define('pgadmin.node.server_group', [ 'backbone', 'pgadmin.browser', 'pgadmin.browser.node' ], function(gettext, url_for, $, _, pgAdmin, Backbone) { - if (!pgAdmin.Browser.Nodes['server-group']) { - pgAdmin.Browser.Nodes['server-group'] = pgAdmin.Browser.Node.extend({ + if (!pgAdmin.Browser.Nodes['server_group']) { + pgAdmin.Browser.Nodes['server_group'] = pgAdmin.Browser.Node.extend({ parent_type: null, - type: 'server-group', + type: 'server_group', dialogHelp: url_for('help.static', {'filename': 'server_group_dialog.html'}), label: gettext('Server Group'), width: '350px', @@ -20,10 +20,10 @@ define('pgadmin.node.server_group', [ this.initialized = true; pgAdmin.Browser.add_menus([{ - name: 'create_server_group', node: 'server-group', module: this, + name: 'create_server_group', node: 'server_group', module: this, applies: ['object', 'context'], callback: 'show_obj_properties', category: 'create', priority: 1, label: gettext('Server Group...'), - data: {'action': 'create'}, icon: 'wcTabIcon icon-server-group' + data: {'action': 'create'}, icon: 'wcTabIcon icon-server_group' }]); }, model: pgAdmin.Browser.Node.Model.extend({ @@ -78,5 +78,5 @@ define('pgadmin.node.server_group', [ }); } - return pgAdmin.Browser.Nodes['server-group']; + return pgAdmin.Browser.Nodes['server_group']; }); diff --git a/web/pgadmin/browser/server_groups/tests/test_sg_get.py b/web/pgadmin/browser/server_groups/tests/test_sg_get.py index 7b3df43f4..352476b2c 100644 --- a/web/pgadmin/browser/server_groups/tests/test_sg_get.py +++ b/web/pgadmin/browser/server_groups/tests/test_sg_get.py @@ -20,7 +20,7 @@ class SgNodeTestCase(BaseTestGenerator): scenarios = [ # Fetching the default url for server group node - ('Check Server Group Node', dict(url='/browser/server-group/obj/')) + ('Check Server Group Node', dict(url='/browser/server_group/obj/')) ] def runTest(self): diff --git a/web/pgadmin/browser/templates/browser/js/browser.js b/web/pgadmin/browser/static/js/browser.js similarity index 99% rename from web/pgadmin/browser/templates/browser/js/browser.js rename to web/pgadmin/browser/static/js/browser.js index c35341851..aa6442e3a 100644 --- a/web/pgadmin/browser/templates/browser/js/browser.js +++ b/web/pgadmin/browser/static/js/browser.js @@ -12,7 +12,7 @@ define( gettext, url_for, require, $, _, S, Bootstrap, pgAdmin, Alertify, codemirror, checkNodeVisibility ) { - + window.jQuery = window.$ = $; // Some scripts do export their object in the window only. // Generally the one, which do no have AMD support. var wcDocker = window.wcDocker; diff --git a/web/pgadmin/browser/templates/browser/js/collection.js b/web/pgadmin/browser/static/js/collection.js similarity index 100% rename from web/pgadmin/browser/templates/browser/js/collection.js rename to web/pgadmin/browser/static/js/collection.js diff --git a/web/pgadmin/browser/templates/browser/js/error.js b/web/pgadmin/browser/static/js/error.js similarity index 100% rename from web/pgadmin/browser/templates/browser/js/error.js rename to web/pgadmin/browser/static/js/error.js diff --git a/web/pgadmin/browser/templates/browser/js/node.js b/web/pgadmin/browser/static/js/node.js similarity index 98% rename from web/pgadmin/browser/templates/browser/js/node.js rename to web/pgadmin/browser/static/js/node.js index 670498da0..9a36dc5d8 100644 --- a/web/pgadmin/browser/templates/browser/js/node.js +++ b/web/pgadmin/browser/static/js/node.js @@ -126,21 +126,23 @@ define( } // show query tool only in context menu of supported nodes. - if (_.indexOf(pgAdmin.unsupported_nodes, self.type) == -1) { - pgAdmin.Browser.add_menus([{ - name: 'show_query_tool', node: self.type, module: self, - applies: ['context'], callback: 'show_query_tool', - priority: 998, label: gettext('Query Tool...'), - icon: 'fa fa-bolt', - enable: function(itemData, item, data) { - if (itemData._type == 'database' && itemData.allowConn) - return true; - else if(itemData._type != 'database') - return true; - else - return false; - } - }]); + if (true) { + if (_.indexOf(pgAdmin.unsupported_nodes, self.type) == -1) { + pgAdmin.Browser.add_menus([{ + name: 'show_query_tool', node: self.type, module: self, + applies: ['context'], callback: 'show_query_tool', + priority: 998, label: gettext('Query Tool...'), + icon: 'fa fa-bolt', + enable: function(itemData, item, data) { + if (itemData._type == 'database' && itemData.allowConn) + return true; + else if(itemData._type != 'database') + return true; + else + return false; + } + }]); + } } // This will add options of scripts eg:'CREATE Script' @@ -173,7 +175,7 @@ define( /////// check_user_permission: function(itemData, item, data) { // Do not display CREATE script on server group and server node - if (itemData._type == 'server-group' || itemData._type == 'server') { + if (itemData._type == 'server_group' || itemData._type == 'server') { return false; } @@ -499,6 +501,7 @@ define( ); b.removeChild(el); + // delete(el); return p; }; @@ -992,6 +995,8 @@ define( if (view) { // Release the view view.remove({data: true, internal: true, silent: true}); + // Deallocate the view + // delete view; view = null; // Reset the data object j.data('obj-view', null); @@ -1174,6 +1179,7 @@ define( if (view) { // Release the view view.remove({data: true, internal: true, silent: true}); + // Deallocate the view view = null; // Reset the data object j.data('obj-view', null); diff --git a/web/pgadmin/dashboard/templates/dashboard/js/dashboard.js b/web/pgadmin/dashboard/static/js/dashboard.js similarity index 100% rename from web/pgadmin/dashboard/templates/dashboard/js/dashboard.js rename to web/pgadmin/dashboard/static/js/dashboard.js diff --git a/web/pgadmin/misc/file_manager/templates/file_manager/js/file_manager.js b/web/pgadmin/misc/file_manager/static/js/file_manager.js similarity index 100% rename from web/pgadmin/misc/file_manager/templates/file_manager/js/file_manager.js rename to web/pgadmin/misc/file_manager/static/js/file_manager.js diff --git a/web/pgadmin/misc/file_manager/templates/file_manager/js/utility.js b/web/pgadmin/misc/file_manager/static/js/utility.js similarity index 100% rename from web/pgadmin/misc/file_manager/templates/file_manager/js/utility.js rename to web/pgadmin/misc/file_manager/static/js/utility.js diff --git a/web/pgadmin/misc/templates/explain/js/explain.js b/web/pgadmin/misc/static/explain/js/explain.js similarity index 100% rename from web/pgadmin/misc/templates/explain/js/explain.js rename to web/pgadmin/misc/static/explain/js/explain.js diff --git a/web/pgadmin/misc/static/explain/vendor/snap.svg/snap.svg-min.js b/web/pgadmin/misc/static/explain/vendor/snap.svg/snap.svg-min.js deleted file mode 100644 index 6567d1992..000000000 --- a/web/pgadmin/misc/static/explain/vendor/snap.svg/snap.svg-min.js +++ /dev/null @@ -1,21 +0,0 @@ -// Snap.svg 0.4.1 -// -// Copyright (c) 2013 – 2015 Adobe Systems Incorporated. All rights reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -// -// build: 2015-04-13 - -!function(a){var b,c,d="0.4.2",e="hasOwnProperty",f=/[\.\/]/,g=/\s*,\s*/,h="*",i=function(a,b){return a-b},j={n:{}},k=function(){for(var a=0,b=this.length;b>a;a++)if("undefined"!=typeof this[a])return this[a]},l=function(){for(var a=this.length;--a;)if("undefined"!=typeof this[a])return this[a]},m=function(a,d){a=String(a);var e,f=c,g=Array.prototype.slice.call(arguments,2),h=m.listeners(a),j=0,n=[],o={},p=[],q=b;p.firstDefined=k,p.lastDefined=l,b=a,c=0;for(var r=0,s=h.length;s>r;r++)"zIndex"in h[r]&&(n.push(h[r].zIndex),h[r].zIndex<0&&(o[h[r].zIndex]=h[r]));for(n.sort(i);n[j]<0;)if(e=o[n[j++]],p.push(e.apply(d,g)),c)return c=f,p;for(r=0;s>r;r++)if(e=h[r],"zIndex"in e)if(e.zIndex==n[j]){if(p.push(e.apply(d,g)),c)break;do if(j++,e=o[n[j]],e&&p.push(e.apply(d,g)),c)break;while(e)}else o[e.zIndex]=e;else if(p.push(e.apply(d,g)),c)break;return c=f,b=q,p};m._events=j,m.listeners=function(a){var b,c,d,e,g,i,k,l,m=a.split(f),n=j,o=[n],p=[];for(e=0,g=m.length;g>e;e++){for(l=[],i=0,k=o.length;k>i;i++)for(n=o[i].n,c=[n[m[e]],n[h]],d=2;d--;)b=c[d],b&&(l.push(b),p=p.concat(b.f||[]));o=l}return p},m.on=function(a,b){if(a=String(a),"function"!=typeof b)return function(){};for(var c=a.split(g),d=0,e=c.length;e>d;d++)!function(a){for(var c,d=a.split(f),e=j,g=0,h=d.length;h>g;g++)e=e.n,e=e.hasOwnProperty(d[g])&&e[d[g]]||(e[d[g]]={n:{}});for(e.f=e.f||[],g=0,h=e.f.length;h>g;g++)if(e.f[g]==b){c=!0;break}!c&&e.f.push(b)}(c[d]);return function(a){+a==+a&&(b.zIndex=+a)}},m.f=function(a){var b=[].slice.call(arguments,1);return function(){m.apply(null,[a,null].concat(b).concat([].slice.call(arguments,0)))}},m.stop=function(){c=1},m.nt=function(a){return a?new RegExp("(?:\\.|\\/|^)"+a+"(?:\\.|\\/|$)").test(b):b},m.nts=function(){return b.split(f)},m.off=m.unbind=function(a,b){if(!a)return void(m._events=j={n:{}});var c=a.split(g);if(c.length>1)for(var d=0,i=c.length;i>d;d++)m.off(c[d],b);else{c=a.split(f);var k,l,n,d,i,o,p,q=[j];for(d=0,i=c.length;i>d;d++)for(o=0;od;d++)for(k=q[d];k.n;){if(b){if(k.f){for(o=0,p=k.f.length;p>o;o++)if(k.f[o]==b){k.f.splice(o,1);break}!k.f.length&&delete k.f}for(l in k.n)if(k.n[e](l)&&k.n[l].f){var r=k.n[l].f;for(o=0,p=r.length;p>o;o++)if(r[o]==b){r.splice(o,1);break}!r.length&&delete k.n[l].f}}else{delete k.f;for(l in k.n)k.n[e](l)&&k.n[l].f&&delete k.n[l].f}k=k.n}}},m.once=function(a,b){var c=function(){return m.unbind(a,c),b.apply(this,arguments)};return m.on(a,c)},m.version=d,m.toString=function(){return"You are running Eve "+d},"undefined"!=typeof module&&module.exports?module.exports=m:"function"==typeof define&&define.amd?define("eve",[],function(){return m}):a.eve=m}(this),function(a,b){if("function"==typeof define&&define.amd)define(["eve"],function(c){return b(a,c)});else if("undefined"!=typeof exports){var c=require("eve");module.exports=b(a,c)}else b(a,a.eve)}(window||this,function(a,b){var c=function(b){var c={},d=a.requestAnimationFrame||a.webkitRequestAnimationFrame||a.mozRequestAnimationFrame||a.oRequestAnimationFrame||a.msRequestAnimationFrame||function(a){setTimeout(a,16)},e=Array.isArray||function(a){return a instanceof Array||"[object Array]"==Object.prototype.toString.call(a)},f=0,g="M"+(+new Date).toString(36),h=function(){return g+(f++).toString(36)},i=Date.now||function(){return+new Date},j=function(a){var b=this;if(null==a)return b.s;var c=b.s-a;b.b+=b.dur*c,b.B+=b.dur*c,b.s=a},k=function(a){var b=this;return null==a?b.spd:void(b.spd=a)},l=function(a){var b=this;return null==a?b.dur:(b.s=b.s*a/b.dur,void(b.dur=a))},m=function(){var a=this;delete c[a.id],a.update(),b("mina.stop."+a.id,a)},n=function(){var a=this;a.pdif||(delete c[a.id],a.update(),a.pdif=a.get()-a.b)},o=function(){var a=this;a.pdif&&(a.b=a.get()-a.pdif,delete a.pdif,c[a.id]=a)},p=function(){var a,b=this;if(e(b.start)){a=[];for(var c=0,d=b.start.length;d>c;c++)a[c]=+b.start[c]+(b.end[c]-b.start[c])*b.easing(b.s)}else a=+b.start+(b.end-b.start)*b.easing(b.s);b.set(a)},q=function(){var a=0;for(var e in c)if(c.hasOwnProperty(e)){var f=c[e],g=f.get();a++,f.s=(g-f.b)/(f.dur/f.spd),f.s>=1&&(delete c[e],f.s=1,a--,function(a){setTimeout(function(){b("mina.finish."+a.id,a)})}(f)),f.update()}a&&d(q)},r=function(a,b,e,f,g,i,s){var t={id:h(),start:a,end:b,b:e,s:0,dur:f-e,spd:1,get:g,set:i,easing:s||r.linear,status:j,speed:k,duration:l,stop:m,pause:n,resume:o,update:p};c[t.id]=t;var u,v=0;for(u in c)if(c.hasOwnProperty(u)&&(v++,2==v))break;return 1==v&&d(q),t};return r.time=i,r.getById=function(a){return c[a]||null},r.linear=function(a){return a},r.easeout=function(a){return Math.pow(a,1.7)},r.easein=function(a){return Math.pow(a,.48)},r.easeinout=function(a){if(1==a)return 1;if(0==a)return 0;var b=.48-a/1.04,c=Math.sqrt(.1734+b*b),d=c-b,e=Math.pow(Math.abs(d),1/3)*(0>d?-1:1),f=-c-b,g=Math.pow(Math.abs(f),1/3)*(0>f?-1:1),h=e+g+.5;return 3*(1-h)*h*h+h*h*h},r.backin=function(a){if(1==a)return 1;var b=1.70158;return a*a*((b+1)*a-b)},r.backout=function(a){if(0==a)return 0;a-=1;var b=1.70158;return a*a*((b+1)*a+b)+1},r.elastic=function(a){return a==!!a?a:Math.pow(2,-10*a)*Math.sin(2*(a-.075)*Math.PI/.3)+1},r.bounce=function(a){var b,c=7.5625,d=2.75;return 1/d>a?b=c*a*a:2/d>a?(a-=1.5/d,b=c*a*a+.75):2.5/d>a?(a-=2.25/d,b=c*a*a+.9375):(a-=2.625/d,b=c*a*a+.984375),b},a.mina=r,r}("undefined"==typeof b?function(){}:b),d=function(a){function c(a,b){if(a){if(a.nodeType)return w(a);if(e(a,"array")&&c.set)return c.set.apply(c,a);if(a instanceof s)return a;if(null==b)return a=y.doc.querySelector(String(a)),w(a)}return a=null==a?"100%":a,b=null==b?"100%":b,new v(a,b)}function d(a,b){if(b){if("#text"==a&&(a=y.doc.createTextNode(b.text||b["#text"]||"")),"#comment"==a&&(a=y.doc.createComment(b.text||b["#text"]||"")),"string"==typeof a&&(a=d(a)),"string"==typeof b)return 1==a.nodeType?"xlink:"==b.substring(0,6)?a.getAttributeNS(T,b.substring(6)):"xml:"==b.substring(0,4)?a.getAttributeNS(U,b.substring(4)):a.getAttribute(b):"text"==b?a.nodeValue:null;if(1==a.nodeType){for(var c in b)if(b[z](c)){var e=A(b[c]);e?"xlink:"==c.substring(0,6)?a.setAttributeNS(T,c.substring(6),e):"xml:"==c.substring(0,4)?a.setAttributeNS(U,c.substring(4),e):a.setAttribute(c,e):a.removeAttribute(c)}}else"text"in b&&(a.nodeValue=b.text)}else a=y.doc.createElementNS(U,a);return a}function e(a,b){return b=A.prototype.toLowerCase.call(b),"finite"==b?isFinite(a):"array"==b&&(a instanceof Array||Array.isArray&&Array.isArray(a))?!0:"null"==b&&null===a||b==typeof a&&null!==a||"object"==b&&a===Object(a)||J.call(a).slice(8,-1).toLowerCase()==b}function f(a){if("function"==typeof a||Object(a)!==a)return a;var b=new a.constructor;for(var c in a)a[z](c)&&(b[c]=f(a[c]));return b}function h(a,b){for(var c=0,d=a.length;d>c;c++)if(a[c]===b)return a.push(a.splice(c,1)[0])}function i(a,b,c){function d(){var e=Array.prototype.slice.call(arguments,0),f=e.join("␀"),g=d.cache=d.cache||{},i=d.count=d.count||[];return g[z](f)?(h(i,f),c?c(g[f]):g[f]):(i.length>=1e3&&delete g[i.shift()],i.push(f),g[f]=a.apply(b,e),c?c(g[f]):g[f])}return d}function j(a,b,c,d,e,f){if(null==e){var g=a-c,h=b-d;return g||h?(180+180*D.atan2(-h,-g)/H+360)%360:0}return j(a,b,e,f)-j(c,d,e,f)}function k(a){return a%360*H/180}function l(a){return 180*a/H%360}function m(a){var b=[];return a=a.replace(/(?:^|\s)(\w+)\(([^)]+)\)/g,function(a,c,d){return d=d.split(/\s*,\s*|\s+/),"rotate"==c&&1==d.length&&d.push(0,0),"scale"==c&&(d.length>2?d=d.slice(0,2):2==d.length&&d.push(0,0),1==d.length&&d.push(d[0],0,0)),b.push("skewX"==c?["m",1,0,D.tan(k(d[0])),1,0,0]:"skewY"==c?["m",1,D.tan(k(d[0])),0,1,0,0]:[c.charAt(0)].concat(d)),a}),b}function n(a,b){var d=ab(a),e=new c.Matrix;if(d)for(var f=0,g=d.length;g>f;f++){var h,i,j,k,l,m=d[f],n=m.length,o=A(m[0]).toLowerCase(),p=m[0]!=o,q=p?e.invert():0;"t"==o&&2==n?e.translate(m[1],0):"t"==o&&3==n?p?(h=q.x(0,0),i=q.y(0,0),j=q.x(m[1],m[2]),k=q.y(m[1],m[2]),e.translate(j-h,k-i)):e.translate(m[1],m[2]):"r"==o?2==n?(l=l||b,e.rotate(m[1],l.x+l.width/2,l.y+l.height/2)):4==n&&(p?(j=q.x(m[2],m[3]),k=q.y(m[2],m[3]),e.rotate(m[1],j,k)):e.rotate(m[1],m[2],m[3])):"s"==o?2==n||3==n?(l=l||b,e.scale(m[1],m[n-1],l.x+l.width/2,l.y+l.height/2)):4==n?p?(j=q.x(m[2],m[3]),k=q.y(m[2],m[3]),e.scale(m[1],m[1],j,k)):e.scale(m[1],m[1],m[2],m[3]):5==n&&(p?(j=q.x(m[3],m[4]),k=q.y(m[3],m[4]),e.scale(m[1],m[2],j,k)):e.scale(m[1],m[2],m[3],m[4])):"m"==o&&7==n&&e.add(m[1],m[2],m[3],m[4],m[5],m[6])}return e}function o(a){var b=a.node.ownerSVGElement&&w(a.node.ownerSVGElement)||a.node.parentNode&&w(a.node.parentNode)||c.select("svg")||c(0,0),d=b.select("defs"),e=null==d?!1:d.node;return e||(e=u("defs",b.node).node),e}function p(a){return a.node.ownerSVGElement&&w(a.node.ownerSVGElement)||c.select("svg")}function q(a,b,c){function e(a){if(null==a)return I;if(a==+a)return a;d(j,{width:a});try{return j.getBBox().width}catch(b){return 0}}function f(a){if(null==a)return I;if(a==+a)return a;d(j,{height:a});try{return j.getBBox().height}catch(b){return 0}}function g(d,e){null==b?i[d]=e(a.attr(d)||0):d==b&&(i=e(null==c?a.attr(d)||0:c))}var h=p(a).node,i={},j=h.querySelector(".svg---mgr");switch(j||(j=d("rect"),d(j,{x:-9e9,y:-9e9,width:10,height:10,"class":"svg---mgr",fill:"none"}),h.appendChild(j)),a.type){case"rect":g("rx",e),g("ry",f);case"image":g("width",e),g("height",f);case"text":g("x",e),g("y",f);break;case"circle":g("cx",e),g("cy",f),g("r",e);break;case"ellipse":g("cx",e),g("cy",f),g("rx",e),g("ry",f);break;case"line":g("x1",e),g("x2",e),g("y1",f),g("y2",f);break;case"marker":g("refX",e),g("markerWidth",e),g("refY",f),g("markerHeight",f);break;case"radialGradient":g("fx",e),g("fy",f);break;case"tspan":g("dx",e),g("dy",f);break;default:g(b,e)}return h.removeChild(j),i}function r(a){e(a,"array")||(a=Array.prototype.slice.call(arguments,0));for(var b=0,c=0,d=this.node;this[b];)delete this[b++];for(b=0;bc;c++){var e={type:a[c].type,attr:a[c].attr()},f=a[c].children();b.push(e),f.length&&x(f,e.childNodes=[])}}c.version="0.4.0",c.toString=function(){return"Snap v"+this.version},c._={};var y={win:a.window,doc:a.window.document};c._.glob=y;{var z="hasOwnProperty",A=String,B=parseFloat,C=parseInt,D=Math,E=D.max,F=D.min,G=D.abs,H=(D.pow,D.PI),I=(D.round,""),J=Object.prototype.toString,K=/^\s*((#[a-f\d]{6})|(#[a-f\d]{3})|rgba?\(\s*([\d\.]+%?\s*,\s*[\d\.]+%?\s*,\s*[\d\.]+%?(?:\s*,\s*[\d\.]+%?)?)\s*\)|hsba?\(\s*([\d\.]+(?:deg|\xb0|%)?\s*,\s*[\d\.]+%?\s*,\s*[\d\.]+(?:%?\s*,\s*[\d\.]+)?%?)\s*\)|hsla?\(\s*([\d\.]+(?:deg|\xb0|%)?\s*,\s*[\d\.]+%?\s*,\s*[\d\.]+(?:%?\s*,\s*[\d\.]+)?%?)\s*\))\s*$/i,L=(c._.separator=/[,\s]+/,/[\s]*,[\s]*/),M={hs:1,rg:1},N=/([a-z])[\s,]*((-?\d*\.?\d*(?:e[\-+]?\d+)?[\s]*,?[\s]*)+)/gi,O=/([rstm])[\s,]*((-?\d*\.?\d*(?:e[\-+]?\d+)?[\s]*,?[\s]*)+)/gi,P=/(-?\d*\.?\d*(?:e[\-+]?\\d+)?)[\s]*,?[\s]*/gi,Q=0,R="S"+(+new Date).toString(36),S=function(a){return(a&&a.type?a.type:I)+R+(Q++).toString(36)},T="http://www.w3.org/1999/xlink",U="http://www.w3.org/2000/svg",V={};c.url=function(a){return"url('#"+a+"')"}}c._.$=d,c._.id=S,c.format=function(){var a=/\{([^\}]+)\}/g,b=/(?:(?:^|\.)(.+?)(?=\[|\.|$|\()|\[('|")(.+?)\2\])(\(\))?/g,c=function(a,c,d){var e=d;return c.replace(b,function(a,b,c,d,f){b=b||d,e&&(b in e&&(e=e[b]),"function"==typeof e&&f&&(e=e()))}),e=(null==e||e==d?a:e)+""};return function(b,d){return A(b).replace(a,function(a,b){return c(a,b,d)})}}(),c._.clone=f,c._.cacher=i,c.rad=k,c.deg=l,c.sin=function(a){return D.sin(c.rad(a))},c.tan=function(a){return D.tan(c.rad(a))},c.cos=function(a){return D.cos(c.rad(a))},c.asin=function(a){return c.deg(D.asin(a))},c.acos=function(a){return c.deg(D.acos(a))},c.atan=function(a){return c.deg(D.atan(a))},c.atan2=function(a){return c.deg(D.atan2(a))},c.angle=j,c.len=function(a,b,d,e){return Math.sqrt(c.len2(a,b,d,e))},c.len2=function(a,b,c,d){return(a-c)*(a-c)+(b-d)*(b-d)},c.closestPoint=function(a,b,c){function d(a){var d=a.x-b,e=a.y-c;return d*d+e*e}for(var e,f,g,h,i=a.node,j=i.getTotalLength(),k=j/i.pathSegList.numberOfItems*.125,l=1/0,m=0;j>=m;m+=k)(h=d(g=i.getPointAtLength(m))).5;){var n,o,p,q,r,s;(p=f-k)>=0&&(r=d(n=i.getPointAtLength(p)))f)return b-f;if(f>a-c)return b-f+a}return b},c.getRGB=i(function(a){if(!a||(a=A(a)).indexOf("-")+1)return{r:-1,g:-1,b:-1,hex:"none",error:1,toString:Z};if("none"==a)return{r:-1,g:-1,b:-1,hex:"none",toString:Z};if(!(M[z](a.toLowerCase().substring(0,2))||"#"==a.charAt())&&(a=W(a)),!a)return{r:-1,g:-1,b:-1,hex:"none",error:1,toString:Z};var b,d,f,g,h,i,j=a.match(K);return j?(j[2]&&(f=C(j[2].substring(5),16),d=C(j[2].substring(3,5),16),b=C(j[2].substring(1,3),16)),j[3]&&(f=C((h=j[3].charAt(3))+h,16),d=C((h=j[3].charAt(2))+h,16),b=C((h=j[3].charAt(1))+h,16)),j[4]&&(i=j[4].split(L),b=B(i[0]),"%"==i[0].slice(-1)&&(b*=2.55),d=B(i[1]),"%"==i[1].slice(-1)&&(d*=2.55),f=B(i[2]),"%"==i[2].slice(-1)&&(f*=2.55),"rgba"==j[1].toLowerCase().slice(0,4)&&(g=B(i[3])),i[3]&&"%"==i[3].slice(-1)&&(g/=100)),j[5]?(i=j[5].split(L),b=B(i[0]),"%"==i[0].slice(-1)&&(b/=100),d=B(i[1]),"%"==i[1].slice(-1)&&(d/=100),f=B(i[2]),"%"==i[2].slice(-1)&&(f/=100),("deg"==i[0].slice(-3)||"°"==i[0].slice(-1))&&(b/=360),"hsba"==j[1].toLowerCase().slice(0,4)&&(g=B(i[3])),i[3]&&"%"==i[3].slice(-1)&&(g/=100),c.hsb2rgb(b,d,f,g)):j[6]?(i=j[6].split(L),b=B(i[0]),"%"==i[0].slice(-1)&&(b/=100),d=B(i[1]),"%"==i[1].slice(-1)&&(d/=100),f=B(i[2]),"%"==i[2].slice(-1)&&(f/=100),("deg"==i[0].slice(-3)||"°"==i[0].slice(-1))&&(b/=360),"hsla"==j[1].toLowerCase().slice(0,4)&&(g=B(i[3])),i[3]&&"%"==i[3].slice(-1)&&(g/=100),c.hsl2rgb(b,d,f,g)):(b=F(D.round(b),255),d=F(D.round(d),255),f=F(D.round(f),255),g=F(E(g,0),1),j={r:b,g:d,b:f,toString:Z},j.hex="#"+(16777216|f|d<<8|b<<16).toString(16).slice(1),j.opacity=e(g,"finite")?g:1,j)):{r:-1,g:-1,b:-1,hex:"none",error:1,toString:Z}},c),c.hsb=i(function(a,b,d){return c.hsb2rgb(a,b,d).hex}),c.hsl=i(function(a,b,d){return c.hsl2rgb(a,b,d).hex}),c.rgb=i(function(a,b,c,d){if(e(d,"finite")){var f=D.round;return"rgba("+[f(a),f(b),f(c),+d.toFixed(2)]+")"}return"#"+(16777216|c|b<<8|a<<16).toString(16).slice(1)});var W=function(a){var b=y.doc.getElementsByTagName("head")[0]||y.doc.getElementsByTagName("svg")[0],c="rgb(255, 0, 0)";return(W=i(function(a){if("red"==a.toLowerCase())return c;b.style.color=c,b.style.color=a;var d=y.doc.defaultView.getComputedStyle(b,I).getPropertyValue("color");return d==c?null:d}))(a)},X=function(){return"hsb("+[this.h,this.s,this.b]+")"},Y=function(){return"hsl("+[this.h,this.s,this.l]+")"},Z=function(){return 1==this.opacity||null==this.opacity?this.hex:"rgba("+[this.r,this.g,this.b,this.opacity]+")"},$=function(a,b,d){if(null==b&&e(a,"object")&&"r"in a&&"g"in a&&"b"in a&&(d=a.b,b=a.g,a=a.r),null==b&&e(a,string)){var f=c.getRGB(a);a=f.r,b=f.g,d=f.b}return(a>1||b>1||d>1)&&(a/=255,b/=255,d/=255),[a,b,d]},_=function(a,b,d,f){a=D.round(255*a),b=D.round(255*b),d=D.round(255*d);var g={r:a,g:b,b:d,opacity:e(f,"finite")?f:1,hex:c.rgb(a,b,d),toString:Z};return e(f,"finite")&&(g.opacity=f),g};c.color=function(a){var b;return e(a,"object")&&"h"in a&&"s"in a&&"b"in a?(b=c.hsb2rgb(a),a.r=b.r,a.g=b.g,a.b=b.b,a.opacity=1,a.hex=b.hex):e(a,"object")&&"h"in a&&"s"in a&&"l"in a?(b=c.hsl2rgb(a),a.r=b.r,a.g=b.g,a.b=b.b,a.opacity=1,a.hex=b.hex):(e(a,"string")&&(a=c.getRGB(a)),e(a,"object")&&"r"in a&&"g"in a&&"b"in a&&!("error"in a)?(b=c.rgb2hsl(a),a.h=b.h,a.s=b.s,a.l=b.l,b=c.rgb2hsb(a),a.v=b.b):(a={hex:"none"},a.r=a.g=a.b=a.h=a.s=a.v=a.l=-1,a.error=1)),a.toString=Z,a},c.hsb2rgb=function(a,b,c,d){e(a,"object")&&"h"in a&&"s"in a&&"b"in a&&(c=a.b,b=a.s,d=a.o,a=a.h),a*=360;var f,g,h,i,j;return a=a%360/60,j=c*b,i=j*(1-G(a%2-1)),f=g=h=c-j,a=~~a,f+=[j,i,0,0,i,j][a],g+=[i,j,j,i,0,0][a],h+=[0,0,i,j,j,i][a],_(f,g,h,d)},c.hsl2rgb=function(a,b,c,d){e(a,"object")&&"h"in a&&"s"in a&&"l"in a&&(c=a.l,b=a.s,a=a.h),(a>1||b>1||c>1)&&(a/=360,b/=100,c/=100),a*=360;var f,g,h,i,j;return a=a%360/60,j=2*b*(.5>c?c:1-c),i=j*(1-G(a%2-1)),f=g=h=c-j/2,a=~~a,f+=[j,i,0,0,i,j][a],g+=[i,j,j,i,0,0][a],h+=[0,0,i,j,j,i][a],_(f,g,h,d)},c.rgb2hsb=function(a,b,c){c=$(a,b,c),a=c[0],b=c[1],c=c[2];var d,e,f,g;return f=E(a,b,c),g=f-F(a,b,c),d=0==g?null:f==a?(b-c)/g:f==b?(c-a)/g+2:(a-b)/g+4,d=(d+360)%6*60/360,e=0==g?0:g/f,{h:d,s:e,b:f,toString:X}},c.rgb2hsl=function(a,b,c){c=$(a,b,c),a=c[0],b=c[1],c=c[2];var d,e,f,g,h,i;return g=E(a,b,c),h=F(a,b,c),i=g-h,d=0==i?null:g==a?(b-c)/i:g==b?(c-a)/i+2:(a-b)/i+4,d=(d+360)%6*60/360,f=(g+h)/2,e=0==i?0:.5>f?i/(2*f):i/(2-2*f),{h:d,s:e,l:f,toString:Y}},c.parsePathString=function(a){if(!a)return null;var b=c.path(a);if(b.arr)return c.path.clone(b.arr);var d={a:7,c:6,o:2,h:1,l:2,m:2,r:4,q:4,s:4,t:2,v:1,u:3,z:0},f=[];return e(a,"array")&&e(a[0],"array")&&(f=c.path.clone(a)),f.length||A(a).replace(N,function(a,b,c){var e=[],g=b.toLowerCase();if(c.replace(P,function(a,b){b&&e.push(+b)}),"m"==g&&e.length>2&&(f.push([b].concat(e.splice(0,2))),g="l",b="m"==b?"l":"L"),"o"==g&&1==e.length&&f.push([b,e[0]]),"r"==g)f.push([b].concat(e));else for(;e.length>=d[g]&&(f.push([b].concat(e.splice(0,d[g]))),d[g]););}),f.toString=c.path.toString,b.arr=c.path.clone(f),f};var ab=c.parseTransformString=function(a){if(!a)return null;var b=[];return e(a,"array")&&e(a[0],"array")&&(b=c.path.clone(a)),b.length||A(a).replace(O,function(a,c,d){{var e=[];c.toLowerCase()}d.replace(P,function(a,b){b&&e.push(+b)}),b.push([c].concat(e))}),b.toString=c.path.toString,b};c._.svgTransform2string=m,c._.rgTransform=/^[a-z][\s]*-?\.?\d/i,c._.transform2matrix=n,c._unit2px=q;y.doc.contains||y.doc.compareDocumentPosition?function(a,b){var c=9==a.nodeType?a.documentElement:a,d=b&&b.parentNode;return a==d||!(!d||1!=d.nodeType||!(c.contains?c.contains(d):a.compareDocumentPosition&&16&a.compareDocumentPosition(d)))}:function(a,b){if(b)for(;b;)if(b=b.parentNode,b==a)return!0;return!1};c._.getSomeDefs=o,c._.getSomeSVG=p,c.select=function(a){return a=A(a).replace(/([^\\]):/g,"$1\\:"),w(y.doc.querySelector(a))},c.selectAll=function(a){for(var b=y.doc.querySelectorAll(a),d=(c.set||Array)(),e=0;ei;i++)h[g[i].nodeName]=g[i].nodeValue;return h}if(e(a,"string")){if(!(arguments.length>1))return b("snap.util.getattr."+a,d).firstDefined();var k={};k[a]=c,a=k}for(var l in a)a[z](l)&&b("snap.util.attr."+l,d,a[l]);return d},c.parse=function(a){var b=y.doc.createDocumentFragment(),c=!0,d=y.doc.createElement("div");if(a=A(a),a.match(/^\s*<\s*svg(?:\s|>)/)||(a=""+a+"",c=!1),d.innerHTML=a,a=d.getElementsByTagName("svg")[0])if(c)b=a;else for(;a.firstChild;)b.appendChild(a.firstChild);return new t(b)},c.fragment=function(){for(var a=Array.prototype.slice.call(arguments,0),b=y.doc.createDocumentFragment(),d=0,e=a.length;e>d;d++){var f=a[d];f.node&&f.node.nodeType&&b.appendChild(f.node),f.nodeType&&b.appendChild(f),"string"==typeof f&&b.appendChild(c.parse(f).node)}return new t(b)},c._.make=u,c._.wrap=w,v.prototype.el=function(a,b){var c=u(a,this.node);return b&&c.attr(b),c},s.prototype.children=function(){for(var a=[],b=this.node.childNodes,d=0,e=b.length;e>d;d++)a[d]=c(b[d]);return a},s.prototype.toJSON=function(){var a=[];return x([this],a),a[0]},b.on("snap.util.getattr",function(){var a=b.nt();a=a.substring(a.lastIndexOf(".")+1);var c=a.replace(/[A-Z]/g,function(a){return"-"+a.toLowerCase()});return bb[z](c)?this.node.ownerDocument.defaultView.getComputedStyle(this.node,null).getPropertyValue(c):d(this.node,a)});var bb={"alignment-baseline":0,"baseline-shift":0,clip:0,"clip-path":0,"clip-rule":0,color:0,"color-interpolation":0,"color-interpolation-filters":0,"color-profile":0,"color-rendering":0,cursor:0,direction:0,display:0,"dominant-baseline":0,"enable-background":0,fill:0,"fill-opacity":0,"fill-rule":0,filter:0,"flood-color":0,"flood-opacity":0,font:0,"font-family":0,"font-size":0,"font-size-adjust":0,"font-stretch":0,"font-style":0,"font-variant":0,"font-weight":0,"glyph-orientation-horizontal":0,"glyph-orientation-vertical":0,"image-rendering":0,kerning:0,"letter-spacing":0,"lighting-color":0,marker:0,"marker-end":0,"marker-mid":0,"marker-start":0,mask:0,opacity:0,overflow:0,"pointer-events":0,"shape-rendering":0,"stop-color":0,"stop-opacity":0,stroke:0,"stroke-dasharray":0,"stroke-dashoffset":0,"stroke-linecap":0,"stroke-linejoin":0,"stroke-miterlimit":0,"stroke-opacity":0,"stroke-width":0,"text-anchor":0,"text-decoration":0,"text-rendering":0,"unicode-bidi":0,visibility:0,"word-spacing":0,"writing-mode":0};b.on("snap.util.attr",function(a){var c=b.nt(),e={};c=c.substring(c.lastIndexOf(".")+1),e[c]=a;var f=c.replace(/-(\w)/gi,function(a,b){return b.toUpperCase()}),g=c.replace(/[A-Z]/g,function(a){return"-"+a.toLowerCase()});bb[z](g)?this.node.style[f]=null==a?I:a:d(this.node,e)}),function(){}(v.prototype),c.ajax=function(a,c,d,f){var g=new XMLHttpRequest,h=S();if(g){if(e(c,"function"))f=d,d=c,c=null;else if(e(c,"object")){var i=[];for(var j in c)c.hasOwnProperty(j)&&i.push(encodeURIComponent(j)+"="+encodeURIComponent(c[j]));c=i.join("&")}return g.open(c?"POST":"GET",a,!0),c&&(g.setRequestHeader("X-Requested-With","XMLHttpRequest"),g.setRequestHeader("Content-type","application/x-www-form-urlencoded")),d&&(b.once("snap.ajax."+h+".0",d),b.once("snap.ajax."+h+".200",d),b.once("snap.ajax."+h+".304",d)),g.onreadystatechange=function(){4==g.readyState&&b("snap.ajax."+h+"."+g.status,f,g)},4==g.readyState?g:(g.send(c),g)}},c.load=function(a,b,d){c.ajax(a,function(a){var e=c.parse(a.responseText);d?b.call(d,e):b(e)})};var cb=function(a){var b=a.getBoundingClientRect(),c=a.ownerDocument,d=c.body,e=c.documentElement,f=e.clientTop||d.clientTop||0,h=e.clientLeft||d.clientLeft||0,i=b.top+(g.win.pageYOffset||e.scrollTop||d.scrollTop)-f,j=b.left+(g.win.pageXOffset||e.scrollLeft||d.scrollLeft)-h;return{y:i,x:j}};return c.getElementByPoint=function(a,b){var c=this,d=(c.canvas,y.doc.elementFromPoint(a,b));if(y.win.opera&&"svg"==d.tagName){var e=cb(d),f=d.createSVGRect();f.x=a-e.x,f.y=b-e.y,f.width=f.height=1;var g=d.getIntersectionList(f,null);g.length&&(d=g[g.length-1])}return d?w(d):null},c.plugin=function(a){a(c,s,v,y,t)},y.win.Snap=c,c}(a||this);return d.plugin(function(d,e,f,g,h){function i(a,b){if(null==b){var c=!0;if(b=a.node.getAttribute("linearGradient"==a.type||"radialGradient"==a.type?"gradientTransform":"pattern"==a.type?"patternTransform":"transform"),!b)return new d.Matrix;b=d._.svgTransform2string(b)}else b=d._.rgTransform.test(b)?o(b).replace(/\.{3}|\u2026/g,a._.transform||""):d._.svgTransform2string(b),n(b,"array")&&(b=d.path?d.path.toString.call(b):o(b)),a._.transform=b;var e=d._.transform2matrix(b,a.getBBox(1));return c?e:void(a.matrix=e)}function j(a){function b(a,b){var c=q(a.node,b);c=c&&c.match(f),c=c&&c[2],c&&"#"==c.charAt()&&(c=c.substring(1),c&&(h[c]=(h[c]||[]).concat(function(c){var d={};d[b]=URL(c),q(a.node,d)})))}function c(a){var b=q(a.node,"xlink:href");b&&"#"==b.charAt()&&(b=b.substring(1),b&&(h[b]=(h[b]||[]).concat(function(b){a.attr("xlink:href","#"+b)})))}for(var d,e=a.selectAll("*"),f=/^\s*url\(("|'|)(.*)\1\)\s*$/,g=[],h={},i=0,j=e.length;j>i;i++){d=e[i],b(d,"fill"),b(d,"stroke"),b(d,"filter"),b(d,"mask"),b(d,"clip-path"),c(d);var k=q(d.node,"id");k&&(q(d.node,{id:d.id}),g.push({old:k,id:d.id}))}for(i=0,j=g.length;j>i;i++){var l=h[g[i].old];if(l)for(var m=0,n=l.length;n>m;m++)l[m](g[i].id)}}function k(a,b,c){return function(d){var e=d.slice(a,b);return 1==e.length&&(e=e[0]),c?c(e):e}}function l(a){return function(){var b=a?"<"+this.type:"",c=this.node.attributes,d=this.node.childNodes;if(a)for(var e=0,f=c.length;f>e;e++)b+=" "+c[e].name+'="'+c[e].value.replace(/"/g,'\\"')+'"';if(d.length){for(a&&(b+=">"),e=0,f=d.length;f>e;e++)3==d[e].nodeType?b+=d[e].nodeValue:1==d[e].nodeType&&(b+=u(d[e]).toString());a&&(b+="")}else a&&(b+="/>");return b}}var m=e.prototype,n=d.is,o=String,p=d._unit2px,q=d._.$,r=d._.make,s=d._.getSomeDefs,t="hasOwnProperty",u=d._.wrap;m.getBBox=function(a){if(!d.Matrix||!d.path)return this.node.getBBox();var b=this,c=new d.Matrix;if(b.removed)return d._.box();for(;"use"==b.type;)if(a||(c=c.add(b.transform().localMatrix.translate(b.attr("x")||0,b.attr("y")||0))),b.original)b=b.original;else{var e=b.attr("xlink:href");b=b.original=b.node.ownerDocument.getElementById(e.substring(e.indexOf("#")+1))}var f=b._,g=d.path.get[b.type]||d.path.get.deflt;try{return a?(f.bboxwt=g?d.path.getBBox(b.realPath=g(b)):d._.box(b.node.getBBox()),d._.box(f.bboxwt)):(b.realPath=g(b),b.matrix=b.transform().localMatrix,f.bbox=d.path.getBBox(d.path.map(b.realPath,c.add(b.matrix))),d._.box(f.bbox))}catch(h){return d._.box()}};var v=function(){return this.string};m.transform=function(a){var b=this._;if(null==a){for(var c,e=this,f=new d.Matrix(this.node.getCTM()),g=i(this),h=[g],j=new d.Matrix,k=g.toTransformString(),l=o(g)==o(this.matrix)?o(b.transform):k;"svg"!=e.type&&(e=e.parent());)h.push(i(e));for(c=h.length;c--;)j.add(h[c]);return{string:l,globalMatrix:f,totalMatrix:j,localMatrix:g,diffMatrix:f.clone().add(g.invert()),global:f.toTransformString(),total:j.toTransformString(),local:k,toString:v}}return a instanceof d.Matrix?(this.matrix=a,this._.transform=a.toTransformString()):i(this,a),this.node&&("linearGradient"==this.type||"radialGradient"==this.type?q(this.node,{gradientTransform:this.matrix}):"pattern"==this.type?q(this.node,{patternTransform:this.matrix}):q(this.node,{transform:this.matrix})),this},m.parent=function(){return u(this.node.parentNode)},m.append=m.add=function(a){if(a){if("set"==a.type){var b=this;return a.forEach(function(a){b.add(a)}),this}a=u(a),this.node.appendChild(a.node),a.paper=this.paper}return this},m.appendTo=function(a){return a&&(a=u(a),a.append(this)),this},m.prepend=function(a){if(a){if("set"==a.type){var b,c=this;return a.forEach(function(a){b?b.after(a):c.prepend(a),b=a}),this}a=u(a);var d=a.parent();this.node.insertBefore(a.node,this.node.firstChild),this.add&&this.add(),a.paper=this.paper,this.parent()&&this.parent().add(),d&&d.add()}return this},m.prependTo=function(a){return a=u(a),a.prepend(this),this},m.before=function(a){if("set"==a.type){var b=this;return a.forEach(function(a){var c=a.parent();b.node.parentNode.insertBefore(a.node,b.node),c&&c.add()}),this.parent().add(),this}a=u(a);var c=a.parent();return this.node.parentNode.insertBefore(a.node,this.node),this.parent()&&this.parent().add(),c&&c.add(),a.paper=this.paper,this},m.after=function(a){a=u(a);var b=a.parent();return this.node.nextSibling?this.node.parentNode.insertBefore(a.node,this.node.nextSibling):this.node.parentNode.appendChild(a.node),this.parent()&&this.parent().add(),b&&b.add(),a.paper=this.paper,this},m.insertBefore=function(a){a=u(a);var b=this.parent();return a.node.parentNode.insertBefore(this.node,a.node),this.paper=a.paper,b&&b.add(),a.parent()&&a.parent().add(),this},m.insertAfter=function(a){a=u(a);var b=this.parent();return a.node.parentNode.insertBefore(this.node,a.node.nextSibling),this.paper=a.paper,b&&b.add(),a.parent()&&a.parent().add(),this},m.remove=function(){var a=this.parent();return this.node.parentNode&&this.node.parentNode.removeChild(this.node),delete this.paper,this.removed=!0,a&&a.add(),this},m.select=function(a){return u(this.node.querySelector(a))},m.selectAll=function(a){for(var b=this.node.querySelectorAll(a),c=(d.set||Array)(),e=0;eb;b++)a[b].stop();return this},m.animate=function(a,d,e,f){"function"!=typeof e||e.length||(f=e,e=c.linear),a instanceof w&&(f=a.callback,e=a.easing,d=a.dur,a=a.attr);var g,h,i,j,l=[],m=[],p={},q=this;for(var r in a)if(a[t](r)){q.equal?(j=q.equal(r,o(a[r])),g=j.from,h=j.to,i=j.f):(g=+q.attr(r),h=+a[r]);var s=n(g,"array")?g.length:1;p[r]=k(l.length,l.length+s,i),l=l.concat(g),m=m.concat(h)}var u=c.time(),v=c(l,m,u,u+d,c.time,function(a){var b={};for(var c in p)p[t](c)&&(b[c]=p[c](a));q.attr(b)},e);return q.anims[v.id]=v,v._attrs=a,v._callback=f,b("snap.animcreated."+q.id,v),b.once("mina.finish."+v.id,function(){delete q.anims[v.id],f&&f.call(q)}),b.once("mina.stop."+v.id,function(){delete q.anims[v.id]}),q};var x={};m.data=function(a,c){var e=x[this.id]=x[this.id]||{};if(0==arguments.length)return b("snap.data.get."+this.id,this,e,null),e; -if(1==arguments.length){if(d.is(a,"object")){for(var f in a)a[t](f)&&this.data(f,a[f]);return this}return b("snap.data.get."+this.id,this,e[a],a),e[a]}return e[a]=c,b("snap.data.set."+this.id,this,c,a),this},m.removeData=function(a){return null==a?x[this.id]={}:x[this.id]&&delete x[this.id][a],this},m.outerSVG=m.toString=l(1),m.innerSVG=l(),m.toDataURL=function(){if(a&&a.btoa){var b=this.getBBox(),c=d.format('{contents}',{x:+b.x.toFixed(3),y:+b.y.toFixed(3),width:+b.width.toFixed(3),height:+b.height.toFixed(3),contents:this.outerSVG()});return"data:image/svg+xml;base64,"+btoa(unescape(encodeURIComponent(c)))}},h.prototype.select=m.select,h.prototype.selectAll=m.selectAll}),d.plugin(function(a){function b(a,b,d,e,f,g){return null==b&&"[object SVGMatrix]"==c.call(a)?(this.a=a.a,this.b=a.b,this.c=a.c,this.d=a.d,this.e=a.e,void(this.f=a.f)):void(null!=a?(this.a=+a,this.b=+b,this.c=+d,this.d=+e,this.e=+f,this.f=+g):(this.a=1,this.b=0,this.c=0,this.d=1,this.e=0,this.f=0))}var c=Object.prototype.toString,d=String,e=Math,f="";!function(c){function g(a){return a[0]*a[0]+a[1]*a[1]}function h(a){var b=e.sqrt(g(a));a[0]&&(a[0]/=b),a[1]&&(a[1]/=b)}c.add=function(a,c,d,e,f,g){var h,i,j,k,l=[[],[],[]],m=[[this.a,this.c,this.e],[this.b,this.d,this.f],[0,0,1]],n=[[a,d,f],[c,e,g],[0,0,1]];for(a&&a instanceof b&&(n=[[a.a,a.c,a.e],[a.b,a.d,a.f],[0,0,1]]),h=0;3>h;h++)for(i=0;3>i;i++){for(k=0,j=0;3>j;j++)k+=m[h][j]*n[j][i];l[h][i]=k}return this.a=l[0][0],this.b=l[1][0],this.c=l[0][1],this.d=l[1][1],this.e=l[0][2],this.f=l[1][2],this},c.invert=function(){var a=this,c=a.a*a.d-a.b*a.c;return new b(a.d/c,-a.b/c,-a.c/c,a.a/c,(a.c*a.f-a.d*a.e)/c,(a.b*a.e-a.a*a.f)/c)},c.clone=function(){return new b(this.a,this.b,this.c,this.d,this.e,this.f)},c.translate=function(a,b){return this.add(1,0,0,1,a,b)},c.scale=function(a,b,c,d){return null==b&&(b=a),(c||d)&&this.add(1,0,0,1,c,d),this.add(a,0,0,b,0,0),(c||d)&&this.add(1,0,0,1,-c,-d),this},c.rotate=function(b,c,d){b=a.rad(b),c=c||0,d=d||0;var f=+e.cos(b).toFixed(9),g=+e.sin(b).toFixed(9);return this.add(f,g,-g,f,c,d),this.add(1,0,0,1,-c,-d)},c.x=function(a,b){return a*this.a+b*this.c+this.e},c.y=function(a,b){return a*this.b+b*this.d+this.f},c.get=function(a){return+this[d.fromCharCode(97+a)].toFixed(4)},c.toString=function(){return"matrix("+[this.get(0),this.get(1),this.get(2),this.get(3),this.get(4),this.get(5)].join()+")"},c.offset=function(){return[this.e.toFixed(4),this.f.toFixed(4)]},c.determinant=function(){return this.a*this.d-this.b*this.c},c.split=function(){var b={};b.dx=this.e,b.dy=this.f;var c=[[this.a,this.c],[this.b,this.d]];b.scalex=e.sqrt(g(c[0])),h(c[0]),b.shear=c[0][0]*c[1][0]+c[0][1]*c[1][1],c[1]=[c[1][0]-c[0][0]*b.shear,c[1][1]-c[0][1]*b.shear],b.scaley=e.sqrt(g(c[1])),h(c[1]),b.shear/=b.scaley,this.determinant()<0&&(b.scalex=-b.scalex);var d=-c[0][1],f=c[1][1];return 0>f?(b.rotate=a.deg(e.acos(f)),0>d&&(b.rotate=360-b.rotate)):b.rotate=a.deg(e.asin(d)),b.isSimple=!(+b.shear.toFixed(9)||b.scalex.toFixed(9)!=b.scaley.toFixed(9)&&b.rotate),b.isSuperSimple=!+b.shear.toFixed(9)&&b.scalex.toFixed(9)==b.scaley.toFixed(9)&&!b.rotate,b.noRotation=!+b.shear.toFixed(9)&&!b.rotate,b},c.toTransformString=function(a){var b=a||this.split();return+b.shear.toFixed(9)?"m"+[this.get(0),this.get(1),this.get(2),this.get(3),this.get(4),this.get(5)]:(b.scalex=+b.scalex.toFixed(4),b.scaley=+b.scaley.toFixed(4),b.rotate=+b.rotate.toFixed(4),(b.dx||b.dy?"t"+[+b.dx.toFixed(4),+b.dy.toFixed(4)]:f)+(1!=b.scalex||1!=b.scaley?"s"+[b.scalex,b.scaley,0,0]:f)+(b.rotate?"r"+[+b.rotate.toFixed(4),0,0]:f))}}(b.prototype),a.Matrix=b,a.matrix=function(a,c,d,e,f,g){return new b(a,c,d,e,f,g)}}),d.plugin(function(a,c,d,e,f){function g(d){return function(e){if(b.stop(),e instanceof f&&1==e.node.childNodes.length&&("radialGradient"==e.node.firstChild.tagName||"linearGradient"==e.node.firstChild.tagName||"pattern"==e.node.firstChild.tagName)&&(e=e.node.firstChild,n(this).appendChild(e),e=l(e)),e instanceof c)if("radialGradient"==e.type||"linearGradient"==e.type||"pattern"==e.type){e.node.id||p(e.node,{id:e.id});var g=q(e.node.id)}else g=e.attr(d);else if(g=a.color(e),g.error){var h=a(n(this).ownerSVGElement).gradient(e);h?(h.node.id||p(h.node,{id:h.id}),g=q(h.node.id)):g=e}else g=r(g);var i={};i[d]=g,p(this.node,i),this.node.style[d]=t}}function h(a){b.stop(),a==+a&&(a+="px"),this.node.style.fontSize=a}function i(a){for(var b=[],c=a.childNodes,d=0,e=c.length;e>d;d++){var f=c[d];3==f.nodeType&&b.push(f.nodeValue),"tspan"==f.tagName&&b.push(1==f.childNodes.length&&3==f.firstChild.nodeType?f.firstChild.nodeValue:i(f))}return b}function j(){return b.stop(),this.node.style.fontSize}var k=a._.make,l=a._.wrap,m=a.is,n=a._.getSomeDefs,o=/^url\(#?([^)]+)\)$/,p=a._.$,q=a.url,r=String,s=a._.separator,t="";b.on("snap.util.attr.mask",function(a){if(a instanceof c||a instanceof f){if(b.stop(),a instanceof f&&1==a.node.childNodes.length&&(a=a.node.firstChild,n(this).appendChild(a),a=l(a)),"mask"==a.type)var d=a;else d=k("mask",n(this)),d.node.appendChild(a.node);!d.node.id&&p(d.node,{id:d.id}),p(this.node,{mask:q(d.id)})}}),function(a){b.on("snap.util.attr.clip",a),b.on("snap.util.attr.clip-path",a),b.on("snap.util.attr.clipPath",a)}(function(a){if(a instanceof c||a instanceof f){if(b.stop(),"clipPath"==a.type)var d=a;else d=k("clipPath",n(this)),d.node.appendChild(a.node),!d.node.id&&p(d.node,{id:d.id});p(this.node,{"clip-path":q(d.node.id||d.id)})}}),b.on("snap.util.attr.fill",g("fill")),b.on("snap.util.attr.stroke",g("stroke"));var u=/^([lr])(?:\(([^)]*)\))?(.*)$/i;b.on("snap.util.grad.parse",function(a){a=r(a);var b=a.match(u);if(!b)return null;var c=b[1],d=b[2],e=b[3];return d=d.split(/\s*,\s*/).map(function(a){return+a==a?+a:a}),1==d.length&&0==d[0]&&(d=[]),e=e.split("-"),e=e.map(function(a){a=a.split(":");var b={color:a[0]};return a[1]&&(b.offset=parseFloat(a[1])),b}),{type:c,params:d,stops:e}}),b.on("snap.util.attr.d",function(c){b.stop(),m(c,"array")&&m(c[0],"array")&&(c=a.path.toString.call(c)),c=r(c),c.match(/[ruo]/i)&&(c=a.path.toAbsolute(c)),p(this.node,{d:c})})(-1),b.on("snap.util.attr.#text",function(a){b.stop(),a=r(a);for(var c=e.doc.createTextNode(a);this.node.firstChild;)this.node.removeChild(this.node.firstChild);this.node.appendChild(c)})(-1),b.on("snap.util.attr.path",function(a){b.stop(),this.attr({d:a})})(-1),b.on("snap.util.attr.class",function(a){b.stop(),this.node.className.baseVal=a})(-1),b.on("snap.util.attr.viewBox",function(a){var c;c=m(a,"object")&&"x"in a?[a.x,a.y,a.width,a.height].join(" "):m(a,"array")?a.join(" "):a,p(this.node,{viewBox:c}),b.stop()})(-1),b.on("snap.util.attr.transform",function(a){this.transform(a),b.stop()})(-1),b.on("snap.util.attr.r",function(a){"rect"==this.type&&(b.stop(),p(this.node,{rx:a,ry:a}))})(-1),b.on("snap.util.attr.textpath",function(a){if(b.stop(),"text"==this.type){var d,e,f;if(!a&&this.textPath){for(e=this.textPath;e.node.firstChild;)this.node.appendChild(e.node.firstChild);return e.remove(),void delete this.textPath}if(m(a,"string")){var g=n(this),h=l(g.parentNode).path(a);g.appendChild(h.node),d=h.id,h.attr({id:d})}else a=l(a),a instanceof c&&(d=a.attr("id"),d||(d=a.id,a.attr({id:d})));if(d)if(e=this.textPath,f=this.node,e)e.attr({"xlink:href":"#"+d});else{for(e=p("textPath",{"xlink:href":"#"+d});f.firstChild;)e.appendChild(f.firstChild);f.appendChild(e),this.textPath=l(e)}}})(-1),b.on("snap.util.attr.text",function(a){if("text"==this.type){for(var c=this.node,d=function(a){var b=p("tspan");if(m(a,"array"))for(var c=0;c1&&(a=Array.prototype.slice.call(arguments,0));var b={};return h(a,"object")&&!h(a,"array")?b=a:null!=a&&(b={points:a}),this.el("polyline",b)},g.polygon=function(a){arguments.length>1&&(a=Array.prototype.slice.call(arguments,0));var b={};return h(a,"object")&&!h(a,"array")?b=a:null!=a&&(b={points:a}),this.el("polygon",b)},function(){function d(){return this.selectAll("stop")}function e(a,b){var d=k("stop"),e={offset:+b+"%"};return a=c.color(a),e["stop-color"]=a.hex,a.opacity<1&&(e["stop-opacity"]=a.opacity),k(d,e),this.node.appendChild(d),this}function f(){if("linearGradient"==this.type){var a=k(this.node,"x1")||0,b=k(this.node,"x2")||1,d=k(this.node,"y1")||0,e=k(this.node,"y2")||0;return c._.box(a,d,math.abs(b-a),math.abs(e-d))}var f=this.node.cx||.5,g=this.node.cy||.5,h=this.node.r||0;return c._.box(f-h,g-h,2*h,2*h)}function h(a,c){function d(a,b){for(var c=(b-l)/(a-m),d=m;a>d;d++)g[d].offset=+(+l+c*(d-m)).toFixed(2);m=a,l=b}var e,f=b("snap.util.grad.parse",null,c).firstDefined();if(!f)return null;f.params.unshift(a),e="l"==f.type.toLowerCase()?i.apply(0,f.params):j.apply(0,f.params),f.type!=f.type.toLowerCase()&&k(e.node,{gradientUnits:"userSpaceOnUse"});var g=f.stops,h=g.length,l=0,m=0;h--;for(var n=0;h>n;n++)"offset"in g[n]&&d(n,g[n].offset);for(g[h].offset=g[h].offset||100,d(h,g[h].offset),n=0;h>=n;n++){var o=g[n];e.addStop(o.color,o.offset)}return e}function i(a,b,g,h,i){var j=c._.make("linearGradient",a);return j.stops=d,j.addStop=e,j.getBBox=f,null!=b&&k(j.node,{x1:b,y1:g,x2:h,y2:i}),j}function j(a,b,g,h,i,j){var l=c._.make("radialGradient",a);return l.stops=d,l.addStop=e,l.getBBox=f,null!=b&&k(l.node,{cx:b,cy:g,r:h}),null!=i&&null!=j&&k(l.node,{fx:i,fy:j}),l}var k=c._.$;g.gradient=function(a){return h(this.defs,a)},g.gradientLinear=function(a,b,c,d){return i(this.defs,a,b,c,d)},g.gradientRadial=function(a,b,c,d,e){return j(this.defs,a,b,c,d,e)},g.toString=function(){var a,b=this.node.ownerDocument,d=b.createDocumentFragment(),e=b.createElement("div"),f=this.node.cloneNode(!0);return d.appendChild(e),e.appendChild(f),c._.$(f,{xmlns:"http://www.w3.org/2000/svg"}),a=e.innerHTML,d.removeChild(d.firstChild),a},g.toDataURL=function(){return a&&a.btoa?"data:image/svg+xml;base64,"+btoa(unescape(encodeURIComponent(this))):void 0},g.clear=function(){for(var a,b=this.node.firstChild;b;)a=b.nextSibling,"defs"!=b.tagName?b.parentNode.removeChild(b):g.clear.call({node:b}),b=a}}()}),d.plugin(function(a,b){function c(a){var b=c.ps=c.ps||{};return b[a]?b[a].sleep=100:b[a]={sleep:100},setTimeout(function(){for(var c in b)b[K](c)&&c!=a&&(b[c].sleep--,!b[c].sleep&&delete b[c])}),b[a]}function d(a,b,c,d){return null==a&&(a=b=c=d=0),null==b&&(b=a.y,c=a.width,d=a.height,a=a.x),{x:a,y:b,width:c,w:c,height:d,h:d,x2:a+c,y2:b+d,cx:a+c/2,cy:b+d/2,r1:N.min(c,d)/2,r2:N.max(c,d)/2,r0:N.sqrt(c*c+d*d)/2,path:w(a,b,c,d),vb:[a,b,c,d].join(" ")}}function e(){return this.join(",").replace(L,"$1")}function f(a){var b=J(a);return b.toString=e,b}function g(a,b,c,d,e,f,g,h,j){return null==j?n(a,b,c,d,e,f,g,h):i(a,b,c,d,e,f,g,h,o(a,b,c,d,e,f,g,h,j))}function h(c,d){function e(a){return+(+a).toFixed(3)}return a._.cacher(function(a,f,h){a instanceof b&&(a=a.attr("d")),a=E(a);for(var j,k,l,m,n,o="",p={},q=0,r=0,s=a.length;s>r;r++){if(l=a[r],"M"==l[0])j=+l[1],k=+l[2];else{if(m=g(j,k,l[1],l[2],l[3],l[4],l[5],l[6]),q+m>f){if(d&&!p.start){if(n=g(j,k,l[1],l[2],l[3],l[4],l[5],l[6],f-q),o+=["C"+e(n.start.x),e(n.start.y),e(n.m.x),e(n.m.y),e(n.x),e(n.y)],h)return o;p.start=o,o=["M"+e(n.x),e(n.y)+"C"+e(n.n.x),e(n.n.y),e(n.end.x),e(n.end.y),e(l[5]),e(l[6])].join(),q+=m,j=+l[5],k=+l[6];continue}if(!c&&!d)return n=g(j,k,l[1],l[2],l[3],l[4],l[5],l[6],f-q)}q+=m,j=+l[5],k=+l[6]}o+=l.shift()+l}return p.end=o,n=c?q:d?p:i(j,k,l[0],l[1],l[2],l[3],l[4],l[5],1)},null,a._.clone)}function i(a,b,c,d,e,f,g,h,i){var j=1-i,k=R(j,3),l=R(j,2),m=i*i,n=m*i,o=k*a+3*l*i*c+3*j*i*i*e+n*g,p=k*b+3*l*i*d+3*j*i*i*f+n*h,q=a+2*i*(c-a)+m*(e-2*c+a),r=b+2*i*(d-b)+m*(f-2*d+b),s=c+2*i*(e-c)+m*(g-2*e+c),t=d+2*i*(f-d)+m*(h-2*f+d),u=j*a+i*c,v=j*b+i*d,w=j*e+i*g,x=j*f+i*h,y=90-180*N.atan2(q-s,r-t)/O;return{x:o,y:p,m:{x:q,y:r},n:{x:s,y:t},start:{x:u,y:v},end:{x:w,y:x},alpha:y}}function j(b,c,e,f,g,h,i,j){a.is(b,"array")||(b=[b,c,e,f,g,h,i,j]);var k=D.apply(null,b);return d(k.min.x,k.min.y,k.max.x-k.min.x,k.max.y-k.min.y)}function k(a,b,c){return b>=a.x&&b<=a.x+a.width&&c>=a.y&&c<=a.y+a.height}function l(a,b){return a=d(a),b=d(b),k(b,a.x,a.y)||k(b,a.x2,a.y)||k(b,a.x,a.y2)||k(b,a.x2,a.y2)||k(a,b.x,b.y)||k(a,b.x2,b.y)||k(a,b.x,b.y2)||k(a,b.x2,b.y2)||(a.xb.x||b.xa.x)&&(a.yb.y||b.ya.y)}function m(a,b,c,d,e){var f=-3*b+9*c-9*d+3*e,g=a*f+6*b-12*c+6*d;return a*g-3*b+3*c}function n(a,b,c,d,e,f,g,h,i){null==i&&(i=1),i=i>1?1:0>i?0:i;for(var j=i/2,k=12,l=[-.1252,.1252,-.3678,.3678,-.5873,.5873,-.7699,.7699,-.9041,.9041,-.9816,.9816],n=[.2491,.2491,.2335,.2335,.2032,.2032,.1601,.1601,.1069,.1069,.0472,.0472],o=0,p=0;k>p;p++){var q=j*l[p]+j,r=m(q,a,c,e,g),s=m(q,b,d,f,h),t=r*r+s*s;o+=n[p]*N.sqrt(t)}return j*o}function o(a,b,c,d,e,f,g,h,i){if(!(0>i||n(a,b,c,d,e,f,g,h)o;)l/=2,m+=(i>j?1:-1)*l,j=n(a,b,c,d,e,f,g,h,m);return m}}function p(a,b,c,d,e,f,g,h){if(!(Q(a,c)Q(e,g)||Q(b,d)Q(f,h))){var i=(a*d-b*c)*(e-g)-(a-c)*(e*h-f*g),j=(a*d-b*c)*(f-h)-(b-d)*(e*h-f*g),k=(a-c)*(f-h)-(b-d)*(e-g);if(k){var l=i/k,m=j/k,n=+l.toFixed(2),o=+m.toFixed(2);if(!(n<+P(a,c).toFixed(2)||n>+Q(a,c).toFixed(2)||n<+P(e,g).toFixed(2)||n>+Q(e,g).toFixed(2)||o<+P(b,d).toFixed(2)||o>+Q(b,d).toFixed(2)||o<+P(f,h).toFixed(2)||o>+Q(f,h).toFixed(2)))return{x:l,y:m}}}}function q(a,b,c){var d=j(a),e=j(b);if(!l(d,e))return c?0:[];for(var f=n.apply(0,a),g=n.apply(0,b),h=~~(f/8),k=~~(g/8),m=[],o=[],q={},r=c?0:[],s=0;h+1>s;s++){var t=i.apply(0,a.concat(s/h));m.push({x:t.x,y:t.y,t:s/h})}for(s=0;k+1>s;s++)t=i.apply(0,b.concat(s/k)),o.push({x:t.x,y:t.y,t:s/k});for(s=0;h>s;s++)for(var u=0;k>u;u++){var v=m[s],w=m[s+1],x=o[u],y=o[u+1],z=S(w.x-v.x)<.001?"y":"x",A=S(y.x-x.x)<.001?"y":"x",B=p(v.x,v.y,w.x,w.y,x.x,x.y,y.x,y.y);if(B){if(q[B.x.toFixed(4)]==B.y.toFixed(4))continue;q[B.x.toFixed(4)]=B.y.toFixed(4);var C=v.t+S((B[z]-v[z])/(w[z]-v[z]))*(w.t-v.t),D=x.t+S((B[A]-x[A])/(y[A]-x[A]))*(y.t-x.t);C>=0&&1>=C&&D>=0&&1>=D&&(c?r++:r.push({x:B.x,y:B.y,t1:C,t2:D}))}}return r}function r(a,b){return t(a,b)}function s(a,b){return t(a,b,1)}function t(a,b,c){a=E(a),b=E(b);for(var d,e,f,g,h,i,j,k,l,m,n=c?0:[],o=0,p=a.length;p>o;o++){var r=a[o];if("M"==r[0])d=h=r[1],e=i=r[2];else{"C"==r[0]?(l=[d,e].concat(r.slice(1)),d=l[6],e=l[7]):(l=[d,e,d,e,h,i,h,i],d=h,e=i);for(var s=0,t=b.length;t>s;s++){var u=b[s];if("M"==u[0])f=j=u[1],g=k=u[2];else{"C"==u[0]?(m=[f,g].concat(u.slice(1)),f=m[6],g=m[7]):(m=[f,g,f,g,j,k,j,k],f=j,g=k);var v=q(l,m,c);if(c)n+=v;else{for(var w=0,x=v.length;x>w;w++)v[w].segment1=o,v[w].segment2=s,v[w].bez1=l,v[w].bez2=m;n=n.concat(v)}}}}}return n}function u(a,b,c){var d=v(a);return k(d,b,c)&&t(a,[["M",b,c],["H",d.x2+10]],1)%2==1}function v(a){var b=c(a);if(b.bbox)return J(b.bbox);if(!a)return d();a=E(a);for(var e,f=0,g=0,h=[],i=[],j=0,k=a.length;k>j;j++)if(e=a[j],"M"==e[0])f=e[1],g=e[2],h.push(f),i.push(g);else{var l=D(f,g,e[1],e[2],e[3],e[4],e[5],e[6]);h=h.concat(l.min.x,l.max.x),i=i.concat(l.min.y,l.max.y),f=e[5],g=e[6]}var m=P.apply(0,h),n=P.apply(0,i),o=Q.apply(0,h),p=Q.apply(0,i),q=d(m,n,o-m,p-n);return b.bbox=J(q),q}function w(a,b,c,d,f){if(f)return[["M",+a+ +f,b],["l",c-2*f,0],["a",f,f,0,0,1,f,f],["l",0,d-2*f],["a",f,f,0,0,1,-f,f],["l",2*f-c,0],["a",f,f,0,0,1,-f,-f],["l",0,2*f-d],["a",f,f,0,0,1,f,-f],["z"]];var g=[["M",a,b],["l",c,0],["l",0,d],["l",-c,0],["z"]];return g.toString=e,g}function x(a,b,c,d,f){if(null==f&&null==d&&(d=c),a=+a,b=+b,c=+c,d=+d,null!=f)var g=Math.PI/180,h=a+c*Math.cos(-d*g),i=a+c*Math.cos(-f*g),j=b+c*Math.sin(-d*g),k=b+c*Math.sin(-f*g),l=[["M",h,j],["A",c,c,0,+(f-d>180),0,i,k]];else l=[["M",a,b],["m",0,-d],["a",c,d,0,1,1,0,2*d],["a",c,d,0,1,1,0,-2*d],["z"]];return l.toString=e,l}function y(b){var d=c(b),g=String.prototype.toLowerCase;if(d.rel)return f(d.rel);a.is(b,"array")&&a.is(b&&b[0],"array")||(b=a.parsePathString(b));var h=[],i=0,j=0,k=0,l=0,m=0;"M"==b[0][0]&&(i=b[0][1],j=b[0][2],k=i,l=j,m++,h.push(["M",i,j]));for(var n=m,o=b.length;o>n;n++){var p=h[n]=[],q=b[n];if(q[0]!=g.call(q[0]))switch(p[0]=g.call(q[0]),p[0]){case"a":p[1]=q[1],p[2]=q[2],p[3]=q[3],p[4]=q[4],p[5]=q[5],p[6]=+(q[6]-i).toFixed(3),p[7]=+(q[7]-j).toFixed(3);break;case"v":p[1]=+(q[1]-j).toFixed(3);break;case"m":k=q[1],l=q[2];default:for(var r=1,s=q.length;s>r;r++)p[r]=+(q[r]-(r%2?i:j)).toFixed(3)}else{p=h[n]=[],"m"==q[0]&&(k=q[1]+i,l=q[2]+j);for(var t=0,u=q.length;u>t;t++)h[n][t]=q[t]}var v=h[n].length;switch(h[n][0]){case"z":i=k,j=l;break;case"h":i+=+h[n][v-1];break;case"v":j+=+h[n][v-1];break;default:i+=+h[n][v-2],j+=+h[n][v-1]}}return h.toString=e,d.rel=f(h),h}function z(b){var d=c(b);if(d.abs)return f(d.abs);if(I(b,"array")&&I(b&&b[0],"array")||(b=a.parsePathString(b)),!b||!b.length)return[["M",0,0]];var g,h=[],i=0,j=0,k=0,l=0,m=0;"M"==b[0][0]&&(i=+b[0][1],j=+b[0][2],k=i,l=j,m++,h[0]=["M",i,j]);for(var n,o,p=3==b.length&&"M"==b[0][0]&&"R"==b[1][0].toUpperCase()&&"Z"==b[2][0].toUpperCase(),q=m,r=b.length;r>q;q++){if(h.push(n=[]),o=b[q],g=o[0],g!=g.toUpperCase())switch(n[0]=g.toUpperCase(),n[0]){case"A":n[1]=o[1],n[2]=o[2],n[3]=o[3],n[4]=o[4],n[5]=o[5],n[6]=+o[6]+i,n[7]=+o[7]+j;break;case"V":n[1]=+o[1]+j;break;case"H":n[1]=+o[1]+i;break;case"R":for(var s=[i,j].concat(o.slice(1)),t=2,u=s.length;u>t;t++)s[t]=+s[t]+i,s[++t]=+s[t]+j;h.pop(),h=h.concat(G(s,p));break;case"O":h.pop(),s=x(i,j,o[1],o[2]),s.push(s[0]),h=h.concat(s);break;case"U":h.pop(),h=h.concat(x(i,j,o[1],o[2],o[3])),n=["U"].concat(h[h.length-1].slice(-2));break;case"M":k=+o[1]+i,l=+o[2]+j;default:for(t=1,u=o.length;u>t;t++)n[t]=+o[t]+(t%2?i:j)}else if("R"==g)s=[i,j].concat(o.slice(1)),h.pop(),h=h.concat(G(s,p)),n=["R"].concat(o.slice(-2));else if("O"==g)h.pop(),s=x(i,j,o[1],o[2]),s.push(s[0]),h=h.concat(s);else if("U"==g)h.pop(),h=h.concat(x(i,j,o[1],o[2],o[3])),n=["U"].concat(h[h.length-1].slice(-2));else for(var v=0,w=o.length;w>v;v++)n[v]=o[v];if(g=g.toUpperCase(),"O"!=g)switch(n[0]){case"Z":i=+k,j=+l;break;case"H":i=n[1];break;case"V":j=n[1];break;case"M":k=n[n.length-2],l=n[n.length-1];default:i=n[n.length-2],j=n[n.length-1]}}return h.toString=e,d.abs=f(h),h}function A(a,b,c,d){return[a,b,c,d,c,d]}function B(a,b,c,d,e,f){var g=1/3,h=2/3;return[g*a+h*c,g*b+h*d,g*e+h*c,g*f+h*d,e,f]}function C(b,c,d,e,f,g,h,i,j,k){var l,m=120*O/180,n=O/180*(+f||0),o=[],p=a._.cacher(function(a,b,c){var d=a*N.cos(c)-b*N.sin(c),e=a*N.sin(c)+b*N.cos(c);return{x:d,y:e}});if(k)y=k[0],z=k[1],w=k[2],x=k[3];else{l=p(b,c,-n),b=l.x,c=l.y,l=p(i,j,-n),i=l.x,j=l.y;var q=(N.cos(O/180*f),N.sin(O/180*f),(b-i)/2),r=(c-j)/2,s=q*q/(d*d)+r*r/(e*e);s>1&&(s=N.sqrt(s),d=s*d,e=s*e);var t=d*d,u=e*e,v=(g==h?-1:1)*N.sqrt(S((t*u-t*r*r-u*q*q)/(t*r*r+u*q*q))),w=v*d*r/e+(b+i)/2,x=v*-e*q/d+(c+j)/2,y=N.asin(((c-x)/e).toFixed(9)),z=N.asin(((j-x)/e).toFixed(9));y=w>b?O-y:y,z=w>i?O-z:z,0>y&&(y=2*O+y),0>z&&(z=2*O+z),h&&y>z&&(y-=2*O),!h&&z>y&&(z-=2*O)}var A=z-y;if(S(A)>m){var B=z,D=i,E=j;z=y+m*(h&&z>y?1:-1),i=w+d*N.cos(z),j=x+e*N.sin(z),o=C(i,j,d,e,f,0,h,D,E,[z,B,w,x])}A=z-y;var F=N.cos(y),G=N.sin(y),H=N.cos(z),I=N.sin(z),J=N.tan(A/4),K=4/3*d*J,L=4/3*e*J,M=[b,c],P=[b+K*G,c-L*F],Q=[i+K*I,j-L*H],R=[i,j];if(P[0]=2*M[0]-P[0],P[1]=2*M[1]-P[1],k)return[P,Q,R].concat(o);o=[P,Q,R].concat(o).join().split(",");for(var T=[],U=0,V=o.length;V>U;U++)T[U]=U%2?p(o[U-1],o[U],n).y:p(o[U],o[U+1],n).x;return T}function D(a,b,c,d,e,f,g,h){for(var i,j,k,l,m,n,o,p,q=[],r=[[],[]],s=0;2>s;++s)if(0==s?(j=6*a-12*c+6*e,i=-3*a+9*c-9*e+3*g,k=3*c-3*a):(j=6*b-12*d+6*f,i=-3*b+9*d-9*f+3*h,k=3*d-3*b),S(i)<1e-12){if(S(j)<1e-12)continue;l=-k/j,l>0&&1>l&&q.push(l)}else o=j*j-4*k*i,p=N.sqrt(o),0>o||(m=(-j+p)/(2*i),m>0&&1>m&&q.push(m),n=(-j-p)/(2*i),n>0&&1>n&&q.push(n));for(var t,u=q.length,v=u;u--;)l=q[u],t=1-l,r[0][u]=t*t*t*a+3*t*t*l*c+3*t*l*l*e+l*l*l*g,r[1][u]=t*t*t*b+3*t*t*l*d+3*t*l*l*f+l*l*l*h;return r[0][v]=a,r[1][v]=b,r[0][v+1]=g,r[1][v+1]=h,r[0].length=r[1].length=v+2,{min:{x:P.apply(0,r[0]),y:P.apply(0,r[1])},max:{x:Q.apply(0,r[0]),y:Q.apply(0,r[1])}}}function E(a,b){var d=!b&&c(a);if(!b&&d.curve)return f(d.curve);for(var e=z(a),g=b&&z(b),h={x:0,y:0,bx:0,by:0,X:0,Y:0,qx:null,qy:null},i={x:0,y:0,bx:0,by:0,X:0,Y:0,qx:null,qy:null},j=(function(a,b,c){var d,e;if(!a)return["C",b.x,b.y,b.x,b.y,b.x,b.y];switch(!(a[0]in{T:1,Q:1})&&(b.qx=b.qy=null),a[0]){case"M":b.X=a[1],b.Y=a[2];break;case"A":a=["C"].concat(C.apply(0,[b.x,b.y].concat(a.slice(1))));break;case"S":"C"==c||"S"==c?(d=2*b.x-b.bx,e=2*b.y-b.by):(d=b.x,e=b.y),a=["C",d,e].concat(a.slice(1));break;case"T":"Q"==c||"T"==c?(b.qx=2*b.x-b.qx,b.qy=2*b.y-b.qy):(b.qx=b.x,b.qy=b.y),a=["C"].concat(B(b.x,b.y,b.qx,b.qy,a[1],a[2]));break;case"Q":b.qx=a[1],b.qy=a[2],a=["C"].concat(B(b.x,b.y,a[1],a[2],a[3],a[4]));break;case"L":a=["C"].concat(A(b.x,b.y,a[1],a[2]));break;case"H":a=["C"].concat(A(b.x,b.y,a[1],b.y));break;case"V":a=["C"].concat(A(b.x,b.y,b.x,a[1]));break;case"Z":a=["C"].concat(A(b.x,b.y,b.X,b.Y))}return a}),k=function(a,b){if(a[b].length>7){a[b].shift();for(var c=a[b];c.length;)m[b]="A",g&&(n[b]="A"),a.splice(b++,0,["C"].concat(c.splice(0,6)));a.splice(b,1),r=Q(e.length,g&&g.length||0)}},l=function(a,b,c,d,f){a&&b&&"M"==a[f][0]&&"M"!=b[f][0]&&(b.splice(f,0,["M",d.x,d.y]),c.bx=0,c.by=0,c.x=a[f][1],c.y=a[f][2],r=Q(e.length,g&&g.length||0))},m=[],n=[],o="",p="",q=0,r=Q(e.length,g&&g.length||0);r>q;q++){e[q]&&(o=e[q][0]),"C"!=o&&(m[q]=o,q&&(p=m[q-1])),e[q]=j(e[q],h,p),"A"!=m[q]&&"C"==o&&(m[q]="C"),k(e,q),g&&(g[q]&&(o=g[q][0]),"C"!=o&&(n[q]=o,q&&(p=n[q-1])),g[q]=j(g[q],i,p),"A"!=n[q]&&"C"==o&&(n[q]="C"),k(g,q)),l(e,g,h,i,q),l(g,e,i,h,q);var s=e[q],t=g&&g[q],u=s.length,v=g&&t.length;h.x=s[u-2],h.y=s[u-1],h.bx=M(s[u-4])||h.x,h.by=M(s[u-3])||h.y,i.bx=g&&(M(t[v-4])||i.x),i.by=g&&(M(t[v-3])||i.y),i.x=g&&t[v-2],i.y=g&&t[v-1]}return g||(d.curve=f(e)),g?[e,g]:e}function F(a,b){if(!b)return a;var c,d,e,f,g,h,i;for(a=E(a),e=0,g=a.length;g>e;e++)for(i=a[e],f=1,h=i.length;h>f;f+=2)c=b.x(i[f],i[f+1]),d=b.y(i[f],i[f+1]),i[f]=c,i[f+1]=d;return a}function G(a,b){for(var c=[],d=0,e=a.length;e-2*!b>d;d+=2){var f=[{x:+a[d-2],y:+a[d-1]},{x:+a[d],y:+a[d+1]},{x:+a[d+2],y:+a[d+3]},{x:+a[d+4],y:+a[d+5]}];b?d?e-4==d?f[3]={x:+a[0],y:+a[1]}:e-2==d&&(f[2]={x:+a[0],y:+a[1]},f[3]={x:+a[2],y:+a[3]}):f[0]={x:+a[e-2],y:+a[e-1]}:e-4==d?f[3]=f[2]:d||(f[0]={x:+a[d],y:+a[d+1]}),c.push(["C",(-f[0].x+6*f[1].x+f[2].x)/6,(-f[0].y+6*f[1].y+f[2].y)/6,(f[1].x+6*f[2].x-f[3].x)/6,(f[1].y+6*f[2].y-f[3].y)/6,f[2].x,f[2].y])}return c}var H=b.prototype,I=a.is,J=a._.clone,K="hasOwnProperty",L=/,?([a-z]),?/gi,M=parseFloat,N=Math,O=N.PI,P=N.min,Q=N.max,R=N.pow,S=N.abs,T=h(1),U=h(),V=h(0,1),W=a._unit2px,X={path:function(a){return a.attr("path")},circle:function(a){var b=W(a);return x(b.cx,b.cy,b.r)},ellipse:function(a){var b=W(a);return x(b.cx||0,b.cy||0,b.rx,b.ry)},rect:function(a){var b=W(a);return w(b.x||0,b.y||0,b.width,b.height,b.rx,b.ry)},image:function(a){var b=W(a);return w(b.x||0,b.y||0,b.width,b.height)},line:function(a){return"M"+[a.attr("x1")||0,a.attr("y1")||0,a.attr("x2"),a.attr("y2")]},polyline:function(a){return"M"+a.attr("points")},polygon:function(a){return"M"+a.attr("points")+"z"},deflt:function(a){var b=a.node.getBBox();return w(b.x,b.y,b.width,b.height)}};a.path=c,a.path.getTotalLength=T,a.path.getPointAtLength=U,a.path.getSubpath=function(a,b,c){if(this.getTotalLength(a)-c<1e-6)return V(a,b).end;var d=V(a,c,1);return b?V(d,b).end:d},H.getTotalLength=function(){return this.node.getTotalLength?this.node.getTotalLength():void 0},H.getPointAtLength=function(a){return U(this.attr("d"),a)},H.getSubpath=function(b,c){return a.path.getSubpath(this.attr("d"),b,c)},a._.box=d,a.path.findDotsAtSegment=i,a.path.bezierBBox=j,a.path.isPointInsideBBox=k,a.closest=function(b,c,e,f){for(var g=100,h=d(b-g/2,c-g/2,g,g),i=[],j=e[0].hasOwnProperty("x")?function(a){return{x:e[a].x,y:e[a].y}}:function(a){return{x:e[a],y:f[a]}},l=0;1e6>=g&&!l;){for(var m=0,n=e.length;n>m;m++){var o=j(m);if(k(h,o.x,o.y)){l++,i.push(o);break}}l||(g*=2,h=d(b-g/2,c-g/2,g,g))}if(1e6!=g){var p,q=1/0;for(m=0,n=i.length;n>m;m++){var r=a.len(b,c,i[m].x,i[m].y);q>r&&(q=r,i[m].len=r,p=i[m])}return p}},a.path.isBBoxIntersect=l,a.path.intersection=r,a.path.intersectionNumber=s,a.path.isPointInside=u,a.path.getBBox=v,a.path.get=X,a.path.toRelative=y,a.path.toAbsolute=z,a.path.toCubic=E,a.path.map=F,a.path.toString=e,a.path.clone=f}),d.plugin(function(a){var d=Math.max,e=Math.min,f=function(a){if(this.items=[],this.bindings={},this.length=0,this.type="set",a)for(var b=0,c=a.length;c>b;b++)a[b]&&(this[this.items.length]=this.items[this.items.length]=a[b],this.length++)},g=f.prototype;g.push=function(){for(var a,b,c=0,d=arguments.length;d>c;c++)a=arguments[c],a&&(b=this.items.length,this[b]=this.items[b]=a,this.length++);return this},g.pop=function(){return this.length&&delete this[this.length--],this.items.pop()},g.forEach=function(a,b){for(var c=0,d=this.items.length;d>c;c++)if(a.call(b,this.items[c],c)===!1)return this;return this},g.animate=function(d,e,f,g){"function"!=typeof f||f.length||(g=f,f=c.linear),d instanceof a._.Animation&&(g=d.callback,f=d.easing,e=f.dur,d=d.attr);var h=arguments;if(a.is(d,"array")&&a.is(h[h.length-1],"array"))var i=!0;var j,k=function(){j?this.b=j:j=this.b},l=0,m=this,n=g&&function(){++l==m.length&&g.call(this) -};return this.forEach(function(a,c){b.once("snap.animcreated."+a.id,k),i?h[c]&&a.animate.apply(a,h[c]):a.animate(d,e,f,n)})},g.remove=function(){for(;this.length;)this.pop().remove();return this},g.bind=function(a,b,c){var d={};if("function"==typeof b)this.bindings[a]=b;else{var e=c||a;this.bindings[a]=function(a){d[e]=a,b.attr(d)}}return this},g.attr=function(a){var b={};for(var c in a)this.bindings[c]?this.bindings[c](a[c]):b[c]=a[c];for(var d=0,e=this.items.length;e>d;d++)this.items[d].attr(b);return this},g.clear=function(){for(;this.length;)this.pop()},g.splice=function(a,b){a=0>a?d(this.length+a,0):a,b=d(0,e(this.length-a,b));var c,g=[],h=[],i=[];for(c=2;cc;c++)h.push(this[a+c]);for(;cc?i[c]:g[c-j];for(c=this.items.length=this.length-=b-j;this[c];)delete this[c++];return new f(h)},g.exclude=function(a){for(var b=0,c=this.length;c>b;b++)if(this[b]==a)return this.splice(b,1),!0;return!1},g.insertAfter=function(a){for(var b=this.items.length;b--;)this.items[b].insertAfter(a);return this},g.getBBox=function(){for(var a=[],b=[],c=[],f=[],g=this.items.length;g--;)if(!this.items[g].removed){var h=this.items[g].getBBox();a.push(h.x),b.push(h.y),c.push(h.x+h.width),f.push(h.y+h.height)}return a=e.apply(0,a),b=e.apply(0,b),c=d.apply(0,c),f=d.apply(0,f),{x:a,y:b,x2:c,y2:f,width:c-a,height:f-b,cx:a+(c-a)/2,cy:b+(f-b)/2}},g.clone=function(a){a=new f;for(var b=0,c=this.items.length;c>b;b++)a.push(this.items[b].clone());return a},g.toString=function(){return"Snap‘s set"},g.type="set",a.Set=f,a.set=function(){var a=new f;return arguments.length&&a.push.apply(a,Array.prototype.slice.call(arguments,0)),a}}),d.plugin(function(a,c){function d(a){var b=a[0];switch(b.toLowerCase()){case"t":return[b,0,0];case"m":return[b,1,0,0,1,0,0];case"r":return 4==a.length?[b,0,a[2],a[3]]:[b,0];case"s":return 5==a.length?[b,1,1,a[3],a[4]]:3==a.length?[b,1,1]:[b,1]}}function e(b,c,e){c=p(c).replace(/\.{3}|\u2026/g,b),b=a.parseTransformString(b)||[],c=a.parseTransformString(c)||[];for(var f,g,h,i,l=Math.max(b.length,c.length),m=[],n=[],o=0;l>o;o++){if(h=b[o]||d(c[o]),i=c[o]||d(h),h[0]!=i[0]||"r"==h[0].toLowerCase()&&(h[2]!=i[2]||h[3]!=i[3])||"s"==h[0].toLowerCase()&&(h[3]!=i[3]||h[4]!=i[4])){b=a._.transform2matrix(b,e()),c=a._.transform2matrix(c,e()),m=[["m",b.a,b.b,b.c,b.d,b.e,b.f]],n=[["m",c.a,c.b,c.c,c.d,c.e,c.f]];break}for(m[o]=[],n[o]=[],f=0,g=Math.max(h.length,i.length);g>f;f++)f in h&&(m[o][f]=h[f]),f in i&&(n[o][f]=i[f])}return{from:k(m),to:k(n),f:j(m)}}function f(a){return a}function g(a){return function(b){return+b.toFixed(3)+a}}function h(a){return a.join(" ")}function i(b){return a.rgb(b[0],b[1],b[2])}function j(a){var b,c,d,e,f,g,h=0,i=[];for(b=0,c=a.length;c>b;b++){for(f="[",g=['"'+a[b][0]+'"'],d=1,e=a[b].length;e>d;d++)g[d]="val["+h++ +"]";f+=g+"]",i[b]=f}return Function("val","return Snap.path.toString.call(["+i+"])")}function k(a){for(var b=[],c=0,d=a.length;d>c;c++)for(var e=1,f=a[c].length;f>e;e++)b.push(a[c][e]);return b}function l(a){return isFinite(parseFloat(a))}function m(b,c){return a.is(b,"array")&&a.is(c,"array")?b.toString()==c.toString():!1}var n={},o=/[a-z]+$/i,p=String;n.stroke=n.fill="colour",c.prototype.equal=function(a,c){return b("snap.util.equal",this,a,c).firstDefined()},b.on("snap.util.equal",function(b,c){var d,q,r=p(this.attr(b)||""),s=this;if(l(r)&&l(c))return{from:parseFloat(r),to:parseFloat(c),f:f};if("colour"==n[b])return d=a.color(r),q=a.color(c),{from:[d.r,d.g,d.b,d.opacity],to:[q.r,q.g,q.b,q.opacity],f:i};if("viewBox"==b)return d=this.attr(b).vb.split(" ").map(Number),q=c.split(" ").map(Number),{from:d,to:q,f:h};if("transform"==b||"gradientTransform"==b||"patternTransform"==b)return c instanceof a.Matrix&&(c=c.toTransformString()),a._.rgTransform.test(c)||(c=a._.svgTransform2string(c)),e(r,c,function(){return s.getBBox(1)});if("d"==b||"path"==b)return d=a.path.toCubic(r,c),{from:k(d[0]),to:k(d[1]),f:j(d[0])};if("points"==b)return d=p(r).split(a._.separator),q=p(c).split(a._.separator),{from:d,to:q,f:function(a){return a}};var t=r.match(o),u=p(c).match(o);return t&&m(t,u)?{from:parseFloat(r),to:parseFloat(c),f:g(t)}:{from:this.asPX(b),to:this.asPX(b,c),f:f}})}),d.plugin(function(a,c,d,e){for(var f=c.prototype,g="hasOwnProperty",h=("createTouch"in e.doc),i=["click","dblclick","mousedown","mousemove","mouseout","mouseover","mouseup","touchstart","touchmove","touchend","touchcancel"],j={mousedown:"touchstart",mousemove:"touchmove",mouseup:"touchend"},k=(function(a,b){var c="y"==a?"scrollTop":"scrollLeft",d=b&&b.node?b.node.ownerDocument:e.doc;return d[c in d.documentElement?"documentElement":"body"][c]}),l=function(){return this.originalEvent.preventDefault()},m=function(){return this.originalEvent.stopPropagation()},n=function(a,b,c,d){var e=h&&j[b]?j[b]:b,f=function(e){var f=k("y",d),i=k("x",d);if(h&&j[g](b))for(var n=0,o=e.targetTouches&&e.targetTouches.length;o>n;n++)if(e.targetTouches[n].target==a||a.contains(e.targetTouches[n].target)){var p=e;e=e.targetTouches[n],e.originalEvent=p,e.preventDefault=l,e.stopPropagation=m;break}var q=e.clientX+i,r=e.clientY+f;return c.call(d,e,q,r)};return b!==e&&a.addEventListener(b,f,!1),a.addEventListener(e,f,!1),function(){return b!==e&&a.removeEventListener(b,f,!1),a.removeEventListener(e,f,!1),!0}},o=[],p=function(a){for(var c,d=a.clientX,e=a.clientY,f=k("y"),g=k("x"),i=o.length;i--;){if(c=o[i],h){for(var j,l=a.touches&&a.touches.length;l--;)if(j=a.touches[l],j.identifier==c.el._drag.id||c.el.node.contains(j.target)){d=j.clientX,e=j.clientY,(a.originalEvent?a.originalEvent:a).preventDefault();break}}else a.preventDefault();{var m=c.el.node;m.nextSibling,m.parentNode,m.style.display}d+=g,e+=f,b("snap.drag.move."+c.el.id,c.move_scope||c.el,d-c.el._drag.x,e-c.el._drag.y,d,e,a)}},q=function(c){a.unmousemove(p).unmouseup(q);for(var d,e=o.length;e--;)d=o[e],d.el._drag={},b("snap.drag.end."+d.el.id,d.end_scope||d.start_scope||d.move_scope||d.el,c),b.off("snap.drag.*."+d.el.id);o=[]},r=i.length;r--;)!function(b){a[b]=f[b]=function(c,d){if(a.is(c,"function"))this.events=this.events||[],this.events.push({name:b,f:c,unbind:n(this.node||document,b,c,d||this)});else for(var e=0,f=this.events.length;f>e;e++)if(this.events[e].name==b)try{this.events[e].f.call(this)}catch(g){}return this},a["un"+b]=f["un"+b]=function(a){for(var c=this.events||[],d=c.length;d--;)if(c[d].name==b&&(c[d].f==a||!a))return c[d].unbind(),c.splice(d,1),!c.length&&delete this.events,this;return this}}(i[r]);f.hover=function(a,b,c,d){return this.mouseover(a,c).mouseout(b,d||c)},f.unhover=function(a,b){return this.unmouseover(a).unmouseout(b)};var s=[];f.drag=function(c,d,e,f,g,h){function i(i,j,l){(i.originalEvent||i).preventDefault(),k._drag.x=j,k._drag.y=l,k._drag.id=i.identifier,!o.length&&a.mousemove(p).mouseup(q),o.push({el:k,move_scope:f,start_scope:g,end_scope:h}),d&&b.on("snap.drag.start."+k.id,d),c&&b.on("snap.drag.move."+k.id,c),e&&b.on("snap.drag.end."+k.id,e),b("snap.drag.start."+k.id,g||f||k,j,l,i)}function j(a,c,d){b("snap.draginit."+k.id,k,a,c,d)}var k=this;if(!arguments.length){var l;return k.drag(function(a,b){this.attr({transform:l+(l?"T":"t")+[a,b]})},function(){l=this.transform().local})}return b.on("snap.draginit."+k.id,i),k._drag={},s.push({el:k,start:i,init:j}),k.mousedown(j),k},f.undrag=function(){for(var c=s.length;c--;)s[c].el==this&&(this.unmousedown(s[c].init),s.splice(c,1),b.unbind("snap.drag.*."+this.id),b.unbind("snap.draginit."+this.id));return!s.length&&a.unmousemove(p).unmouseup(q),this}}),d.plugin(function(a,c,d){var e=(c.prototype,d.prototype),f=/^\s*url\((.+)\)/,g=String,h=a._.$;a.filter={},e.filter=function(b){var d=this;"svg"!=d.type&&(d=d.paper);var e=a.parse(g(b)),f=a._.id(),i=(d.node.offsetWidth,d.node.offsetHeight,h("filter"));return h(i,{id:f,filterUnits:"userSpaceOnUse"}),i.appendChild(e.node),d.defs.appendChild(i),new c(i)},b.on("snap.util.getattr.filter",function(){b.stop();var c=h(this.node,"filter");if(c){var d=g(c).match(f);return d&&a.select(d[1])}}),b.on("snap.util.attr.filter",function(d){if(d instanceof c&&"filter"==d.type){b.stop();var e=d.node.id;e||(h(d.node,{id:d.id}),e=d.id),h(this.node,{filter:a.url(e)})}d&&"none"!=d||(b.stop(),this.node.removeAttribute("filter"))}),a.filter.blur=function(b,c){null==b&&(b=2);var d=null==c?b:[b,c];return a.format('',{def:d})},a.filter.blur.toString=function(){return this()},a.filter.shadow=function(b,c,d,e,f){return"string"==typeof d&&(e=d,f=e,d=4),"string"!=typeof e&&(f=e,e="#000"),e=e||"#000",null==d&&(d=4),null==f&&(f=1),null==b&&(b=0,c=2),null==c&&(c=b),e=a.color(e),a.format('',{color:e,dx:b,dy:c,blur:d,opacity:f})},a.filter.shadow.toString=function(){return this()},a.filter.grayscale=function(b){return null==b&&(b=1),a.format('',{a:.2126+.7874*(1-b),b:.7152-.7152*(1-b),c:.0722-.0722*(1-b),d:.2126-.2126*(1-b),e:.7152+.2848*(1-b),f:.0722-.0722*(1-b),g:.2126-.2126*(1-b),h:.0722+.9278*(1-b)})},a.filter.grayscale.toString=function(){return this()},a.filter.sepia=function(b){return null==b&&(b=1),a.format('',{a:.393+.607*(1-b),b:.769-.769*(1-b),c:.189-.189*(1-b),d:.349-.349*(1-b),e:.686+.314*(1-b),f:.168-.168*(1-b),g:.272-.272*(1-b),h:.534-.534*(1-b),i:.131+.869*(1-b)})},a.filter.sepia.toString=function(){return this()},a.filter.saturate=function(b){return null==b&&(b=1),a.format('',{amount:1-b})},a.filter.saturate.toString=function(){return this()},a.filter.hueRotate=function(b){return b=b||0,a.format('',{angle:b})},a.filter.hueRotate.toString=function(){return this()},a.filter.invert=function(b){return null==b&&(b=1),a.format('',{amount:b,amount2:1-b})},a.filter.invert.toString=function(){return this()},a.filter.brightness=function(b){return null==b&&(b=1),a.format('',{amount:b})},a.filter.brightness.toString=function(){return this()},a.filter.contrast=function(b){return null==b&&(b=1),a.format('',{amount:b,amount2:.5-b/2})},a.filter.contrast.toString=function(){return this()}}),d.plugin(function(a,b){var c=a._.box,d=a.is,e=/^[^a-z]*([tbmlrc])/i,f=function(){return"T"+this.dx+","+this.dy};b.prototype.getAlign=function(a,b){null==b&&d(a,"string")&&(b=a,a=null),a=a||this.paper;var g=a.getBBox?a.getBBox():c(a),h=this.getBBox(),i={};switch(b=b&&b.match(e),b=b?b[1].toLowerCase():"c"){case"t":i.dx=0,i.dy=g.y-h.y;break;case"b":i.dx=0,i.dy=g.y2-h.y2;break;case"m":i.dx=0,i.dy=g.cy-h.cy;break;case"l":i.dx=g.x-h.x,i.dy=0;break;case"r":i.dx=g.x2-h.x2,i.dy=0;break;default:i.dx=g.cx-h.cx,i.dy=0}return i.toString=f,i},b.prototype.align=function(a,b){return this.transform("..."+this.getAlign(a,b))}}),d}); diff --git a/web/pgadmin/misc/static/explain/vendor/snap.svg/snap.svg.js b/web/pgadmin/misc/static/explain/vendor/snap.svg/snap.svg.js deleted file mode 100644 index ef0fb6d40..000000000 --- a/web/pgadmin/misc/static/explain/vendor/snap.svg/snap.svg.js +++ /dev/null @@ -1,8149 +0,0 @@ -// Snap.svg 0.4.1 -// Copyright (c) 2013 – 2015 Adobe Systems Incorporated. All rights reserved. -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// http://www.apache.org/licenses/LICENSE-2.0 -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -// build: 2015-04-13 -// Copyright (c) 2013 Adobe Systems Incorporated. All rights reserved. -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -// ┌────────────────────────────────────────────────────────────┐ \\ -// │ Eve 0.4.2 - JavaScript Events Library │ \\ -// ├────────────────────────────────────────────────────────────┤ \\ -// │ Author Dmitry Baranovskiy (http://dmitry.baranovskiy.com/) │ \\ -// └────────────────────────────────────────────────────────────┘ \\ -(function (glob) { - var version = "0.4.2", - has = "hasOwnProperty", - separator = /[\.\/]/, - comaseparator = /\s*,\s*/, - wildcard = "*", - fun = function () {}, - numsort = function (a, b) { - return a - b; - }, - current_event, - stop, - events = {n: {}}, - firstDefined = function () { - for (var i = 0, ii = this.length; i < ii; i++) { - if (typeof this[i] != "undefined") { - return this[i]; - } - } - }, - lastDefined = function () { - var i = this.length; - while (--i) { - if (typeof this[i] != "undefined") { - return this[i]; - } - } - }, - /*\ - * eve - [ method ] - * Fires event with given `name`, given scope and other parameters. - > Arguments - - name (string) name of the *event*, dot (`.`) or slash (`/`) separated - - scope (object) context for the event handlers - - varargs (...) the rest of arguments will be sent to event handlers - = (object) array of returned values from the listeners. Array has two methods `.firstDefined()` and `.lastDefined()` to get first or last not `undefined` value. - \*/ - eve = function (name, scope) { - name = String(name); - var e = events, - oldstop = stop, - args = Array.prototype.slice.call(arguments, 2), - listeners = eve.listeners(name), - z = 0, - f = false, - l, - indexed = [], - queue = {}, - out = [], - ce = current_event, - errors = []; - out.firstDefined = firstDefined; - out.lastDefined = lastDefined; - current_event = name; - stop = 0; - for (var i = 0, ii = listeners.length; i < ii; i++) if ("zIndex" in listeners[i]) { - indexed.push(listeners[i].zIndex); - if (listeners[i].zIndex < 0) { - queue[listeners[i].zIndex] = listeners[i]; - } - } - indexed.sort(numsort); - while (indexed[z] < 0) { - l = queue[indexed[z++]]; - out.push(l.apply(scope, args)); - if (stop) { - stop = oldstop; - return out; - } - } - for (i = 0; i < ii; i++) { - l = listeners[i]; - if ("zIndex" in l) { - if (l.zIndex == indexed[z]) { - out.push(l.apply(scope, args)); - if (stop) { - break; - } - do { - z++; - l = queue[indexed[z]]; - l && out.push(l.apply(scope, args)); - if (stop) { - break; - } - } while (l) - } else { - queue[l.zIndex] = l; - } - } else { - out.push(l.apply(scope, args)); - if (stop) { - break; - } - } - } - stop = oldstop; - current_event = ce; - return out; - }; - // Undocumented. Debug only. - eve._events = events; - /*\ - * eve.listeners - [ method ] - * Internal method which gives you array of all event handlers that will be triggered by the given `name`. - > Arguments - - name (string) name of the event, dot (`.`) or slash (`/`) separated - = (array) array of event handlers - \*/ - eve.listeners = function (name) { - var names = name.split(separator), - e = events, - item, - items, - k, - i, - ii, - j, - jj, - nes, - es = [e], - out = []; - for (i = 0, ii = names.length; i < ii; i++) { - nes = []; - for (j = 0, jj = es.length; j < jj; j++) { - e = es[j].n; - items = [e[names[i]], e[wildcard]]; - k = 2; - while (k--) { - item = items[k]; - if (item) { - nes.push(item); - out = out.concat(item.f || []); - } - } - } - es = nes; - } - return out; - }; - /*\ - * eve.on - [ method ] - ** - * Binds given event handler with a given name. You can use wildcards “`*`” for the names: - | eve.on("*.under.*", f); - | eve("mouse.under.floor"); // triggers f - * Use @eve to trigger the listener. - ** - > Arguments - ** - - name (string) name of the event, dot (`.`) or slash (`/`) separated, with optional wildcards - - f (function) event handler function - ** - = (function) returned function accepts a single numeric parameter that represents z-index of the handler. It is an optional feature and only used when you need to ensure that some subset of handlers will be invoked in a given order, despite of the order of assignment. - > Example: - | eve.on("mouse", eatIt)(2); - | eve.on("mouse", scream); - | eve.on("mouse", catchIt)(1); - * This will ensure that `catchIt` function will be called before `eatIt`. - * - * If you want to put your handler before non-indexed handlers, specify a negative value. - * Note: I assume most of the time you don’t need to worry about z-index, but it’s nice to have this feature “just in case”. - \*/ - eve.on = function (name, f) { - name = String(name); - if (typeof f != "function") { - return function () {}; - } - var names = name.split(comaseparator); - for (var i = 0, ii = names.length; i < ii; i++) { - (function (name) { - var names = name.split(separator), - e = events, - exist; - for (var i = 0, ii = names.length; i < ii; i++) { - e = e.n; - e = e.hasOwnProperty(names[i]) && e[names[i]] || (e[names[i]] = {n: {}}); - } - e.f = e.f || []; - for (i = 0, ii = e.f.length; i < ii; i++) if (e.f[i] == f) { - exist = true; - break; - } - !exist && e.f.push(f); - }(names[i])); - } - return function (zIndex) { - if (+zIndex == +zIndex) { - f.zIndex = +zIndex; - } - }; - }; - /*\ - * eve.f - [ method ] - ** - * Returns function that will fire given event with optional arguments. - * Arguments that will be passed to the result function will be also - * concated to the list of final arguments. - | el.onclick = eve.f("click", 1, 2); - | eve.on("click", function (a, b, c) { - | console.log(a, b, c); // 1, 2, [event object] - | }); - > Arguments - - event (string) event name - - varargs (…) and any other arguments - = (function) possible event handler function - \*/ - eve.f = function (event) { - var attrs = [].slice.call(arguments, 1); - return function () { - eve.apply(null, [event, null].concat(attrs).concat([].slice.call(arguments, 0))); - }; - }; - /*\ - * eve.stop - [ method ] - ** - * Is used inside an event handler to stop the event, preventing any subsequent listeners from firing. - \*/ - eve.stop = function () { - stop = 1; - }; - /*\ - * eve.nt - [ method ] - ** - * Could be used inside event handler to figure out actual name of the event. - ** - > Arguments - ** - - subname (string) #optional subname of the event - ** - = (string) name of the event, if `subname` is not specified - * or - = (boolean) `true`, if current event’s name contains `subname` - \*/ - eve.nt = function (subname) { - if (subname) { - return new RegExp("(?:\\.|\\/|^)" + subname + "(?:\\.|\\/|$)").test(current_event); - } - return current_event; - }; - /*\ - * eve.nts - [ method ] - ** - * Could be used inside event handler to figure out actual name of the event. - ** - ** - = (array) names of the event - \*/ - eve.nts = function () { - return current_event.split(separator); - }; - /*\ - * eve.off - [ method ] - ** - * Removes given function from the list of event listeners assigned to given name. - * If no arguments specified all the events will be cleared. - ** - > Arguments - ** - - name (string) name of the event, dot (`.`) or slash (`/`) separated, with optional wildcards - - f (function) event handler function - \*/ - /*\ - * eve.unbind - [ method ] - ** - * See @eve.off - \*/ - eve.off = eve.unbind = function (name, f) { - if (!name) { - eve._events = events = {n: {}}; - return; - } - var names = name.split(comaseparator); - if (names.length > 1) { - for (var i = 0, ii = names.length; i < ii; i++) { - eve.off(names[i], f); - } - return; - } - names = name.split(separator); - var e, - key, - splice, - i, ii, j, jj, - cur = [events]; - for (i = 0, ii = names.length; i < ii; i++) { - for (j = 0; j < cur.length; j += splice.length - 2) { - splice = [j, 1]; - e = cur[j].n; - if (names[i] != wildcard) { - if (e[names[i]]) { - splice.push(e[names[i]]); - } - } else { - for (key in e) if (e[has](key)) { - splice.push(e[key]); - } - } - cur.splice.apply(cur, splice); - } - } - for (i = 0, ii = cur.length; i < ii; i++) { - e = cur[i]; - while (e.n) { - if (f) { - if (e.f) { - for (j = 0, jj = e.f.length; j < jj; j++) if (e.f[j] == f) { - e.f.splice(j, 1); - break; - } - !e.f.length && delete e.f; - } - for (key in e.n) if (e.n[has](key) && e.n[key].f) { - var funcs = e.n[key].f; - for (j = 0, jj = funcs.length; j < jj; j++) if (funcs[j] == f) { - funcs.splice(j, 1); - break; - } - !funcs.length && delete e.n[key].f; - } - } else { - delete e.f; - for (key in e.n) if (e.n[has](key) && e.n[key].f) { - delete e.n[key].f; - } - } - e = e.n; - } - } - }; - /*\ - * eve.once - [ method ] - ** - * Binds given event handler with a given name to only run once then unbind itself. - | eve.once("login", f); - | eve("login"); // triggers f - | eve("login"); // no listeners - * Use @eve to trigger the listener. - ** - > Arguments - ** - - name (string) name of the event, dot (`.`) or slash (`/`) separated, with optional wildcards - - f (function) event handler function - ** - = (function) same return function as @eve.on - \*/ - eve.once = function (name, f) { - var f2 = function () { - eve.unbind(name, f2); - return f.apply(this, arguments); - }; - return eve.on(name, f2); - }; - /*\ - * eve.version - [ property (string) ] - ** - * Current version of the library. - \*/ - eve.version = version; - eve.toString = function () { - return "You are running Eve " + version; - }; - (typeof module != "undefined" && module.exports) ? (module.exports = eve) : (typeof define === "function" && define.amd ? (define("eve", [], function() { return eve; })) : (glob.eve = eve)); -})(this); - -(function (glob, factory) { - // AMD support - if (typeof define == "function" && define.amd) { - // Define as an anonymous module - define(["eve"], function (eve) { - return factory(glob, eve); - }); - } else if (typeof exports != 'undefined') { - // Next for Node.js or CommonJS - var eve = require('eve'); - module.exports = factory(glob, eve); - } else { - // Browser globals (glob is window) - // Snap adds itself to window - factory(glob, glob.eve); - } -}(window || this, function (window, eve) { -// Copyright (c) 2013 Adobe Systems Incorporated. All rights reserved. -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// http://www.apache.org/licenses/LICENSE-2.0 -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -var mina = (function (eve) { - var animations = {}, - requestAnimFrame = window.requestAnimationFrame || - window.webkitRequestAnimationFrame || - window.mozRequestAnimationFrame || - window.oRequestAnimationFrame || - window.msRequestAnimationFrame || - function (callback) { - setTimeout(callback, 16); - }, - isArray = Array.isArray || function (a) { - return a instanceof Array || - Object.prototype.toString.call(a) == "[object Array]"; - }, - idgen = 0, - idprefix = "M" + (+new Date).toString(36), - ID = function () { - return idprefix + (idgen++).toString(36); - }, - diff = function (a, b, A, B) { - if (isArray(a)) { - res = []; - for (var i = 0, ii = a.length; i < ii; i++) { - res[i] = diff(a[i], b, A[i], B); - } - return res; - } - var dif = (A - a) / (B - b); - return function (bb) { - return a + dif * (bb - b); - }; - }, - timer = Date.now || function () { - return +new Date; - }, - sta = function (val) { - var a = this; - if (val == null) { - return a.s; - } - var ds = a.s - val; - a.b += a.dur * ds; - a.B += a.dur * ds; - a.s = val; - }, - speed = function (val) { - var a = this; - if (val == null) { - return a.spd; - } - a.spd = val; - }, - duration = function (val) { - var a = this; - if (val == null) { - return a.dur; - } - a.s = a.s * val / a.dur; - a.dur = val; - }, - stopit = function () { - var a = this; - delete animations[a.id]; - a.update(); - eve("mina.stop." + a.id, a); - }, - pause = function () { - var a = this; - if (a.pdif) { - return; - } - delete animations[a.id]; - a.update(); - a.pdif = a.get() - a.b; - }, - resume = function () { - var a = this; - if (!a.pdif) { - return; - } - a.b = a.get() - a.pdif; - delete a.pdif; - animations[a.id] = a; - }, - update = function () { - var a = this, - res; - if (isArray(a.start)) { - res = []; - for (var j = 0, jj = a.start.length; j < jj; j++) { - res[j] = +a.start[j] + - (a.end[j] - a.start[j]) * a.easing(a.s); - } - } else { - res = +a.start + (a.end - a.start) * a.easing(a.s); - } - a.set(res); - }, - frame = function () { - var len = 0; - for (var i in animations) if (animations.hasOwnProperty(i)) { - var a = animations[i], - b = a.get(), - res; - len++; - a.s = (b - a.b) / (a.dur / a.spd); - if (a.s >= 1) { - delete animations[i]; - a.s = 1; - len--; - (function (a) { - setTimeout(function () { - eve("mina.finish." + a.id, a); - }); - }(a)); - } - a.update(); - } - len && requestAnimFrame(frame); - }, - /*\ - * mina - [ method ] - ** - * Generic animation of numbers - ** - - a (number) start _slave_ number - - A (number) end _slave_ number - - b (number) start _master_ number (start time in general case) - - B (number) end _master_ number (end time in gereal case) - - get (function) getter of _master_ number (see @mina.time) - - set (function) setter of _slave_ number - - easing (function) #optional easing function, default is @mina.linear - = (object) animation descriptor - o { - o id (string) animation id, - o start (number) start _slave_ number, - o end (number) end _slave_ number, - o b (number) start _master_ number, - o s (number) animation status (0..1), - o dur (number) animation duration, - o spd (number) animation speed, - o get (function) getter of _master_ number (see @mina.time), - o set (function) setter of _slave_ number, - o easing (function) easing function, default is @mina.linear, - o status (function) status getter/setter, - o speed (function) speed getter/setter, - o duration (function) duration getter/setter, - o stop (function) animation stopper - o pause (function) pauses the animation - o resume (function) resumes the animation - o update (function) calles setter with the right value of the animation - o } - \*/ - mina = function (a, A, b, B, get, set, easing) { - var anim = { - id: ID(), - start: a, - end: A, - b: b, - s: 0, - dur: B - b, - spd: 1, - get: get, - set: set, - easing: easing || mina.linear, - status: sta, - speed: speed, - duration: duration, - stop: stopit, - pause: pause, - resume: resume, - update: update - }; - animations[anim.id] = anim; - var len = 0, i; - for (i in animations) if (animations.hasOwnProperty(i)) { - len++; - if (len == 2) { - break; - } - } - len == 1 && requestAnimFrame(frame); - return anim; - }; - /*\ - * mina.time - [ method ] - ** - * Returns the current time. Equivalent to: - | function () { - | return (new Date).getTime(); - | } - \*/ - mina.time = timer; - /*\ - * mina.getById - [ method ] - ** - * Returns an animation by its id - - id (string) animation's id - = (object) See @mina - \*/ - mina.getById = function (id) { - return animations[id] || null; - }; - - /*\ - * mina.linear - [ method ] - ** - * Default linear easing - - n (number) input 0..1 - = (number) output 0..1 - \*/ - mina.linear = function (n) { - return n; - }; - /*\ - * mina.easeout - [ method ] - ** - * Easeout easing - - n (number) input 0..1 - = (number) output 0..1 - \*/ - mina.easeout = function (n) { - return Math.pow(n, 1.7); - }; - /*\ - * mina.easein - [ method ] - ** - * Easein easing - - n (number) input 0..1 - = (number) output 0..1 - \*/ - mina.easein = function (n) { - return Math.pow(n, .48); - }; - /*\ - * mina.easeinout - [ method ] - ** - * Easeinout easing - - n (number) input 0..1 - = (number) output 0..1 - \*/ - mina.easeinout = function (n) { - if (n == 1) { - return 1; - } - if (n == 0) { - return 0; - } - var q = .48 - n / 1.04, - Q = Math.sqrt(.1734 + q * q), - x = Q - q, - X = Math.pow(Math.abs(x), 1 / 3) * (x < 0 ? -1 : 1), - y = -Q - q, - Y = Math.pow(Math.abs(y), 1 / 3) * (y < 0 ? -1 : 1), - t = X + Y + .5; - return (1 - t) * 3 * t * t + t * t * t; - }; - /*\ - * mina.backin - [ method ] - ** - * Backin easing - - n (number) input 0..1 - = (number) output 0..1 - \*/ - mina.backin = function (n) { - if (n == 1) { - return 1; - } - var s = 1.70158; - return n * n * ((s + 1) * n - s); - }; - /*\ - * mina.backout - [ method ] - ** - * Backout easing - - n (number) input 0..1 - = (number) output 0..1 - \*/ - mina.backout = function (n) { - if (n == 0) { - return 0; - } - n = n - 1; - var s = 1.70158; - return n * n * ((s + 1) * n + s) + 1; - }; - /*\ - * mina.elastic - [ method ] - ** - * Elastic easing - - n (number) input 0..1 - = (number) output 0..1 - \*/ - mina.elastic = function (n) { - if (n == !!n) { - return n; - } - return Math.pow(2, -10 * n) * Math.sin((n - .075) * - (2 * Math.PI) / .3) + 1; - }; - /*\ - * mina.bounce - [ method ] - ** - * Bounce easing - - n (number) input 0..1 - = (number) output 0..1 - \*/ - mina.bounce = function (n) { - var s = 7.5625, - p = 2.75, - l; - if (n < (1 / p)) { - l = s * n * n; - } else { - if (n < (2 / p)) { - n -= (1.5 / p); - l = s * n * n + .75; - } else { - if (n < (2.5 / p)) { - n -= (2.25 / p); - l = s * n * n + .9375; - } else { - n -= (2.625 / p); - l = s * n * n + .984375; - } - } - } - return l; - }; - window.mina = mina; - return mina; -})(typeof eve == "undefined" ? function () {} : eve); -// Copyright (c) 2013 - 2015 Adobe Systems Incorporated. All rights reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -var Snap = (function(root) { -Snap.version = "0.4.0"; -/*\ - * Snap - [ method ] - ** - * Creates a drawing surface or wraps existing SVG element. - ** - - width (number|string) width of surface - - height (number|string) height of surface - * or - - DOM (SVGElement) element to be wrapped into Snap structure - * or - - array (array) array of elements (will return set of elements) - * or - - query (string) CSS query selector - = (object) @Element -\*/ -function Snap(w, h) { - if (w) { - if (w.nodeType) { - return wrap(w); - } - if (is(w, "array") && Snap.set) { - return Snap.set.apply(Snap, w); - } - if (w instanceof Element) { - return w; - } - if (h == null) { - w = glob.doc.querySelector(String(w)); - return wrap(w); - } - } - w = w == null ? "100%" : w; - h = h == null ? "100%" : h; - return new Paper(w, h); -} -Snap.toString = function () { - return "Snap v" + this.version; -}; -Snap._ = {}; -var glob = { - win: root.window, - doc: root.window.document -}; -Snap._.glob = glob; -var has = "hasOwnProperty", - Str = String, - toFloat = parseFloat, - toInt = parseInt, - math = Math, - mmax = math.max, - mmin = math.min, - abs = math.abs, - pow = math.pow, - PI = math.PI, - round = math.round, - E = "", - S = " ", - objectToString = Object.prototype.toString, - ISURL = /^url\(['"]?([^\)]+?)['"]?\)$/i, - colourRegExp = /^\s*((#[a-f\d]{6})|(#[a-f\d]{3})|rgba?\(\s*([\d\.]+%?\s*,\s*[\d\.]+%?\s*,\s*[\d\.]+%?(?:\s*,\s*[\d\.]+%?)?)\s*\)|hsba?\(\s*([\d\.]+(?:deg|\xb0|%)?\s*,\s*[\d\.]+%?\s*,\s*[\d\.]+(?:%?\s*,\s*[\d\.]+)?%?)\s*\)|hsla?\(\s*([\d\.]+(?:deg|\xb0|%)?\s*,\s*[\d\.]+%?\s*,\s*[\d\.]+(?:%?\s*,\s*[\d\.]+)?%?)\s*\))\s*$/i, - bezierrg = /^(?:cubic-)?bezier\(([^,]+),([^,]+),([^,]+),([^\)]+)\)/, - reURLValue = /^url\(#?([^)]+)\)$/, - separator = Snap._.separator = /[,\s]+/, - whitespace = /[\s]/g, - commaSpaces = /[\s]*,[\s]*/, - hsrg = {hs: 1, rg: 1}, - pathCommand = /([a-z])[\s,]*((-?\d*\.?\d*(?:e[\-+]?\d+)?[\s]*,?[\s]*)+)/ig, - tCommand = /([rstm])[\s,]*((-?\d*\.?\d*(?:e[\-+]?\d+)?[\s]*,?[\s]*)+)/ig, - pathValues = /(-?\d*\.?\d*(?:e[\-+]?\\d+)?)[\s]*,?[\s]*/ig, - idgen = 0, - idprefix = "S" + (+new Date).toString(36), - ID = function (el) { - return (el && el.type ? el.type : E) + idprefix + (idgen++).toString(36); - }, - xlink = "http://www.w3.org/1999/xlink", - xmlns = "http://www.w3.org/2000/svg", - hub = {}, - URL = Snap.url = function (url) { - return "url('#" + url + "')"; - }; - -function $(el, attr) { - if (attr) { - if (el == "#text") { - el = glob.doc.createTextNode(attr.text || attr["#text"] || ""); - } - if (el == "#comment") { - el = glob.doc.createComment(attr.text || attr["#text"] || ""); - } - if (typeof el == "string") { - el = $(el); - } - if (typeof attr == "string") { - if (el.nodeType == 1) { - if (attr.substring(0, 6) == "xlink:") { - return el.getAttributeNS(xlink, attr.substring(6)); - } - if (attr.substring(0, 4) == "xml:") { - return el.getAttributeNS(xmlns, attr.substring(4)); - } - return el.getAttribute(attr); - } else if (attr == "text") { - return el.nodeValue; - } else { - return null; - } - } - if (el.nodeType == 1) { - for (var key in attr) if (attr[has](key)) { - var val = Str(attr[key]); - if (val) { - if (key.substring(0, 6) == "xlink:") { - el.setAttributeNS(xlink, key.substring(6), val); - } else if (key.substring(0, 4) == "xml:") { - el.setAttributeNS(xmlns, key.substring(4), val); - } else { - el.setAttribute(key, val); - } - } else { - el.removeAttribute(key); - } - } - } else if ("text" in attr) { - el.nodeValue = attr.text; - } - } else { - el = glob.doc.createElementNS(xmlns, el); - } - return el; -} -Snap._.$ = $; -Snap._.id = ID; -function getAttrs(el) { - var attrs = el.attributes, - name, - out = {}; - for (var i = 0; i < attrs.length; i++) { - if (attrs[i].namespaceURI == xlink) { - name = "xlink:"; - } else { - name = ""; - } - name += attrs[i].name; - out[name] = attrs[i].textContent; - } - return out; -} -function is(o, type) { - type = Str.prototype.toLowerCase.call(type); - if (type == "finite") { - return isFinite(o); - } - if (type == "array" && - (o instanceof Array || Array.isArray && Array.isArray(o))) { - return true; - } - return (type == "null" && o === null) || - (type == typeof o && o !== null) || - (type == "object" && o === Object(o)) || - objectToString.call(o).slice(8, -1).toLowerCase() == type; -} -/*\ - * Snap.format - [ method ] - ** - * Replaces construction of type `{}` to the corresponding argument - ** - - token (string) string to format - - json (object) object which properties are used as a replacement - = (string) formatted string - > Usage - | // this draws a rectangular shape equivalent to "M10,20h40v50h-40z" - | paper.path(Snap.format("M{x},{y}h{dim.width}v{dim.height}h{dim['negative width']}z", { - | x: 10, - | y: 20, - | dim: { - | width: 40, - | height: 50, - | "negative width": -40 - | } - | })); -\*/ -Snap.format = (function () { - var tokenRegex = /\{([^\}]+)\}/g, - objNotationRegex = /(?:(?:^|\.)(.+?)(?=\[|\.|$|\()|\[('|")(.+?)\2\])(\(\))?/g, // matches .xxxxx or ["xxxxx"] to run over object properties - replacer = function (all, key, obj) { - var res = obj; - key.replace(objNotationRegex, function (all, name, quote, quotedName, isFunc) { - name = name || quotedName; - if (res) { - if (name in res) { - res = res[name]; - } - typeof res == "function" && isFunc && (res = res()); - } - }); - res = (res == null || res == obj ? all : res) + ""; - return res; - }; - return function (str, obj) { - return Str(str).replace(tokenRegex, function (all, key) { - return replacer(all, key, obj); - }); - }; -})(); -function clone(obj) { - if (typeof obj == "function" || Object(obj) !== obj) { - return obj; - } - var res = new obj.constructor; - for (var key in obj) if (obj[has](key)) { - res[key] = clone(obj[key]); - } - return res; -} -Snap._.clone = clone; -function repush(array, item) { - for (var i = 0, ii = array.length; i < ii; i++) if (array[i] === item) { - return array.push(array.splice(i, 1)[0]); - } -} -function cacher(f, scope, postprocessor) { - function newf() { - var arg = Array.prototype.slice.call(arguments, 0), - args = arg.join("\u2400"), - cache = newf.cache = newf.cache || {}, - count = newf.count = newf.count || []; - if (cache[has](args)) { - repush(count, args); - return postprocessor ? postprocessor(cache[args]) : cache[args]; - } - count.length >= 1e3 && delete cache[count.shift()]; - count.push(args); - cache[args] = f.apply(scope, arg); - return postprocessor ? postprocessor(cache[args]) : cache[args]; - } - return newf; -} -Snap._.cacher = cacher; -function angle(x1, y1, x2, y2, x3, y3) { - if (x3 == null) { - var x = x1 - x2, - y = y1 - y2; - if (!x && !y) { - return 0; - } - return (180 + math.atan2(-y, -x) * 180 / PI + 360) % 360; - } else { - return angle(x1, y1, x3, y3) - angle(x2, y2, x3, y3); - } -} -function rad(deg) { - return deg % 360 * PI / 180; -} -function deg(rad) { - return rad * 180 / PI % 360; -} -function x_y() { - return this.x + S + this.y; -} -function x_y_w_h() { - return this.x + S + this.y + S + this.width + " \xd7 " + this.height; -} - -/*\ - * Snap.rad - [ method ] - ** - * Transform angle to radians - - deg (number) angle in degrees - = (number) angle in radians -\*/ -Snap.rad = rad; -/*\ - * Snap.deg - [ method ] - ** - * Transform angle to degrees - - rad (number) angle in radians - = (number) angle in degrees -\*/ -Snap.deg = deg; -/*\ - * Snap.sin - [ method ] - ** - * Equivalent to `Math.sin()` only works with degrees, not radians. - - angle (number) angle in degrees - = (number) sin -\*/ -Snap.sin = function (angle) { - return math.sin(Snap.rad(angle)); -}; -/*\ - * Snap.tan - [ method ] - ** - * Equivalent to `Math.tan()` only works with degrees, not radians. - - angle (number) angle in degrees - = (number) tan -\*/ -Snap.tan = function (angle) { - return math.tan(Snap.rad(angle)); -}; -/*\ - * Snap.cos - [ method ] - ** - * Equivalent to `Math.cos()` only works with degrees, not radians. - - angle (number) angle in degrees - = (number) cos -\*/ -Snap.cos = function (angle) { - return math.cos(Snap.rad(angle)); -}; -/*\ - * Snap.asin - [ method ] - ** - * Equivalent to `Math.asin()` only works with degrees, not radians. - - num (number) value - = (number) asin in degrees -\*/ -Snap.asin = function (num) { - return Snap.deg(math.asin(num)); -}; -/*\ - * Snap.acos - [ method ] - ** - * Equivalent to `Math.acos()` only works with degrees, not radians. - - num (number) value - = (number) acos in degrees -\*/ -Snap.acos = function (num) { - return Snap.deg(math.acos(num)); -}; -/*\ - * Snap.atan - [ method ] - ** - * Equivalent to `Math.atan()` only works with degrees, not radians. - - num (number) value - = (number) atan in degrees -\*/ -Snap.atan = function (num) { - return Snap.deg(math.atan(num)); -}; -/*\ - * Snap.atan2 - [ method ] - ** - * Equivalent to `Math.atan2()` only works with degrees, not radians. - - num (number) value - = (number) atan2 in degrees -\*/ -Snap.atan2 = function (num) { - return Snap.deg(math.atan2(num)); -}; -/*\ - * Snap.angle - [ method ] - ** - * Returns an angle between two or three points - > Parameters - - x1 (number) x coord of first point - - y1 (number) y coord of first point - - x2 (number) x coord of second point - - y2 (number) y coord of second point - - x3 (number) #optional x coord of third point - - y3 (number) #optional y coord of third point - = (number) angle in degrees -\*/ -Snap.angle = angle; -/*\ - * Snap.len - [ method ] - ** - * Returns distance between two points - > Parameters - - x1 (number) x coord of first point - - y1 (number) y coord of first point - - x2 (number) x coord of second point - - y2 (number) y coord of second point - = (number) distance -\*/ -Snap.len = function (x1, y1, x2, y2) { - return Math.sqrt(Snap.len2(x1, y1, x2, y2)); -}; -/*\ - * Snap.len2 - [ method ] - ** - * Returns squared distance between two points - > Parameters - - x1 (number) x coord of first point - - y1 (number) y coord of first point - - x2 (number) x coord of second point - - y2 (number) y coord of second point - = (number) distance -\*/ -Snap.len2 = function (x1, y1, x2, y2) { - return (x1 - x2) * (x1 - x2) + (y1 - y2) * (y1 - y2); -}; -/*\ - * Snap.closestPoint - [ method ] - ** - * Returns closest point to a given one on a given path. - > Parameters - - path (Element) path element - - x (number) x coord of a point - - y (number) y coord of a point - = (object) in format - { - x (number) x coord of the point on the path - y (number) y coord of the point on the path - length (number) length of the path to the point - distance (number) distance from the given point to the path - } -\*/ -// Copied from http://bl.ocks.org/mbostock/8027637 -Snap.closestPoint = function (path, x, y) { - function distance2(p) { - var dx = p.x - x, - dy = p.y - y; - return dx * dx + dy * dy; - } - var pathNode = path.node, - pathLength = pathNode.getTotalLength(), - precision = pathLength / pathNode.pathSegList.numberOfItems * .125, - best, - bestLength, - bestDistance = Infinity; - - // linear scan for coarse approximation - for (var scan, scanLength = 0, scanDistance; scanLength <= pathLength; scanLength += precision) { - if ((scanDistance = distance2(scan = pathNode.getPointAtLength(scanLength))) < bestDistance) { - best = scan, bestLength = scanLength, bestDistance = scanDistance; - } - } - - // binary search for precise estimate - precision *= .5; - while (precision > .5) { - var before, - after, - beforeLength, - afterLength, - beforeDistance, - afterDistance; - if ((beforeLength = bestLength - precision) >= 0 && (beforeDistance = distance2(before = pathNode.getPointAtLength(beforeLength))) < bestDistance) { - best = before, bestLength = beforeLength, bestDistance = beforeDistance; - } else if ((afterLength = bestLength + precision) <= pathLength && (afterDistance = distance2(after = pathNode.getPointAtLength(afterLength))) < bestDistance) { - best = after, bestLength = afterLength, bestDistance = afterDistance; - } else { - precision *= .5; - } - } - - best = { - x: best.x, - y: best.y, - length: bestLength, - distance: Math.sqrt(bestDistance) - }; - return best; -} -/*\ - * Snap.is - [ method ] - ** - * Handy replacement for the `typeof` operator - - o (…) any object or primitive - - type (string) name of the type, e.g., `string`, `function`, `number`, etc. - = (boolean) `true` if given value is of given type -\*/ -Snap.is = is; -/*\ - * Snap.snapTo - [ method ] - ** - * Snaps given value to given grid - - values (array|number) given array of values or step of the grid - - value (number) value to adjust - - tolerance (number) #optional maximum distance to the target value that would trigger the snap. Default is `10`. - = (number) adjusted value -\*/ -Snap.snapTo = function (values, value, tolerance) { - tolerance = is(tolerance, "finite") ? tolerance : 10; - if (is(values, "array")) { - var i = values.length; - while (i--) if (abs(values[i] - value) <= tolerance) { - return values[i]; - } - } else { - values = +values; - var rem = value % values; - if (rem < tolerance) { - return value - rem; - } - if (rem > values - tolerance) { - return value - rem + values; - } - } - return value; -}; -// Colour -/*\ - * Snap.getRGB - [ method ] - ** - * Parses color string as RGB object - - color (string) color string in one of the following formats: - #
    - #
  • Color name (red, green, cornflowerblue, etc)
  • - #
  • #••• — shortened HTML color: (#000, #fc0, etc.)
  • - #
  • #•••••• — full length HTML color: (#000000, #bd2300)
  • - #
  • rgb(•••, •••, •••) — red, green and blue channels values: (rgb(200, 100, 0))
  • - #
  • rgba(•••, •••, •••, •••) — also with opacity
  • - #
  • rgb(•••%, •••%, •••%) — same as above, but in %: (rgb(100%, 175%, 0%))
  • - #
  • rgba(•••%, •••%, •••%, •••%) — also with opacity
  • - #
  • hsb(•••, •••, •••) — hue, saturation and brightness values: (hsb(0.5, 0.25, 1))
  • - #
  • hsba(•••, •••, •••, •••) — also with opacity
  • - #
  • hsb(•••%, •••%, •••%) — same as above, but in %
  • - #
  • hsba(•••%, •••%, •••%, •••%) — also with opacity
  • - #
  • hsl(•••, •••, •••) — hue, saturation and luminosity values: (hsb(0.5, 0.25, 0.5))
  • - #
  • hsla(•••, •••, •••, •••) — also with opacity
  • - #
  • hsl(•••%, •••%, •••%) — same as above, but in %
  • - #
  • hsla(•••%, •••%, •••%, •••%) — also with opacity
  • - #
- * Note that `%` can be used any time: `rgb(20%, 255, 50%)`. - = (object) RGB object in the following format: - o { - o r (number) red, - o g (number) green, - o b (number) blue, - o hex (string) color in HTML/CSS format: #••••••, - o error (boolean) true if string can't be parsed - o } -\*/ -Snap.getRGB = cacher(function (colour) { - if (!colour || !!((colour = Str(colour)).indexOf("-") + 1)) { - return {r: -1, g: -1, b: -1, hex: "none", error: 1, toString: rgbtoString}; - } - if (colour == "none") { - return {r: -1, g: -1, b: -1, hex: "none", toString: rgbtoString}; - } - !(hsrg[has](colour.toLowerCase().substring(0, 2)) || colour.charAt() == "#") && (colour = toHex(colour)); - if (!colour) { - return {r: -1, g: -1, b: -1, hex: "none", error: 1, toString: rgbtoString}; - } - var res, - red, - green, - blue, - opacity, - t, - values, - rgb = colour.match(colourRegExp); - if (rgb) { - if (rgb[2]) { - blue = toInt(rgb[2].substring(5), 16); - green = toInt(rgb[2].substring(3, 5), 16); - red = toInt(rgb[2].substring(1, 3), 16); - } - if (rgb[3]) { - blue = toInt((t = rgb[3].charAt(3)) + t, 16); - green = toInt((t = rgb[3].charAt(2)) + t, 16); - red = toInt((t = rgb[3].charAt(1)) + t, 16); - } - if (rgb[4]) { - values = rgb[4].split(commaSpaces); - red = toFloat(values[0]); - values[0].slice(-1) == "%" && (red *= 2.55); - green = toFloat(values[1]); - values[1].slice(-1) == "%" && (green *= 2.55); - blue = toFloat(values[2]); - values[2].slice(-1) == "%" && (blue *= 2.55); - rgb[1].toLowerCase().slice(0, 4) == "rgba" && (opacity = toFloat(values[3])); - values[3] && values[3].slice(-1) == "%" && (opacity /= 100); - } - if (rgb[5]) { - values = rgb[5].split(commaSpaces); - red = toFloat(values[0]); - values[0].slice(-1) == "%" && (red /= 100); - green = toFloat(values[1]); - values[1].slice(-1) == "%" && (green /= 100); - blue = toFloat(values[2]); - values[2].slice(-1) == "%" && (blue /= 100); - (values[0].slice(-3) == "deg" || values[0].slice(-1) == "\xb0") && (red /= 360); - rgb[1].toLowerCase().slice(0, 4) == "hsba" && (opacity = toFloat(values[3])); - values[3] && values[3].slice(-1) == "%" && (opacity /= 100); - return Snap.hsb2rgb(red, green, blue, opacity); - } - if (rgb[6]) { - values = rgb[6].split(commaSpaces); - red = toFloat(values[0]); - values[0].slice(-1) == "%" && (red /= 100); - green = toFloat(values[1]); - values[1].slice(-1) == "%" && (green /= 100); - blue = toFloat(values[2]); - values[2].slice(-1) == "%" && (blue /= 100); - (values[0].slice(-3) == "deg" || values[0].slice(-1) == "\xb0") && (red /= 360); - rgb[1].toLowerCase().slice(0, 4) == "hsla" && (opacity = toFloat(values[3])); - values[3] && values[3].slice(-1) == "%" && (opacity /= 100); - return Snap.hsl2rgb(red, green, blue, opacity); - } - red = mmin(math.round(red), 255); - green = mmin(math.round(green), 255); - blue = mmin(math.round(blue), 255); - opacity = mmin(mmax(opacity, 0), 1); - rgb = {r: red, g: green, b: blue, toString: rgbtoString}; - rgb.hex = "#" + (16777216 | blue | (green << 8) | (red << 16)).toString(16).slice(1); - rgb.opacity = is(opacity, "finite") ? opacity : 1; - return rgb; - } - return {r: -1, g: -1, b: -1, hex: "none", error: 1, toString: rgbtoString}; -}, Snap); -/*\ - * Snap.hsb - [ method ] - ** - * Converts HSB values to a hex representation of the color - - h (number) hue - - s (number) saturation - - b (number) value or brightness - = (string) hex representation of the color -\*/ -Snap.hsb = cacher(function (h, s, b) { - return Snap.hsb2rgb(h, s, b).hex; -}); -/*\ - * Snap.hsl - [ method ] - ** - * Converts HSL values to a hex representation of the color - - h (number) hue - - s (number) saturation - - l (number) luminosity - = (string) hex representation of the color -\*/ -Snap.hsl = cacher(function (h, s, l) { - return Snap.hsl2rgb(h, s, l).hex; -}); -/*\ - * Snap.rgb - [ method ] - ** - * Converts RGB values to a hex representation of the color - - r (number) red - - g (number) green - - b (number) blue - = (string) hex representation of the color -\*/ -Snap.rgb = cacher(function (r, g, b, o) { - if (is(o, "finite")) { - var round = math.round; - return "rgba(" + [round(r), round(g), round(b), +o.toFixed(2)] + ")"; - } - return "#" + (16777216 | b | (g << 8) | (r << 16)).toString(16).slice(1); -}); -var toHex = function (color) { - var i = glob.doc.getElementsByTagName("head")[0] || glob.doc.getElementsByTagName("svg")[0], - red = "rgb(255, 0, 0)"; - toHex = cacher(function (color) { - if (color.toLowerCase() == "red") { - return red; - } - i.style.color = red; - i.style.color = color; - var out = glob.doc.defaultView.getComputedStyle(i, E).getPropertyValue("color"); - return out == red ? null : out; - }); - return toHex(color); -}, -hsbtoString = function () { - return "hsb(" + [this.h, this.s, this.b] + ")"; -}, -hsltoString = function () { - return "hsl(" + [this.h, this.s, this.l] + ")"; -}, -rgbtoString = function () { - return this.opacity == 1 || this.opacity == null ? - this.hex : - "rgba(" + [this.r, this.g, this.b, this.opacity] + ")"; -}, -prepareRGB = function (r, g, b) { - if (g == null && is(r, "object") && "r" in r && "g" in r && "b" in r) { - b = r.b; - g = r.g; - r = r.r; - } - if (g == null && is(r, string)) { - var clr = Snap.getRGB(r); - r = clr.r; - g = clr.g; - b = clr.b; - } - if (r > 1 || g > 1 || b > 1) { - r /= 255; - g /= 255; - b /= 255; - } - - return [r, g, b]; -}, -packageRGB = function (r, g, b, o) { - r = math.round(r * 255); - g = math.round(g * 255); - b = math.round(b * 255); - var rgb = { - r: r, - g: g, - b: b, - opacity: is(o, "finite") ? o : 1, - hex: Snap.rgb(r, g, b), - toString: rgbtoString - }; - is(o, "finite") && (rgb.opacity = o); - return rgb; -}; -/*\ - * Snap.color - [ method ] - ** - * Parses the color string and returns an object featuring the color's component values - - clr (string) color string in one of the supported formats (see @Snap.getRGB) - = (object) Combined RGB/HSB object in the following format: - o { - o r (number) red, - o g (number) green, - o b (number) blue, - o hex (string) color in HTML/CSS format: #••••••, - o error (boolean) `true` if string can't be parsed, - o h (number) hue, - o s (number) saturation, - o v (number) value (brightness), - o l (number) lightness - o } -\*/ -Snap.color = function (clr) { - var rgb; - if (is(clr, "object") && "h" in clr && "s" in clr && "b" in clr) { - rgb = Snap.hsb2rgb(clr); - clr.r = rgb.r; - clr.g = rgb.g; - clr.b = rgb.b; - clr.opacity = 1; - clr.hex = rgb.hex; - } else if (is(clr, "object") && "h" in clr && "s" in clr && "l" in clr) { - rgb = Snap.hsl2rgb(clr); - clr.r = rgb.r; - clr.g = rgb.g; - clr.b = rgb.b; - clr.opacity = 1; - clr.hex = rgb.hex; - } else { - if (is(clr, "string")) { - clr = Snap.getRGB(clr); - } - if (is(clr, "object") && "r" in clr && "g" in clr && "b" in clr && !("error" in clr)) { - rgb = Snap.rgb2hsl(clr); - clr.h = rgb.h; - clr.s = rgb.s; - clr.l = rgb.l; - rgb = Snap.rgb2hsb(clr); - clr.v = rgb.b; - } else { - clr = {hex: "none"}; - clr.r = clr.g = clr.b = clr.h = clr.s = clr.v = clr.l = -1; - clr.error = 1; - } - } - clr.toString = rgbtoString; - return clr; -}; -/*\ - * Snap.hsb2rgb - [ method ] - ** - * Converts HSB values to an RGB object - - h (number) hue - - s (number) saturation - - v (number) value or brightness - = (object) RGB object in the following format: - o { - o r (number) red, - o g (number) green, - o b (number) blue, - o hex (string) color in HTML/CSS format: #•••••• - o } -\*/ -Snap.hsb2rgb = function (h, s, v, o) { - if (is(h, "object") && "h" in h && "s" in h && "b" in h) { - v = h.b; - s = h.s; - o = h.o; - h = h.h; - } - h *= 360; - var R, G, B, X, C; - h = (h % 360) / 60; - C = v * s; - X = C * (1 - abs(h % 2 - 1)); - R = G = B = v - C; - - h = ~~h; - R += [C, X, 0, 0, X, C][h]; - G += [X, C, C, X, 0, 0][h]; - B += [0, 0, X, C, C, X][h]; - return packageRGB(R, G, B, o); -}; -/*\ - * Snap.hsl2rgb - [ method ] - ** - * Converts HSL values to an RGB object - - h (number) hue - - s (number) saturation - - l (number) luminosity - = (object) RGB object in the following format: - o { - o r (number) red, - o g (number) green, - o b (number) blue, - o hex (string) color in HTML/CSS format: #•••••• - o } -\*/ -Snap.hsl2rgb = function (h, s, l, o) { - if (is(h, "object") && "h" in h && "s" in h && "l" in h) { - l = h.l; - s = h.s; - h = h.h; - } - if (h > 1 || s > 1 || l > 1) { - h /= 360; - s /= 100; - l /= 100; - } - h *= 360; - var R, G, B, X, C; - h = (h % 360) / 60; - C = 2 * s * (l < .5 ? l : 1 - l); - X = C * (1 - abs(h % 2 - 1)); - R = G = B = l - C / 2; - - h = ~~h; - R += [C, X, 0, 0, X, C][h]; - G += [X, C, C, X, 0, 0][h]; - B += [0, 0, X, C, C, X][h]; - return packageRGB(R, G, B, o); -}; -/*\ - * Snap.rgb2hsb - [ method ] - ** - * Converts RGB values to an HSB object - - r (number) red - - g (number) green - - b (number) blue - = (object) HSB object in the following format: - o { - o h (number) hue, - o s (number) saturation, - o b (number) brightness - o } -\*/ -Snap.rgb2hsb = function (r, g, b) { - b = prepareRGB(r, g, b); - r = b[0]; - g = b[1]; - b = b[2]; - - var H, S, V, C; - V = mmax(r, g, b); - C = V - mmin(r, g, b); - H = (C == 0 ? null : - V == r ? (g - b) / C : - V == g ? (b - r) / C + 2 : - (r - g) / C + 4 - ); - H = ((H + 360) % 6) * 60 / 360; - S = C == 0 ? 0 : C / V; - return {h: H, s: S, b: V, toString: hsbtoString}; -}; -/*\ - * Snap.rgb2hsl - [ method ] - ** - * Converts RGB values to an HSL object - - r (number) red - - g (number) green - - b (number) blue - = (object) HSL object in the following format: - o { - o h (number) hue, - o s (number) saturation, - o l (number) luminosity - o } -\*/ -Snap.rgb2hsl = function (r, g, b) { - b = prepareRGB(r, g, b); - r = b[0]; - g = b[1]; - b = b[2]; - - var H, S, L, M, m, C; - M = mmax(r, g, b); - m = mmin(r, g, b); - C = M - m; - H = (C == 0 ? null : - M == r ? (g - b) / C : - M == g ? (b - r) / C + 2 : - (r - g) / C + 4); - H = ((H + 360) % 6) * 60 / 360; - L = (M + m) / 2; - S = (C == 0 ? 0 : - L < .5 ? C / (2 * L) : - C / (2 - 2 * L)); - return {h: H, s: S, l: L, toString: hsltoString}; -}; - -// Transformations -/*\ - * Snap.parsePathString - [ method ] - ** - * Utility method - ** - * Parses given path string into an array of arrays of path segments - - pathString (string|array) path string or array of segments (in the last case it is returned straight away) - = (array) array of segments -\*/ -Snap.parsePathString = function (pathString) { - if (!pathString) { - return null; - } - var pth = Snap.path(pathString); - if (pth.arr) { - return Snap.path.clone(pth.arr); - } - - var paramCounts = {a: 7, c: 6, o: 2, h: 1, l: 2, m: 2, r: 4, q: 4, s: 4, t: 2, v: 1, u: 3, z: 0}, - data = []; - if (is(pathString, "array") && is(pathString[0], "array")) { // rough assumption - data = Snap.path.clone(pathString); - } - if (!data.length) { - Str(pathString).replace(pathCommand, function (a, b, c) { - var params = [], - name = b.toLowerCase(); - c.replace(pathValues, function (a, b) { - b && params.push(+b); - }); - if (name == "m" && params.length > 2) { - data.push([b].concat(params.splice(0, 2))); - name = "l"; - b = b == "m" ? "l" : "L"; - } - if (name == "o" && params.length == 1) { - data.push([b, params[0]]); - } - if (name == "r") { - data.push([b].concat(params)); - } else while (params.length >= paramCounts[name]) { - data.push([b].concat(params.splice(0, paramCounts[name]))); - if (!paramCounts[name]) { - break; - } - } - }); - } - data.toString = Snap.path.toString; - pth.arr = Snap.path.clone(data); - return data; -}; -/*\ - * Snap.parseTransformString - [ method ] - ** - * Utility method - ** - * Parses given transform string into an array of transformations - - TString (string|array) transform string or array of transformations (in the last case it is returned straight away) - = (array) array of transformations -\*/ -var parseTransformString = Snap.parseTransformString = function (TString) { - if (!TString) { - return null; - } - var paramCounts = {r: 3, s: 4, t: 2, m: 6}, - data = []; - if (is(TString, "array") && is(TString[0], "array")) { // rough assumption - data = Snap.path.clone(TString); - } - if (!data.length) { - Str(TString).replace(tCommand, function (a, b, c) { - var params = [], - name = b.toLowerCase(); - c.replace(pathValues, function (a, b) { - b && params.push(+b); - }); - data.push([b].concat(params)); - }); - } - data.toString = Snap.path.toString; - return data; -}; -function svgTransform2string(tstr) { - var res = []; - tstr = tstr.replace(/(?:^|\s)(\w+)\(([^)]+)\)/g, function (all, name, params) { - params = params.split(/\s*,\s*|\s+/); - if (name == "rotate" && params.length == 1) { - params.push(0, 0); - } - if (name == "scale") { - if (params.length > 2) { - params = params.slice(0, 2); - } else if (params.length == 2) { - params.push(0, 0); - } - if (params.length == 1) { - params.push(params[0], 0, 0); - } - } - if (name == "skewX") { - res.push(["m", 1, 0, math.tan(rad(params[0])), 1, 0, 0]); - } else if (name == "skewY") { - res.push(["m", 1, math.tan(rad(params[0])), 0, 1, 0, 0]); - } else { - res.push([name.charAt(0)].concat(params)); - } - return all; - }); - return res; -} -Snap._.svgTransform2string = svgTransform2string; -Snap._.rgTransform = /^[a-z][\s]*-?\.?\d/i; -function transform2matrix(tstr, bbox) { - var tdata = parseTransformString(tstr), - m = new Snap.Matrix; - if (tdata) { - for (var i = 0, ii = tdata.length; i < ii; i++) { - var t = tdata[i], - tlen = t.length, - command = Str(t[0]).toLowerCase(), - absolute = t[0] != command, - inver = absolute ? m.invert() : 0, - x1, - y1, - x2, - y2, - bb; - if (command == "t" && tlen == 2){ - m.translate(t[1], 0); - } else if (command == "t" && tlen == 3) { - if (absolute) { - x1 = inver.x(0, 0); - y1 = inver.y(0, 0); - x2 = inver.x(t[1], t[2]); - y2 = inver.y(t[1], t[2]); - m.translate(x2 - x1, y2 - y1); - } else { - m.translate(t[1], t[2]); - } - } else if (command == "r") { - if (tlen == 2) { - bb = bb || bbox; - m.rotate(t[1], bb.x + bb.width / 2, bb.y + bb.height / 2); - } else if (tlen == 4) { - if (absolute) { - x2 = inver.x(t[2], t[3]); - y2 = inver.y(t[2], t[3]); - m.rotate(t[1], x2, y2); - } else { - m.rotate(t[1], t[2], t[3]); - } - } - } else if (command == "s") { - if (tlen == 2 || tlen == 3) { - bb = bb || bbox; - m.scale(t[1], t[tlen - 1], bb.x + bb.width / 2, bb.y + bb.height / 2); - } else if (tlen == 4) { - if (absolute) { - x2 = inver.x(t[2], t[3]); - y2 = inver.y(t[2], t[3]); - m.scale(t[1], t[1], x2, y2); - } else { - m.scale(t[1], t[1], t[2], t[3]); - } - } else if (tlen == 5) { - if (absolute) { - x2 = inver.x(t[3], t[4]); - y2 = inver.y(t[3], t[4]); - m.scale(t[1], t[2], x2, y2); - } else { - m.scale(t[1], t[2], t[3], t[4]); - } - } - } else if (command == "m" && tlen == 7) { - m.add(t[1], t[2], t[3], t[4], t[5], t[6]); - } - } - } - return m; -} -Snap._.transform2matrix = transform2matrix; -Snap._unit2px = unit2px; -var contains = glob.doc.contains || glob.doc.compareDocumentPosition ? - function (a, b) { - var adown = a.nodeType == 9 ? a.documentElement : a, - bup = b && b.parentNode; - return a == bup || !!(bup && bup.nodeType == 1 && ( - adown.contains ? - adown.contains(bup) : - a.compareDocumentPosition && a.compareDocumentPosition(bup) & 16 - )); - } : - function (a, b) { - if (b) { - while (b) { - b = b.parentNode; - if (b == a) { - return true; - } - } - } - return false; - }; -function getSomeDefs(el) { - var p = (el.node.ownerSVGElement && wrap(el.node.ownerSVGElement)) || - (el.node.parentNode && wrap(el.node.parentNode)) || - Snap.select("svg") || - Snap(0, 0), - pdefs = p.select("defs"), - defs = pdefs == null ? false : pdefs.node; - if (!defs) { - defs = make("defs", p.node).node; - } - return defs; -} -function getSomeSVG(el) { - return el.node.ownerSVGElement && wrap(el.node.ownerSVGElement) || Snap.select("svg"); -} -Snap._.getSomeDefs = getSomeDefs; -Snap._.getSomeSVG = getSomeSVG; -function unit2px(el, name, value) { - var svg = getSomeSVG(el).node, - out = {}, - mgr = svg.querySelector(".svg---mgr"); - if (!mgr) { - mgr = $("rect"); - $(mgr, {x: -9e9, y: -9e9, width: 10, height: 10, "class": "svg---mgr", fill: "none"}); - svg.appendChild(mgr); - } - function getW(val) { - if (val == null) { - return E; - } - if (val == +val) { - return val; - } - $(mgr, {width: val}); - try { - return mgr.getBBox().width; - } catch (e) { - return 0; - } - } - function getH(val) { - if (val == null) { - return E; - } - if (val == +val) { - return val; - } - $(mgr, {height: val}); - try { - return mgr.getBBox().height; - } catch (e) { - return 0; - } - } - function set(nam, f) { - if (name == null) { - out[nam] = f(el.attr(nam) || 0); - } else if (nam == name) { - out = f(value == null ? el.attr(nam) || 0 : value); - } - } - switch (el.type) { - case "rect": - set("rx", getW); - set("ry", getH); - case "image": - set("width", getW); - set("height", getH); - case "text": - set("x", getW); - set("y", getH); - break; - case "circle": - set("cx", getW); - set("cy", getH); - set("r", getW); - break; - case "ellipse": - set("cx", getW); - set("cy", getH); - set("rx", getW); - set("ry", getH); - break; - case "line": - set("x1", getW); - set("x2", getW); - set("y1", getH); - set("y2", getH); - break; - case "marker": - set("refX", getW); - set("markerWidth", getW); - set("refY", getH); - set("markerHeight", getH); - break; - case "radialGradient": - set("fx", getW); - set("fy", getH); - break; - case "tspan": - set("dx", getW); - set("dy", getH); - break; - default: - set(name, getW); - } - svg.removeChild(mgr); - return out; -} -/*\ - * Snap.select - [ method ] - ** - * Wraps a DOM element specified by CSS selector as @Element - - query (string) CSS selector of the element - = (Element) the current element -\*/ -Snap.select = function (query) { - query = Str(query).replace(/([^\\]):/g, "$1\\:"); - return wrap(glob.doc.querySelector(query)); -}; -/*\ - * Snap.selectAll - [ method ] - ** - * Wraps DOM elements specified by CSS selector as set or array of @Element - - query (string) CSS selector of the element - = (Element) the current element -\*/ -Snap.selectAll = function (query) { - var nodelist = glob.doc.querySelectorAll(query), - set = (Snap.set || Array)(); - for (var i = 0; i < nodelist.length; i++) { - set.push(wrap(nodelist[i])); - } - return set; -}; - -function add2group(list) { - if (!is(list, "array")) { - list = Array.prototype.slice.call(arguments, 0); - } - var i = 0, - j = 0, - node = this.node; - while (this[i]) delete this[i++]; - for (i = 0; i < list.length; i++) { - if (list[i].type == "set") { - list[i].forEach(function (el) { - node.appendChild(el.node); - }); - } else { - node.appendChild(list[i].node); - } - } - var children = node.childNodes; - for (i = 0; i < children.length; i++) { - this[j++] = wrap(children[i]); - } - return this; -} -// Hub garbage collector every 10s -setInterval(function () { - for (var key in hub) if (hub[has](key)) { - var el = hub[key], - node = el.node; - if (el.type != "svg" && !node.ownerSVGElement || el.type == "svg" && (!node.parentNode || "ownerSVGElement" in node.parentNode && !node.ownerSVGElement)) { - delete hub[key]; - } - } -}, 1e4); -function Element(el) { - if (el.snap in hub) { - return hub[el.snap]; - } - var svg; - try { - svg = el.ownerSVGElement; - } catch(e) {} - /*\ - * Element.node - [ property (object) ] - ** - * Gives you a reference to the DOM object, so you can assign event handlers or just mess around. - > Usage - | // draw a circle at coordinate 10,10 with radius of 10 - | var c = paper.circle(10, 10, 10); - | c.node.onclick = function () { - | c.attr("fill", "red"); - | }; - \*/ - this.node = el; - if (svg) { - this.paper = new Paper(svg); - } - /*\ - * Element.type - [ property (string) ] - ** - * SVG tag name of the given element. - \*/ - this.type = el.tagName || el.nodeName; - var id = this.id = ID(this); - this.anims = {}; - this._ = { - transform: [] - }; - el.snap = id; - hub[id] = this; - if (this.type == "g") { - this.add = add2group; - } - if (this.type in {g: 1, mask: 1, pattern: 1, symbol: 1}) { - for (var method in Paper.prototype) if (Paper.prototype[has](method)) { - this[method] = Paper.prototype[method]; - } - } -} - /*\ - * Element.attr - [ method ] - ** - * Gets or sets given attributes of the element. - ** - - params (object) contains key-value pairs of attributes you want to set - * or - - param (string) name of the attribute - = (Element) the current element - * or - = (string) value of attribute - > Usage - | el.attr({ - | fill: "#fc0", - | stroke: "#000", - | strokeWidth: 2, // CamelCase... - | "fill-opacity": 0.5, // or dash-separated names - | width: "*=2" // prefixed values - | }); - | console.log(el.attr("fill")); // #fc0 - * Prefixed values in format `"+=10"` supported. All four operations - * (`+`, `-`, `*` and `/`) could be used. Optionally you can use units for `+` - * and `-`: `"+=2em"`. - \*/ - Element.prototype.attr = function (params, value) { - var el = this, - node = el.node; - if (!params) { - if (node.nodeType != 1) { - return { - text: node.nodeValue - }; - } - var attr = node.attributes, - out = {}; - for (var i = 0, ii = attr.length; i < ii; i++) { - out[attr[i].nodeName] = attr[i].nodeValue; - } - return out; - } - if (is(params, "string")) { - if (arguments.length > 1) { - var json = {}; - json[params] = value; - params = json; - } else { - return eve("snap.util.getattr." + params, el).firstDefined(); - } - } - for (var att in params) { - if (params[has](att)) { - eve("snap.util.attr." + att, el, params[att]); - } - } - return el; - }; -/*\ - * Snap.parse - [ method ] - ** - * Parses SVG fragment and converts it into a @Fragment - ** - - svg (string) SVG string - = (Fragment) the @Fragment -\*/ -Snap.parse = function (svg) { - var f = glob.doc.createDocumentFragment(), - full = true, - div = glob.doc.createElement("div"); - svg = Str(svg); - if (!svg.match(/^\s*<\s*svg(?:\s|>)/)) { - svg = "" + svg + ""; - full = false; - } - div.innerHTML = svg; - svg = div.getElementsByTagName("svg")[0]; - if (svg) { - if (full) { - f = svg; - } else { - while (svg.firstChild) { - f.appendChild(svg.firstChild); - } - } - } - return new Fragment(f); -}; -function Fragment(frag) { - this.node = frag; -} -/*\ - * Snap.fragment - [ method ] - ** - * Creates a DOM fragment from a given list of elements or strings - ** - - varargs (…) SVG string - = (Fragment) the @Fragment -\*/ -Snap.fragment = function () { - var args = Array.prototype.slice.call(arguments, 0), - f = glob.doc.createDocumentFragment(); - for (var i = 0, ii = args.length; i < ii; i++) { - var item = args[i]; - if (item.node && item.node.nodeType) { - f.appendChild(item.node); - } - if (item.nodeType) { - f.appendChild(item); - } - if (typeof item == "string") { - f.appendChild(Snap.parse(item).node); - } - } - return new Fragment(f); -}; - -function make(name, parent) { - var res = $(name); - parent.appendChild(res); - var el = wrap(res); - return el; -} -function Paper(w, h) { - var res, - desc, - defs, - proto = Paper.prototype; - if (w && w.tagName == "svg") { - if (w.snap in hub) { - return hub[w.snap]; - } - var doc = w.ownerDocument; - res = new Element(w); - desc = w.getElementsByTagName("desc")[0]; - defs = w.getElementsByTagName("defs")[0]; - if (!desc) { - desc = $("desc"); - desc.appendChild(doc.createTextNode("Created with Snap")); - res.node.appendChild(desc); - } - if (!defs) { - defs = $("defs"); - res.node.appendChild(defs); - } - res.defs = defs; - for (var key in proto) if (proto[has](key)) { - res[key] = proto[key]; - } - res.paper = res.root = res; - } else { - res = make("svg", glob.doc.body); - $(res.node, { - height: h, - version: 1.1, - width: w, - xmlns: xmlns - }); - } - return res; -} -function wrap(dom) { - if (!dom) { - return dom; - } - if (dom instanceof Element || dom instanceof Fragment) { - return dom; - } - if (dom.tagName && dom.tagName.toLowerCase() == "svg") { - return new Paper(dom); - } - if (dom.tagName && dom.tagName.toLowerCase() == "object" && dom.type == "image/svg+xml") { - return new Paper(dom.contentDocument.getElementsByTagName("svg")[0]); - } - return new Element(dom); -} - -Snap._.make = make; -Snap._.wrap = wrap; -/*\ - * Paper.el - [ method ] - ** - * Creates an element on paper with a given name and no attributes - ** - - name (string) tag name - - attr (object) attributes - = (Element) the current element - > Usage - | var c = paper.circle(10, 10, 10); // is the same as... - | var c = paper.el("circle").attr({ - | cx: 10, - | cy: 10, - | r: 10 - | }); - | // and the same as - | var c = paper.el("circle", { - | cx: 10, - | cy: 10, - | r: 10 - | }); -\*/ -Paper.prototype.el = function (name, attr) { - var el = make(name, this.node); - attr && el.attr(attr); - return el; -}; -/*\ - * Element.children - [ method ] - ** - * Returns array of all the children of the element. - = (array) array of Elements -\*/ -Element.prototype.children = function () { - var out = [], - ch = this.node.childNodes; - for (var i = 0, ii = ch.length; i < ii; i++) { - out[i] = Snap(ch[i]); - } - return out; -}; -function jsonFiller(root, o) { - for (var i = 0, ii = root.length; i < ii; i++) { - var item = { - type: root[i].type, - attr: root[i].attr() - }, - children = root[i].children(); - o.push(item); - if (children.length) { - jsonFiller(children, item.childNodes = []); - } - } -} -/*\ - * Element.toJSON - [ method ] - ** - * Returns object representation of the given element and all its children. - = (object) in format - o { - o type (string) this.type, - o attr (object) attributes map, - o childNodes (array) optional array of children in the same format - o } -\*/ -Element.prototype.toJSON = function () { - var out = []; - jsonFiller([this], out); - return out[0]; -}; -// default -eve.on("snap.util.getattr", function () { - var att = eve.nt(); - att = att.substring(att.lastIndexOf(".") + 1); - var css = att.replace(/[A-Z]/g, function (letter) { - return "-" + letter.toLowerCase(); - }); - if (cssAttr[has](css)) { - return this.node.ownerDocument.defaultView.getComputedStyle(this.node, null).getPropertyValue(css); - } else { - return $(this.node, att); - } -}); -var cssAttr = { - "alignment-baseline": 0, - "baseline-shift": 0, - "clip": 0, - "clip-path": 0, - "clip-rule": 0, - "color": 0, - "color-interpolation": 0, - "color-interpolation-filters": 0, - "color-profile": 0, - "color-rendering": 0, - "cursor": 0, - "direction": 0, - "display": 0, - "dominant-baseline": 0, - "enable-background": 0, - "fill": 0, - "fill-opacity": 0, - "fill-rule": 0, - "filter": 0, - "flood-color": 0, - "flood-opacity": 0, - "font": 0, - "font-family": 0, - "font-size": 0, - "font-size-adjust": 0, - "font-stretch": 0, - "font-style": 0, - "font-variant": 0, - "font-weight": 0, - "glyph-orientation-horizontal": 0, - "glyph-orientation-vertical": 0, - "image-rendering": 0, - "kerning": 0, - "letter-spacing": 0, - "lighting-color": 0, - "marker": 0, - "marker-end": 0, - "marker-mid": 0, - "marker-start": 0, - "mask": 0, - "opacity": 0, - "overflow": 0, - "pointer-events": 0, - "shape-rendering": 0, - "stop-color": 0, - "stop-opacity": 0, - "stroke": 0, - "stroke-dasharray": 0, - "stroke-dashoffset": 0, - "stroke-linecap": 0, - "stroke-linejoin": 0, - "stroke-miterlimit": 0, - "stroke-opacity": 0, - "stroke-width": 0, - "text-anchor": 0, - "text-decoration": 0, - "text-rendering": 0, - "unicode-bidi": 0, - "visibility": 0, - "word-spacing": 0, - "writing-mode": 0 -}; - -eve.on("snap.util.attr", function (value) { - var att = eve.nt(), - attr = {}; - att = att.substring(att.lastIndexOf(".") + 1); - attr[att] = value; - var style = att.replace(/-(\w)/gi, function (all, letter) { - return letter.toUpperCase(); - }), - css = att.replace(/[A-Z]/g, function (letter) { - return "-" + letter.toLowerCase(); - }); - if (cssAttr[has](css)) { - this.node.style[style] = value == null ? E : value; - } else { - $(this.node, attr); - } -}); -(function (proto) {}(Paper.prototype)); - -// simple ajax -/*\ - * Snap.ajax - [ method ] - ** - * Simple implementation of Ajax - ** - - url (string) URL - - postData (object|string) data for post request - - callback (function) callback - - scope (object) #optional scope of callback - * or - - url (string) URL - - callback (function) callback - - scope (object) #optional scope of callback - = (XMLHttpRequest) the XMLHttpRequest object, just in case -\*/ -Snap.ajax = function (url, postData, callback, scope){ - var req = new XMLHttpRequest, - id = ID(); - if (req) { - if (is(postData, "function")) { - scope = callback; - callback = postData; - postData = null; - } else if (is(postData, "object")) { - var pd = []; - for (var key in postData) if (postData.hasOwnProperty(key)) { - pd.push(encodeURIComponent(key) + "=" + encodeURIComponent(postData[key])); - } - postData = pd.join("&"); - } - req.open((postData ? "POST" : "GET"), url, true); - if (postData) { - req.setRequestHeader("X-Requested-With", "XMLHttpRequest"); - req.setRequestHeader("Content-type", "application/x-www-form-urlencoded"); - } - if (callback) { - eve.once("snap.ajax." + id + ".0", callback); - eve.once("snap.ajax." + id + ".200", callback); - eve.once("snap.ajax." + id + ".304", callback); - } - req.onreadystatechange = function() { - if (req.readyState != 4) return; - eve("snap.ajax." + id + "." + req.status, scope, req); - }; - if (req.readyState == 4) { - return req; - } - req.send(postData); - return req; - } -}; -/*\ - * Snap.load - [ method ] - ** - * Loads external SVG file as a @Fragment (see @Snap.ajax for more advanced AJAX) - ** - - url (string) URL - - callback (function) callback - - scope (object) #optional scope of callback -\*/ -Snap.load = function (url, callback, scope) { - Snap.ajax(url, function (req) { - var f = Snap.parse(req.responseText); - scope ? callback.call(scope, f) : callback(f); - }); -}; -var getOffset = function (elem) { - var box = elem.getBoundingClientRect(), - doc = elem.ownerDocument, - body = doc.body, - docElem = doc.documentElement, - clientTop = docElem.clientTop || body.clientTop || 0, clientLeft = docElem.clientLeft || body.clientLeft || 0, - top = box.top + (g.win.pageYOffset || docElem.scrollTop || body.scrollTop ) - clientTop, - left = box.left + (g.win.pageXOffset || docElem.scrollLeft || body.scrollLeft) - clientLeft; - return { - y: top, - x: left - }; -}; -/*\ - * Snap.getElementByPoint - [ method ] - ** - * Returns you topmost element under given point. - ** - = (object) Snap element object - - x (number) x coordinate from the top left corner of the window - - y (number) y coordinate from the top left corner of the window - > Usage - | Snap.getElementByPoint(mouseX, mouseY).attr({stroke: "#f00"}); -\*/ -Snap.getElementByPoint = function (x, y) { - var paper = this, - svg = paper.canvas, - target = glob.doc.elementFromPoint(x, y); - if (glob.win.opera && target.tagName == "svg") { - var so = getOffset(target), - sr = target.createSVGRect(); - sr.x = x - so.x; - sr.y = y - so.y; - sr.width = sr.height = 1; - var hits = target.getIntersectionList(sr, null); - if (hits.length) { - target = hits[hits.length - 1]; - } - } - if (!target) { - return null; - } - return wrap(target); -}; -/*\ - * Snap.plugin - [ method ] - ** - * Let you write plugins. You pass in a function with five arguments, like this: - | Snap.plugin(function (Snap, Element, Paper, global, Fragment) { - | Snap.newmethod = function () {}; - | Element.prototype.newmethod = function () {}; - | Paper.prototype.newmethod = function () {}; - | }); - * Inside the function you have access to all main objects (and their - * prototypes). This allow you to extend anything you want. - ** - - f (function) your plugin body -\*/ -Snap.plugin = function (f) { - f(Snap, Element, Paper, glob, Fragment); -}; -glob.win.Snap = Snap; -return Snap; -}(window || this)); - -// Copyright (c) 2013 Adobe Systems Incorporated. All rights reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -Snap.plugin(function (Snap, Element, Paper, glob, Fragment) { - var elproto = Element.prototype, - is = Snap.is, - Str = String, - unit2px = Snap._unit2px, - $ = Snap._.$, - make = Snap._.make, - getSomeDefs = Snap._.getSomeDefs, - has = "hasOwnProperty", - wrap = Snap._.wrap; - /*\ - * Element.getBBox - [ method ] - ** - * Returns the bounding box descriptor for the given element - ** - = (object) bounding box descriptor: - o { - o cx: (number) x of the center, - o cy: (number) x of the center, - o h: (number) height, - o height: (number) height, - o path: (string) path command for the box, - o r0: (number) radius of a circle that fully encloses the box, - o r1: (number) radius of the smallest circle that can be enclosed, - o r2: (number) radius of the largest circle that can be enclosed, - o vb: (string) box as a viewbox command, - o w: (number) width, - o width: (number) width, - o x2: (number) x of the right side, - o x: (number) x of the left side, - o y2: (number) y of the bottom edge, - o y: (number) y of the top edge - o } - \*/ - elproto.getBBox = function (isWithoutTransform) { - if (!Snap.Matrix || !Snap.path) { - return this.node.getBBox(); - } - var el = this, - m = new Snap.Matrix; - if (el.removed) { - return Snap._.box(); - } - while (el.type == "use") { - if (!isWithoutTransform) { - m = m.add(el.transform().localMatrix.translate(el.attr("x") || 0, el.attr("y") || 0)); - } - if (el.original) { - el = el.original; - } else { - var href = el.attr("xlink:href"); - el = el.original = el.node.ownerDocument.getElementById(href.substring(href.indexOf("#") + 1)); - } - } - var _ = el._, - pathfinder = Snap.path.get[el.type] || Snap.path.get.deflt; - try { - if (isWithoutTransform) { - _.bboxwt = pathfinder ? Snap.path.getBBox(el.realPath = pathfinder(el)) : Snap._.box(el.node.getBBox()); - return Snap._.box(_.bboxwt); - } else { - el.realPath = pathfinder(el); - el.matrix = el.transform().localMatrix; - _.bbox = Snap.path.getBBox(Snap.path.map(el.realPath, m.add(el.matrix))); - return Snap._.box(_.bbox); - } - } catch (e) { - // Firefox doesn’t give you bbox of hidden element - return Snap._.box(); - } - }; - var propString = function () { - return this.string; - }; - function extractTransform(el, tstr) { - if (tstr == null) { - var doReturn = true; - if (el.type == "linearGradient" || el.type == "radialGradient") { - tstr = el.node.getAttribute("gradientTransform"); - } else if (el.type == "pattern") { - tstr = el.node.getAttribute("patternTransform"); - } else { - tstr = el.node.getAttribute("transform"); - } - if (!tstr) { - return new Snap.Matrix; - } - tstr = Snap._.svgTransform2string(tstr); - } else { - if (!Snap._.rgTransform.test(tstr)) { - tstr = Snap._.svgTransform2string(tstr); - } else { - tstr = Str(tstr).replace(/\.{3}|\u2026/g, el._.transform || ""); - } - if (is(tstr, "array")) { - tstr = Snap.path ? Snap.path.toString.call(tstr) : Str(tstr); - } - el._.transform = tstr; - } - var m = Snap._.transform2matrix(tstr, el.getBBox(1)); - if (doReturn) { - return m; - } else { - el.matrix = m; - } - } - /*\ - * Element.transform - [ method ] - ** - * Gets or sets transformation of the element - ** - - tstr (string) transform string in Snap or SVG format - = (Element) the current element - * or - = (object) transformation descriptor: - o { - o string (string) transform string, - o globalMatrix (Matrix) matrix of all transformations applied to element or its parents, - o localMatrix (Matrix) matrix of transformations applied only to the element, - o diffMatrix (Matrix) matrix of difference between global and local transformations, - o global (string) global transformation as string, - o local (string) local transformation as string, - o toString (function) returns `string` property - o } - \*/ - elproto.transform = function (tstr) { - var _ = this._; - if (tstr == null) { - var papa = this, - global = new Snap.Matrix(this.node.getCTM()), - local = extractTransform(this), - ms = [local], - m = new Snap.Matrix, - i, - localString = local.toTransformString(), - string = Str(local) == Str(this.matrix) ? - Str(_.transform) : localString; - while (papa.type != "svg" && (papa = papa.parent())) { - ms.push(extractTransform(papa)); - } - i = ms.length; - while (i--) { - m.add(ms[i]); - } - return { - string: string, - globalMatrix: global, - totalMatrix: m, - localMatrix: local, - diffMatrix: global.clone().add(local.invert()), - global: global.toTransformString(), - total: m.toTransformString(), - local: localString, - toString: propString - }; - } - if (tstr instanceof Snap.Matrix) { - this.matrix = tstr; - this._.transform = tstr.toTransformString(); - } else { - extractTransform(this, tstr); - } - - if (this.node) { - if (this.type == "linearGradient" || this.type == "radialGradient") { - $(this.node, {gradientTransform: this.matrix}); - } else if (this.type == "pattern") { - $(this.node, {patternTransform: this.matrix}); - } else { - $(this.node, {transform: this.matrix}); - } - } - - return this; - }; - /*\ - * Element.parent - [ method ] - ** - * Returns the element's parent - ** - = (Element) the parent element - \*/ - elproto.parent = function () { - return wrap(this.node.parentNode); - }; - /*\ - * Element.append - [ method ] - ** - * Appends the given element to current one - ** - - el (Element|Set) element to append - = (Element) the parent element - \*/ - /*\ - * Element.add - [ method ] - ** - * See @Element.append - \*/ - elproto.append = elproto.add = function (el) { - if (el) { - if (el.type == "set") { - var it = this; - el.forEach(function (el) { - it.add(el); - }); - return this; - } - el = wrap(el); - this.node.appendChild(el.node); - el.paper = this.paper; - } - return this; - }; - /*\ - * Element.appendTo - [ method ] - ** - * Appends the current element to the given one - ** - - el (Element) parent element to append to - = (Element) the child element - \*/ - elproto.appendTo = function (el) { - if (el) { - el = wrap(el); - el.append(this); - } - return this; - }; - /*\ - * Element.prepend - [ method ] - ** - * Prepends the given element to the current one - ** - - el (Element) element to prepend - = (Element) the parent element - \*/ - elproto.prepend = function (el) { - if (el) { - if (el.type == "set") { - var it = this, - first; - el.forEach(function (el) { - if (first) { - first.after(el); - } else { - it.prepend(el); - } - first = el; - }); - return this; - } - el = wrap(el); - var parent = el.parent(); - this.node.insertBefore(el.node, this.node.firstChild); - this.add && this.add(); - el.paper = this.paper; - this.parent() && this.parent().add(); - parent && parent.add(); - } - return this; - }; - /*\ - * Element.prependTo - [ method ] - ** - * Prepends the current element to the given one - ** - - el (Element) parent element to prepend to - = (Element) the child element - \*/ - elproto.prependTo = function (el) { - el = wrap(el); - el.prepend(this); - return this; - }; - /*\ - * Element.before - [ method ] - ** - * Inserts given element before the current one - ** - - el (Element) element to insert - = (Element) the parent element - \*/ - elproto.before = function (el) { - if (el.type == "set") { - var it = this; - el.forEach(function (el) { - var parent = el.parent(); - it.node.parentNode.insertBefore(el.node, it.node); - parent && parent.add(); - }); - this.parent().add(); - return this; - } - el = wrap(el); - var parent = el.parent(); - this.node.parentNode.insertBefore(el.node, this.node); - this.parent() && this.parent().add(); - parent && parent.add(); - el.paper = this.paper; - return this; - }; - /*\ - * Element.after - [ method ] - ** - * Inserts given element after the current one - ** - - el (Element) element to insert - = (Element) the parent element - \*/ - elproto.after = function (el) { - el = wrap(el); - var parent = el.parent(); - if (this.node.nextSibling) { - this.node.parentNode.insertBefore(el.node, this.node.nextSibling); - } else { - this.node.parentNode.appendChild(el.node); - } - this.parent() && this.parent().add(); - parent && parent.add(); - el.paper = this.paper; - return this; - }; - /*\ - * Element.insertBefore - [ method ] - ** - * Inserts the element after the given one - ** - - el (Element) element next to whom insert to - = (Element) the parent element - \*/ - elproto.insertBefore = function (el) { - el = wrap(el); - var parent = this.parent(); - el.node.parentNode.insertBefore(this.node, el.node); - this.paper = el.paper; - parent && parent.add(); - el.parent() && el.parent().add(); - return this; - }; - /*\ - * Element.insertAfter - [ method ] - ** - * Inserts the element after the given one - ** - - el (Element) element next to whom insert to - = (Element) the parent element - \*/ - elproto.insertAfter = function (el) { - el = wrap(el); - var parent = this.parent(); - el.node.parentNode.insertBefore(this.node, el.node.nextSibling); - this.paper = el.paper; - parent && parent.add(); - el.parent() && el.parent().add(); - return this; - }; - /*\ - * Element.remove - [ method ] - ** - * Removes element from the DOM - = (Element) the detached element - \*/ - elproto.remove = function () { - var parent = this.parent(); - this.node.parentNode && this.node.parentNode.removeChild(this.node); - delete this.paper; - this.removed = true; - parent && parent.add(); - return this; - }; - /*\ - * Element.select - [ method ] - ** - * Gathers the nested @Element matching the given set of CSS selectors - ** - - query (string) CSS selector - = (Element) result of query selection - \*/ - elproto.select = function (query) { - return wrap(this.node.querySelector(query)); - }; - /*\ - * Element.selectAll - [ method ] - ** - * Gathers nested @Element objects matching the given set of CSS selectors - ** - - query (string) CSS selector - = (Set|array) result of query selection - \*/ - elproto.selectAll = function (query) { - var nodelist = this.node.querySelectorAll(query), - set = (Snap.set || Array)(); - for (var i = 0; i < nodelist.length; i++) { - set.push(wrap(nodelist[i])); - } - return set; - }; - /*\ - * Element.asPX - [ method ] - ** - * Returns given attribute of the element as a `px` value (not %, em, etc.) - ** - - attr (string) attribute name - - value (string) #optional attribute value - = (Element) result of query selection - \*/ - elproto.asPX = function (attr, value) { - if (value == null) { - value = this.attr(attr); - } - return +unit2px(this, attr, value); - }; - // SIERRA Element.use(): I suggest adding a note about how to access the original element the returned instantiates. It's a part of SVG with which ordinary web developers may be least familiar. - /*\ - * Element.use - [ method ] - ** - * Creates a `` element linked to the current element - ** - = (Element) the `` element - \*/ - elproto.use = function () { - var use, - id = this.node.id; - if (!id) { - id = this.id; - $(this.node, { - id: id - }); - } - if (this.type == "linearGradient" || this.type == "radialGradient" || - this.type == "pattern") { - use = make(this.type, this.node.parentNode); - } else { - use = make("use", this.node.parentNode); - } - $(use.node, { - "xlink:href": "#" + id - }); - use.original = this; - return use; - }; - function fixids(el) { - var els = el.selectAll("*"), - it, - url = /^\s*url\(("|'|)(.*)\1\)\s*$/, - ids = [], - uses = {}; - function urltest(it, name) { - var val = $(it.node, name); - val = val && val.match(url); - val = val && val[2]; - if (val && val.charAt() == "#") { - val = val.substring(1); - } else { - return; - } - if (val) { - uses[val] = (uses[val] || []).concat(function (id) { - var attr = {}; - attr[name] = URL(id); - $(it.node, attr); - }); - } - } - function linktest(it) { - var val = $(it.node, "xlink:href"); - if (val && val.charAt() == "#") { - val = val.substring(1); - } else { - return; - } - if (val) { - uses[val] = (uses[val] || []).concat(function (id) { - it.attr("xlink:href", "#" + id); - }); - } - } - for (var i = 0, ii = els.length; i < ii; i++) { - it = els[i]; - urltest(it, "fill"); - urltest(it, "stroke"); - urltest(it, "filter"); - urltest(it, "mask"); - urltest(it, "clip-path"); - linktest(it); - var oldid = $(it.node, "id"); - if (oldid) { - $(it.node, {id: it.id}); - ids.push({ - old: oldid, - id: it.id - }); - } - } - for (i = 0, ii = ids.length; i < ii; i++) { - var fs = uses[ids[i].old]; - if (fs) { - for (var j = 0, jj = fs.length; j < jj; j++) { - fs[j](ids[i].id); - } - } - } - } - /*\ - * Element.clone - [ method ] - ** - * Creates a clone of the element and inserts it after the element - ** - = (Element) the clone - \*/ - elproto.clone = function () { - var clone = wrap(this.node.cloneNode(true)); - if ($(clone.node, "id")) { - $(clone.node, {id: clone.id}); - } - fixids(clone); - clone.insertAfter(this); - return clone; - }; - /*\ - * Element.toDefs - [ method ] - ** - * Moves element to the shared `` area - ** - = (Element) the element - \*/ - elproto.toDefs = function () { - var defs = getSomeDefs(this); - defs.appendChild(this.node); - return this; - }; - /*\ - * Element.toPattern - [ method ] - ** - * Creates a `` element from the current element - ** - * To create a pattern you have to specify the pattern rect: - - x (string|number) - - y (string|number) - - width (string|number) - - height (string|number) - = (Element) the `` element - * You can use pattern later on as an argument for `fill` attribute: - | var p = paper.path("M10-5-10,15M15,0,0,15M0-5-20,15").attr({ - | fill: "none", - | stroke: "#bada55", - | strokeWidth: 5 - | }).pattern(0, 0, 10, 10), - | c = paper.circle(200, 200, 100); - | c.attr({ - | fill: p - | }); - \*/ - elproto.pattern = elproto.toPattern = function (x, y, width, height) { - var p = make("pattern", getSomeDefs(this)); - if (x == null) { - x = this.getBBox(); - } - if (is(x, "object") && "x" in x) { - y = x.y; - width = x.width; - height = x.height; - x = x.x; - } - $(p.node, { - x: x, - y: y, - width: width, - height: height, - patternUnits: "userSpaceOnUse", - id: p.id, - viewBox: [x, y, width, height].join(" ") - }); - p.node.appendChild(this.node); - return p; - }; -// SIERRA Element.marker(): clarify what a reference point is. E.g., helps you offset the object from its edge such as when centering it over a path. -// SIERRA Element.marker(): I suggest the method should accept default reference point values. Perhaps centered with (refX = width/2) and (refY = height/2)? Also, couldn't it assume the element's current _width_ and _height_? And please specify what _x_ and _y_ mean: offsets? If so, from where? Couldn't they also be assigned default values? - /*\ - * Element.marker - [ method ] - ** - * Creates a `` element from the current element - ** - * To create a marker you have to specify the bounding rect and reference point: - - x (number) - - y (number) - - width (number) - - height (number) - - refX (number) - - refY (number) - = (Element) the `` element - * You can specify the marker later as an argument for `marker-start`, `marker-end`, `marker-mid`, and `marker` attributes. The `marker` attribute places the marker at every point along the path, and `marker-mid` places them at every point except the start and end. - \*/ - // TODO add usage for markers - elproto.marker = function (x, y, width, height, refX, refY) { - var p = make("marker", getSomeDefs(this)); - if (x == null) { - x = this.getBBox(); - } - if (is(x, "object") && "x" in x) { - y = x.y; - width = x.width; - height = x.height; - refX = x.refX || x.cx; - refY = x.refY || x.cy; - x = x.x; - } - $(p.node, { - viewBox: [x, y, width, height].join(" "), - markerWidth: width, - markerHeight: height, - orient: "auto", - refX: refX || 0, - refY: refY || 0, - id: p.id - }); - p.node.appendChild(this.node); - return p; - }; - // animation - function slice(from, to, f) { - return function (arr) { - var res = arr.slice(from, to); - if (res.length == 1) { - res = res[0]; - } - return f ? f(res) : res; - }; - } - var Animation = function (attr, ms, easing, callback) { - if (typeof easing == "function" && !easing.length) { - callback = easing; - easing = mina.linear; - } - this.attr = attr; - this.dur = ms; - easing && (this.easing = easing); - callback && (this.callback = callback); - }; - Snap._.Animation = Animation; - /*\ - * Snap.animation - [ method ] - ** - * Creates an animation object - ** - - attr (object) attributes of final destination - - duration (number) duration of the animation, in milliseconds - - easing (function) #optional one of easing functions of @mina or custom one - - callback (function) #optional callback function that fires when animation ends - = (object) animation object - \*/ - Snap.animation = function (attr, ms, easing, callback) { - return new Animation(attr, ms, easing, callback); - }; - /*\ - * Element.inAnim - [ method ] - ** - * Returns a set of animations that may be able to manipulate the current element - ** - = (object) in format: - o { - o anim (object) animation object, - o mina (object) @mina object, - o curStatus (number) 0..1 — status of the animation: 0 — just started, 1 — just finished, - o status (function) gets or sets the status of the animation, - o stop (function) stops the animation - o } - \*/ - elproto.inAnim = function () { - var el = this, - res = []; - for (var id in el.anims) if (el.anims[has](id)) { - (function (a) { - res.push({ - anim: new Animation(a._attrs, a.dur, a.easing, a._callback), - mina: a, - curStatus: a.status(), - status: function (val) { - return a.status(val); - }, - stop: function () { - a.stop(); - } - }); - }(el.anims[id])); - } - return res; - }; - /*\ - * Snap.animate - [ method ] - ** - * Runs generic animation of one number into another with a caring function - ** - - from (number|array) number or array of numbers - - to (number|array) number or array of numbers - - setter (function) caring function that accepts one number argument - - duration (number) duration, in milliseconds - - easing (function) #optional easing function from @mina or custom - - callback (function) #optional callback function to execute when animation ends - = (object) animation object in @mina format - o { - o id (string) animation id, consider it read-only, - o duration (function) gets or sets the duration of the animation, - o easing (function) easing, - o speed (function) gets or sets the speed of the animation, - o status (function) gets or sets the status of the animation, - o stop (function) stops the animation - o } - | var rect = Snap().rect(0, 0, 10, 10); - | Snap.animate(0, 10, function (val) { - | rect.attr({ - | x: val - | }); - | }, 1000); - | // in given context is equivalent to - | rect.animate({x: 10}, 1000); - \*/ - Snap.animate = function (from, to, setter, ms, easing, callback) { - if (typeof easing == "function" && !easing.length) { - callback = easing; - easing = mina.linear; - } - var now = mina.time(), - anim = mina(from, to, now, now + ms, mina.time, setter, easing); - callback && eve.once("mina.finish." + anim.id, callback); - return anim; - }; - /*\ - * Element.stop - [ method ] - ** - * Stops all the animations for the current element - ** - = (Element) the current element - \*/ - elproto.stop = function () { - var anims = this.inAnim(); - for (var i = 0, ii = anims.length; i < ii; i++) { - anims[i].stop(); - } - return this; - }; - /*\ - * Element.animate - [ method ] - ** - * Animates the given attributes of the element - ** - - attrs (object) key-value pairs of destination attributes - - duration (number) duration of the animation in milliseconds - - easing (function) #optional easing function from @mina or custom - - callback (function) #optional callback function that executes when the animation ends - = (Element) the current element - \*/ - elproto.animate = function (attrs, ms, easing, callback) { - if (typeof easing == "function" && !easing.length) { - callback = easing; - easing = mina.linear; - } - if (attrs instanceof Animation) { - callback = attrs.callback; - easing = attrs.easing; - ms = attrs.dur; - attrs = attrs.attr; - } - var fkeys = [], tkeys = [], keys = {}, from, to, f, eq, - el = this; - for (var key in attrs) if (attrs[has](key)) { - if (el.equal) { - eq = el.equal(key, Str(attrs[key])); - from = eq.from; - to = eq.to; - f = eq.f; - } else { - from = +el.attr(key); - to = +attrs[key]; - } - var len = is(from, "array") ? from.length : 1; - keys[key] = slice(fkeys.length, fkeys.length + len, f); - fkeys = fkeys.concat(from); - tkeys = tkeys.concat(to); - } - var now = mina.time(), - anim = mina(fkeys, tkeys, now, now + ms, mina.time, function (val) { - var attr = {}; - for (var key in keys) if (keys[has](key)) { - attr[key] = keys[key](val); - } - el.attr(attr); - }, easing); - el.anims[anim.id] = anim; - anim._attrs = attrs; - anim._callback = callback; - eve("snap.animcreated." + el.id, anim); - eve.once("mina.finish." + anim.id, function () { - delete el.anims[anim.id]; - callback && callback.call(el); - }); - eve.once("mina.stop." + anim.id, function () { - delete el.anims[anim.id]; - }); - return el; - }; - var eldata = {}; - /*\ - * Element.data - [ method ] - ** - * Adds or retrieves given value associated with given key. (Don’t confuse - * with `data-` attributes) - * - * See also @Element.removeData - - key (string) key to store data - - value (any) #optional value to store - = (object) @Element - * or, if value is not specified: - = (any) value - > Usage - | for (var i = 0, i < 5, i++) { - | paper.circle(10 + 15 * i, 10, 10) - | .attr({fill: "#000"}) - | .data("i", i) - | .click(function () { - | alert(this.data("i")); - | }); - | } - \*/ - elproto.data = function (key, value) { - var data = eldata[this.id] = eldata[this.id] || {}; - if (arguments.length == 0){ - eve("snap.data.get." + this.id, this, data, null); - return data; - } - if (arguments.length == 1) { - if (Snap.is(key, "object")) { - for (var i in key) if (key[has](i)) { - this.data(i, key[i]); - } - return this; - } - eve("snap.data.get." + this.id, this, data[key], key); - return data[key]; - } - data[key] = value; - eve("snap.data.set." + this.id, this, value, key); - return this; - }; - /*\ - * Element.removeData - [ method ] - ** - * Removes value associated with an element by given key. - * If key is not provided, removes all the data of the element. - - key (string) #optional key - = (object) @Element - \*/ - elproto.removeData = function (key) { - if (key == null) { - eldata[this.id] = {}; - } else { - eldata[this.id] && delete eldata[this.id][key]; - } - return this; - }; - /*\ - * Element.outerSVG - [ method ] - ** - * Returns SVG code for the element, equivalent to HTML's `outerHTML`. - * - * See also @Element.innerSVG - = (string) SVG code for the element - \*/ - /*\ - * Element.toString - [ method ] - ** - * See @Element.outerSVG - \*/ - elproto.outerSVG = elproto.toString = toString(1); - /*\ - * Element.innerSVG - [ method ] - ** - * Returns SVG code for the element's contents, equivalent to HTML's `innerHTML` - = (string) SVG code for the element - \*/ - elproto.innerSVG = toString(); - function toString(type) { - return function () { - var res = type ? "<" + this.type : "", - attr = this.node.attributes, - chld = this.node.childNodes; - if (type) { - for (var i = 0, ii = attr.length; i < ii; i++) { - res += " " + attr[i].name + '="' + - attr[i].value.replace(/"/g, '\\"') + '"'; - } - } - if (chld.length) { - type && (res += ">"); - for (i = 0, ii = chld.length; i < ii; i++) { - if (chld[i].nodeType == 3) { - res += chld[i].nodeValue; - } else if (chld[i].nodeType == 1) { - res += wrap(chld[i]).toString(); - } - } - type && (res += ""); - } else { - type && (res += "/>"); - } - return res; - }; - } - elproto.toDataURL = function () { - if (window && window.btoa) { - var bb = this.getBBox(), - svg = Snap.format('{contents}', { - x: +bb.x.toFixed(3), - y: +bb.y.toFixed(3), - width: +bb.width.toFixed(3), - height: +bb.height.toFixed(3), - contents: this.outerSVG() - }); - return "data:image/svg+xml;base64," + btoa(unescape(encodeURIComponent(svg))); - } - }; - /*\ - * Fragment.select - [ method ] - ** - * See @Element.select - \*/ - Fragment.prototype.select = elproto.select; - /*\ - * Fragment.selectAll - [ method ] - ** - * See @Element.selectAll - \*/ - Fragment.prototype.selectAll = elproto.selectAll; -}); - -// Copyright (c) 2013 Adobe Systems Incorporated. All rights reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -Snap.plugin(function (Snap, Element, Paper, glob, Fragment) { - var objectToString = Object.prototype.toString, - Str = String, - math = Math, - E = ""; - function Matrix(a, b, c, d, e, f) { - if (b == null && objectToString.call(a) == "[object SVGMatrix]") { - this.a = a.a; - this.b = a.b; - this.c = a.c; - this.d = a.d; - this.e = a.e; - this.f = a.f; - return; - } - if (a != null) { - this.a = +a; - this.b = +b; - this.c = +c; - this.d = +d; - this.e = +e; - this.f = +f; - } else { - this.a = 1; - this.b = 0; - this.c = 0; - this.d = 1; - this.e = 0; - this.f = 0; - } - } - (function (matrixproto) { - /*\ - * Matrix.add - [ method ] - ** - * Adds the given matrix to existing one - - a (number) - - b (number) - - c (number) - - d (number) - - e (number) - - f (number) - * or - - matrix (object) @Matrix - \*/ - matrixproto.add = function (a, b, c, d, e, f) { - var out = [[], [], []], - m = [[this.a, this.c, this.e], [this.b, this.d, this.f], [0, 0, 1]], - matrix = [[a, c, e], [b, d, f], [0, 0, 1]], - x, y, z, res; - - if (a && a instanceof Matrix) { - matrix = [[a.a, a.c, a.e], [a.b, a.d, a.f], [0, 0, 1]]; - } - - for (x = 0; x < 3; x++) { - for (y = 0; y < 3; y++) { - res = 0; - for (z = 0; z < 3; z++) { - res += m[x][z] * matrix[z][y]; - } - out[x][y] = res; - } - } - this.a = out[0][0]; - this.b = out[1][0]; - this.c = out[0][1]; - this.d = out[1][1]; - this.e = out[0][2]; - this.f = out[1][2]; - return this; - }; - /*\ - * Matrix.invert - [ method ] - ** - * Returns an inverted version of the matrix - = (object) @Matrix - \*/ - matrixproto.invert = function () { - var me = this, - x = me.a * me.d - me.b * me.c; - return new Matrix(me.d / x, -me.b / x, -me.c / x, me.a / x, (me.c * me.f - me.d * me.e) / x, (me.b * me.e - me.a * me.f) / x); - }; - /*\ - * Matrix.clone - [ method ] - ** - * Returns a copy of the matrix - = (object) @Matrix - \*/ - matrixproto.clone = function () { - return new Matrix(this.a, this.b, this.c, this.d, this.e, this.f); - }; - /*\ - * Matrix.translate - [ method ] - ** - * Translate the matrix - - x (number) horizontal offset distance - - y (number) vertical offset distance - \*/ - matrixproto.translate = function (x, y) { - return this.add(1, 0, 0, 1, x, y); - }; - /*\ - * Matrix.scale - [ method ] - ** - * Scales the matrix - - x (number) amount to be scaled, with `1` resulting in no change - - y (number) #optional amount to scale along the vertical axis. (Otherwise `x` applies to both axes.) - - cx (number) #optional horizontal origin point from which to scale - - cy (number) #optional vertical origin point from which to scale - * Default cx, cy is the middle point of the element. - \*/ - matrixproto.scale = function (x, y, cx, cy) { - y == null && (y = x); - (cx || cy) && this.add(1, 0, 0, 1, cx, cy); - this.add(x, 0, 0, y, 0, 0); - (cx || cy) && this.add(1, 0, 0, 1, -cx, -cy); - return this; - }; - /*\ - * Matrix.rotate - [ method ] - ** - * Rotates the matrix - - a (number) angle of rotation, in degrees - - x (number) horizontal origin point from which to rotate - - y (number) vertical origin point from which to rotate - \*/ - matrixproto.rotate = function (a, x, y) { - a = Snap.rad(a); - x = x || 0; - y = y || 0; - var cos = +math.cos(a).toFixed(9), - sin = +math.sin(a).toFixed(9); - this.add(cos, sin, -sin, cos, x, y); - return this.add(1, 0, 0, 1, -x, -y); - }; - /*\ - * Matrix.x - [ method ] - ** - * Returns x coordinate for given point after transformation described by the matrix. See also @Matrix.y - - x (number) - - y (number) - = (number) x - \*/ - matrixproto.x = function (x, y) { - return x * this.a + y * this.c + this.e; - }; - /*\ - * Matrix.y - [ method ] - ** - * Returns y coordinate for given point after transformation described by the matrix. See also @Matrix.x - - x (number) - - y (number) - = (number) y - \*/ - matrixproto.y = function (x, y) { - return x * this.b + y * this.d + this.f; - }; - matrixproto.get = function (i) { - return +this[Str.fromCharCode(97 + i)].toFixed(4); - }; - matrixproto.toString = function () { - return "matrix(" + [this.get(0), this.get(1), this.get(2), this.get(3), this.get(4), this.get(5)].join() + ")"; - }; - matrixproto.offset = function () { - return [this.e.toFixed(4), this.f.toFixed(4)]; - }; - function norm(a) { - return a[0] * a[0] + a[1] * a[1]; - } - function normalize(a) { - var mag = math.sqrt(norm(a)); - a[0] && (a[0] /= mag); - a[1] && (a[1] /= mag); - } - /*\ - * Matrix.determinant - [ method ] - ** - * Finds determinant of the given matrix. - = (number) determinant - \*/ - matrixproto.determinant = function () { - return this.a * this.d - this.b * this.c; - }; - /*\ - * Matrix.split - [ method ] - ** - * Splits matrix into primitive transformations - = (object) in format: - o dx (number) translation by x - o dy (number) translation by y - o scalex (number) scale by x - o scaley (number) scale by y - o shear (number) shear - o rotate (number) rotation in deg - o isSimple (boolean) could it be represented via simple transformations - \*/ - matrixproto.split = function () { - var out = {}; - // translation - out.dx = this.e; - out.dy = this.f; - - // scale and shear - var row = [[this.a, this.c], [this.b, this.d]]; - out.scalex = math.sqrt(norm(row[0])); - normalize(row[0]); - - out.shear = row[0][0] * row[1][0] + row[0][1] * row[1][1]; - row[1] = [row[1][0] - row[0][0] * out.shear, row[1][1] - row[0][1] * out.shear]; - - out.scaley = math.sqrt(norm(row[1])); - normalize(row[1]); - out.shear /= out.scaley; - - if (this.determinant() < 0) { - out.scalex = -out.scalex; - } - - // rotation - var sin = -row[0][1], - cos = row[1][1]; - if (cos < 0) { - out.rotate = Snap.deg(math.acos(cos)); - if (sin < 0) { - out.rotate = 360 - out.rotate; - } - } else { - out.rotate = Snap.deg(math.asin(sin)); - } - - out.isSimple = !+out.shear.toFixed(9) && (out.scalex.toFixed(9) == out.scaley.toFixed(9) || !out.rotate); - out.isSuperSimple = !+out.shear.toFixed(9) && out.scalex.toFixed(9) == out.scaley.toFixed(9) && !out.rotate; - out.noRotation = !+out.shear.toFixed(9) && !out.rotate; - return out; - }; - /*\ - * Matrix.toTransformString - [ method ] - ** - * Returns transform string that represents given matrix - = (string) transform string - \*/ - matrixproto.toTransformString = function (shorter) { - var s = shorter || this.split(); - if (!+s.shear.toFixed(9)) { - s.scalex = +s.scalex.toFixed(4); - s.scaley = +s.scaley.toFixed(4); - s.rotate = +s.rotate.toFixed(4); - return (s.dx || s.dy ? "t" + [+s.dx.toFixed(4), +s.dy.toFixed(4)] : E) + - (s.scalex != 1 || s.scaley != 1 ? "s" + [s.scalex, s.scaley, 0, 0] : E) + - (s.rotate ? "r" + [+s.rotate.toFixed(4), 0, 0] : E); - } else { - return "m" + [this.get(0), this.get(1), this.get(2), this.get(3), this.get(4), this.get(5)]; - } - }; - })(Matrix.prototype); - /*\ - * Snap.Matrix - [ method ] - ** - * Matrix constructor, extend on your own risk. - * To create matrices use @Snap.matrix. - \*/ - Snap.Matrix = Matrix; - /*\ - * Snap.matrix - [ method ] - ** - * Utility method - ** - * Returns a matrix based on the given parameters - - a (number) - - b (number) - - c (number) - - d (number) - - e (number) - - f (number) - * or - - svgMatrix (SVGMatrix) - = (object) @Matrix - \*/ - Snap.matrix = function (a, b, c, d, e, f) { - return new Matrix(a, b, c, d, e, f); - }; -}); -// Copyright (c) 2013 Adobe Systems Incorporated. All rights reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -Snap.plugin(function (Snap, Element, Paper, glob, Fragment) { - var has = "hasOwnProperty", - make = Snap._.make, - wrap = Snap._.wrap, - is = Snap.is, - getSomeDefs = Snap._.getSomeDefs, - reURLValue = /^url\(#?([^)]+)\)$/, - $ = Snap._.$, - URL = Snap.url, - Str = String, - separator = Snap._.separator, - E = ""; - // Attributes event handlers - eve.on("snap.util.attr.mask", function (value) { - if (value instanceof Element || value instanceof Fragment) { - eve.stop(); - if (value instanceof Fragment && value.node.childNodes.length == 1) { - value = value.node.firstChild; - getSomeDefs(this).appendChild(value); - value = wrap(value); - } - if (value.type == "mask") { - var mask = value; - } else { - mask = make("mask", getSomeDefs(this)); - mask.node.appendChild(value.node); - } - !mask.node.id && $(mask.node, { - id: mask.id - }); - $(this.node, { - mask: URL(mask.id) - }); - } - }); - (function (clipIt) { - eve.on("snap.util.attr.clip", clipIt); - eve.on("snap.util.attr.clip-path", clipIt); - eve.on("snap.util.attr.clipPath", clipIt); - }(function (value) { - if (value instanceof Element || value instanceof Fragment) { - eve.stop(); - if (value.type == "clipPath") { - var clip = value; - } else { - clip = make("clipPath", getSomeDefs(this)); - clip.node.appendChild(value.node); - !clip.node.id && $(clip.node, { - id: clip.id - }); - } - $(this.node, { - "clip-path": URL(clip.node.id || clip.id) - }); - } - })); - function fillStroke(name) { - return function (value) { - eve.stop(); - if (value instanceof Fragment && value.node.childNodes.length == 1 && - (value.node.firstChild.tagName == "radialGradient" || - value.node.firstChild.tagName == "linearGradient" || - value.node.firstChild.tagName == "pattern")) { - value = value.node.firstChild; - getSomeDefs(this).appendChild(value); - value = wrap(value); - } - if (value instanceof Element) { - if (value.type == "radialGradient" || value.type == "linearGradient" - || value.type == "pattern") { - if (!value.node.id) { - $(value.node, { - id: value.id - }); - } - var fill = URL(value.node.id); - } else { - fill = value.attr(name); - } - } else { - fill = Snap.color(value); - if (fill.error) { - var grad = Snap(getSomeDefs(this).ownerSVGElement).gradient(value); - if (grad) { - if (!grad.node.id) { - $(grad.node, { - id: grad.id - }); - } - fill = URL(grad.node.id); - } else { - fill = value; - } - } else { - fill = Str(fill); - } - } - var attrs = {}; - attrs[name] = fill; - $(this.node, attrs); - this.node.style[name] = E; - }; - } - eve.on("snap.util.attr.fill", fillStroke("fill")); - eve.on("snap.util.attr.stroke", fillStroke("stroke")); - var gradrg = /^([lr])(?:\(([^)]*)\))?(.*)$/i; - eve.on("snap.util.grad.parse", function parseGrad(string) { - string = Str(string); - var tokens = string.match(gradrg); - if (!tokens) { - return null; - } - var type = tokens[1], - params = tokens[2], - stops = tokens[3]; - params = params.split(/\s*,\s*/).map(function (el) { - return +el == el ? +el : el; - }); - if (params.length == 1 && params[0] == 0) { - params = []; - } - stops = stops.split("-"); - stops = stops.map(function (el) { - el = el.split(":"); - var out = { - color: el[0] - }; - if (el[1]) { - out.offset = parseFloat(el[1]); - } - return out; - }); - return { - type: type, - params: params, - stops: stops - }; - }); - - eve.on("snap.util.attr.d", function (value) { - eve.stop(); - if (is(value, "array") && is(value[0], "array")) { - value = Snap.path.toString.call(value); - } - value = Str(value); - if (value.match(/[ruo]/i)) { - value = Snap.path.toAbsolute(value); - } - $(this.node, {d: value}); - })(-1); - eve.on("snap.util.attr.#text", function (value) { - eve.stop(); - value = Str(value); - var txt = glob.doc.createTextNode(value); - while (this.node.firstChild) { - this.node.removeChild(this.node.firstChild); - } - this.node.appendChild(txt); - })(-1); - eve.on("snap.util.attr.path", function (value) { - eve.stop(); - this.attr({d: value}); - })(-1); - eve.on("snap.util.attr.class", function (value) { - eve.stop(); - this.node.className.baseVal = value; - })(-1); - eve.on("snap.util.attr.viewBox", function (value) { - var vb; - if (is(value, "object") && "x" in value) { - vb = [value.x, value.y, value.width, value.height].join(" "); - } else if (is(value, "array")) { - vb = value.join(" "); - } else { - vb = value; - } - $(this.node, { - viewBox: vb - }); - eve.stop(); - })(-1); - eve.on("snap.util.attr.transform", function (value) { - this.transform(value); - eve.stop(); - })(-1); - eve.on("snap.util.attr.r", function (value) { - if (this.type == "rect") { - eve.stop(); - $(this.node, { - rx: value, - ry: value - }); - } - })(-1); - eve.on("snap.util.attr.textpath", function (value) { - eve.stop(); - if (this.type == "text") { - var id, tp, node; - if (!value && this.textPath) { - tp = this.textPath; - while (tp.node.firstChild) { - this.node.appendChild(tp.node.firstChild); - } - tp.remove(); - delete this.textPath; - return; - } - if (is(value, "string")) { - var defs = getSomeDefs(this), - path = wrap(defs.parentNode).path(value); - defs.appendChild(path.node); - id = path.id; - path.attr({id: id}); - } else { - value = wrap(value); - if (value instanceof Element) { - id = value.attr("id"); - if (!id) { - id = value.id; - value.attr({id: id}); - } - } - } - if (id) { - tp = this.textPath; - node = this.node; - if (tp) { - tp.attr({"xlink:href": "#" + id}); - } else { - tp = $("textPath", { - "xlink:href": "#" + id - }); - while (node.firstChild) { - tp.appendChild(node.firstChild); - } - node.appendChild(tp); - this.textPath = wrap(tp); - } - } - } - })(-1); - eve.on("snap.util.attr.text", function (value) { - if (this.type == "text") { - var i = 0, - node = this.node, - tuner = function (chunk) { - var out = $("tspan"); - if (is(chunk, "array")) { - for (var i = 0; i < chunk.length; i++) { - out.appendChild(tuner(chunk[i])); - } - } else { - out.appendChild(glob.doc.createTextNode(chunk)); - } - out.normalize && out.normalize(); - return out; - }; - while (node.firstChild) { - node.removeChild(node.firstChild); - } - var tuned = tuner(value); - while (tuned.firstChild) { - node.appendChild(tuned.firstChild); - } - } - eve.stop(); - })(-1); - function setFontSize(value) { - eve.stop(); - if (value == +value) { - value += "px"; - } - this.node.style.fontSize = value; - } - eve.on("snap.util.attr.fontSize", setFontSize)(-1); - eve.on("snap.util.attr.font-size", setFontSize)(-1); - - - eve.on("snap.util.getattr.transform", function () { - eve.stop(); - return this.transform(); - })(-1); - eve.on("snap.util.getattr.textpath", function () { - eve.stop(); - return this.textPath; - })(-1); - // Markers - (function () { - function getter(end) { - return function () { - eve.stop(); - var style = glob.doc.defaultView.getComputedStyle(this.node, null).getPropertyValue("marker-" + end); - if (style == "none") { - return style; - } else { - return Snap(glob.doc.getElementById(style.match(reURLValue)[1])); - } - }; - } - function setter(end) { - return function (value) { - eve.stop(); - var name = "marker" + end.charAt(0).toUpperCase() + end.substring(1); - if (value == "" || !value) { - this.node.style[name] = "none"; - return; - } - if (value.type == "marker") { - var id = value.node.id; - if (!id) { - $(value.node, {id: value.id}); - } - this.node.style[name] = URL(id); - return; - } - }; - } - eve.on("snap.util.getattr.marker-end", getter("end"))(-1); - eve.on("snap.util.getattr.markerEnd", getter("end"))(-1); - eve.on("snap.util.getattr.marker-start", getter("start"))(-1); - eve.on("snap.util.getattr.markerStart", getter("start"))(-1); - eve.on("snap.util.getattr.marker-mid", getter("mid"))(-1); - eve.on("snap.util.getattr.markerMid", getter("mid"))(-1); - eve.on("snap.util.attr.marker-end", setter("end"))(-1); - eve.on("snap.util.attr.markerEnd", setter("end"))(-1); - eve.on("snap.util.attr.marker-start", setter("start"))(-1); - eve.on("snap.util.attr.markerStart", setter("start"))(-1); - eve.on("snap.util.attr.marker-mid", setter("mid"))(-1); - eve.on("snap.util.attr.markerMid", setter("mid"))(-1); - }()); - eve.on("snap.util.getattr.r", function () { - if (this.type == "rect" && $(this.node, "rx") == $(this.node, "ry")) { - eve.stop(); - return $(this.node, "rx"); - } - })(-1); - function textExtract(node) { - var out = []; - var children = node.childNodes; - for (var i = 0, ii = children.length; i < ii; i++) { - var chi = children[i]; - if (chi.nodeType == 3) { - out.push(chi.nodeValue); - } - if (chi.tagName == "tspan") { - if (chi.childNodes.length == 1 && chi.firstChild.nodeType == 3) { - out.push(chi.firstChild.nodeValue); - } else { - out.push(textExtract(chi)); - } - } - } - return out; - } - eve.on("snap.util.getattr.text", function () { - if (this.type == "text" || this.type == "tspan") { - eve.stop(); - var out = textExtract(this.node); - return out.length == 1 ? out[0] : out; - } - })(-1); - eve.on("snap.util.getattr.#text", function () { - return this.node.textContent; - })(-1); - eve.on("snap.util.getattr.viewBox", function () { - eve.stop(); - var vb = $(this.node, "viewBox"); - if (vb) { - vb = vb.split(separator); - return Snap._.box(+vb[0], +vb[1], +vb[2], +vb[3]); - } else { - return; - } - })(-1); - eve.on("snap.util.getattr.points", function () { - var p = $(this.node, "points"); - eve.stop(); - if (p) { - return p.split(separator); - } else { - return; - } - })(-1); - eve.on("snap.util.getattr.path", function () { - var p = $(this.node, "d"); - eve.stop(); - return p; - })(-1); - eve.on("snap.util.getattr.class", function () { - return this.node.className.baseVal; - })(-1); - function getFontSize() { - eve.stop(); - return this.node.style.fontSize; - } - eve.on("snap.util.getattr.fontSize", getFontSize)(-1); - eve.on("snap.util.getattr.font-size", getFontSize)(-1); -}); - -// Copyright (c) 2014 Adobe Systems Incorporated. All rights reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -Snap.plugin(function (Snap, Element, Paper, glob, Fragment) { - var rgNotSpace = /\S+/g, - rgBadSpace = /[\t\r\n\f]/g, - rgTrim = /(^\s+|\s+$)/g, - Str = String, - elproto = Element.prototype; - /*\ - * Element.addClass - [ method ] - ** - * Adds given class name or list of class names to the element. - - value (string) class name or space separated list of class names - ** - = (Element) original element. - \*/ - elproto.addClass = function (value) { - var classes = Str(value || "").match(rgNotSpace) || [], - elem = this.node, - className = elem.className.baseVal, - curClasses = className.match(rgNotSpace) || [], - j, - pos, - clazz, - finalValue; - - if (classes.length) { - j = 0; - while ((clazz = classes[j++])) { - pos = curClasses.indexOf(clazz); - if (!~pos) { - curClasses.push(clazz); - } - } - - finalValue = curClasses.join(" "); - if (className != finalValue) { - elem.className.baseVal = finalValue; - } - } - return this; - }; - /*\ - * Element.removeClass - [ method ] - ** - * Removes given class name or list of class names from the element. - - value (string) class name or space separated list of class names - ** - = (Element) original element. - \*/ - elproto.removeClass = function (value) { - var classes = Str(value || "").match(rgNotSpace) || [], - elem = this.node, - className = elem.className.baseVal, - curClasses = className.match(rgNotSpace) || [], - j, - pos, - clazz, - finalValue; - if (curClasses.length) { - j = 0; - while ((clazz = classes[j++])) { - pos = curClasses.indexOf(clazz); - if (~pos) { - curClasses.splice(pos, 1); - } - } - - finalValue = curClasses.join(" "); - if (className != finalValue) { - elem.className.baseVal = finalValue; - } - } - return this; - }; - /*\ - * Element.hasClass - [ method ] - ** - * Checks if the element has a given class name in the list of class names applied to it. - - value (string) class name - ** - = (boolean) `true` if the element has given class - \*/ - elproto.hasClass = function (value) { - var elem = this.node, - className = elem.className.baseVal, - curClasses = className.match(rgNotSpace) || []; - return !!~curClasses.indexOf(value); - }; - /*\ - * Element.toggleClass - [ method ] - ** - * Add or remove one or more classes from the element, depending on either - * the class’s presence or the value of the `flag` argument. - - value (string) class name or space separated list of class names - - flag (boolean) value to determine whether the class should be added or removed - ** - = (Element) original element. - \*/ - elproto.toggleClass = function (value, flag) { - if (flag != null) { - if (flag) { - return this.addClass(value); - } else { - return this.removeClass(value); - } - } - var classes = (value || "").match(rgNotSpace) || [], - elem = this.node, - className = elem.className.baseVal, - curClasses = className.match(rgNotSpace) || [], - j, - pos, - clazz, - finalValue; - j = 0; - while ((clazz = classes[j++])) { - pos = curClasses.indexOf(clazz); - if (~pos) { - curClasses.splice(pos, 1); - } else { - curClasses.push(clazz); - } - } - - finalValue = curClasses.join(" "); - if (className != finalValue) { - elem.className.baseVal = finalValue; - } - return this; - }; -}); - -// Copyright (c) 2013 Adobe Systems Incorporated. All rights reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -Snap.plugin(function (Snap, Element, Paper, glob, Fragment) { - var operators = { - "+": function (x, y) { - return x + y; - }, - "-": function (x, y) { - return x - y; - }, - "/": function (x, y) { - return x / y; - }, - "*": function (x, y) { - return x * y; - } - }, - Str = String, - reUnit = /[a-z]+$/i, - reAddon = /^\s*([+\-\/*])\s*=\s*([\d.eE+\-]+)\s*([^\d\s]+)?\s*$/; - function getNumber(val) { - return val; - } - function getUnit(unit) { - return function (val) { - return +val.toFixed(3) + unit; - }; - } - eve.on("snap.util.attr", function (val) { - var plus = Str(val).match(reAddon); - if (plus) { - var evnt = eve.nt(), - name = evnt.substring(evnt.lastIndexOf(".") + 1), - a = this.attr(name), - atr = {}; - eve.stop(); - var unit = plus[3] || "", - aUnit = a.match(reUnit), - op = operators[plus[1]]; - if (aUnit && aUnit == unit) { - val = op(parseFloat(a), +plus[2]); - } else { - a = this.asPX(name); - val = op(this.asPX(name), this.asPX(name, plus[2] + unit)); - } - if (isNaN(a) || isNaN(val)) { - return; - } - atr[name] = val; - this.attr(atr); - } - })(-10); - eve.on("snap.util.equal", function (name, b) { - var A, B, a = Str(this.attr(name) || ""), - el = this, - bplus = Str(b).match(reAddon); - if (bplus) { - eve.stop(); - var unit = bplus[3] || "", - aUnit = a.match(reUnit), - op = operators[bplus[1]]; - if (aUnit && aUnit == unit) { - return { - from: parseFloat(a), - to: op(parseFloat(a), +bplus[2]), - f: getUnit(aUnit) - }; - } else { - a = this.asPX(name); - return { - from: a, - to: op(a, this.asPX(name, bplus[2] + unit)), - f: getNumber - }; - } - } - })(-10); -}); -// Copyright (c) 2013 Adobe Systems Incorporated. All rights reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -Snap.plugin(function (Snap, Element, Paper, glob, Fragment) { - var proto = Paper.prototype, - is = Snap.is; - /*\ - * Paper.rect - [ method ] - * - * Draws a rectangle - ** - - x (number) x coordinate of the top left corner - - y (number) y coordinate of the top left corner - - width (number) width - - height (number) height - - rx (number) #optional horizontal radius for rounded corners, default is 0 - - ry (number) #optional vertical radius for rounded corners, default is rx or 0 - = (object) the `rect` element - ** - > Usage - | // regular rectangle - | var c = paper.rect(10, 10, 50, 50); - | // rectangle with rounded corners - | var c = paper.rect(40, 40, 50, 50, 10); - \*/ - proto.rect = function (x, y, w, h, rx, ry) { - var attr; - if (ry == null) { - ry = rx; - } - if (is(x, "object") && x == "[object Object]") { - attr = x; - } else if (x != null) { - attr = { - x: x, - y: y, - width: w, - height: h - }; - if (rx != null) { - attr.rx = rx; - attr.ry = ry; - } - } - return this.el("rect", attr); - }; - /*\ - * Paper.circle - [ method ] - ** - * Draws a circle - ** - - x (number) x coordinate of the centre - - y (number) y coordinate of the centre - - r (number) radius - = (object) the `circle` element - ** - > Usage - | var c = paper.circle(50, 50, 40); - \*/ - proto.circle = function (cx, cy, r) { - var attr; - if (is(cx, "object") && cx == "[object Object]") { - attr = cx; - } else if (cx != null) { - attr = { - cx: cx, - cy: cy, - r: r - }; - } - return this.el("circle", attr); - }; - - var preload = (function () { - function onerror() { - this.parentNode.removeChild(this); - } - return function (src, f) { - var img = glob.doc.createElement("img"), - body = glob.doc.body; - img.style.cssText = "position:absolute;left:-9999em;top:-9999em"; - img.onload = function () { - f.call(img); - img.onload = img.onerror = null; - body.removeChild(img); - }; - img.onerror = onerror; - body.appendChild(img); - img.src = src; - }; - }()); - - /*\ - * Paper.image - [ method ] - ** - * Places an image on the surface - ** - - src (string) URI of the source image - - x (number) x offset position - - y (number) y offset position - - width (number) width of the image - - height (number) height of the image - = (object) the `image` element - * or - = (object) Snap element object with type `image` - ** - > Usage - | var c = paper.image("apple.png", 10, 10, 80, 80); - \*/ - proto.image = function (src, x, y, width, height) { - var el = this.el("image"); - if (is(src, "object") && "src" in src) { - el.attr(src); - } else if (src != null) { - var set = { - "xlink:href": src, - preserveAspectRatio: "none" - }; - if (x != null && y != null) { - set.x = x; - set.y = y; - } - if (width != null && height != null) { - set.width = width; - set.height = height; - } else { - preload(src, function () { - Snap._.$(el.node, { - width: this.offsetWidth, - height: this.offsetHeight - }); - }); - } - Snap._.$(el.node, set); - } - return el; - }; - /*\ - * Paper.ellipse - [ method ] - ** - * Draws an ellipse - ** - - x (number) x coordinate of the centre - - y (number) y coordinate of the centre - - rx (number) horizontal radius - - ry (number) vertical radius - = (object) the `ellipse` element - ** - > Usage - | var c = paper.ellipse(50, 50, 40, 20); - \*/ - proto.ellipse = function (cx, cy, rx, ry) { - var attr; - if (is(cx, "object") && cx == "[object Object]") { - attr = cx; - } else if (cx != null) { - attr ={ - cx: cx, - cy: cy, - rx: rx, - ry: ry - }; - } - return this.el("ellipse", attr); - }; - // SIERRA Paper.path(): Unclear from the link what a Catmull-Rom curveto is, and why it would make life any easier. - /*\ - * Paper.path - [ method ] - ** - * Creates a `` element using the given string as the path's definition - - pathString (string) #optional path string in SVG format - * Path string consists of one-letter commands, followed by comma seprarated arguments in numerical form. Example: - | "M10,20L30,40" - * This example features two commands: `M`, with arguments `(10, 20)` and `L` with arguments `(30, 40)`. Uppercase letter commands express coordinates in absolute terms, while lowercase commands express them in relative terms from the most recently declared coordinates. - * - #

Here is short list of commands available, for more details see SVG path string format or article about path strings at MDN.

- # - # - # - # - # - # - # - # - # - # - # - #
CommandNameParameters
Mmoveto(x y)+
Zclosepath(none)
Llineto(x y)+
Hhorizontal linetox+
Vvertical linetoy+
Ccurveto(x1 y1 x2 y2 x y)+
Ssmooth curveto(x2 y2 x y)+
Qquadratic Bézier curveto(x1 y1 x y)+
Tsmooth quadratic Bézier curveto(x y)+
Aelliptical arc(rx ry x-axis-rotation large-arc-flag sweep-flag x y)+
RCatmull-Rom curveto*x1 y1 (x y)+
- * * _Catmull-Rom curveto_ is a not standard SVG command and added to make life easier. - * Note: there is a special case when a path consists of only three commands: `M10,10R…z`. In this case the path connects back to its starting point. - > Usage - | var c = paper.path("M10 10L90 90"); - | // draw a diagonal line: - | // move to 10,10, line to 90,90 - \*/ - proto.path = function (d) { - var attr; - if (is(d, "object") && !is(d, "array")) { - attr = d; - } else if (d) { - attr = {d: d}; - } - return this.el("path", attr); - }; - /*\ - * Paper.g - [ method ] - ** - * Creates a group element - ** - - varargs (…) #optional elements to nest within the group - = (object) the `g` element - ** - > Usage - | var c1 = paper.circle(), - | c2 = paper.rect(), - | g = paper.g(c2, c1); // note that the order of elements is different - * or - | var c1 = paper.circle(), - | c2 = paper.rect(), - | g = paper.g(); - | g.add(c2, c1); - \*/ - /*\ - * Paper.group - [ method ] - ** - * See @Paper.g - \*/ - proto.group = proto.g = function (first) { - var attr, - el = this.el("g"); - if (arguments.length == 1 && first && !first.type) { - el.attr(first); - } else if (arguments.length) { - el.add(Array.prototype.slice.call(arguments, 0)); - } - return el; - }; - /*\ - * Paper.svg - [ method ] - ** - * Creates a nested SVG element. - - x (number) @optional X of the element - - y (number) @optional Y of the element - - width (number) @optional width of the element - - height (number) @optional height of the element - - vbx (number) @optional viewbox X - - vby (number) @optional viewbox Y - - vbw (number) @optional viewbox width - - vbh (number) @optional viewbox height - ** - = (object) the `svg` element - ** - \*/ - proto.svg = function (x, y, width, height, vbx, vby, vbw, vbh) { - var attrs = {}; - if (is(x, "object") && y == null) { - attrs = x; - } else { - if (x != null) { - attrs.x = x; - } - if (y != null) { - attrs.y = y; - } - if (width != null) { - attrs.width = width; - } - if (height != null) { - attrs.height = height; - } - if (vbx != null && vby != null && vbw != null && vbh != null) { - attrs.viewBox = [vbx, vby, vbw, vbh]; - } - } - return this.el("svg", attrs); - }; - /*\ - * Paper.mask - [ method ] - ** - * Equivalent in behaviour to @Paper.g, except it’s a mask. - ** - = (object) the `mask` element - ** - \*/ - proto.mask = function (first) { - var attr, - el = this.el("mask"); - if (arguments.length == 1 && first && !first.type) { - el.attr(first); - } else if (arguments.length) { - el.add(Array.prototype.slice.call(arguments, 0)); - } - return el; - }; - /*\ - * Paper.ptrn - [ method ] - ** - * Equivalent in behaviour to @Paper.g, except it’s a pattern. - - x (number) @optional X of the element - - y (number) @optional Y of the element - - width (number) @optional width of the element - - height (number) @optional height of the element - - vbx (number) @optional viewbox X - - vby (number) @optional viewbox Y - - vbw (number) @optional viewbox width - - vbh (number) @optional viewbox height - ** - = (object) the `pattern` element - ** - \*/ - proto.ptrn = function (x, y, width, height, vx, vy, vw, vh) { - if (is(x, "object")) { - var attr = x; - } else { - attr = {patternUnits: "userSpaceOnUse"}; - if (x) { - attr.x = x; - } - if (y) { - attr.y = y; - } - if (width != null) { - attr.width = width; - } - if (height != null) { - attr.height = height; - } - if (vx != null && vy != null && vw != null && vh != null) { - attr.viewBox = [vx, vy, vw, vh]; - } else { - attr.viewBox = [x || 0, y || 0, width || 0, height || 0]; - } - } - return this.el("pattern", attr); - }; - /*\ - * Paper.use - [ method ] - ** - * Creates a element. - - id (string) @optional id of element to link - * or - - id (Element) @optional element to link - ** - = (object) the `use` element - ** - \*/ - proto.use = function (id) { - if (id != null) { - if (id instanceof Element) { - if (!id.attr("id")) { - id.attr({id: Snap._.id(id)}); - } - id = id.attr("id"); - } - if (String(id).charAt() == "#") { - id = id.substring(1); - } - return this.el("use", {"xlink:href": "#" + id}); - } else { - return Element.prototype.use.call(this); - } - }; - /*\ - * Paper.symbol - [ method ] - ** - * Creates a element. - - vbx (number) @optional viewbox X - - vby (number) @optional viewbox Y - - vbw (number) @optional viewbox width - - vbh (number) @optional viewbox height - = (object) the `symbol` element - ** - \*/ - proto.symbol = function (vx, vy, vw, vh) { - var attr = {}; - if (vx != null && vy != null && vw != null && vh != null) { - attr.viewBox = [vx, vy, vw, vh]; - } - - return this.el("symbol", attr); - }; - /*\ - * Paper.text - [ method ] - ** - * Draws a text string - ** - - x (number) x coordinate position - - y (number) y coordinate position - - text (string|array) The text string to draw or array of strings to nest within separate `` elements - = (object) the `text` element - ** - > Usage - | var t1 = paper.text(50, 50, "Snap"); - | var t2 = paper.text(50, 50, ["S","n","a","p"]); - | // Text path usage - | t1.attr({textpath: "M10,10L100,100"}); - | // or - | var pth = paper.path("M10,10L100,100"); - | t1.attr({textpath: pth}); - \*/ - proto.text = function (x, y, text) { - var attr = {}; - if (is(x, "object")) { - attr = x; - } else if (x != null) { - attr = { - x: x, - y: y, - text: text || "" - }; - } - return this.el("text", attr); - }; - /*\ - * Paper.line - [ method ] - ** - * Draws a line - ** - - x1 (number) x coordinate position of the start - - y1 (number) y coordinate position of the start - - x2 (number) x coordinate position of the end - - y2 (number) y coordinate position of the end - = (object) the `line` element - ** - > Usage - | var t1 = paper.line(50, 50, 100, 100); - \*/ - proto.line = function (x1, y1, x2, y2) { - var attr = {}; - if (is(x1, "object")) { - attr = x1; - } else if (x1 != null) { - attr = { - x1: x1, - x2: x2, - y1: y1, - y2: y2 - }; - } - return this.el("line", attr); - }; - /*\ - * Paper.polyline - [ method ] - ** - * Draws a polyline - ** - - points (array) array of points - * or - - varargs (…) points - = (object) the `polyline` element - ** - > Usage - | var p1 = paper.polyline([10, 10, 100, 100]); - | var p2 = paper.polyline(10, 10, 100, 100); - \*/ - proto.polyline = function (points) { - if (arguments.length > 1) { - points = Array.prototype.slice.call(arguments, 0); - } - var attr = {}; - if (is(points, "object") && !is(points, "array")) { - attr = points; - } else if (points != null) { - attr = {points: points}; - } - return this.el("polyline", attr); - }; - /*\ - * Paper.polygon - [ method ] - ** - * Draws a polygon. See @Paper.polyline - \*/ - proto.polygon = function (points) { - if (arguments.length > 1) { - points = Array.prototype.slice.call(arguments, 0); - } - var attr = {}; - if (is(points, "object") && !is(points, "array")) { - attr = points; - } else if (points != null) { - attr = {points: points}; - } - return this.el("polygon", attr); - }; - // gradients - (function () { - var $ = Snap._.$; - // gradients' helpers - function Gstops() { - return this.selectAll("stop"); - } - function GaddStop(color, offset) { - var stop = $("stop"), - attr = { - offset: +offset + "%" - }; - color = Snap.color(color); - attr["stop-color"] = color.hex; - if (color.opacity < 1) { - attr["stop-opacity"] = color.opacity; - } - $(stop, attr); - this.node.appendChild(stop); - return this; - } - function GgetBBox() { - if (this.type == "linearGradient") { - var x1 = $(this.node, "x1") || 0, - x2 = $(this.node, "x2") || 1, - y1 = $(this.node, "y1") || 0, - y2 = $(this.node, "y2") || 0; - return Snap._.box(x1, y1, math.abs(x2 - x1), math.abs(y2 - y1)); - } else { - var cx = this.node.cx || .5, - cy = this.node.cy || .5, - r = this.node.r || 0; - return Snap._.box(cx - r, cy - r, r * 2, r * 2); - } - } - function gradient(defs, str) { - var grad = eve("snap.util.grad.parse", null, str).firstDefined(), - el; - if (!grad) { - return null; - } - grad.params.unshift(defs); - if (grad.type.toLowerCase() == "l") { - el = gradientLinear.apply(0, grad.params); - } else { - el = gradientRadial.apply(0, grad.params); - } - if (grad.type != grad.type.toLowerCase()) { - $(el.node, { - gradientUnits: "userSpaceOnUse" - }); - } - var stops = grad.stops, - len = stops.length, - start = 0, - j = 0; - function seed(i, end) { - var step = (end - start) / (i - j); - for (var k = j; k < i; k++) { - stops[k].offset = +(+start + step * (k - j)).toFixed(2); - } - j = i; - start = end; - } - len--; - for (var i = 0; i < len; i++) if ("offset" in stops[i]) { - seed(i, stops[i].offset); - } - stops[len].offset = stops[len].offset || 100; - seed(len, stops[len].offset); - for (i = 0; i <= len; i++) { - var stop = stops[i]; - el.addStop(stop.color, stop.offset); - } - return el; - } - function gradientLinear(defs, x1, y1, x2, y2) { - var el = Snap._.make("linearGradient", defs); - el.stops = Gstops; - el.addStop = GaddStop; - el.getBBox = GgetBBox; - if (x1 != null) { - $(el.node, { - x1: x1, - y1: y1, - x2: x2, - y2: y2 - }); - } - return el; - } - function gradientRadial(defs, cx, cy, r, fx, fy) { - var el = Snap._.make("radialGradient", defs); - el.stops = Gstops; - el.addStop = GaddStop; - el.getBBox = GgetBBox; - if (cx != null) { - $(el.node, { - cx: cx, - cy: cy, - r: r - }); - } - if (fx != null && fy != null) { - $(el.node, { - fx: fx, - fy: fy - }); - } - return el; - } - /*\ - * Paper.gradient - [ method ] - ** - * Creates a gradient element - ** - - gradient (string) gradient descriptor - > Gradient Descriptor - * The gradient descriptor is an expression formatted as - * follows: `()`. The `` can be - * either linear or radial. The uppercase `L` or `R` letters - * indicate absolute coordinates offset from the SVG surface. - * Lowercase `l` or `r` letters indicate coordinates - * calculated relative to the element to which the gradient is - * applied. Coordinates specify a linear gradient vector as - * `x1`, `y1`, `x2`, `y2`, or a radial gradient as `cx`, `cy`, - * `r` and optional `fx`, `fy` specifying a focal point away - * from the center of the circle. Specify `` as a list - * of dash-separated CSS color values. Each color may be - * followed by a custom offset value, separated with a colon - * character. - > Examples - * Linear gradient, relative from top-left corner to bottom-right - * corner, from black through red to white: - | var g = paper.gradient("l(0, 0, 1, 1)#000-#f00-#fff"); - * Linear gradient, absolute from (0, 0) to (100, 100), from black - * through red at 25% to white: - | var g = paper.gradient("L(0, 0, 100, 100)#000-#f00:25-#fff"); - * Radial gradient, relative from the center of the element with radius - * half the width, from black to white: - | var g = paper.gradient("r(0.5, 0.5, 0.5)#000-#fff"); - * To apply the gradient: - | paper.circle(50, 50, 40).attr({ - | fill: g - | }); - = (object) the `gradient` element - \*/ - proto.gradient = function (str) { - return gradient(this.defs, str); - }; - proto.gradientLinear = function (x1, y1, x2, y2) { - return gradientLinear(this.defs, x1, y1, x2, y2); - }; - proto.gradientRadial = function (cx, cy, r, fx, fy) { - return gradientRadial(this.defs, cx, cy, r, fx, fy); - }; - /*\ - * Paper.toString - [ method ] - ** - * Returns SVG code for the @Paper - = (string) SVG code for the @Paper - \*/ - proto.toString = function () { - var doc = this.node.ownerDocument, - f = doc.createDocumentFragment(), - d = doc.createElement("div"), - svg = this.node.cloneNode(true), - res; - f.appendChild(d); - d.appendChild(svg); - Snap._.$(svg, {xmlns: "http://www.w3.org/2000/svg"}); - res = d.innerHTML; - f.removeChild(f.firstChild); - return res; - }; - /*\ - * Paper.toDataURL - [ method ] - ** - * Returns SVG code for the @Paper as Data URI string. - = (string) Data URI string - \*/ - proto.toDataURL = function () { - if (window && window.btoa) { - return "data:image/svg+xml;base64," + btoa(unescape(encodeURIComponent(this))); - } - }; - /*\ - * Paper.clear - [ method ] - ** - * Removes all child nodes of the paper, except . - \*/ - proto.clear = function () { - var node = this.node.firstChild, - next; - while (node) { - next = node.nextSibling; - if (node.tagName != "defs") { - node.parentNode.removeChild(node); - } else { - proto.clear.call({node: node}); - } - node = next; - } - }; - }()); -}); - -// Copyright (c) 2013 Adobe Systems Incorporated. All rights reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -Snap.plugin(function (Snap, Element, Paper, glob) { - var elproto = Element.prototype, - is = Snap.is, - clone = Snap._.clone, - has = "hasOwnProperty", - p2s = /,?([a-z]),?/gi, - toFloat = parseFloat, - math = Math, - PI = math.PI, - mmin = math.min, - mmax = math.max, - pow = math.pow, - abs = math.abs; - function paths(ps) { - var p = paths.ps = paths.ps || {}; - if (p[ps]) { - p[ps].sleep = 100; - } else { - p[ps] = { - sleep: 100 - }; - } - setTimeout(function () { - for (var key in p) if (p[has](key) && key != ps) { - p[key].sleep--; - !p[key].sleep && delete p[key]; - } - }); - return p[ps]; - } - function box(x, y, width, height) { - if (x == null) { - x = y = width = height = 0; - } - if (y == null) { - y = x.y; - width = x.width; - height = x.height; - x = x.x; - } - return { - x: x, - y: y, - width: width, - w: width, - height: height, - h: height, - x2: x + width, - y2: y + height, - cx: x + width / 2, - cy: y + height / 2, - r1: math.min(width, height) / 2, - r2: math.max(width, height) / 2, - r0: math.sqrt(width * width + height * height) / 2, - path: rectPath(x, y, width, height), - vb: [x, y, width, height].join(" ") - }; - } - function toString() { - return this.join(",").replace(p2s, "$1"); - } - function pathClone(pathArray) { - var res = clone(pathArray); - res.toString = toString; - return res; - } - function getPointAtSegmentLength(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y, length) { - if (length == null) { - return bezlen(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y); - } else { - return findDotsAtSegment(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y, - getTotLen(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y, length)); - } - } - function getLengthFactory(istotal, subpath) { - function O(val) { - return +(+val).toFixed(3); - } - return Snap._.cacher(function (path, length, onlystart) { - if (path instanceof Element) { - path = path.attr("d"); - } - path = path2curve(path); - var x, y, p, l, sp = "", subpaths = {}, point, - len = 0; - for (var i = 0, ii = path.length; i < ii; i++) { - p = path[i]; - if (p[0] == "M") { - x = +p[1]; - y = +p[2]; - } else { - l = getPointAtSegmentLength(x, y, p[1], p[2], p[3], p[4], p[5], p[6]); - if (len + l > length) { - if (subpath && !subpaths.start) { - point = getPointAtSegmentLength(x, y, p[1], p[2], p[3], p[4], p[5], p[6], length - len); - sp += [ - "C" + O(point.start.x), - O(point.start.y), - O(point.m.x), - O(point.m.y), - O(point.x), - O(point.y) - ]; - if (onlystart) {return sp;} - subpaths.start = sp; - sp = [ - "M" + O(point.x), - O(point.y) + "C" + O(point.n.x), - O(point.n.y), - O(point.end.x), - O(point.end.y), - O(p[5]), - O(p[6]) - ].join(); - len += l; - x = +p[5]; - y = +p[6]; - continue; - } - if (!istotal && !subpath) { - point = getPointAtSegmentLength(x, y, p[1], p[2], p[3], p[4], p[5], p[6], length - len); - return point; - } - } - len += l; - x = +p[5]; - y = +p[6]; - } - sp += p.shift() + p; - } - subpaths.end = sp; - point = istotal ? len : subpath ? subpaths : findDotsAtSegment(x, y, p[0], p[1], p[2], p[3], p[4], p[5], 1); - return point; - }, null, Snap._.clone); - } - var getTotalLength = getLengthFactory(1), - getPointAtLength = getLengthFactory(), - getSubpathsAtLength = getLengthFactory(0, 1); - function findDotsAtSegment(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y, t) { - var t1 = 1 - t, - t13 = pow(t1, 3), - t12 = pow(t1, 2), - t2 = t * t, - t3 = t2 * t, - x = t13 * p1x + t12 * 3 * t * c1x + t1 * 3 * t * t * c2x + t3 * p2x, - y = t13 * p1y + t12 * 3 * t * c1y + t1 * 3 * t * t * c2y + t3 * p2y, - mx = p1x + 2 * t * (c1x - p1x) + t2 * (c2x - 2 * c1x + p1x), - my = p1y + 2 * t * (c1y - p1y) + t2 * (c2y - 2 * c1y + p1y), - nx = c1x + 2 * t * (c2x - c1x) + t2 * (p2x - 2 * c2x + c1x), - ny = c1y + 2 * t * (c2y - c1y) + t2 * (p2y - 2 * c2y + c1y), - ax = t1 * p1x + t * c1x, - ay = t1 * p1y + t * c1y, - cx = t1 * c2x + t * p2x, - cy = t1 * c2y + t * p2y, - alpha = (90 - math.atan2(mx - nx, my - ny) * 180 / PI); - // (mx > nx || my < ny) && (alpha += 180); - return { - x: x, - y: y, - m: {x: mx, y: my}, - n: {x: nx, y: ny}, - start: {x: ax, y: ay}, - end: {x: cx, y: cy}, - alpha: alpha - }; - } - function bezierBBox(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y) { - if (!Snap.is(p1x, "array")) { - p1x = [p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y]; - } - var bbox = curveDim.apply(null, p1x); - return box( - bbox.min.x, - bbox.min.y, - bbox.max.x - bbox.min.x, - bbox.max.y - bbox.min.y - ); - } - function isPointInsideBBox(bbox, x, y) { - return x >= bbox.x && - x <= bbox.x + bbox.width && - y >= bbox.y && - y <= bbox.y + bbox.height; - } - function isBBoxIntersect(bbox1, bbox2) { - bbox1 = box(bbox1); - bbox2 = box(bbox2); - return isPointInsideBBox(bbox2, bbox1.x, bbox1.y) - || isPointInsideBBox(bbox2, bbox1.x2, bbox1.y) - || isPointInsideBBox(bbox2, bbox1.x, bbox1.y2) - || isPointInsideBBox(bbox2, bbox1.x2, bbox1.y2) - || isPointInsideBBox(bbox1, bbox2.x, bbox2.y) - || isPointInsideBBox(bbox1, bbox2.x2, bbox2.y) - || isPointInsideBBox(bbox1, bbox2.x, bbox2.y2) - || isPointInsideBBox(bbox1, bbox2.x2, bbox2.y2) - || (bbox1.x < bbox2.x2 && bbox1.x > bbox2.x - || bbox2.x < bbox1.x2 && bbox2.x > bbox1.x) - && (bbox1.y < bbox2.y2 && bbox1.y > bbox2.y - || bbox2.y < bbox1.y2 && bbox2.y > bbox1.y); - } - function base3(t, p1, p2, p3, p4) { - var t1 = -3 * p1 + 9 * p2 - 9 * p3 + 3 * p4, - t2 = t * t1 + 6 * p1 - 12 * p2 + 6 * p3; - return t * t2 - 3 * p1 + 3 * p2; - } - function bezlen(x1, y1, x2, y2, x3, y3, x4, y4, z) { - if (z == null) { - z = 1; - } - z = z > 1 ? 1 : z < 0 ? 0 : z; - var z2 = z / 2, - n = 12, - Tvalues = [-.1252,.1252,-.3678,.3678,-.5873,.5873,-.7699,.7699,-.9041,.9041,-.9816,.9816], - Cvalues = [0.2491,0.2491,0.2335,0.2335,0.2032,0.2032,0.1601,0.1601,0.1069,0.1069,0.0472,0.0472], - sum = 0; - for (var i = 0; i < n; i++) { - var ct = z2 * Tvalues[i] + z2, - xbase = base3(ct, x1, x2, x3, x4), - ybase = base3(ct, y1, y2, y3, y4), - comb = xbase * xbase + ybase * ybase; - sum += Cvalues[i] * math.sqrt(comb); - } - return z2 * sum; - } - function getTotLen(x1, y1, x2, y2, x3, y3, x4, y4, ll) { - if (ll < 0 || bezlen(x1, y1, x2, y2, x3, y3, x4, y4) < ll) { - return; - } - var t = 1, - step = t / 2, - t2 = t - step, - l, - e = .01; - l = bezlen(x1, y1, x2, y2, x3, y3, x4, y4, t2); - while (abs(l - ll) > e) { - step /= 2; - t2 += (l < ll ? 1 : -1) * step; - l = bezlen(x1, y1, x2, y2, x3, y3, x4, y4, t2); - } - return t2; - } - function intersect(x1, y1, x2, y2, x3, y3, x4, y4) { - if ( - mmax(x1, x2) < mmin(x3, x4) || - mmin(x1, x2) > mmax(x3, x4) || - mmax(y1, y2) < mmin(y3, y4) || - mmin(y1, y2) > mmax(y3, y4) - ) { - return; - } - var nx = (x1 * y2 - y1 * x2) * (x3 - x4) - (x1 - x2) * (x3 * y4 - y3 * x4), - ny = (x1 * y2 - y1 * x2) * (y3 - y4) - (y1 - y2) * (x3 * y4 - y3 * x4), - denominator = (x1 - x2) * (y3 - y4) - (y1 - y2) * (x3 - x4); - - if (!denominator) { - return; - } - var px = nx / denominator, - py = ny / denominator, - px2 = +px.toFixed(2), - py2 = +py.toFixed(2); - if ( - px2 < +mmin(x1, x2).toFixed(2) || - px2 > +mmax(x1, x2).toFixed(2) || - px2 < +mmin(x3, x4).toFixed(2) || - px2 > +mmax(x3, x4).toFixed(2) || - py2 < +mmin(y1, y2).toFixed(2) || - py2 > +mmax(y1, y2).toFixed(2) || - py2 < +mmin(y3, y4).toFixed(2) || - py2 > +mmax(y3, y4).toFixed(2) - ) { - return; - } - return {x: px, y: py}; - } - function inter(bez1, bez2) { - return interHelper(bez1, bez2); - } - function interCount(bez1, bez2) { - return interHelper(bez1, bez2, 1); - } - function interHelper(bez1, bez2, justCount) { - var bbox1 = bezierBBox(bez1), - bbox2 = bezierBBox(bez2); - if (!isBBoxIntersect(bbox1, bbox2)) { - return justCount ? 0 : []; - } - var l1 = bezlen.apply(0, bez1), - l2 = bezlen.apply(0, bez2), - n1 = ~~(l1 / 8), - n2 = ~~(l2 / 8), - dots1 = [], - dots2 = [], - xy = {}, - res = justCount ? 0 : []; - for (var i = 0; i < n1 + 1; i++) { - var p = findDotsAtSegment.apply(0, bez1.concat(i / n1)); - dots1.push({x: p.x, y: p.y, t: i / n1}); - } - for (i = 0; i < n2 + 1; i++) { - p = findDotsAtSegment.apply(0, bez2.concat(i / n2)); - dots2.push({x: p.x, y: p.y, t: i / n2}); - } - for (i = 0; i < n1; i++) { - for (var j = 0; j < n2; j++) { - var di = dots1[i], - di1 = dots1[i + 1], - dj = dots2[j], - dj1 = dots2[j + 1], - ci = abs(di1.x - di.x) < .001 ? "y" : "x", - cj = abs(dj1.x - dj.x) < .001 ? "y" : "x", - is = intersect(di.x, di.y, di1.x, di1.y, dj.x, dj.y, dj1.x, dj1.y); - if (is) { - if (xy[is.x.toFixed(4)] == is.y.toFixed(4)) { - continue; - } - xy[is.x.toFixed(4)] = is.y.toFixed(4); - var t1 = di.t + abs((is[ci] - di[ci]) / (di1[ci] - di[ci])) * (di1.t - di.t), - t2 = dj.t + abs((is[cj] - dj[cj]) / (dj1[cj] - dj[cj])) * (dj1.t - dj.t); - if (t1 >= 0 && t1 <= 1 && t2 >= 0 && t2 <= 1) { - if (justCount) { - res++; - } else { - res.push({ - x: is.x, - y: is.y, - t1: t1, - t2: t2 - }); - } - } - } - } - } - return res; - } - function pathIntersection(path1, path2) { - return interPathHelper(path1, path2); - } - function pathIntersectionNumber(path1, path2) { - return interPathHelper(path1, path2, 1); - } - function interPathHelper(path1, path2, justCount) { - path1 = path2curve(path1); - path2 = path2curve(path2); - var x1, y1, x2, y2, x1m, y1m, x2m, y2m, bez1, bez2, - res = justCount ? 0 : []; - for (var i = 0, ii = path1.length; i < ii; i++) { - var pi = path1[i]; - if (pi[0] == "M") { - x1 = x1m = pi[1]; - y1 = y1m = pi[2]; - } else { - if (pi[0] == "C") { - bez1 = [x1, y1].concat(pi.slice(1)); - x1 = bez1[6]; - y1 = bez1[7]; - } else { - bez1 = [x1, y1, x1, y1, x1m, y1m, x1m, y1m]; - x1 = x1m; - y1 = y1m; - } - for (var j = 0, jj = path2.length; j < jj; j++) { - var pj = path2[j]; - if (pj[0] == "M") { - x2 = x2m = pj[1]; - y2 = y2m = pj[2]; - } else { - if (pj[0] == "C") { - bez2 = [x2, y2].concat(pj.slice(1)); - x2 = bez2[6]; - y2 = bez2[7]; - } else { - bez2 = [x2, y2, x2, y2, x2m, y2m, x2m, y2m]; - x2 = x2m; - y2 = y2m; - } - var intr = interHelper(bez1, bez2, justCount); - if (justCount) { - res += intr; - } else { - for (var k = 0, kk = intr.length; k < kk; k++) { - intr[k].segment1 = i; - intr[k].segment2 = j; - intr[k].bez1 = bez1; - intr[k].bez2 = bez2; - } - res = res.concat(intr); - } - } - } - } - } - return res; - } - function isPointInsidePath(path, x, y) { - var bbox = pathBBox(path); - return isPointInsideBBox(bbox, x, y) && - interPathHelper(path, [["M", x, y], ["H", bbox.x2 + 10]], 1) % 2 == 1; - } - function pathBBox(path) { - var pth = paths(path); - if (pth.bbox) { - return clone(pth.bbox); - } - if (!path) { - return box(); - } - path = path2curve(path); - var x = 0, - y = 0, - X = [], - Y = [], - p; - for (var i = 0, ii = path.length; i < ii; i++) { - p = path[i]; - if (p[0] == "M") { - x = p[1]; - y = p[2]; - X.push(x); - Y.push(y); - } else { - var dim = curveDim(x, y, p[1], p[2], p[3], p[4], p[5], p[6]); - X = X.concat(dim.min.x, dim.max.x); - Y = Y.concat(dim.min.y, dim.max.y); - x = p[5]; - y = p[6]; - } - } - var xmin = mmin.apply(0, X), - ymin = mmin.apply(0, Y), - xmax = mmax.apply(0, X), - ymax = mmax.apply(0, Y), - bb = box(xmin, ymin, xmax - xmin, ymax - ymin); - pth.bbox = clone(bb); - return bb; - } - function rectPath(x, y, w, h, r) { - if (r) { - return [ - ["M", +x + (+r), y], - ["l", w - r * 2, 0], - ["a", r, r, 0, 0, 1, r, r], - ["l", 0, h - r * 2], - ["a", r, r, 0, 0, 1, -r, r], - ["l", r * 2 - w, 0], - ["a", r, r, 0, 0, 1, -r, -r], - ["l", 0, r * 2 - h], - ["a", r, r, 0, 0, 1, r, -r], - ["z"] - ]; - } - var res = [["M", x, y], ["l", w, 0], ["l", 0, h], ["l", -w, 0], ["z"]]; - res.toString = toString; - return res; - } - function ellipsePath(x, y, rx, ry, a) { - if (a == null && ry == null) { - ry = rx; - } - x = +x; - y = +y; - rx = +rx; - ry = +ry; - if (a != null) { - var rad = Math.PI / 180, - x1 = x + rx * Math.cos(-ry * rad), - x2 = x + rx * Math.cos(-a * rad), - y1 = y + rx * Math.sin(-ry * rad), - y2 = y + rx * Math.sin(-a * rad), - res = [["M", x1, y1], ["A", rx, rx, 0, +(a - ry > 180), 0, x2, y2]]; - } else { - res = [ - ["M", x, y], - ["m", 0, -ry], - ["a", rx, ry, 0, 1, 1, 0, 2 * ry], - ["a", rx, ry, 0, 1, 1, 0, -2 * ry], - ["z"] - ]; - } - res.toString = toString; - return res; - } - var unit2px = Snap._unit2px, - getPath = { - path: function (el) { - return el.attr("path"); - }, - circle: function (el) { - var attr = unit2px(el); - return ellipsePath(attr.cx, attr.cy, attr.r); - }, - ellipse: function (el) { - var attr = unit2px(el); - return ellipsePath(attr.cx || 0, attr.cy || 0, attr.rx, attr.ry); - }, - rect: function (el) { - var attr = unit2px(el); - return rectPath(attr.x || 0, attr.y || 0, attr.width, attr.height, attr.rx, attr.ry); - }, - image: function (el) { - var attr = unit2px(el); - return rectPath(attr.x || 0, attr.y || 0, attr.width, attr.height); - }, - line: function (el) { - return "M" + [el.attr("x1") || 0, el.attr("y1") || 0, el.attr("x2"), el.attr("y2")]; - }, - polyline: function (el) { - return "M" + el.attr("points"); - }, - polygon: function (el) { - return "M" + el.attr("points") + "z"; - }, - deflt: function (el) { - var bbox = el.node.getBBox(); - return rectPath(bbox.x, bbox.y, bbox.width, bbox.height); - } - }; - function pathToRelative(pathArray) { - var pth = paths(pathArray), - lowerCase = String.prototype.toLowerCase; - if (pth.rel) { - return pathClone(pth.rel); - } - if (!Snap.is(pathArray, "array") || !Snap.is(pathArray && pathArray[0], "array")) { - pathArray = Snap.parsePathString(pathArray); - } - var res = [], - x = 0, - y = 0, - mx = 0, - my = 0, - start = 0; - if (pathArray[0][0] == "M") { - x = pathArray[0][1]; - y = pathArray[0][2]; - mx = x; - my = y; - start++; - res.push(["M", x, y]); - } - for (var i = start, ii = pathArray.length; i < ii; i++) { - var r = res[i] = [], - pa = pathArray[i]; - if (pa[0] != lowerCase.call(pa[0])) { - r[0] = lowerCase.call(pa[0]); - switch (r[0]) { - case "a": - r[1] = pa[1]; - r[2] = pa[2]; - r[3] = pa[3]; - r[4] = pa[4]; - r[5] = pa[5]; - r[6] = +(pa[6] - x).toFixed(3); - r[7] = +(pa[7] - y).toFixed(3); - break; - case "v": - r[1] = +(pa[1] - y).toFixed(3); - break; - case "m": - mx = pa[1]; - my = pa[2]; - default: - for (var j = 1, jj = pa.length; j < jj; j++) { - r[j] = +(pa[j] - ((j % 2) ? x : y)).toFixed(3); - } - } - } else { - r = res[i] = []; - if (pa[0] == "m") { - mx = pa[1] + x; - my = pa[2] + y; - } - for (var k = 0, kk = pa.length; k < kk; k++) { - res[i][k] = pa[k]; - } - } - var len = res[i].length; - switch (res[i][0]) { - case "z": - x = mx; - y = my; - break; - case "h": - x += +res[i][len - 1]; - break; - case "v": - y += +res[i][len - 1]; - break; - default: - x += +res[i][len - 2]; - y += +res[i][len - 1]; - } - } - res.toString = toString; - pth.rel = pathClone(res); - return res; - } - function pathToAbsolute(pathArray) { - var pth = paths(pathArray); - if (pth.abs) { - return pathClone(pth.abs); - } - if (!is(pathArray, "array") || !is(pathArray && pathArray[0], "array")) { // rough assumption - pathArray = Snap.parsePathString(pathArray); - } - if (!pathArray || !pathArray.length) { - return [["M", 0, 0]]; - } - var res = [], - x = 0, - y = 0, - mx = 0, - my = 0, - start = 0, - pa0; - if (pathArray[0][0] == "M") { - x = +pathArray[0][1]; - y = +pathArray[0][2]; - mx = x; - my = y; - start++; - res[0] = ["M", x, y]; - } - var crz = pathArray.length == 3 && - pathArray[0][0] == "M" && - pathArray[1][0].toUpperCase() == "R" && - pathArray[2][0].toUpperCase() == "Z"; - for (var r, pa, i = start, ii = pathArray.length; i < ii; i++) { - res.push(r = []); - pa = pathArray[i]; - pa0 = pa[0]; - if (pa0 != pa0.toUpperCase()) { - r[0] = pa0.toUpperCase(); - switch (r[0]) { - case "A": - r[1] = pa[1]; - r[2] = pa[2]; - r[3] = pa[3]; - r[4] = pa[4]; - r[5] = pa[5]; - r[6] = +pa[6] + x; - r[7] = +pa[7] + y; - break; - case "V": - r[1] = +pa[1] + y; - break; - case "H": - r[1] = +pa[1] + x; - break; - case "R": - var dots = [x, y].concat(pa.slice(1)); - for (var j = 2, jj = dots.length; j < jj; j++) { - dots[j] = +dots[j] + x; - dots[++j] = +dots[j] + y; - } - res.pop(); - res = res.concat(catmullRom2bezier(dots, crz)); - break; - case "O": - res.pop(); - dots = ellipsePath(x, y, pa[1], pa[2]); - dots.push(dots[0]); - res = res.concat(dots); - break; - case "U": - res.pop(); - res = res.concat(ellipsePath(x, y, pa[1], pa[2], pa[3])); - r = ["U"].concat(res[res.length - 1].slice(-2)); - break; - case "M": - mx = +pa[1] + x; - my = +pa[2] + y; - default: - for (j = 1, jj = pa.length; j < jj; j++) { - r[j] = +pa[j] + ((j % 2) ? x : y); - } - } - } else if (pa0 == "R") { - dots = [x, y].concat(pa.slice(1)); - res.pop(); - res = res.concat(catmullRom2bezier(dots, crz)); - r = ["R"].concat(pa.slice(-2)); - } else if (pa0 == "O") { - res.pop(); - dots = ellipsePath(x, y, pa[1], pa[2]); - dots.push(dots[0]); - res = res.concat(dots); - } else if (pa0 == "U") { - res.pop(); - res = res.concat(ellipsePath(x, y, pa[1], pa[2], pa[3])); - r = ["U"].concat(res[res.length - 1].slice(-2)); - } else { - for (var k = 0, kk = pa.length; k < kk; k++) { - r[k] = pa[k]; - } - } - pa0 = pa0.toUpperCase(); - if (pa0 != "O") { - switch (r[0]) { - case "Z": - x = +mx; - y = +my; - break; - case "H": - x = r[1]; - break; - case "V": - y = r[1]; - break; - case "M": - mx = r[r.length - 2]; - my = r[r.length - 1]; - default: - x = r[r.length - 2]; - y = r[r.length - 1]; - } - } - } - res.toString = toString; - pth.abs = pathClone(res); - return res; - } - function l2c(x1, y1, x2, y2) { - return [x1, y1, x2, y2, x2, y2]; - } - function q2c(x1, y1, ax, ay, x2, y2) { - var _13 = 1 / 3, - _23 = 2 / 3; - return [ - _13 * x1 + _23 * ax, - _13 * y1 + _23 * ay, - _13 * x2 + _23 * ax, - _13 * y2 + _23 * ay, - x2, - y2 - ]; - } - function a2c(x1, y1, rx, ry, angle, large_arc_flag, sweep_flag, x2, y2, recursive) { - // for more information of where this math came from visit: - // http://www.w3.org/TR/SVG11/implnote.html#ArcImplementationNotes - var _120 = PI * 120 / 180, - rad = PI / 180 * (+angle || 0), - res = [], - xy, - rotate = Snap._.cacher(function (x, y, rad) { - var X = x * math.cos(rad) - y * math.sin(rad), - Y = x * math.sin(rad) + y * math.cos(rad); - return {x: X, y: Y}; - }); - if (!recursive) { - xy = rotate(x1, y1, -rad); - x1 = xy.x; - y1 = xy.y; - xy = rotate(x2, y2, -rad); - x2 = xy.x; - y2 = xy.y; - var cos = math.cos(PI / 180 * angle), - sin = math.sin(PI / 180 * angle), - x = (x1 - x2) / 2, - y = (y1 - y2) / 2; - var h = (x * x) / (rx * rx) + (y * y) / (ry * ry); - if (h > 1) { - h = math.sqrt(h); - rx = h * rx; - ry = h * ry; - } - var rx2 = rx * rx, - ry2 = ry * ry, - k = (large_arc_flag == sweep_flag ? -1 : 1) * - math.sqrt(abs((rx2 * ry2 - rx2 * y * y - ry2 * x * x) / (rx2 * y * y + ry2 * x * x))), - cx = k * rx * y / ry + (x1 + x2) / 2, - cy = k * -ry * x / rx + (y1 + y2) / 2, - f1 = math.asin(((y1 - cy) / ry).toFixed(9)), - f2 = math.asin(((y2 - cy) / ry).toFixed(9)); - - f1 = x1 < cx ? PI - f1 : f1; - f2 = x2 < cx ? PI - f2 : f2; - f1 < 0 && (f1 = PI * 2 + f1); - f2 < 0 && (f2 = PI * 2 + f2); - if (sweep_flag && f1 > f2) { - f1 = f1 - PI * 2; - } - if (!sweep_flag && f2 > f1) { - f2 = f2 - PI * 2; - } - } else { - f1 = recursive[0]; - f2 = recursive[1]; - cx = recursive[2]; - cy = recursive[3]; - } - var df = f2 - f1; - if (abs(df) > _120) { - var f2old = f2, - x2old = x2, - y2old = y2; - f2 = f1 + _120 * (sweep_flag && f2 > f1 ? 1 : -1); - x2 = cx + rx * math.cos(f2); - y2 = cy + ry * math.sin(f2); - res = a2c(x2, y2, rx, ry, angle, 0, sweep_flag, x2old, y2old, [f2, f2old, cx, cy]); - } - df = f2 - f1; - var c1 = math.cos(f1), - s1 = math.sin(f1), - c2 = math.cos(f2), - s2 = math.sin(f2), - t = math.tan(df / 4), - hx = 4 / 3 * rx * t, - hy = 4 / 3 * ry * t, - m1 = [x1, y1], - m2 = [x1 + hx * s1, y1 - hy * c1], - m3 = [x2 + hx * s2, y2 - hy * c2], - m4 = [x2, y2]; - m2[0] = 2 * m1[0] - m2[0]; - m2[1] = 2 * m1[1] - m2[1]; - if (recursive) { - return [m2, m3, m4].concat(res); - } else { - res = [m2, m3, m4].concat(res).join().split(","); - var newres = []; - for (var i = 0, ii = res.length; i < ii; i++) { - newres[i] = i % 2 ? rotate(res[i - 1], res[i], rad).y : rotate(res[i], res[i + 1], rad).x; - } - return newres; - } - } - function findDotAtSegment(p1x, p1y, c1x, c1y, c2x, c2y, p2x, p2y, t) { - var t1 = 1 - t; - return { - x: pow(t1, 3) * p1x + pow(t1, 2) * 3 * t * c1x + t1 * 3 * t * t * c2x + pow(t, 3) * p2x, - y: pow(t1, 3) * p1y + pow(t1, 2) * 3 * t * c1y + t1 * 3 * t * t * c2y + pow(t, 3) * p2y - }; - } - - // Returns bounding box of cubic bezier curve. - // Source: http://blog.hackers-cafe.net/2009/06/how-to-calculate-bezier-curves-bounding.html - // Original version: NISHIO Hirokazu - // Modifications: https://github.com/timo22345 - function curveDim(x0, y0, x1, y1, x2, y2, x3, y3) { - var tvalues = [], - bounds = [[], []], - a, b, c, t, t1, t2, b2ac, sqrtb2ac; - for (var i = 0; i < 2; ++i) { - if (i == 0) { - b = 6 * x0 - 12 * x1 + 6 * x2; - a = -3 * x0 + 9 * x1 - 9 * x2 + 3 * x3; - c = 3 * x1 - 3 * x0; - } else { - b = 6 * y0 - 12 * y1 + 6 * y2; - a = -3 * y0 + 9 * y1 - 9 * y2 + 3 * y3; - c = 3 * y1 - 3 * y0; - } - if (abs(a) < 1e-12) { - if (abs(b) < 1e-12) { - continue; - } - t = -c / b; - if (0 < t && t < 1) { - tvalues.push(t); - } - continue; - } - b2ac = b * b - 4 * c * a; - sqrtb2ac = math.sqrt(b2ac); - if (b2ac < 0) { - continue; - } - t1 = (-b + sqrtb2ac) / (2 * a); - if (0 < t1 && t1 < 1) { - tvalues.push(t1); - } - t2 = (-b - sqrtb2ac) / (2 * a); - if (0 < t2 && t2 < 1) { - tvalues.push(t2); - } - } - - var x, y, j = tvalues.length, - jlen = j, - mt; - while (j--) { - t = tvalues[j]; - mt = 1 - t; - bounds[0][j] = (mt * mt * mt * x0) + (3 * mt * mt * t * x1) + (3 * mt * t * t * x2) + (t * t * t * x3); - bounds[1][j] = (mt * mt * mt * y0) + (3 * mt * mt * t * y1) + (3 * mt * t * t * y2) + (t * t * t * y3); - } - - bounds[0][jlen] = x0; - bounds[1][jlen] = y0; - bounds[0][jlen + 1] = x3; - bounds[1][jlen + 1] = y3; - bounds[0].length = bounds[1].length = jlen + 2; - - - return { - min: {x: mmin.apply(0, bounds[0]), y: mmin.apply(0, bounds[1])}, - max: {x: mmax.apply(0, bounds[0]), y: mmax.apply(0, bounds[1])} - }; - } - - function path2curve(path, path2) { - var pth = !path2 && paths(path); - if (!path2 && pth.curve) { - return pathClone(pth.curve); - } - var p = pathToAbsolute(path), - p2 = path2 && pathToAbsolute(path2), - attrs = {x: 0, y: 0, bx: 0, by: 0, X: 0, Y: 0, qx: null, qy: null}, - attrs2 = {x: 0, y: 0, bx: 0, by: 0, X: 0, Y: 0, qx: null, qy: null}, - processPath = function (path, d, pcom) { - var nx, ny; - if (!path) { - return ["C", d.x, d.y, d.x, d.y, d.x, d.y]; - } - !(path[0] in {T: 1, Q: 1}) && (d.qx = d.qy = null); - switch (path[0]) { - case "M": - d.X = path[1]; - d.Y = path[2]; - break; - case "A": - path = ["C"].concat(a2c.apply(0, [d.x, d.y].concat(path.slice(1)))); - break; - case "S": - if (pcom == "C" || pcom == "S") { // In "S" case we have to take into account, if the previous command is C/S. - nx = d.x * 2 - d.bx; // And reflect the previous - ny = d.y * 2 - d.by; // command's control point relative to the current point. - } - else { // or some else or nothing - nx = d.x; - ny = d.y; - } - path = ["C", nx, ny].concat(path.slice(1)); - break; - case "T": - if (pcom == "Q" || pcom == "T") { // In "T" case we have to take into account, if the previous command is Q/T. - d.qx = d.x * 2 - d.qx; // And make a reflection similar - d.qy = d.y * 2 - d.qy; // to case "S". - } - else { // or something else or nothing - d.qx = d.x; - d.qy = d.y; - } - path = ["C"].concat(q2c(d.x, d.y, d.qx, d.qy, path[1], path[2])); - break; - case "Q": - d.qx = path[1]; - d.qy = path[2]; - path = ["C"].concat(q2c(d.x, d.y, path[1], path[2], path[3], path[4])); - break; - case "L": - path = ["C"].concat(l2c(d.x, d.y, path[1], path[2])); - break; - case "H": - path = ["C"].concat(l2c(d.x, d.y, path[1], d.y)); - break; - case "V": - path = ["C"].concat(l2c(d.x, d.y, d.x, path[1])); - break; - case "Z": - path = ["C"].concat(l2c(d.x, d.y, d.X, d.Y)); - break; - } - return path; - }, - fixArc = function (pp, i) { - if (pp[i].length > 7) { - pp[i].shift(); - var pi = pp[i]; - while (pi.length) { - pcoms1[i] = "A"; // if created multiple C:s, their original seg is saved - p2 && (pcoms2[i] = "A"); // the same as above - pp.splice(i++, 0, ["C"].concat(pi.splice(0, 6))); - } - pp.splice(i, 1); - ii = mmax(p.length, p2 && p2.length || 0); - } - }, - fixM = function (path1, path2, a1, a2, i) { - if (path1 && path2 && path1[i][0] == "M" && path2[i][0] != "M") { - path2.splice(i, 0, ["M", a2.x, a2.y]); - a1.bx = 0; - a1.by = 0; - a1.x = path1[i][1]; - a1.y = path1[i][2]; - ii = mmax(p.length, p2 && p2.length || 0); - } - }, - pcoms1 = [], // path commands of original path p - pcoms2 = [], // path commands of original path p2 - pfirst = "", // temporary holder for original path command - pcom = ""; // holder for previous path command of original path - for (var i = 0, ii = mmax(p.length, p2 && p2.length || 0); i < ii; i++) { - p[i] && (pfirst = p[i][0]); // save current path command - - if (pfirst != "C") // C is not saved yet, because it may be result of conversion - { - pcoms1[i] = pfirst; // Save current path command - i && ( pcom = pcoms1[i - 1]); // Get previous path command pcom - } - p[i] = processPath(p[i], attrs, pcom); // Previous path command is inputted to processPath - - if (pcoms1[i] != "A" && pfirst == "C") pcoms1[i] = "C"; // A is the only command - // which may produce multiple C:s - // so we have to make sure that C is also C in original path - - fixArc(p, i); // fixArc adds also the right amount of A:s to pcoms1 - - if (p2) { // the same procedures is done to p2 - p2[i] && (pfirst = p2[i][0]); - if (pfirst != "C") { - pcoms2[i] = pfirst; - i && (pcom = pcoms2[i - 1]); - } - p2[i] = processPath(p2[i], attrs2, pcom); - - if (pcoms2[i] != "A" && pfirst == "C") { - pcoms2[i] = "C"; - } - - fixArc(p2, i); - } - fixM(p, p2, attrs, attrs2, i); - fixM(p2, p, attrs2, attrs, i); - var seg = p[i], - seg2 = p2 && p2[i], - seglen = seg.length, - seg2len = p2 && seg2.length; - attrs.x = seg[seglen - 2]; - attrs.y = seg[seglen - 1]; - attrs.bx = toFloat(seg[seglen - 4]) || attrs.x; - attrs.by = toFloat(seg[seglen - 3]) || attrs.y; - attrs2.bx = p2 && (toFloat(seg2[seg2len - 4]) || attrs2.x); - attrs2.by = p2 && (toFloat(seg2[seg2len - 3]) || attrs2.y); - attrs2.x = p2 && seg2[seg2len - 2]; - attrs2.y = p2 && seg2[seg2len - 1]; - } - if (!p2) { - pth.curve = pathClone(p); - } - return p2 ? [p, p2] : p; - } - function mapPath(path, matrix) { - if (!matrix) { - return path; - } - var x, y, i, j, ii, jj, pathi; - path = path2curve(path); - for (i = 0, ii = path.length; i < ii; i++) { - pathi = path[i]; - for (j = 1, jj = pathi.length; j < jj; j += 2) { - x = matrix.x(pathi[j], pathi[j + 1]); - y = matrix.y(pathi[j], pathi[j + 1]); - pathi[j] = x; - pathi[j + 1] = y; - } - } - return path; - } - - // http://schepers.cc/getting-to-the-point - function catmullRom2bezier(crp, z) { - var d = []; - for (var i = 0, iLen = crp.length; iLen - 2 * !z > i; i += 2) { - var p = [ - {x: +crp[i - 2], y: +crp[i - 1]}, - {x: +crp[i], y: +crp[i + 1]}, - {x: +crp[i + 2], y: +crp[i + 3]}, - {x: +crp[i + 4], y: +crp[i + 5]} - ]; - if (z) { - if (!i) { - p[0] = {x: +crp[iLen - 2], y: +crp[iLen - 1]}; - } else if (iLen - 4 == i) { - p[3] = {x: +crp[0], y: +crp[1]}; - } else if (iLen - 2 == i) { - p[2] = {x: +crp[0], y: +crp[1]}; - p[3] = {x: +crp[2], y: +crp[3]}; - } - } else { - if (iLen - 4 == i) { - p[3] = p[2]; - } else if (!i) { - p[0] = {x: +crp[i], y: +crp[i + 1]}; - } - } - d.push(["C", - (-p[0].x + 6 * p[1].x + p[2].x) / 6, - (-p[0].y + 6 * p[1].y + p[2].y) / 6, - (p[1].x + 6 * p[2].x - p[3].x) / 6, - (p[1].y + 6*p[2].y - p[3].y) / 6, - p[2].x, - p[2].y - ]); - } - - return d; - } - - // export - Snap.path = paths; - - /*\ - * Snap.path.getTotalLength - [ method ] - ** - * Returns the length of the given path in pixels - ** - - path (string) SVG path string - ** - = (number) length - \*/ - Snap.path.getTotalLength = getTotalLength; - /*\ - * Snap.path.getPointAtLength - [ method ] - ** - * Returns the coordinates of the point located at the given length along the given path - ** - - path (string) SVG path string - - length (number) length, in pixels, from the start of the path, excluding non-rendering jumps - ** - = (object) representation of the point: - o { - o x: (number) x coordinate, - o y: (number) y coordinate, - o alpha: (number) angle of derivative - o } - \*/ - Snap.path.getPointAtLength = getPointAtLength; - /*\ - * Snap.path.getSubpath - [ method ] - ** - * Returns the subpath of a given path between given start and end lengths - ** - - path (string) SVG path string - - from (number) length, in pixels, from the start of the path to the start of the segment - - to (number) length, in pixels, from the start of the path to the end of the segment - ** - = (string) path string definition for the segment - \*/ - Snap.path.getSubpath = function (path, from, to) { - if (this.getTotalLength(path) - to < 1e-6) { - return getSubpathsAtLength(path, from).end; - } - var a = getSubpathsAtLength(path, to, 1); - return from ? getSubpathsAtLength(a, from).end : a; - }; - /*\ - * Element.getTotalLength - [ method ] - ** - * Returns the length of the path in pixels (only works for `path` elements) - = (number) length - \*/ - elproto.getTotalLength = function () { - if (this.node.getTotalLength) { - return this.node.getTotalLength(); - } - }; - // SIERRA Element.getPointAtLength()/Element.getTotalLength(): If a is broken into different segments, is the jump distance to the new coordinates set by the _M_ or _m_ commands calculated as part of the path's total length? - /*\ - * Element.getPointAtLength - [ method ] - ** - * Returns coordinates of the point located at the given length on the given path (only works for `path` elements) - ** - - length (number) length, in pixels, from the start of the path, excluding non-rendering jumps - ** - = (object) representation of the point: - o { - o x: (number) x coordinate, - o y: (number) y coordinate, - o alpha: (number) angle of derivative - o } - \*/ - elproto.getPointAtLength = function (length) { - return getPointAtLength(this.attr("d"), length); - }; - // SIERRA Element.getSubpath(): Similar to the problem for Element.getPointAtLength(). Unclear how this would work for a segmented path. Overall, the concept of _subpath_ and what I'm calling a _segment_ (series of non-_M_ or _Z_ commands) is unclear. - /*\ - * Element.getSubpath - [ method ] - ** - * Returns subpath of a given element from given start and end lengths (only works for `path` elements) - ** - - from (number) length, in pixels, from the start of the path to the start of the segment - - to (number) length, in pixels, from the start of the path to the end of the segment - ** - = (string) path string definition for the segment - \*/ - elproto.getSubpath = function (from, to) { - return Snap.path.getSubpath(this.attr("d"), from, to); - }; - Snap._.box = box; - /*\ - * Snap.path.findDotsAtSegment - [ method ] - ** - * Utility method - ** - * Finds dot coordinates on the given cubic beziér curve at the given t - - p1x (number) x of the first point of the curve - - p1y (number) y of the first point of the curve - - c1x (number) x of the first anchor of the curve - - c1y (number) y of the first anchor of the curve - - c2x (number) x of the second anchor of the curve - - c2y (number) y of the second anchor of the curve - - p2x (number) x of the second point of the curve - - p2y (number) y of the second point of the curve - - t (number) position on the curve (0..1) - = (object) point information in format: - o { - o x: (number) x coordinate of the point, - o y: (number) y coordinate of the point, - o m: { - o x: (number) x coordinate of the left anchor, - o y: (number) y coordinate of the left anchor - o }, - o n: { - o x: (number) x coordinate of the right anchor, - o y: (number) y coordinate of the right anchor - o }, - o start: { - o x: (number) x coordinate of the start of the curve, - o y: (number) y coordinate of the start of the curve - o }, - o end: { - o x: (number) x coordinate of the end of the curve, - o y: (number) y coordinate of the end of the curve - o }, - o alpha: (number) angle of the curve derivative at the point - o } - \*/ - Snap.path.findDotsAtSegment = findDotsAtSegment; - /*\ - * Snap.path.bezierBBox - [ method ] - ** - * Utility method - ** - * Returns the bounding box of a given cubic beziér curve - - p1x (number) x of the first point of the curve - - p1y (number) y of the first point of the curve - - c1x (number) x of the first anchor of the curve - - c1y (number) y of the first anchor of the curve - - c2x (number) x of the second anchor of the curve - - c2y (number) y of the second anchor of the curve - - p2x (number) x of the second point of the curve - - p2y (number) y of the second point of the curve - * or - - bez (array) array of six points for beziér curve - = (object) bounding box - o { - o x: (number) x coordinate of the left top point of the box, - o y: (number) y coordinate of the left top point of the box, - o x2: (number) x coordinate of the right bottom point of the box, - o y2: (number) y coordinate of the right bottom point of the box, - o width: (number) width of the box, - o height: (number) height of the box - o } - \*/ - Snap.path.bezierBBox = bezierBBox; - /*\ - * Snap.path.isPointInsideBBox - [ method ] - ** - * Utility method - ** - * Returns `true` if given point is inside bounding box - - bbox (string) bounding box - - x (string) x coordinate of the point - - y (string) y coordinate of the point - = (boolean) `true` if point is inside - \*/ - Snap.path.isPointInsideBBox = isPointInsideBBox; - Snap.closest = function (x, y, X, Y) { - var r = 100, - b = box(x - r / 2, y - r / 2, r, r), - inside = [], - getter = X[0].hasOwnProperty("x") ? function (i) { - return { - x: X[i].x, - y: X[i].y - }; - } : function (i) { - return { - x: X[i], - y: Y[i] - }; - }, - found = 0; - while (r <= 1e6 && !found) { - for (var i = 0, ii = X.length; i < ii; i++) { - var xy = getter(i); - if (isPointInsideBBox(b, xy.x, xy.y)) { - found++; - inside.push(xy); - break; - } - } - if (!found) { - r *= 2; - b = box(x - r / 2, y - r / 2, r, r) - } - } - if (r == 1e6) { - return; - } - var len = Infinity, - res; - for (i = 0, ii = inside.length; i < ii; i++) { - var l = Snap.len(x, y, inside[i].x, inside[i].y); - if (len > l) { - len = l; - inside[i].len = l; - res = inside[i]; - } - } - return res; - }; - /*\ - * Snap.path.isBBoxIntersect - [ method ] - ** - * Utility method - ** - * Returns `true` if two bounding boxes intersect - - bbox1 (string) first bounding box - - bbox2 (string) second bounding box - = (boolean) `true` if bounding boxes intersect - \*/ - Snap.path.isBBoxIntersect = isBBoxIntersect; - /*\ - * Snap.path.intersection - [ method ] - ** - * Utility method - ** - * Finds intersections of two paths - - path1 (string) path string - - path2 (string) path string - = (array) dots of intersection - o [ - o { - o x: (number) x coordinate of the point, - o y: (number) y coordinate of the point, - o t1: (number) t value for segment of path1, - o t2: (number) t value for segment of path2, - o segment1: (number) order number for segment of path1, - o segment2: (number) order number for segment of path2, - o bez1: (array) eight coordinates representing beziér curve for the segment of path1, - o bez2: (array) eight coordinates representing beziér curve for the segment of path2 - o } - o ] - \*/ - Snap.path.intersection = pathIntersection; - Snap.path.intersectionNumber = pathIntersectionNumber; - /*\ - * Snap.path.isPointInside - [ method ] - ** - * Utility method - ** - * Returns `true` if given point is inside a given closed path. - * - * Note: fill mode doesn’t affect the result of this method. - - path (string) path string - - x (number) x of the point - - y (number) y of the point - = (boolean) `true` if point is inside the path - \*/ - Snap.path.isPointInside = isPointInsidePath; - /*\ - * Snap.path.getBBox - [ method ] - ** - * Utility method - ** - * Returns the bounding box of a given path - - path (string) path string - = (object) bounding box - o { - o x: (number) x coordinate of the left top point of the box, - o y: (number) y coordinate of the left top point of the box, - o x2: (number) x coordinate of the right bottom point of the box, - o y2: (number) y coordinate of the right bottom point of the box, - o width: (number) width of the box, - o height: (number) height of the box - o } - \*/ - Snap.path.getBBox = pathBBox; - Snap.path.get = getPath; - /*\ - * Snap.path.toRelative - [ method ] - ** - * Utility method - ** - * Converts path coordinates into relative values - - path (string) path string - = (array) path string - \*/ - Snap.path.toRelative = pathToRelative; - /*\ - * Snap.path.toAbsolute - [ method ] - ** - * Utility method - ** - * Converts path coordinates into absolute values - - path (string) path string - = (array) path string - \*/ - Snap.path.toAbsolute = pathToAbsolute; - /*\ - * Snap.path.toCubic - [ method ] - ** - * Utility method - ** - * Converts path to a new path where all segments are cubic beziér curves - - pathString (string|array) path string or array of segments - = (array) array of segments - \*/ - Snap.path.toCubic = path2curve; - /*\ - * Snap.path.map - [ method ] - ** - * Transform the path string with the given matrix - - path (string) path string - - matrix (object) see @Matrix - = (string) transformed path string - \*/ - Snap.path.map = mapPath; - Snap.path.toString = toString; - Snap.path.clone = pathClone; -}); - -// Copyright (c) 2013 Adobe Systems Incorporated. All rights reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -Snap.plugin(function (Snap, Element, Paper, glob) { - var mmax = Math.max, - mmin = Math.min; - - // Set - var Set = function (items) { - this.items = []; - this.bindings = {}; - this.length = 0; - this.type = "set"; - if (items) { - for (var i = 0, ii = items.length; i < ii; i++) { - if (items[i]) { - this[this.items.length] = this.items[this.items.length] = items[i]; - this.length++; - } - } - } - }, - setproto = Set.prototype; - /*\ - * Set.push - [ method ] - ** - * Adds each argument to the current set - = (object) original element - \*/ - setproto.push = function () { - var item, - len; - for (var i = 0, ii = arguments.length; i < ii; i++) { - item = arguments[i]; - if (item) { - len = this.items.length; - this[len] = this.items[len] = item; - this.length++; - } - } - return this; - }; - /*\ - * Set.pop - [ method ] - ** - * Removes last element and returns it - = (object) element - \*/ - setproto.pop = function () { - this.length && delete this[this.length--]; - return this.items.pop(); - }; - /*\ - * Set.forEach - [ method ] - ** - * Executes given function for each element in the set - * - * If the function returns `false`, the loop stops running. - ** - - callback (function) function to run - - thisArg (object) context object for the callback - = (object) Set object - \*/ - setproto.forEach = function (callback, thisArg) { - for (var i = 0, ii = this.items.length; i < ii; i++) { - if (callback.call(thisArg, this.items[i], i) === false) { - return this; - } - } - return this; - }; - /*\ - * Set.animate - [ method ] - ** - * Animates each element in set in sync. - * - ** - - attrs (object) key-value pairs of destination attributes - - duration (number) duration of the animation in milliseconds - - easing (function) #optional easing function from @mina or custom - - callback (function) #optional callback function that executes when the animation ends - * or - - animation (array) array of animation parameter for each element in set in format `[attrs, duration, easing, callback]` - > Usage - | // animate all elements in set to radius 10 - | set.animate({r: 10}, 500, mina.easein); - | // or - | // animate first element to radius 10, but second to radius 20 and in different time - | set.animate([{r: 10}, 500, mina.easein], [{r: 20}, 1500, mina.easein]); - = (Element) the current element - \*/ - setproto.animate = function (attrs, ms, easing, callback) { - if (typeof easing == "function" && !easing.length) { - callback = easing; - easing = mina.linear; - } - if (attrs instanceof Snap._.Animation) { - callback = attrs.callback; - easing = attrs.easing; - ms = easing.dur; - attrs = attrs.attr; - } - var args = arguments; - if (Snap.is(attrs, "array") && Snap.is(args[args.length - 1], "array")) { - var each = true; - } - var begin, - handler = function () { - if (begin) { - this.b = begin; - } else { - begin = this.b; - } - }, - cb = 0, - set = this, - callbacker = callback && function () { - if (++cb == set.length) { - callback.call(this); - } - }; - return this.forEach(function (el, i) { - eve.once("snap.animcreated." + el.id, handler); - if (each) { - args[i] && el.animate.apply(el, args[i]); - } else { - el.animate(attrs, ms, easing, callbacker); - } - }); - }; - setproto.remove = function () { - while (this.length) { - this.pop().remove(); - } - return this; - }; - /*\ - * Set.bind - [ method ] - ** - * Specifies how to handle a specific attribute when applied - * to a set. - * - ** - - attr (string) attribute name - - callback (function) function to run - * or - - attr (string) attribute name - - element (Element) specific element in the set to apply the attribute to - * or - - attr (string) attribute name - - element (Element) specific element in the set to apply the attribute to - - eattr (string) attribute on the element to bind the attribute to - = (object) Set object - \*/ - setproto.bind = function (attr, a, b) { - var data = {}; - if (typeof a == "function") { - this.bindings[attr] = a; - } else { - var aname = b || attr; - this.bindings[attr] = function (v) { - data[aname] = v; - a.attr(data); - }; - } - return this; - }; - setproto.attr = function (value) { - var unbound = {}; - for (var k in value) { - if (this.bindings[k]) { - this.bindings[k](value[k]); - } else { - unbound[k] = value[k]; - } - } - for (var i = 0, ii = this.items.length; i < ii; i++) { - this.items[i].attr(unbound); - } - return this; - }; - /*\ - * Set.clear - [ method ] - ** - * Removes all elements from the set - \*/ - setproto.clear = function () { - while (this.length) { - this.pop(); - } - }; - /*\ - * Set.splice - [ method ] - ** - * Removes range of elements from the set - ** - - index (number) position of the deletion - - count (number) number of element to remove - - insertion… (object) #optional elements to insert - = (object) set elements that were deleted - \*/ - setproto.splice = function (index, count, insertion) { - index = index < 0 ? mmax(this.length + index, 0) : index; - count = mmax(0, mmin(this.length - index, count)); - var tail = [], - todel = [], - args = [], - i; - for (i = 2; i < arguments.length; i++) { - args.push(arguments[i]); - } - for (i = 0; i < count; i++) { - todel.push(this[index + i]); - } - for (; i < this.length - index; i++) { - tail.push(this[index + i]); - } - var arglen = args.length; - for (i = 0; i < arglen + tail.length; i++) { - this.items[index + i] = this[index + i] = i < arglen ? args[i] : tail[i - arglen]; - } - i = this.items.length = this.length -= count - arglen; - while (this[i]) { - delete this[i++]; - } - return new Set(todel); - }; - /*\ - * Set.exclude - [ method ] - ** - * Removes given element from the set - ** - - element (object) element to remove - = (boolean) `true` if object was found and removed from the set - \*/ - setproto.exclude = function (el) { - for (var i = 0, ii = this.length; i < ii; i++) if (this[i] == el) { - this.splice(i, 1); - return true; - } - return false; - }; - setproto.insertAfter = function (el) { - var i = this.items.length; - while (i--) { - this.items[i].insertAfter(el); - } - return this; - }; - setproto.getBBox = function () { - var x = [], - y = [], - x2 = [], - y2 = []; - for (var i = this.items.length; i--;) if (!this.items[i].removed) { - var box = this.items[i].getBBox(); - x.push(box.x); - y.push(box.y); - x2.push(box.x + box.width); - y2.push(box.y + box.height); - } - x = mmin.apply(0, x); - y = mmin.apply(0, y); - x2 = mmax.apply(0, x2); - y2 = mmax.apply(0, y2); - return { - x: x, - y: y, - x2: x2, - y2: y2, - width: x2 - x, - height: y2 - y, - cx: x + (x2 - x) / 2, - cy: y + (y2 - y) / 2 - }; - }; - setproto.clone = function (s) { - s = new Set; - for (var i = 0, ii = this.items.length; i < ii; i++) { - s.push(this.items[i].clone()); - } - return s; - }; - setproto.toString = function () { - return "Snap\u2018s set"; - }; - setproto.type = "set"; - // export - Snap.Set = Set; - Snap.set = function () { - var set = new Set; - if (arguments.length) { - set.push.apply(set, Array.prototype.slice.call(arguments, 0)); - } - return set; - }; -}); - -// Copyright (c) 2013 Adobe Systems Incorporated. All rights reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -Snap.plugin(function (Snap, Element, Paper, glob) { - var names = {}, - reUnit = /[a-z]+$/i, - Str = String; - names.stroke = names.fill = "colour"; - function getEmpty(item) { - var l = item[0]; - switch (l.toLowerCase()) { - case "t": return [l, 0, 0]; - case "m": return [l, 1, 0, 0, 1, 0, 0]; - case "r": if (item.length == 4) { - return [l, 0, item[2], item[3]]; - } else { - return [l, 0]; - } - case "s": if (item.length == 5) { - return [l, 1, 1, item[3], item[4]]; - } else if (item.length == 3) { - return [l, 1, 1]; - } else { - return [l, 1]; - } - } - } - function equaliseTransform(t1, t2, getBBox) { - t2 = Str(t2).replace(/\.{3}|\u2026/g, t1); - t1 = Snap.parseTransformString(t1) || []; - t2 = Snap.parseTransformString(t2) || []; - var maxlength = Math.max(t1.length, t2.length), - from = [], - to = [], - i = 0, j, jj, - tt1, tt2; - for (; i < maxlength; i++) { - tt1 = t1[i] || getEmpty(t2[i]); - tt2 = t2[i] || getEmpty(tt1); - if ((tt1[0] != tt2[0]) || - (tt1[0].toLowerCase() == "r" && (tt1[2] != tt2[2] || tt1[3] != tt2[3])) || - (tt1[0].toLowerCase() == "s" && (tt1[3] != tt2[3] || tt1[4] != tt2[4])) - ) { - t1 = Snap._.transform2matrix(t1, getBBox()); - t2 = Snap._.transform2matrix(t2, getBBox()); - from = [["m", t1.a, t1.b, t1.c, t1.d, t1.e, t1.f]]; - to = [["m", t2.a, t2.b, t2.c, t2.d, t2.e, t2.f]]; - break; - } - from[i] = []; - to[i] = []; - for (j = 0, jj = Math.max(tt1.length, tt2.length); j < jj; j++) { - j in tt1 && (from[i][j] = tt1[j]); - j in tt2 && (to[i][j] = tt2[j]); - } - } - return { - from: path2array(from), - to: path2array(to), - f: getPath(from) - }; - } - function getNumber(val) { - return val; - } - function getUnit(unit) { - return function (val) { - return +val.toFixed(3) + unit; - }; - } - function getViewBox(val) { - return val.join(" "); - } - function getColour(clr) { - return Snap.rgb(clr[0], clr[1], clr[2]); - } - function getPath(path) { - var k = 0, i, ii, j, jj, out, a, b = []; - for (i = 0, ii = path.length; i < ii; i++) { - out = "["; - a = ['"' + path[i][0] + '"']; - for (j = 1, jj = path[i].length; j < jj; j++) { - a[j] = "val[" + (k++) + "]"; - } - out += a + "]"; - b[i] = out; - } - return Function("val", "return Snap.path.toString.call([" + b + "])"); - } - function path2array(path) { - var out = []; - for (var i = 0, ii = path.length; i < ii; i++) { - for (var j = 1, jj = path[i].length; j < jj; j++) { - out.push(path[i][j]); - } - } - return out; - } - function isNumeric(obj) { - return isFinite(parseFloat(obj)); - } - function arrayEqual(arr1, arr2) { - if (!Snap.is(arr1, "array") || !Snap.is(arr2, "array")) { - return false; - } - return arr1.toString() == arr2.toString(); - } - Element.prototype.equal = function (name, b) { - return eve("snap.util.equal", this, name, b).firstDefined(); - }; - eve.on("snap.util.equal", function (name, b) { - var A, B, a = Str(this.attr(name) || ""), - el = this; - if (isNumeric(a) && isNumeric(b)) { - return { - from: parseFloat(a), - to: parseFloat(b), - f: getNumber - }; - } - if (names[name] == "colour") { - A = Snap.color(a); - B = Snap.color(b); - return { - from: [A.r, A.g, A.b, A.opacity], - to: [B.r, B.g, B.b, B.opacity], - f: getColour - }; - } - if (name == "viewBox") { - A = this.attr(name).vb.split(" ").map(Number); - B = b.split(" ").map(Number); - return { - from: A, - to: B, - f: getViewBox - }; - } - if (name == "transform" || name == "gradientTransform" || name == "patternTransform") { - if (b instanceof Snap.Matrix) { - b = b.toTransformString(); - } - if (!Snap._.rgTransform.test(b)) { - b = Snap._.svgTransform2string(b); - } - return equaliseTransform(a, b, function () { - return el.getBBox(1); - }); - } - if (name == "d" || name == "path") { - A = Snap.path.toCubic(a, b); - return { - from: path2array(A[0]), - to: path2array(A[1]), - f: getPath(A[0]) - }; - } - if (name == "points") { - A = Str(a).split(Snap._.separator); - B = Str(b).split(Snap._.separator); - return { - from: A, - to: B, - f: function (val) { return val; } - }; - } - var aUnit = a.match(reUnit), - bUnit = Str(b).match(reUnit); - if (aUnit && arrayEqual(aUnit, bUnit)) { - return { - from: parseFloat(a), - to: parseFloat(b), - f: getUnit(aUnit) - }; - } else { - return { - from: this.asPX(name), - to: this.asPX(name, b), - f: getNumber - }; - } - }); -}); - -// Copyright (c) 2013 Adobe Systems Incorporated. All rights reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -Snap.plugin(function (Snap, Element, Paper, glob) { - var elproto = Element.prototype, - has = "hasOwnProperty", - supportsTouch = "createTouch" in glob.doc, - events = [ - "click", "dblclick", "mousedown", "mousemove", "mouseout", - "mouseover", "mouseup", "touchstart", "touchmove", "touchend", - "touchcancel" - ], - touchMap = { - mousedown: "touchstart", - mousemove: "touchmove", - mouseup: "touchend" - }, - getScroll = function (xy, el) { - var name = xy == "y" ? "scrollTop" : "scrollLeft", - doc = el && el.node ? el.node.ownerDocument : glob.doc; - return doc[name in doc.documentElement ? "documentElement" : "body"][name]; - }, - preventDefault = function () { - this.returnValue = false; - }, - preventTouch = function () { - return this.originalEvent.preventDefault(); - }, - stopPropagation = function () { - this.cancelBubble = true; - }, - stopTouch = function () { - return this.originalEvent.stopPropagation(); - }, - addEvent = function (obj, type, fn, element) { - var realName = supportsTouch && touchMap[type] ? touchMap[type] : type, - f = function (e) { - var scrollY = getScroll("y", element), - scrollX = getScroll("x", element); - if (supportsTouch && touchMap[has](type)) { - for (var i = 0, ii = e.targetTouches && e.targetTouches.length; i < ii; i++) { - if (e.targetTouches[i].target == obj || obj.contains(e.targetTouches[i].target)) { - var olde = e; - e = e.targetTouches[i]; - e.originalEvent = olde; - e.preventDefault = preventTouch; - e.stopPropagation = stopTouch; - break; - } - } - } - var x = e.clientX + scrollX, - y = e.clientY + scrollY; - return fn.call(element, e, x, y); - }; - - if (type !== realName) { - obj.addEventListener(type, f, false); - } - - obj.addEventListener(realName, f, false); - - return function () { - if (type !== realName) { - obj.removeEventListener(type, f, false); - } - - obj.removeEventListener(realName, f, false); - return true; - }; - }, - drag = [], - dragMove = function (e) { - var x = e.clientX, - y = e.clientY, - scrollY = getScroll("y"), - scrollX = getScroll("x"), - dragi, - j = drag.length; - while (j--) { - dragi = drag[j]; - if (supportsTouch) { - var i = e.touches && e.touches.length, - touch; - while (i--) { - touch = e.touches[i]; - if (touch.identifier == dragi.el._drag.id || dragi.el.node.contains(touch.target)) { - x = touch.clientX; - y = touch.clientY; - (e.originalEvent ? e.originalEvent : e).preventDefault(); - break; - } - } - } else { - e.preventDefault(); - } - var node = dragi.el.node, - o, - next = node.nextSibling, - parent = node.parentNode, - display = node.style.display; - // glob.win.opera && parent.removeChild(node); - // node.style.display = "none"; - // o = dragi.el.paper.getElementByPoint(x, y); - // node.style.display = display; - // glob.win.opera && (next ? parent.insertBefore(node, next) : parent.appendChild(node)); - // o && eve("snap.drag.over." + dragi.el.id, dragi.el, o); - x += scrollX; - y += scrollY; - eve("snap.drag.move." + dragi.el.id, dragi.move_scope || dragi.el, x - dragi.el._drag.x, y - dragi.el._drag.y, x, y, e); - } - }, - dragUp = function (e) { - Snap.unmousemove(dragMove).unmouseup(dragUp); - var i = drag.length, - dragi; - while (i--) { - dragi = drag[i]; - dragi.el._drag = {}; - eve("snap.drag.end." + dragi.el.id, dragi.end_scope || dragi.start_scope || dragi.move_scope || dragi.el, e); - eve.off("snap.drag.*." + dragi.el.id); - } - drag = []; - }; - /*\ - * Element.click - [ method ] - ** - * Adds a click event handler to the element - - handler (function) handler for the event - = (object) @Element - \*/ - /*\ - * Element.unclick - [ method ] - ** - * Removes a click event handler from the element - - handler (function) handler for the event - = (object) @Element - \*/ - - /*\ - * Element.dblclick - [ method ] - ** - * Adds a double click event handler to the element - - handler (function) handler for the event - = (object) @Element - \*/ - /*\ - * Element.undblclick - [ method ] - ** - * Removes a double click event handler from the element - - handler (function) handler for the event - = (object) @Element - \*/ - - /*\ - * Element.mousedown - [ method ] - ** - * Adds a mousedown event handler to the element - - handler (function) handler for the event - = (object) @Element - \*/ - /*\ - * Element.unmousedown - [ method ] - ** - * Removes a mousedown event handler from the element - - handler (function) handler for the event - = (object) @Element - \*/ - - /*\ - * Element.mousemove - [ method ] - ** - * Adds a mousemove event handler to the element - - handler (function) handler for the event - = (object) @Element - \*/ - /*\ - * Element.unmousemove - [ method ] - ** - * Removes a mousemove event handler from the element - - handler (function) handler for the event - = (object) @Element - \*/ - - /*\ - * Element.mouseout - [ method ] - ** - * Adds a mouseout event handler to the element - - handler (function) handler for the event - = (object) @Element - \*/ - /*\ - * Element.unmouseout - [ method ] - ** - * Removes a mouseout event handler from the element - - handler (function) handler for the event - = (object) @Element - \*/ - - /*\ - * Element.mouseover - [ method ] - ** - * Adds a mouseover event handler to the element - - handler (function) handler for the event - = (object) @Element - \*/ - /*\ - * Element.unmouseover - [ method ] - ** - * Removes a mouseover event handler from the element - - handler (function) handler for the event - = (object) @Element - \*/ - - /*\ - * Element.mouseup - [ method ] - ** - * Adds a mouseup event handler to the element - - handler (function) handler for the event - = (object) @Element - \*/ - /*\ - * Element.unmouseup - [ method ] - ** - * Removes a mouseup event handler from the element - - handler (function) handler for the event - = (object) @Element - \*/ - - /*\ - * Element.touchstart - [ method ] - ** - * Adds a touchstart event handler to the element - - handler (function) handler for the event - = (object) @Element - \*/ - /*\ - * Element.untouchstart - [ method ] - ** - * Removes a touchstart event handler from the element - - handler (function) handler for the event - = (object) @Element - \*/ - - /*\ - * Element.touchmove - [ method ] - ** - * Adds a touchmove event handler to the element - - handler (function) handler for the event - = (object) @Element - \*/ - /*\ - * Element.untouchmove - [ method ] - ** - * Removes a touchmove event handler from the element - - handler (function) handler for the event - = (object) @Element - \*/ - - /*\ - * Element.touchend - [ method ] - ** - * Adds a touchend event handler to the element - - handler (function) handler for the event - = (object) @Element - \*/ - /*\ - * Element.untouchend - [ method ] - ** - * Removes a touchend event handler from the element - - handler (function) handler for the event - = (object) @Element - \*/ - - /*\ - * Element.touchcancel - [ method ] - ** - * Adds a touchcancel event handler to the element - - handler (function) handler for the event - = (object) @Element - \*/ - /*\ - * Element.untouchcancel - [ method ] - ** - * Removes a touchcancel event handler from the element - - handler (function) handler for the event - = (object) @Element - \*/ - for (var i = events.length; i--;) { - (function (eventName) { - Snap[eventName] = elproto[eventName] = function (fn, scope) { - if (Snap.is(fn, "function")) { - this.events = this.events || []; - this.events.push({ - name: eventName, - f: fn, - unbind: addEvent(this.node || document, eventName, fn, scope || this) - }); - } else { - for (var i = 0, ii = this.events.length; i < ii; i++) if (this.events[i].name == eventName) { - try { - this.events[i].f.call(this); - } catch (e) {} - } - } - return this; - }; - Snap["un" + eventName] = - elproto["un" + eventName] = function (fn) { - var events = this.events || [], - l = events.length; - while (l--) if (events[l].name == eventName && - (events[l].f == fn || !fn)) { - events[l].unbind(); - events.splice(l, 1); - !events.length && delete this.events; - return this; - } - return this; - }; - })(events[i]); - } - /*\ - * Element.hover - [ method ] - ** - * Adds hover event handlers to the element - - f_in (function) handler for hover in - - f_out (function) handler for hover out - - icontext (object) #optional context for hover in handler - - ocontext (object) #optional context for hover out handler - = (object) @Element - \*/ - elproto.hover = function (f_in, f_out, scope_in, scope_out) { - return this.mouseover(f_in, scope_in).mouseout(f_out, scope_out || scope_in); - }; - /*\ - * Element.unhover - [ method ] - ** - * Removes hover event handlers from the element - - f_in (function) handler for hover in - - f_out (function) handler for hover out - = (object) @Element - \*/ - elproto.unhover = function (f_in, f_out) { - return this.unmouseover(f_in).unmouseout(f_out); - }; - var draggable = []; - // SIERRA unclear what _context_ refers to for starting, ending, moving the drag gesture. - // SIERRA Element.drag(): _x position of the mouse_: Where are the x/y values offset from? - // SIERRA Element.drag(): much of this member's doc appears to be duplicated for some reason. - // SIERRA Unclear about this sentence: _Additionally following drag events will be triggered: drag.start. on start, drag.end. on end and drag.move. on every move._ Is there a global _drag_ object to which you can assign handlers keyed by an element's ID? - /*\ - * Element.drag - [ method ] - ** - * Adds event handlers for an element's drag gesture - ** - - onmove (function) handler for moving - - onstart (function) handler for drag start - - onend (function) handler for drag end - - mcontext (object) #optional context for moving handler - - scontext (object) #optional context for drag start handler - - econtext (object) #optional context for drag end handler - * Additionaly following `drag` events are triggered: `drag.start.` on start, - * `drag.end.` on end and `drag.move.` on every move. When element is dragged over another element - * `drag.over.` fires as well. - * - * Start event and start handler are called in specified context or in context of the element with following parameters: - o x (number) x position of the mouse - o y (number) y position of the mouse - o event (object) DOM event object - * Move event and move handler are called in specified context or in context of the element with following parameters: - o dx (number) shift by x from the start point - o dy (number) shift by y from the start point - o x (number) x position of the mouse - o y (number) y position of the mouse - o event (object) DOM event object - * End event and end handler are called in specified context or in context of the element with following parameters: - o event (object) DOM event object - = (object) @Element - \*/ - elproto.drag = function (onmove, onstart, onend, move_scope, start_scope, end_scope) { - var el = this; - if (!arguments.length) { - var origTransform; - return el.drag(function (dx, dy) { - this.attr({ - transform: origTransform + (origTransform ? "T" : "t") + [dx, dy] - }); - }, function () { - origTransform = this.transform().local; - }); - } - function start(e, x, y) { - (e.originalEvent || e).preventDefault(); - el._drag.x = x; - el._drag.y = y; - el._drag.id = e.identifier; - !drag.length && Snap.mousemove(dragMove).mouseup(dragUp); - drag.push({el: el, move_scope: move_scope, start_scope: start_scope, end_scope: end_scope}); - onstart && eve.on("snap.drag.start." + el.id, onstart); - onmove && eve.on("snap.drag.move." + el.id, onmove); - onend && eve.on("snap.drag.end." + el.id, onend); - eve("snap.drag.start." + el.id, start_scope || move_scope || el, x, y, e); - } - function init(e, x, y) { - eve("snap.draginit." + el.id, el, e, x, y); - } - eve.on("snap.draginit." + el.id, start); - el._drag = {}; - draggable.push({el: el, start: start, init: init}); - el.mousedown(init); - return el; - }; - /* - * Element.onDragOver - [ method ] - ** - * Shortcut to assign event handler for `drag.over.` event, where `id` is the element's `id` (see @Element.id) - - f (function) handler for event, first argument would be the element you are dragging over - \*/ - // elproto.onDragOver = function (f) { - // f ? eve.on("snap.drag.over." + this.id, f) : eve.unbind("snap.drag.over." + this.id); - // }; - /*\ - * Element.undrag - [ method ] - ** - * Removes all drag event handlers from the given element - \*/ - elproto.undrag = function () { - var i = draggable.length; - while (i--) if (draggable[i].el == this) { - this.unmousedown(draggable[i].init); - draggable.splice(i, 1); - eve.unbind("snap.drag.*." + this.id); - eve.unbind("snap.draginit." + this.id); - } - !draggable.length && Snap.unmousemove(dragMove).unmouseup(dragUp); - return this; - }; -}); - -// Copyright (c) 2013 Adobe Systems Incorporated. All rights reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -Snap.plugin(function (Snap, Element, Paper, glob) { - var elproto = Element.prototype, - pproto = Paper.prototype, - rgurl = /^\s*url\((.+)\)/, - Str = String, - $ = Snap._.$; - Snap.filter = {}; - /*\ - * Paper.filter - [ method ] - ** - * Creates a `` element - ** - - filstr (string) SVG fragment of filter provided as a string - = (object) @Element - * Note: It is recommended to use filters embedded into the page inside an empty SVG element. - > Usage - | var f = paper.filter(''), - | c = paper.circle(10, 10, 10).attr({ - | filter: f - | }); - \*/ - pproto.filter = function (filstr) { - var paper = this; - if (paper.type != "svg") { - paper = paper.paper; - } - var f = Snap.parse(Str(filstr)), - id = Snap._.id(), - width = paper.node.offsetWidth, - height = paper.node.offsetHeight, - filter = $("filter"); - $(filter, { - id: id, - filterUnits: "userSpaceOnUse" - }); - filter.appendChild(f.node); - paper.defs.appendChild(filter); - return new Element(filter); - }; - - eve.on("snap.util.getattr.filter", function () { - eve.stop(); - var p = $(this.node, "filter"); - if (p) { - var match = Str(p).match(rgurl); - return match && Snap.select(match[1]); - } - }); - eve.on("snap.util.attr.filter", function (value) { - if (value instanceof Element && value.type == "filter") { - eve.stop(); - var id = value.node.id; - if (!id) { - $(value.node, {id: value.id}); - id = value.id; - } - $(this.node, { - filter: Snap.url(id) - }); - } - if (!value || value == "none") { - eve.stop(); - this.node.removeAttribute("filter"); - } - }); - /*\ - * Snap.filter.blur - [ method ] - ** - * Returns an SVG markup string for the blur filter - ** - - x (number) amount of horizontal blur, in pixels - - y (number) #optional amount of vertical blur, in pixels - = (string) filter representation - > Usage - | var f = paper.filter(Snap.filter.blur(5, 10)), - | c = paper.circle(10, 10, 10).attr({ - | filter: f - | }); - \*/ - Snap.filter.blur = function (x, y) { - if (x == null) { - x = 2; - } - var def = y == null ? x : [x, y]; - return Snap.format('\', { - def: def - }); - }; - Snap.filter.blur.toString = function () { - return this(); - }; - /*\ - * Snap.filter.shadow - [ method ] - ** - * Returns an SVG markup string for the shadow filter - ** - - dx (number) #optional horizontal shift of the shadow, in pixels - - dy (number) #optional vertical shift of the shadow, in pixels - - blur (number) #optional amount of blur - - color (string) #optional color of the shadow - - opacity (number) #optional `0..1` opacity of the shadow - * or - - dx (number) #optional horizontal shift of the shadow, in pixels - - dy (number) #optional vertical shift of the shadow, in pixels - - color (string) #optional color of the shadow - - opacity (number) #optional `0..1` opacity of the shadow - * which makes blur default to `4`. Or - - dx (number) #optional horizontal shift of the shadow, in pixels - - dy (number) #optional vertical shift of the shadow, in pixels - - opacity (number) #optional `0..1` opacity of the shadow - = (string) filter representation - > Usage - | var f = paper.filter(Snap.filter.shadow(0, 2, 3)), - | c = paper.circle(10, 10, 10).attr({ - | filter: f - | }); - \*/ - Snap.filter.shadow = function (dx, dy, blur, color, opacity) { - if (typeof blur == "string") { - color = blur; - opacity = color; - blur = 4; - } - if (typeof color != "string") { - opacity = color; - color = "#000"; - } - color = color || "#000"; - if (blur == null) { - blur = 4; - } - if (opacity == null) { - opacity = 1; - } - if (dx == null) { - dx = 0; - dy = 2; - } - if (dy == null) { - dy = dx; - } - color = Snap.color(color); - return Snap.format('', { - color: color, - dx: dx, - dy: dy, - blur: blur, - opacity: opacity - }); - }; - Snap.filter.shadow.toString = function () { - return this(); - }; - /*\ - * Snap.filter.grayscale - [ method ] - ** - * Returns an SVG markup string for the grayscale filter - ** - - amount (number) amount of filter (`0..1`) - = (string) filter representation - \*/ - Snap.filter.grayscale = function (amount) { - if (amount == null) { - amount = 1; - } - return Snap.format('', { - a: 0.2126 + 0.7874 * (1 - amount), - b: 0.7152 - 0.7152 * (1 - amount), - c: 0.0722 - 0.0722 * (1 - amount), - d: 0.2126 - 0.2126 * (1 - amount), - e: 0.7152 + 0.2848 * (1 - amount), - f: 0.0722 - 0.0722 * (1 - amount), - g: 0.2126 - 0.2126 * (1 - amount), - h: 0.0722 + 0.9278 * (1 - amount) - }); - }; - Snap.filter.grayscale.toString = function () { - return this(); - }; - /*\ - * Snap.filter.sepia - [ method ] - ** - * Returns an SVG markup string for the sepia filter - ** - - amount (number) amount of filter (`0..1`) - = (string) filter representation - \*/ - Snap.filter.sepia = function (amount) { - if (amount == null) { - amount = 1; - } - return Snap.format('', { - a: 0.393 + 0.607 * (1 - amount), - b: 0.769 - 0.769 * (1 - amount), - c: 0.189 - 0.189 * (1 - amount), - d: 0.349 - 0.349 * (1 - amount), - e: 0.686 + 0.314 * (1 - amount), - f: 0.168 - 0.168 * (1 - amount), - g: 0.272 - 0.272 * (1 - amount), - h: 0.534 - 0.534 * (1 - amount), - i: 0.131 + 0.869 * (1 - amount) - }); - }; - Snap.filter.sepia.toString = function () { - return this(); - }; - /*\ - * Snap.filter.saturate - [ method ] - ** - * Returns an SVG markup string for the saturate filter - ** - - amount (number) amount of filter (`0..1`) - = (string) filter representation - \*/ - Snap.filter.saturate = function (amount) { - if (amount == null) { - amount = 1; - } - return Snap.format('', { - amount: 1 - amount - }); - }; - Snap.filter.saturate.toString = function () { - return this(); - }; - /*\ - * Snap.filter.hueRotate - [ method ] - ** - * Returns an SVG markup string for the hue-rotate filter - ** - - angle (number) angle of rotation - = (string) filter representation - \*/ - Snap.filter.hueRotate = function (angle) { - angle = angle || 0; - return Snap.format('', { - angle: angle - }); - }; - Snap.filter.hueRotate.toString = function () { - return this(); - }; - /*\ - * Snap.filter.invert - [ method ] - ** - * Returns an SVG markup string for the invert filter - ** - - amount (number) amount of filter (`0..1`) - = (string) filter representation - \*/ - Snap.filter.invert = function (amount) { - if (amount == null) { - amount = 1; - } -// - return Snap.format('', { - amount: amount, - amount2: 1 - amount - }); - }; - Snap.filter.invert.toString = function () { - return this(); - }; - /*\ - * Snap.filter.brightness - [ method ] - ** - * Returns an SVG markup string for the brightness filter - ** - - amount (number) amount of filter (`0..1`) - = (string) filter representation - \*/ - Snap.filter.brightness = function (amount) { - if (amount == null) { - amount = 1; - } - return Snap.format('', { - amount: amount - }); - }; - Snap.filter.brightness.toString = function () { - return this(); - }; - /*\ - * Snap.filter.contrast - [ method ] - ** - * Returns an SVG markup string for the contrast filter - ** - - amount (number) amount of filter (`0..1`) - = (string) filter representation - \*/ - Snap.filter.contrast = function (amount) { - if (amount == null) { - amount = 1; - } - return Snap.format('', { - amount: amount, - amount2: .5 - amount / 2 - }); - }; - Snap.filter.contrast.toString = function () { - return this(); - }; -}); - -// Copyright (c) 2014 Adobe Systems Incorporated. All rights reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -Snap.plugin(function (Snap, Element, Paper, glob, Fragment) { - var box = Snap._.box, - is = Snap.is, - firstLetter = /^[^a-z]*([tbmlrc])/i, - toString = function () { - return "T" + this.dx + "," + this.dy; - }; - /*\ - * Element.getAlign - [ method ] - ** - * Returns shift needed to align the element relatively to given element. - * If no elements specified, parent `` container will be used. - - el (object) @optional alignment element - - way (string) one of six values: `"top"`, `"middle"`, `"bottom"`, `"left"`, `"center"`, `"right"` - = (object|string) Object in format `{dx: , dy: }` also has a string representation as a transformation string - > Usage - | el.transform(el.getAlign(el2, "top")); - * or - | var dy = el.getAlign(el2, "top").dy; - \*/ - Element.prototype.getAlign = function (el, way) { - if (way == null && is(el, "string")) { - way = el; - el = null; - } - el = el || this.paper; - var bx = el.getBBox ? el.getBBox() : box(el), - bb = this.getBBox(), - out = {}; - way = way && way.match(firstLetter); - way = way ? way[1].toLowerCase() : "c"; - switch (way) { - case "t": - out.dx = 0; - out.dy = bx.y - bb.y; - break; - case "b": - out.dx = 0; - out.dy = bx.y2 - bb.y2; - break; - case "m": - out.dx = 0; - out.dy = bx.cy - bb.cy; - break; - case "l": - out.dx = bx.x - bb.x; - out.dy = 0; - break; - case "r": - out.dx = bx.x2 - bb.x2; - out.dy = 0; - break; - default: - out.dx = bx.cx - bb.cx; - out.dy = 0; - break; - } - out.toString = toString; - return out; - }; - /*\ - * Element.align - [ method ] - ** - * Aligns the element relatively to given one via transformation. - * If no elements specified, parent `` container will be used. - - el (object) @optional alignment element - - way (string) one of six values: `"top"`, `"middle"`, `"bottom"`, `"left"`, `"center"`, `"right"` - = (object) this element - > Usage - | el.align(el2, "top"); - * or - | el.align("middle"); - \*/ - Element.prototype.align = function (el, way) { - return this.transform("..." + this.getAlign(el, way)); - }; -}); - -return Snap; -})); diff --git a/web/pgadmin/preferences/templates/preferences/preferences.js b/web/pgadmin/preferences/static/js/preferences.js similarity index 100% rename from web/pgadmin/preferences/templates/preferences/preferences.js rename to web/pgadmin/preferences/static/js/preferences.js diff --git a/web/pgadmin/settings/templates/settings/settings.js b/web/pgadmin/settings/static/js/settings.js similarity index 100% rename from web/pgadmin/settings/templates/settings/settings.js rename to web/pgadmin/settings/static/js/settings.js diff --git a/web/pgadmin/static/bundle/app.js b/web/pgadmin/static/bundle/app.js index e4d6c421f..a8c9e07d3 100644 --- a/web/pgadmin/static/bundle/app.js +++ b/web/pgadmin/static/bundle/app.js @@ -1,5 +1,5 @@ define('app', [ - 'babel-polyfill','pgadmin', 'browser_node', 'tools.datagrid' + 'babel-polyfill', 'pgadmin', 'bundled_browser', 'pgadmin.datagrid' ], function() { var initializeModules = function(Object) { for (var key in Object) { @@ -20,4 +20,4 @@ define('app', [ // create menus after all modules are initialized. pgAdmin.Browser.create_menus(); -}); \ No newline at end of file +}); diff --git a/web/pgadmin/static/bundle/browser.js b/web/pgadmin/static/bundle/browser.js index cf3a90899..c415d2e9a 100644 --- a/web/pgadmin/static/bundle/browser.js +++ b/web/pgadmin/static/bundle/browser.js @@ -1,5 +1,5 @@ -define('browser_node',[ +define('bundled_browser',[ 'pgadmin.browser' ], function(pgBrowser) { pgBrowser.init(); -}); \ No newline at end of file +}); diff --git a/web/pgadmin/static/bundle/codemirror.js b/web/pgadmin/static/bundle/codemirror.js index c8766ff13..4c79d1de0 100644 --- a/web/pgadmin/static/bundle/codemirror.js +++ b/web/pgadmin/static/bundle/codemirror.js @@ -14,6 +14,6 @@ import 'codemirror/addon/search/jump-to-line'; import 'codemirror/addon/edit/matchbrackets'; import 'codemirror/addon/edit/closebrackets'; import 'codemirror/addon/comment/comment' -import 'pgadmin.sqlfoldcode'; +import '../js/codemirror/addon/fold/pgadmin-sqlfoldcode'; export default CodeMirror; \ No newline at end of file diff --git a/web/pgadmin/static/js/url_for.js b/web/pgadmin/static/js/url_for.js index 700776db7..b1005381c 100644 --- a/web/pgadmin/static/js/url_for.js +++ b/web/pgadmin/static/js/url_for.js @@ -1,5 +1,4 @@ define(["pgadmin.browser.endpoints"], function (endpoints) { - /*** * This method behaves as a drop-in replacement for flask url_for function. * It uses the exposed URLs file under the hood, and replace the substitions provided by the modules. diff --git a/web/pgadmin/templates/base.html b/web/pgadmin/templates/base.html index f0d170396..142ab0bab 100755 --- a/web/pgadmin/templates/base.html +++ b/web/pgadmin/templates/base.html @@ -42,7 +42,6 @@ codemirror: "{{ url_for('static', filename='js/generated/codemirror') }}", datagrid: "{{ url_for('static', filename='js/generated/datagrid') }}", sqleditor: "{{ url_for('static', filename='js/generated/sqleditor') }}", - 'browser_node': "{{ url_for('static', filename='js/generated/browser_node') }}", 'pgadmin.browser.utils': "{{ url_for('browser.index') }}" + "js/utils", 'pgadmin.browser.endpoints': "{{ url_for('browser.index') }}" + "js/endpoints", 'pgadmin.browser.messages': "{{ url_for('browser.index') }}" + "js/messages", diff --git a/web/pgadmin/tools/backup/templates/backup/js/backup.js b/web/pgadmin/tools/backup/static/js/backup.js similarity index 100% rename from web/pgadmin/tools/backup/templates/backup/js/backup.js rename to web/pgadmin/tools/backup/static/js/backup.js diff --git a/web/pgadmin/tools/datagrid/templates/datagrid/js/datagrid.js b/web/pgadmin/tools/datagrid/static/js/datagrid.js similarity index 99% rename from web/pgadmin/tools/datagrid/templates/datagrid/js/datagrid.js rename to web/pgadmin/tools/datagrid/static/js/datagrid.js index ce952f0f7..ff7171748 100644 --- a/web/pgadmin/tools/datagrid/templates/datagrid/js/datagrid.js +++ b/web/pgadmin/tools/datagrid/static/js/datagrid.js @@ -1,4 +1,4 @@ -define('tools.datagrid', [ +define('pgadmin.datagrid', [ 'sources/gettext', 'sources/url_for', 'jquery', 'underscore', 'alertify', 'pgadmin', 'bundled_codemirror', 'sources/sqleditor_utils', 'wcdocker' diff --git a/web/pgadmin/tools/debugger/templates/debugger/js/debugger.js b/web/pgadmin/tools/debugger/static/js/debugger.js similarity index 99% rename from web/pgadmin/tools/debugger/templates/debugger/js/debugger.js rename to web/pgadmin/tools/debugger/static/js/debugger.js index acf374086..b791b2ccf 100644 --- a/web/pgadmin/tools/debugger/templates/debugger/js/debugger.js +++ b/web/pgadmin/tools/debugger/static/js/debugger.js @@ -1,7 +1,7 @@ define([ 'sources/gettext', 'sources/url_for', 'jquery', 'underscore', 'underscore.string', 'alertify', 'pgadmin', 'pgadmin.browser', 'backbone', 'backgrid', 'codemirror', - 'backform', 'tools.debugger.ui', 'wcdocker', 'pgadmin.backform', + 'backform', 'pgadmin.tools.debugger.ui', 'wcdocker', 'pgadmin.backform', 'pgadmin.backgrid', 'pgadmin.browser.frame' ], function(gettext, url_for, $, _, S, Alertify, pgAdmin, pgBrowser, Backbone, Backgrid, CodeMirror, Backform, get_function_arguments) { @@ -162,7 +162,7 @@ define([ _.values( _.pick(treeInfo, function(v, k, o) { - return (k != 'server-group'); + return (k != 'server_group'); }) ), function(o) { return o.priority; } diff --git a/web/pgadmin/tools/debugger/templates/debugger/js/debugger_ui.js b/web/pgadmin/tools/debugger/static/js/debugger_ui.js similarity index 100% rename from web/pgadmin/tools/debugger/templates/debugger/js/debugger_ui.js rename to web/pgadmin/tools/debugger/static/js/debugger_ui.js diff --git a/web/pgadmin/tools/debugger/templates/debugger/js/direct.js b/web/pgadmin/tools/debugger/static/js/direct.js similarity index 99% rename from web/pgadmin/tools/debugger/templates/debugger/js/direct.js rename to web/pgadmin/tools/debugger/static/js/direct.js index cfa2db9c1..7dd72fee1 100644 --- a/web/pgadmin/tools/debugger/templates/debugger/js/direct.js +++ b/web/pgadmin/tools/debugger/static/js/direct.js @@ -1,14 +1,14 @@ define([ - 'babel-polyfill', 'sources/gettext', 'sources/url_for' ,'jquery', 'underscore', 'underscore.string', 'alertify', + 'sources/gettext', 'sources/url_for' ,'jquery', 'underscore', 'underscore.string', 'alertify', 'pgadmin','pgadmin.browser', 'backbone', 'backgrid', 'sources/../bundle/codemirror', 'backform', - 'tools.debugger.ui', + 'pgadmin.tools.debugger.ui', 'sources/alerts/alertify_wrapper', 'wcdocker', 'pgadmin.backform', 'pgadmin.backgrid' ], function( - babelPolyfill, gettext, url_for, $, _, S, Alertify, pgAdmin, pgBrowser, Backbone, Backgrid, + gettext, url_for, $, _, S, Alertify, pgAdmin, pgBrowser, Backbone, Backgrid, codemirror, Backform, debug_function_again, AlertifyWrapper ) { diff --git a/web/pgadmin/tools/grant_wizard/templates/grant_wizard/js/grant_wizard.js b/web/pgadmin/tools/grant_wizard/static/js/grant_wizard.js similarity index 99% rename from web/pgadmin/tools/grant_wizard/templates/grant_wizard/js/grant_wizard.js rename to web/pgadmin/tools/grant_wizard/static/js/grant_wizard.js index ee618b327..3de742a7e 100644 --- a/web/pgadmin/tools/grant_wizard/templates/grant_wizard/js/grant_wizard.js +++ b/web/pgadmin/tools/grant_wizard/static/js/grant_wizard.js @@ -446,7 +446,7 @@ define([ node_(node name), node_type(node type) and pass it to collection which will fetch Object Type properties. */ - var gid = info['server-group']._id, + var gid = info['server_group']._id, sid = info.server._id, did = info.database._id, node_id = d._id, diff --git a/web/pgadmin/tools/import_export/templates/import_export/js/import_export.js b/web/pgadmin/tools/import_export/static/js/import_export.js similarity index 100% rename from web/pgadmin/tools/import_export/templates/import_export/js/import_export.js rename to web/pgadmin/tools/import_export/static/js/import_export.js diff --git a/web/pgadmin/tools/maintenance/templates/maintenance/js/maintenance.js b/web/pgadmin/tools/maintenance/static/js/maintenance.js similarity index 100% rename from web/pgadmin/tools/maintenance/templates/maintenance/js/maintenance.js rename to web/pgadmin/tools/maintenance/static/js/maintenance.js diff --git a/web/pgadmin/tools/restore/templates/restore/js/restore.js b/web/pgadmin/tools/restore/static/js/restore.js similarity index 100% rename from web/pgadmin/tools/restore/templates/restore/js/restore.js rename to web/pgadmin/tools/restore/static/js/restore.js diff --git a/web/pgadmin/tools/sqleditor/templates/sqleditor/js/sqleditor.js b/web/pgadmin/tools/sqleditor/static/js/sqleditor.js similarity index 99% rename from web/pgadmin/tools/sqleditor/templates/sqleditor/js/sqleditor.js rename to web/pgadmin/tools/sqleditor/static/js/sqleditor.js index a402ff4fd..3134c8df5 100644 --- a/web/pgadmin/tools/sqleditor/templates/sqleditor/js/sqleditor.js +++ b/web/pgadmin/tools/sqleditor/static/js/sqleditor.js @@ -1,6 +1,8 @@ define('tools.querytool', [ - 'babel-polyfill', 'sources/gettext','sources/url_for', 'jquery', 'underscore', 'underscore.string', 'alertify', - 'pgadmin', 'backbone', 'sources/../bundle/codemirror', 'pgadmin.misc.explain', + 'babel-polyfill', 'sources/gettext','sources/url_for', 'jquery', + 'underscore', 'underscore.string', 'alertify', + 'pgadmin', 'backbone', 'sources/../bundle/codemirror', + 'pgadmin.misc.explain', 'sources/selection/grid_selector', 'sources/selection/active_cell_capture', 'sources/selection/clipboard', @@ -16,7 +18,7 @@ define('tools.querytool', [ 'sources/alerts/alertify_wrapper', 'sources/sqleditor/keyboard_shortcuts', 'sources/../bundle/slickgrid', - 'misc.file_manager', + 'pgadmin.file_manager', 'backgrid.sizeable.columns', 'slick.pgadmin.formatters', 'slick.pgadmin.editors', @@ -30,12 +32,12 @@ define('tools.querytool', [ /* Return back, this has been called more than once */ if (pgAdmin.SqlEditor) return pgAdmin.SqlEditor; - var CodeMirror = codemirror.default; // Some scripts do export their object in the window only. // Generally the one, which do no have AMD support. var wcDocker = window.wcDocker, pgBrowser = pgAdmin.Browser, + CodeMirror = codemirror.default, Slick = window.Slick; var is_query_running = false; diff --git a/web/pgadmin/tools/user_management/templates/user_management/js/user_management.js b/web/pgadmin/tools/user_management/static/js/user_management.js similarity index 100% rename from web/pgadmin/tools/user_management/templates/user_management/js/user_management.js rename to web/pgadmin/tools/user_management/static/js/user_management.js diff --git a/web/webpack.config.js b/web/webpack.config.js index 5919a0ad8..232bed412 100644 --- a/web/webpack.config.js +++ b/web/webpack.config.js @@ -100,9 +100,9 @@ module.exports = { entry: { 'app.bundle': sourceDir + '/bundle/app.js', codemirror: sourceDir + '/bundle/codemirror.js', - sqleditor: './pgadmin/tools/sqleditor/templates/sqleditor/js/sqleditor.js', - debugger_direct: './pgadmin/tools/debugger/templates/debugger/js/direct.js', - file_utils: './pgadmin/misc/file_manager/templates/file_manager/js/utility.js', + sqleditor: './pgadmin/tools/sqleditor/static/js/sqleditor.js', + debugger_direct: './pgadmin/tools/debugger/static/js/direct.js', + file_utils: './pgadmin/misc/file_manager/static/js/utility.js', pgadmin_css: './pgadmin/static/scss/pgadmin.scss', style_css: './pgadmin/static/css/style.css', }, @@ -117,15 +117,7 @@ module.exports = { // Templates files which contains python code needs to load dynamically // Such files specified in externals are loaded at first and defined in // the start of generated bundle within define(['libname'],fn) etc. - externals: { - 'pgadmin.browser.messages': 'pgadmin.browser.messages', - 'pgadmin.browser.utils': 'pgadmin.browser.utils', - 'pgadmin.browser.endpoints': 'pgadmin.browser.endpoints', - 'pgadmin.server.supported_servers': 'pgadmin.server.supported_servers', - 'pgadmin.user_management.current_user': 'pgadmin.user_management.current_user', - 'pgadmin.node.unique_key': 'pgadmin.node.unique_key', - 'translations': 'translations', - }, + externals: webpackShimConfig.externals, module: { // References: // Module and Rules: https://webpack.js.org/configuration/module/ @@ -155,15 +147,15 @@ module.exports = { query: webpackShimConfig, include: path.join(__dirname, '/pgadmin/browser'), }, { - test: require.resolve('./pgadmin/tools/datagrid/templates/datagrid/js/datagrid'), + test: require.resolve('./pgadmin/tools/datagrid/static/js/datagrid'), use: { loader: 'imports-loader?' + 'pgadmin.dashboard' + ',pgadmin.tools.user_management' + - ',misc.statistics' + - ',misc.depends' + - ',misc.sql' + - ',misc.bgprocess' + + ',pgadmin.browser.object_statistics' + + ',pgadmin.browser.object_depends' + + ',pgadmin.browser.object_sql' + + ',pgadmin.browser.bgprocess' + ',pgadmin.node.server_group' + ',pgadmin.node.server' + ',pgadmin.node.database' + @@ -221,15 +213,15 @@ module.exports = { loader: 'imports-loader?' + 'pgadmin.about' + ',pgadmin.preferences' + - ',misc.file_manager' + + ',pgadmin.file_manager' + ',pgadmin.settings' + - ',tools.backup' + - ',tools.restore' + - ',tools.grant_wizard' + - ',tools.maintenance' + - ',tools.import_export' + - ',tools.debugger' + - ',tools.direct', + ',pgadmin.tools.backup' + + ',pgadmin.tools.restore' + + ',pgadmin.tools.grant_wizard' + + ',pgadmin.tools.maintenance' + + ',pgadmin.tools.import_export' + + ',pgadmin.tools.debugger.controller' + + ',pgadmin.tools.debugger.direct', }, }, { test: require.resolve('snapsvg'), diff --git a/web/webpack.shim.js b/web/webpack.shim.js index d3d560bd8..fd25fc4a3 100644 --- a/web/webpack.shim.js +++ b/web/webpack.shim.js @@ -116,9 +116,8 @@ var webpackShimConfig = { // Map module id to file path used in 'define(['baseurl', 'misc']). It is // used by webpack while creating bundle resolveAlias: { - 'baseurl': path.join(__dirname, './pgadmin'), - 'misc': path.join(__dirname, './pgadmin/static/bundle/misc'), - 'browser_node': path.join(__dirname, './pgadmin/static/bundle/browser'), + 'bundled_codemirror': path.join(__dirname, './pgadmin/static/bundle/codemirror'), + 'bundled_browser': path.join(__dirname, './pgadmin/static/bundle/browser'), 'sources': path.join(__dirname, './pgadmin/static/js'), 'pgadmin': path.join(__dirname, './pgadmin/static/js/pgadmin'), 'tools.translations': path.join(__dirname, './pgadmin/tools/templates/js/translations'), @@ -156,112 +155,114 @@ var webpackShimConfig = { 'backgrid.filter': path.join(__dirname, './node_modules/backgrid-filter/backgrid-filter'), 'backgrid.sizeable.columns': path.join(__dirname, './node_modules/backgrid-sizeable-columns/backgrid-sizeable-columns'), 'backgrid.select.all': path.join(__dirname, './node_modules/backgrid-select-all/backgrid-select-all'), - 'pgadmin.alertifyjs': path.join(__dirname, './pgadmin/static/js/alertify.pgadmin.defaults'), 'pgadmin.backform': path.join(__dirname, './pgadmin/static/js/backform.pgadmin'), 'pgadmin.backgrid': path.join(__dirname, './pgadmin/static/js/backgrid.pgadmin'), - 'pgadmin.misc.explain': path.join(__dirname, './pgadmin/misc/templates/explain/js/explain'), - 'pgadmin.settings': path.join(__dirname, './pgadmin/settings/templates/settings/settings'), - 'pgadmin.preferences': path.join(__dirname, './pgadmin/preferences/templates/preferences/preferences'), - 'pgadmin.dashboard': path.join(__dirname, './pgadmin/dashboard/templates/dashboard/js/dashboard'), - 'bundled_codemirror': path.join(__dirname, './pgadmin/static/bundle/codemirror'), - 'pgadmin.sqlfoldcode': path.join(__dirname, './pgadmin/static/js/codemirror/addon/fold/pgadmin-sqlfoldcode'), - 'pgadmin.about': path.join(__dirname, './pgadmin/about/templates/about/about'), - //tools JS - 'tools.backup': path.join(__dirname, './pgadmin/tools/backup/templates/backup/js/backup'), - 'tools.restore': path.join(__dirname, './pgadmin/tools/restore/templates/restore/js/restore'), - 'pgadmin.browser.wizard': path.join(__dirname, './pgadmin/browser/static/js/wizard'), - 'tools.grant_wizard': path.join(__dirname, './pgadmin/tools/grant_wizard/templates/grant_wizard/js/grant_wizard'), - 'tools.datagrid': path.join(__dirname, './pgadmin/tools/datagrid/templates/datagrid/js/datagrid'), - 'tools.querytool': path.join(__dirname, './pgadmin/tools/sqleditor/templates/sqleditor/js/sqleditor'), - 'tools.maintenance': path.join(__dirname, './pgadmin/tools/maintenance/templates/maintenance/js/maintenance'), - 'tools.import_export': path.join(__dirname, './pgadmin/tools/import_export/templates/import_export/js/import_export'), - 'tools.debugger.ui': path.join(__dirname, './pgadmin/tools/debugger/templates/debugger/js/debugger_ui'), - 'tools.debugger': path.join(__dirname, './pgadmin/tools/debugger/templates/debugger/js/debugger'), - 'tools.direct': path.join(__dirname, './pgadmin/tools/debugger/templates/debugger/js/direct'), - - // Misc JS - 'misc.bgprocess': path.join(__dirname, './pgadmin/misc/bgprocess/static/js/bgprocess'), - 'misc.file_manager': path.join(__dirname, './pgadmin/misc/file_manager/templates/file_manager/js/file_manager'), - 'misc.file_utility': path.join(__dirname, './pgadmin/misc/file_manager/templates/file_manager/js/utility'), - 'misc.statistics': path.join(__dirname, './pgadmin/misc/statistics/static/js/statistics'), - 'misc.depends': path.join(__dirname, './pgadmin/misc/depends/static/js/depends'), - 'misc.sql': path.join(__dirname, './pgadmin/misc/sql/static/js/sql'), - - // Browser Plugins JS - 'pgadmin.browser': path.join(__dirname, './pgadmin/browser/templates/browser/js/browser'), - 'pgadmin.browser.error': path.join(__dirname, './pgadmin/browser/templates/browser/js/error'), - 'pgadmin.browser.utils': path.join(__dirname, './pgadmin/browser/templates/browser/js/utils'), - 'pgadmin.browser.server.privilege': path.join(__dirname, './pgadmin/browser/server_groups/servers/static/js/privilege'), - 'pgadmin.browser.server.variable': path.join(__dirname, './pgadmin/browser/server_groups/servers/static/js/variable'), - 'pgadmin.browser.collection': path.join(__dirname, './pgadmin/browser/templates/browser/js/collection'), - 'pgadmin.browser.node': path.join(__dirname, './pgadmin/browser/templates/browser/js/node'), - 'pgadmin.browser.node.ui': path.join(__dirname, './pgadmin/browser/static/js/node.ui'), - 'pgadmin.browser.datamodel': path.join(__dirname, './pgadmin/browser/static/js/datamodel'), - 'pgadmin.browser.menu': path.join(__dirname, './pgadmin/browser/static/js/menu'), 'pgadmin.browser.panel': path.join(__dirname, './pgadmin/browser/static/js/panel'), - 'pgadmin.browser.frame': path.join(__dirname, './pgadmin/browser/static/js/frame'), - 'pgadmin.tools.user_management': path.join(__dirname, './pgadmin/tools/user_management/templates/user_management/js/user_management'), - 'slick.pgadmin.editors': path.join(__dirname, './pgadmin/static/js/slickgrid/slick.pgadmin.editors'), - 'slick.pgadmin.formatters': path.join(__dirname, './pgadmin/static/js/slickgrid/slick.pgadmin.formatters'), - - // Browser Nodes JS - 'pgadmin.node.server_group': path.join(__dirname, './pgadmin/browser/server_groups/static/js/server-group'), - 'pgadmin.node.server': path.join(__dirname, './pgadmin/browser/server_groups/servers/static/js/server'), - 'pgadmin.node.database': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/static/js/database'), - 'pgadmin.node.role': path.join(__dirname, './pgadmin/browser/server_groups/servers/roles/templates/role/js/role'), - 'pgadmin.node.tablespace': path.join(__dirname, './pgadmin/browser/server_groups/servers/tablespaces/templates/tablespaces/js/tablespaces'), - 'pgadmin.node.resource_group': path.join(__dirname, './pgadmin/browser/server_groups/servers/resource_groups/templates/resource_groups/js/resource_groups'), - 'pgadmin.node.cast': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/casts/static/js/cast'), - 'pgadmin.node.event_trigger': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/event_triggers/static/js/event_trigger'), - 'pgadmin.node.extension': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/extensions/static/js/extension'), - 'pgadmin.node.foreign_data_wrapper': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/static/js/foreign_data_wrapper'), 'pgadmin.node.language': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/languages/static/js/language'), - 'pgadmin.node.schema': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/static/js/schema'), - 'pgadmin.node.catalog': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/static/js/catalog'), - 'pgadmin.node.catalog_object': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/catalog_objects/static/js/catalog_object'), - 'pgadmin.node.collation': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/collations/static/js/collation'), - 'pgadmin.node.domain': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/domains/static/js/domain'), - 'pgadmin.node.domain_constraints': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/domains/domain_constraints/static/js/domain_constraints'), - 'pgadmin.node.foreign_table': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/static/js/foreign-table'), - 'pgadmin.node.fts_configuration': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/fts_configurations/static/js/fts_configuration'), - 'pgadmin.node.fts_dictionary': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/fts_dictionaries/static/js/fts_dictionary'), - 'pgadmin.node.fts_parser': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/fts_parser/static/js/fts_parser'), - 'pgadmin.node.fts_template': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/fts_templates/static/js/fts_template'), - - 'pgadmin.node.function': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/functions/static/js/function'), - 'pgadmin.node.procedure': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/functions/static/js/procedure'), - 'pgadmin.node.trigger_function': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/functions/static/js/trigger_function'), - 'pgadmin.node.package': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/packages/static/js/package'), - 'pgadmin.node.sequence': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/sequences/static/js/sequence'), - 'pgadmin.node.synonym': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/synonyms/static/js/synonym'), - - 'pgadmin.node.table': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/static/js/table'), - 'pgadmin.browser.table.partition.utils': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/static/js/partition.utils'), - 'pgadmin.node.type': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/types/static/js/type'), - 'pgadmin.node.view': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/views/static/js/view'), 'pgadmin.node.mview': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/views/static/js/mview'), - 'pgadmin.node.rule': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/rules/templates/rules/js/rules'), - 'pgadmin.node.index': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/indexes/templates/index/js/index'), - 'pgadmin.node.trigger': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/triggers/templates/trigger/js/trigger'), - 'pgadmin.node.column': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/column/templates/column/js/column'), - 'pgadmin.node.constraints': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/templates/constraints/js/constraints'), - 'pgadmin.node.check_constraints': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/templates/check_constraint/js/check_constraint'), - 'pgadmin.node.exclusion_constraint': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/exclusion_constraint/templates/exclusion_constraint/js/exclusion_constraint'), - 'pgadmin.node.foreign_key': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/foreign_key/templates/foreign_key/js/foreign_key'), - 'pgadmin.node.primary_key': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/index_constraint/static/js/primary_key'), - 'pgadmin.node.unique_constraint': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/index_constraint/static/js/unique_constraint'), - 'pgadmin.node.catalog_object_column': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/catalog_objects/columns/templates/catalog_object_column/js/catalog_object_column'), - 'pgadmin.node.edbfunc': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/templates/edbfunc/js/edbfunc'), - 'pgadmin.node.edbproc': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/templates/edbproc/js/edbproc'), - 'pgadmin.node.edbvar': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/packages/edbvars/templates/edbvar/js/edbvar'), - - // pgAgent jobs JS - 'pgadmin.node.pga_job': path.join(__dirname, './pgadmin/browser/server_groups/servers/pgagent/static/js/pga_job'), - 'pgadmin.node.pga_schedule': path.join(__dirname, './pgadmin/browser/server_groups/servers/pgagent/schedules/static/js/pga_schedule'), + 'pgadmin.tools.maintenance': path.join(__dirname, './pgadmin/tools/maintenance/static/js/maintenance'), 'pgadmin.node.pga_jobstep': path.join(__dirname, './pgadmin/browser/server_groups/servers/pgagent/steps/static/js/pga_jobstep'), + 'pgadmin.sqleditor': path.join(__dirname, './pgadmin/tools/sqleditor/static/js/sqleditor'), + 'pgadmin.node.foreign_server': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/static/js/foreign_server'), + 'pgadmin.node.domain': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/domains/static/js/domain'), + 'pgadmin.tools.user_management': path.join(__dirname, './pgadmin/tools/user_management/static/js/user_management'), + 'pgadmin.browser': path.join(__dirname, './pgadmin/browser/static/js/browser'), + 'pgadmin.browser.object_statistics': path.join(__dirname, './pgadmin/misc/statistics/static/js/statistics'), + 'pgadmin.node.constraints': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/static/js/constraints'), + 'pgadmin.browser.table.partition.utils': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/static/js/partition.utils'), + 'pgadmin.node.catalog': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/static/js/catalog'), + 'pgadmin.node.role': path.join(__dirname, './pgadmin/browser/server_groups/servers/roles/static/js/role'), + 'pgadmin.node.check_constraint': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/check_constraint/static/js/check_constraint'), + 'translations': '/tools/translations', + 'pgadmin.node.user_mapping': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/foreign_servers/user_mapping/static/js/user_mapping'), + 'pgadmin.browser.messages': '/browser/js/messages', + 'pgadmin.node.collation': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/collations/static/js/collation'), + 'pgadmin.browser.endpoints': '/browser/js/endpoints', + 'pgadmin.node.table': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/static/js/table'), + 'pgadmin.node.tablespace': path.join(__dirname, './pgadmin/browser/server_groups/servers/tablespaces/static/js/tablespace'), + 'pgadmin.node.server': path.join(__dirname, './pgadmin/browser/server_groups/servers/static/js/server'), + 'pgadmin.node.package': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/packages/static/js/package'), + 'pgadmin.browser.menu': path.join(__dirname, './pgadmin/browser/static/js/menu'), + 'pgadmin.browser.node.ui': path.join(__dirname, './pgadmin/browser/static/js/node.ui'), + 'pgadmin.node.rule': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/rules/static/js/rule'), + 'pgadmin.node.server_group': path.join(__dirname, './pgadmin/browser/server_groups/static/js/server_group'), + 'pgadmin.tools.backup': path.join(__dirname, './pgadmin/tools/backup/static/js/backup'), + 'pgadmin.node.fts_configuration': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/fts_configurations/static/js/fts_configuration'), + 'pgadmin.node.event_trigger': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/event_triggers/static/js/event_trigger'), + 'pgadmin.browser.bgprocess': path.join(__dirname, './pgadmin/misc/bgprocess/static/js/bgprocess'), + 'pgadmin.node.pga_job': path.join(__dirname, './pgadmin/browser/server_groups/servers/pgagent/static/js/pga_job'), + 'pgadmin.node.function': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/functions/static/js/function'), + 'pgadmin.file_utility': path.join(__dirname, './pgadmin/misc/file_manager/static/js/utility'), + 'pgadmin.browser.object_depends': path.join(__dirname, './pgadmin/misc/depends/static/js/depends'), + 'pgadmin.node.edbfunc': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/static/js/edbfunc'), + 'pgadmin.node.sequence': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/sequences/static/js/sequence'), + 'pgadmin.node.edbproc': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/packages/edbfuncs/static/js/edbproc'), + 'pgadmin.browser.object_sql': path.join(__dirname, './pgadmin/misc/sql/static/js/sql'), + 'pgadmin.preferences': path.join(__dirname, './pgadmin/preferences/static/js/preferences'), + 'pgadmin.node.domain_constraints': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/domains/domain_constraints/static/js/domain_constraints'), + 'slick.pgadmin.formatters': path.join(__dirname, './pgadmin/tools/../static/js/slickgrid/slick.pgadmin.formatters'), + 'pgadmin.node.catalog_object': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/catalog_objects/static/js/catalog_object'), + 'pgadmin.dashboard': path.join(__dirname, './pgadmin/dashboard/static/js/dashboard'), + 'pgadmin.node.foreign_data_wrapper': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/foreign_data_wrappers/static/js/foreign_data_wrapper'), + 'pgadmin.node.foreign_key': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/foreign_key/static/js/foreign_key'), + 'pgadmin.browser.server.variable': path.join(__dirname, './pgadmin/browser/server_groups/servers/static/js/variable'), + 'pgadmin.tools.grant_wizard': path.join(__dirname, './pgadmin/tools/grant_wizard/static/js/grant_wizard'), + 'pgadmin.browser.datamodel': path.join(__dirname, './pgadmin/browser/static/js/datamodel'), + 'pgadmin.tools.restore': path.join(__dirname, './pgadmin/tools/restore/static/js/restore'), + 'pgadmin.node.procedure': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/functions/static/js/procedure'), + 'pgadmin.browser.server.privilege': path.join(__dirname, './pgadmin/browser/server_groups/servers/static/js/privilege'), + 'pgadmin.node.resource_group': path.join(__dirname, './pgadmin/browser/server_groups/servers/resource_groups/static/js/resource_group'), + 'pgadmin.node.exclusion_constraint': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/exclusion_constraint/static/js/exclusion_constraint'), + 'pgadmin.node.primary_key': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/index_constraint/static/js/primary_key'), + 'pgadmin.tools.debugger.direct': path.join(__dirname, './pgadmin/tools/debugger/static/js/direct'), + 'pgadmin.settings': path.join(__dirname, './pgadmin/settings/static/js/settings'), + 'pgadmin.node.schema': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/static/js/schema'), + 'pgadmin.browser.error': path.join(__dirname, './pgadmin/browser/static/js/error'), + 'pgadmin.tools.import_export': path.join(__dirname, './pgadmin/tools/import_export/static/js/import_export'), + 'pgadmin.node.view': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/views/static/js/view'), + 'pgadmin.tools.debugger.ui': path.join(__dirname, './pgadmin/tools/debugger/static/js/debugger_ui'), + 'pgadmin.node.pga_schedule': path.join(__dirname, './pgadmin/browser/server_groups/servers/pgagent/schedules/static/js/pga_schedule'), + 'pgadmin.node.catalog_object_column': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/catalog_objects/columns/static/js/catalog_object_column'), + 'pgadmin.browser.collection': path.join(__dirname, './pgadmin/browser/static/js/collection'), + 'pgadmin.browser.node': path.join(__dirname, './pgadmin/browser/static/js/node'), + 'pgadmin.misc.explain': path.join(__dirname, './pgadmin/misc/static/explain/js/explain'), + 'pgadmin.node.synonym': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/synonyms/static/js/synonym'), + 'pgadmin.node.extension': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/extensions/static/js/extension'), + 'pgadmin.node.unique_constraint': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/constraints/index_constraint/static/js/unique_constraint'), + 'pgadmin.node.database': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/static/js/database'), + 'pgadmin.node.edbvar': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/packages/edbvars/static/js/edbvar'), + 'pgadmin.node.trigger': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/triggers/static/js/trigger'), + 'pgadmin.browser.wizard': path.join(__dirname, './pgadmin/browser/static/js/wizard'), + 'pgadmin.server.supported_servers': '/browser/server/supported_servers', + 'pgadmin.node.partition': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/partitions/static/js/partition'), + 'pgadmin.node.fts_template': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/fts_templates/static/js/fts_template'), + 'pgadmin.node.cast': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/casts/static/js/cast'), + 'pgadmin.tools.debugger.controller': path.join(__dirname, './pgadmin/tools/debugger/static/js/debugger'), + 'pgadmin.node.fts_parser': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/fts_parser/static/js/fts_parser'), + 'pgadmin.browser.utils': '/browser/js/utils', + 'pgadmin.about': path.join(__dirname, './pgadmin/about/static/js/about'), + 'slick.pgadmin.editors': path.join(__dirname, './pgadmin/tools/../static/js/slickgrid/slick.pgadmin.editors'), + 'pgadmin.node.column': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/column/static/js/column'), + 'pgadmin.node.foreign_table': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/foreign_tables/static/js/foreign_table'), + 'pgadmin.node.fts_dictionary': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/fts_dictionaries/static/js/fts_dictionary'), + 'pgadmin.datagrid': path.join(__dirname, './pgadmin/tools/datagrid/static/js/datagrid'), + 'pgadmin.node.trigger_function': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/functions/static/js/trigger_function'), + 'pgadmin.user_management.current_user': '/user_management/current_user', + 'pgadmin.node.index': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/tables/indexes/static/js/index'), + 'pgadmin.browser.frame': path.join(__dirname, './pgadmin/browser/static/js/frame'), + 'pgadmin.node.type': path.join(__dirname, './pgadmin/browser/server_groups/servers/databases/schemas/types/static/js/type'), + 'pgadmin.file_manager': path.join(__dirname, './pgadmin/misc/file_manager/static/js/file_manager'), }, + externals: [ + 'pgadmin.user_management.current_user', + 'translations', + 'pgadmin.browser.endpoints', + 'pgadmin.browser.messages', + 'pgadmin.browser.utils', + 'pgadmin.server.supported_servers', + ], // Define list of pgAdmin common libraries to bundle them separately // into commons JS from app.bundle.js pgLibs: [ @@ -269,8 +270,8 @@ var webpackShimConfig = { 'pgadmin.browser.server.variable', 'pgadmin.browser.collection', 'pgadmin.browser.node.ui', 'pgadmin.browser.datamodel', 'pgadmin.browser.menu', 'pgadmin.browser.panel', 'pgadmin', 'pgadmin.browser.frame', 'slick.pgadmin.editors', 'slick.pgadmin.formatters', - 'pgadmin.backform', 'pgadmin.backgrid', 'pgadmin.browser', 'misc.file_manager', - 'misc.file_utility', 'sources/alerts/alertify_wrapper', 'pgadmin.browser.node', + 'pgadmin.backform', 'pgadmin.backgrid', 'pgadmin.browser', 'pgadmin.file_manager', + 'pgadmin.file_utility', 'sources/alerts/alertify_wrapper', 'pgadmin.browser.node', 'pgadmin.alertifyjs', 'pgadmin.settings', 'pgadmin.preferences', 'pgadmin.sqlfoldcode', ], // Checks whether JS module is npm module or not