Commit 640f24dd authored by Jérome Perrin's avatar Jérome Perrin

Graph editor for visual edition of workflow and business process

Uses graph editor component from DREAM simulation project http://dream-simulation.eu/

This editor is in early stage; it supports edition of business paths from business process and edition of workflow layout in DCWorkflow.

Known problems / TODO:
 - DCWorkflow editor only saves the graph layout and does not allow designing the workflow
 - DCWorkflow graph has to be enabled in history tab for history visualisation
 - rendering of fields in the property edition dialog is extremely slow
 - mixin_promise.js have to be merged. Other TODO's in test.js and jsplumb.js. Generally speaking, this javascript code is poor quality
parent 1aa70bbf
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ActionInformation" module="Products.CMFCore.ActionInformation"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>action</string> </key>
<value>
<persistent> <string encoding="base64">AAAAAAAAAAI=</string> </persistent>
</value>
</item>
<item>
<key> <string>categories</string> </key>
<value>
<tuple>
<string>action_type/object_view</string>
</tuple>
</value>
</item>
<item>
<key> <string>category</string> </key>
<value> <string>object_view</string> </value>
</item>
<item>
<key> <string>condition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>description</string> </key>
<value>
<none/>
</value>
</item>
<item>
<key> <string>icon</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>view_graph_editor</string> </value>
</item>
<item>
<key> <string>permissions</string> </key>
<value>
<tuple>
<string>View</string>
</tuple>
</value>
</item>
<item>
<key> <string>priority</string> </key>
<value> <float>3.0</float> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>Graph Editor</string> </value>
</item>
<item>
<key> <string>visible</string> </key>
<value> <int>1</int> </value>
</item>
</dictionary>
</pickle>
</record>
<record id="2" aka="AAAAAAAAAAI=">
<pickle>
<global name="Expression" module="Products.CMFCore.Expression"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>text</string> </key>
<value> <string>string:${object_url}/BusinessProcess_viewGraphEditor</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<workflow_chain>
<chain>
<type>Business Process</type>
<workflow>business_process_graph_editor_interaction_workflow</workflow>
</chain>
</workflow_chain>
\ No newline at end of file
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Folder" module="OFS.Folder"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>erp5_graph_editor</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="PythonScript" module="Products.PythonScripts.PythonScript"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>Script_magic</string> </key>
<value> <int>3</int> </value>
</item>
<item>
<key> <string>_bind_names</string> </key>
<value>
<object>
<klass>
<global name="NameAssignments" module="Shared.DC.Scripts.Bindings"/>
</klass>
<tuple/>
<state>
<dictionary>
<item>
<key> <string>_asgns</string> </key>
<value>
<dictionary>
<item>
<key> <string>name_container</string> </key>
<value> <string>container</string> </value>
</item>
<item>
<key> <string>name_context</string> </key>
<value> <string>context</string> </value>
</item>
<item>
<key> <string>name_m_self</string> </key>
<value> <string>script</string> </value>
</item>
<item>
<key> <string>name_subpath</string> </key>
<value> <string>traverse_subpath</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</state>
</object>
</value>
</item>
<item>
<key> <string>_body</string> </key>
<value> <string>from Products.ERP5Type.Message import translateString\n
import json\n
portal = context.getPortalObject()\n
\n
# if a graph has been saved, we use this info for node coordinates.\n
position_graph = context.getProperty(\'jsplumb_graph\')\n
if position_graph:\n
position_graph = json.loads(position_graph)[\'graph\']\n
\n
visited_business_process_set = set() # prevent infinite recurisions\n
\n
def getBusinessProcessGraph(business_process):\n
graph = dict(node=dict(start=dict(_class=\'erp5.business_process.start\',\n
name=str(translateString(\'Start\'))),),\n
edge=dict())\n
\n
\n
for trade_state in portal.portal_categories.trade_state.getCategoryChildValueList(): # XXX do we really want to display all trade states ?\n
state_id = trade_state.getReference() or trade_state.getId()\n
graph[\'node\'][state_id] = dict(\n
_class=\'erp5.business_process.trade_state\',\n
name=trade_state.getTranslatedTitle())\n
\n
for state_id in graph[\'node\'].keys():\n
if position_graph and state_id in position_graph[\'node\']:\n
graph[\'node\'][state_id][\'coordinate\'] = position_graph[\'node\'][state_id][\'coordinate\']\n
\n
if business_process in visited_business_process_set:\n
return graph\n
visited_business_process_set.add(business_process)\n
for link in business_process.contentValues(portal_type=\'Business Link\'):\n
\n
predecessor = \'start\'\n
if link.getPredecessor():\n
predecessor = link.getPredecessorReference() or link.getPredecessorId()\n
successor = \'end\'\n
if link.getSuccessor():\n
successor = link.getSuccessorReference() or link.getSuccessorId()\n
\n
graph[\'edge\'][link.getRelativeUrl()] = dict(\n
_class=\'erp5.business_process.business_link\',\n
source=predecessor,\n
destination=successor,\n
name=link.getTranslatedTitle(),\n
business_link_url=link.getRelativeUrl(),\n
trade_phase=link.getTradePhase() or \'\')\n
\n
for specialise in [context] + business_process.getSpecialiseValueList(portal_type=\'Business Process\'):\n
specialise_graph = getBusinessProcessGraph(specialise)\n
for node_id, node_data in specialise_graph[\'node\'].items():\n
graph[\'node\'].setdefault(node_id, node_data)\n
for node_id, node_data in specialise_graph[\'edge\'].items():\n
graph[\'edge\'].setdefault(node_id, node_data)\n
return graph\n
\n
\n
class_definition = {\n
\'erp5.business_process.business_link\': {\n
\'_class\': \'edge\',\n
\'type\': \'object\',\n
\'description\': \'An ERP5 Business Link\',\n
\'properties\': {\n
\'name\': {\'type\': \'string\', \'name\': str(translateString(\'Name\'))},\n
\'trade_phase\': {\'type\': \'string\', \'name\': str(translateString(\'Trade Phase\')), \'enum\': [\'\'] + [\n
trade_phase.getId() for trade_phase in portal.portal_categories.trade_phase.getCategoryChildValueList(local_sort_on=(\'int_index\', \'title\'))]}, \n
}\n
}\n
}\n
\n
return json.dumps(dict(graph=getBusinessProcessGraph(context), class_definition=class_definition), indent=2)\n
</string> </value>
</item>
<item>
<key> <string>_params</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>BusinessProcess_getGraph</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ERP5 Form" module="erp5.portal_type"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_bind_names</string> </key>
<value>
<object>
<klass>
<global name="NameAssignments" module="Shared.DC.Scripts.Bindings"/>
</klass>
<tuple/>
<state>
<dictionary>
<item>
<key> <string>_asgns</string> </key>
<value>
<dictionary/>
</value>
</item>
</dictionary>
</state>
</object>
</value>
</item>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>action</string> </key>
<value> <string>Base_edit</string> </value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>edit_order</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>encoding</string> </key>
<value> <string>UTF-8</string> </value>
</item>
<item>
<key> <string>enctype</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>group_list</string> </key>
<value>
<list>
<string>left</string>
<string>right</string>
<string>center</string>
<string>bottom</string>
<string>hidden</string>
</list>
</value>
</item>
<item>
<key> <string>groups</string> </key>
<value>
<dictionary>
<item>
<key> <string>bottom</string> </key>
<value>
<list>
<string>listbox</string>
</list>
</value>
</item>
<item>
<key> <string>center</string> </key>
<value>
<list>
<string>my_jsplumb_graph</string>
</list>
</value>
</item>
<item>
<key> <string>hidden</string> </key>
<value>
<list>
<string>listbox_int_index</string>
<string>listbox_order_builder_title_list</string>
<string>listbox_delivery_builder_title_list</string>
</list>
</value>
</item>
<item>
<key> <string>left</string> </key>
<value>
<list>
<string>my_title</string>
</list>
</value>
</item>
<item>
<key> <string>right</string> </key>
<value>
<list>
<string>my_reference</string>
</list>
</value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>BusinessProcess_viewGraphEditor</string> </value>
</item>
<item>
<key> <string>method</string> </key>
<value> <string>POST</string> </value>
</item>
<item>
<key> <string>name</string> </key>
<value> <string>BusinessProcessModel_view</string> </value>
</item>
<item>
<key> <string>pt</string> </key>
<value> <string>form_view</string> </value>
</item>
<item>
<key> <string>row_length</string> </key>
<value> <int>4</int> </value>
</item>
<item>
<key> <string>stored_encoding</string> </key>
<value> <string>UTF-8</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>Graph Editor</string> </value>
</item>
<item>
<key> <string>unicode_mode</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>update_action</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>update_action_title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ProxyField" module="Products.ERP5Form.ProxyField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>delegated_list</string> </key>
<value>
<list>
<string>columns</string>
<string>editable_columns</string>
<string>enabled</string>
<string>portal_types</string>
<string>selection_name</string>
<string>sort</string>
<string>title</string>
</list>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>listbox</string> </value>
</item>
<item>
<key> <string>message_values</string> </key>
<value>
<dictionary>
<item>
<key> <string>external_validator_failed</string> </key>
<value> <string>The input failed the external validator.</string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>overrides</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>tales</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>values</string> </key>
<value>
<dictionary>
<item>
<key> <string>columns</string> </key>
<value>
<list>
<tuple>
<string>int_index</string>
<string>Index</string>
</tuple>
<tuple>
<string>title</string>
<string>Title</string>
</tuple>
<tuple>
<string>predecessor_title</string>
<string>Predecessor</string>
</tuple>
<tuple>
<string>successor_title</string>
<string>Successor</string>
</tuple>
<tuple>
<string>order_builder_title_list</string>
<string>Order Builders</string>
</tuple>
<tuple>
<string>delivery_builder_title_list</string>
<string>Delivery Builders</string>
</tuple>
<tuple>
<string>trade_phase_title</string>
<string>Trade Phase</string>
</tuple>
</list>
</value>
</item>
<item>
<key> <string>editable_columns</string> </key>
<value>
<list>
<tuple>
<string>int_index</string>
<string>int_index</string>
</tuple>
</list>
</value>
</item>
<item>
<key> <string>enabled</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>field_id</string> </key>
<value> <string>my_view_mode_listbox</string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string>Base_viewTradeFieldLibrary</string> </value>
</item>
<item>
<key> <string>portal_types</string> </key>
<value>
<list>
<tuple>
<string>Business Link</string>
<string>Business Link</string>
</tuple>
</list>
</value>
</item>
<item>
<key> <string>selection_name</string> </key>
<value> <string>business_process_model_view_selection</string> </value>
</item>
<item>
<key> <string>sort</string> </key>
<value>
<list>
<tuple>
<string>int_index</string>
<string>ascending</string>
</tuple>
</list>
</value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string>Click to edit the target</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>Business Links</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ProxyField" module="Products.ERP5Form.ProxyField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>delegated_list</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>listbox_delivery_builder_title_list</string> </value>
</item>
<item>
<key> <string>message_values</string> </key>
<value>
<dictionary>
<item>
<key> <string>external_validator_failed</string> </key>
<value> <string>The input failed the external validator.</string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>overrides</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>tales</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>values</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string>my_view_mode_listbox_delivery_builder_title_list</string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string>Base_viewTradeFieldLibrary</string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string>Click to edit the target</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ProxyField" module="Products.ERP5Form.ProxyField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>delegated_list</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>listbox_int_index</string> </value>
</item>
<item>
<key> <string>message_values</string> </key>
<value>
<dictionary>
<item>
<key> <string>external_validator_failed</string> </key>
<value> <string>The input failed the external validator.</string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>overrides</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>tales</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>values</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string>my_view_mode_listbox_int_index</string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string>Base_viewTradeFieldLibrary</string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string>Click to edit the target</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ProxyField" module="Products.ERP5Form.ProxyField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>delegated_list</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>listbox_order_builder_title_list</string> </value>
</item>
<item>
<key> <string>message_values</string> </key>
<value>
<dictionary>
<item>
<key> <string>external_validator_failed</string> </key>
<value> <string>The input failed the external validator.</string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>overrides</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>tales</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>values</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string>my_view_mode_listbox_order_builder_title_list</string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string>Base_viewTradeFieldLibrary</string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string>Click to edit the target</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="GadgetField" module="Products.ERP5Form.GadgetField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>id</string> </key>
<value> <string>my_jsplumb_graph</string> </value>
</item>
<item>
<key> <string>message_values</string> </key>
<value>
<dictionary>
<item>
<key> <string>external_validator_failed</string> </key>
<value> <string>The input failed the external validator.</string> </value>
</item>
<item>
<key> <string>required_not_found</string> </key>
<value> <string>Input is required but no input given.</string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>overrides</string> </key>
<value>
<dictionary>
<item>
<key> <string>alternate_name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>css_class</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>default</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>display_maxwidth</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>display_width</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>editable</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>enabled</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>external_validator</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>extra</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>gadget_url</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>hidden</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>js_sandbox</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>required</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>tales</string> </key>
<value>
<dictionary>
<item>
<key> <string>alternate_name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>css_class</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>data_url</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>default</string> </key>
<value>
<persistent> <string encoding="base64">AAAAAAAAAAI=</string> </persistent>
</value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>display_maxwidth</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>display_width</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>editable</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>enabled</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>external_validator</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>extra</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>gadget_url</string> </key>
<value>
<persistent> <string encoding="base64">AAAAAAAAAAM=</string> </persistent>
</value>
</item>
<item>
<key> <string>hidden</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>js_sandbox</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>required</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>values</string> </key>
<value>
<dictionary>
<item>
<key> <string>alternate_name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>css_class</string> </key>
<value> <string>page</string> </value>
</item>
<item>
<key> <string>data_url</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>default</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>display_maxwidth</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>display_width</string> </key>
<value> <int>20</int> </value>
</item>
<item>
<key> <string>editable</string> </key>
<value> <int>1</int> </value>
</item>
<item>
<key> <string>enabled</string> </key>
<value> <int>1</int> </value>
</item>
<item>
<key> <string>external_validator</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>extra</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>gadget_url</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>hidden</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>js_sandbox</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>required</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>Graph</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</pickle>
</record>
<record id="2" aka="AAAAAAAAAAI=">
<pickle>
<global name="TALESMethod" module="Products.Formulator.TALESField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_text</string> </key>
<value> <string>context/BusinessProcess_getGraph</string> </value>
</item>
</dictionary>
</pickle>
</record>
<record id="3" aka="AAAAAAAAAAM=">
<pickle>
<global name="TALESMethod" module="Products.Formulator.TALESField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_text</string> </key>
<value> <string>python: context.getPortalObject().restrictedTraverse(\'dream_graph_editor/jsplumb/index.html\').absolute_url()</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ProxyField" module="Products.ERP5Form.ProxyField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>delegated_list</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>my_reference</string> </value>
</item>
<item>
<key> <string>message_values</string> </key>
<value>
<dictionary>
<item>
<key> <string>external_validator_failed</string> </key>
<value> <string>The input failed the external validator.</string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>overrides</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>tales</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>values</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string>my_view_mode_reference</string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string>Base_viewTradeFieldLibrary</string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string>Click to edit the target</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ProxyField" module="Products.ERP5Form.ProxyField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>delegated_list</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>my_title</string> </value>
</item>
<item>
<key> <string>message_values</string> </key>
<value>
<dictionary>
<item>
<key> <string>external_validator_failed</string> </key>
<value> <string>The input failed the external validator.</string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>overrides</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>tales</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>values</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string>my_view_mode_title</string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string>Base_viewTradeFieldLibrary</string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string>Click to edit the target</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="PythonScript" module="Products.PythonScripts.PythonScript"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>Script_magic</string> </key>
<value> <int>3</int> </value>
</item>
<item>
<key> <string>_bind_names</string> </key>
<value>
<object>
<klass>
<global name="NameAssignments" module="Shared.DC.Scripts.Bindings"/>
</klass>
<tuple/>
<state>
<dictionary>
<item>
<key> <string>_asgns</string> </key>
<value>
<dictionary>
<item>
<key> <string>name_container</string> </key>
<value> <string>container</string> </value>
</item>
<item>
<key> <string>name_context</string> </key>
<value> <string>context</string> </value>
</item>
<item>
<key> <string>name_m_self</string> </key>
<value> <string>script</string> </value>
</item>
<item>
<key> <string>name_subpath</string> </key>
<value> <string>traverse_subpath</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</state>
</object>
</value>
</item>
<item>
<key> <string>_body</string> </key>
<value> <string>from Products.ERP5Type.Message import translateString\n
from Products.Formulator.Errors import FormValidationError\n
request = container.REQUEST\n
\n
form = getattr(context, form_id)\n
edit_order = form.edit_order\n
try:\n
# Validate\n
form.validate_all_to_request(request, key_prefix=\'my_\')\n
except FormValidationError, validation_errors:\n
# Pack errors into the request\n
result = {}\n
result[\'field_errors\'] = {}\n
field_errors = form.ErrorFields(validation_errors)\n
for key, value in field_errors.items():\n
result[\'field_errors\'][key] = value.error_text\n
return form()\n
\n
(kw, encapsulated_editor_list), action = context.Base_edit(form_id, silent_mode=1)\n
assert not encapsulated_editor_list\n
\n
context.setProperties(\n
title=kw[\'title\'],\n
description=kw[\'description\'],\n
manager_bypass=context.manager_bypass)\n
marker = []\n
if context.getProperty("jsplumb_graph", marker) is marker:\n
context.manage_setProperty("jsplumb_graph", kw["jsplumb_graph"])\n
else:\n
context.manage_changeProperties({\'jsplumb_graph\': kw["jsplumb_graph"]})\n
\n
# XXX handle workflow edition here.\n
\n
return context.Base_redirect(form_id, \n
keep_items={\'portal_status_message\': translateString("Data updated.")})\n
</string> </value>
</item>
<item>
<key> <string>_params</string> </key>
<value> <string>form_id, *args, **kw</string> </value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>DCWorkflow_edit</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="PythonScript" module="Products.PythonScripts.PythonScript"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>Script_magic</string> </key>
<value> <int>3</int> </value>
</item>
<item>
<key> <string>_bind_names</string> </key>
<value>
<object>
<klass>
<global name="NameAssignments" module="Shared.DC.Scripts.Bindings"/>
</klass>
<tuple/>
<state>
<dictionary>
<item>
<key> <string>_asgns</string> </key>
<value>
<dictionary>
<item>
<key> <string>name_container</string> </key>
<value> <string>container</string> </value>
</item>
<item>
<key> <string>name_context</string> </key>
<value> <string>context</string> </value>
</item>
<item>
<key> <string>name_m_self</string> </key>
<value> <string>script</string> </value>
</item>
<item>
<key> <string>name_subpath</string> </key>
<value> <string>traverse_subpath</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</state>
</object>
</value>
</item>
<item>
<key> <string>_body</string> </key>
<value> <string>from Products.ERP5Type.Message import translateString\n
import json\n
portal = context.getPortalObject()\n
\n
# if a graph has been saved, we use this info for node coordinates.\n
position_graph = context.getProperty(\'jsplumb_graph\')\n
if position_graph:\n
position_graph = json.loads(position_graph)[\'graph\']\n
\n
# TODO:\n
# select after script in edge properties\n
# checked box for validation ? or at least select before script\n
\n
def getDCWorkflowGraph(dc_workflow):\n
graph = dict(node=dict(), edge=dict())\n
for state in dc_workflow.states.objectValues():\n
is_initial_state = state.getId() == dc_workflow.states.initial_state\n
graph[\'node\'][state.getId()] = dict(\n
_class=\'dc_workflow.state\',\n
name=state.title_or_id(),\n
is_initial_state="Yes" if is_initial_state else "No")\n
if is_initial_state:\n
graph[\'node\'][state.getId()][\'css\'] = { "color": "red" } # TODO: use different CSS for initial state\n
\n
for transition in state.transitions:\n
if transition in dc_workflow.transitions:\n
transition = dc_workflow.transitions[transition]\n
if transition.new_state_id:\n
graph[\'edge\']["%s_%s" % (state.getId(), transition.id)] = (\n
dict(_class=\'dc_workflow.transition\',\n
source=state.getId(),\n
destination=transition.new_state_id,\n
name=transition.actbox_name or transition.title_or_id(),\n
description=transition.description,\n
actbox_url=transition.actbox_url,\n
transition_id=transition.getId() # used for edition.\n
))\n
\n
if position_graph:\n
for state_id in graph[\'node\'].keys():\n
if state_id in position_graph[\'node\']:\n
graph[\'node\'][state_id][\'coordinate\'] = position_graph[\'node\'][state_id][\'coordinate\']\n
return graph\n
\n
\n
class_definition = {\n
\'dc_workflow.transition\': {\n
\'_class\': \'edge\',\n
\'type\': \'object\',\n
\'description\': \'A DCWorkflow Transition\',\n
\'properties\': {\n
\'name\': {\n
\'type\': \'string\',\n
\'name\': \'Name\',\n
\'description\': \'Name of this transition, will be displayed in the document actions\',\n
},\n
\'description\': {\n
\'type\': \'string\',\n
\'name\': \'Description\',\n
},\n
\'actbox_url\': {\n
\'type\': \'string\',\n
\'name\': \'Action URL\',\n
\'description\': \'URL of the action, variables will be substitued. XXX TODO: higher level ! just configure "script name" \'\n
},\n
}\n
},\n
\'dc_workflow.state\': {\n
\'_class\': \'node\',\n
\'type\': \'object\',\n
\'description\': \'A DCWorkflow State\',\n
\'properties\': {\n
\'name\': {\n
\'type\': \'string\',\n
\'name\': \'Name\',\n
\'description\': \'The name of the state, will be displayed in document view\',\n
},\n
\'id\': {\n
\'type\': \'string\',\n
\'name\': \'Id\',\n
\'description\': \'Id of the state, will be used for catalog searches\',\n
},\n
\'is_initial_state\': {\n
\'type\': \'string\',\n
\'enum\': [\'Yes\', \'No\'],\n
\'name\': \'Is initial State\',\n
\'description\': \'Set to Yes if this state is the initial state for newly created documents\',\n
},\n
}\n
}\n
}\n
\n
return json.dumps(dict(graph=getDCWorkflowGraph(context), class_definition=class_definition), indent=2)\n
</string> </value>
</item>
<item>
<key> <string>_params</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>DCWorkflow_getGraph</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="PythonScript" module="Products.PythonScripts.PythonScript"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>Script_magic</string> </key>
<value> <int>3</int> </value>
</item>
<item>
<key> <string>_bind_names</string> </key>
<value>
<object>
<klass>
<global name="NameAssignments" module="Shared.DC.Scripts.Bindings"/>
</klass>
<tuple/>
<state>
<dictionary>
<item>
<key> <string>_asgns</string> </key>
<value>
<dictionary>
<item>
<key> <string>name_container</string> </key>
<value> <string>container</string> </value>
</item>
<item>
<key> <string>name_context</string> </key>
<value> <string>context</string> </value>
</item>
<item>
<key> <string>name_m_self</string> </key>
<value> <string>script</string> </value>
</item>
<item>
<key> <string>name_subpath</string> </key>
<value> <string>traverse_subpath</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</state>
</object>
</value>
</item>
<item>
<key> <string>_body</string> </key>
<value> <string>from Products.PythonScripts.standard import Object\n
object_list = []\n
\n
def add(script):\n
# we use a function for lambda\'s closure\n
object_list.append(\n
Object(uid=\'new_\',\n
getUid=lambda: \'new_\',\n
id=script.id,\n
title_or_id=script.title_or_id,\n
absolute_url=lambda: "%s/manage_main" % script.absolute_url(),\n
getListItemUrl=lambda *args: "%s/manage_main" % script.absolute_url()))\n
\n
for script in context.scripts.objectValues(\'Script (Python)\'):\n
add(script)\n
return object_list\n
</string> </value>
</item>
<item>
<key> <string>_params</string> </key>
<value> <string>*args, **kw</string> </value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>DCWorkflow_getScriptList</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ERP5 Form" module="erp5.portal_type"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_bind_names</string> </key>
<value>
<object>
<klass>
<global name="NameAssignments" module="Shared.DC.Scripts.Bindings"/>
</klass>
<tuple/>
<state>
<dictionary>
<item>
<key> <string>_asgns</string> </key>
<value>
<dictionary/>
</value>
</item>
</dictionary>
</state>
</object>
</value>
</item>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>action</string> </key>
<value> <string>DCWorkflow_edit</string> </value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>edit_order</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>encoding</string> </key>
<value> <string>UTF-8</string> </value>
</item>
<item>
<key> <string>enctype</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>group_list</string> </key>
<value>
<list>
<string>left</string>
<string>right</string>
<string>center</string>
<string>bottom</string>
<string>hidden</string>
</list>
</value>
</item>
<item>
<key> <string>groups</string> </key>
<value>
<dictionary>
<item>
<key> <string>bottom</string> </key>
<value>
<list>
<string>listbox</string>
</list>
</value>
</item>
<item>
<key> <string>center</string> </key>
<value>
<list>
<string>my_jsplumb_graph</string>
</list>
</value>
</item>
<item>
<key> <string>hidden</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>left</string> </key>
<value>
<list>
<string>my_title</string>
</list>
</value>
</item>
<item>
<key> <string>right</string> </key>
<value>
<list>
<string>my_description</string>
</list>
</value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>DCWorkflow_viewGraphEditor</string> </value>
</item>
<item>
<key> <string>method</string> </key>
<value> <string>POST</string> </value>
</item>
<item>
<key> <string>name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>pt</string> </key>
<value> <string>form_view</string> </value>
</item>
<item>
<key> <string>row_length</string> </key>
<value> <int>4</int> </value>
</item>
<item>
<key> <string>stored_encoding</string> </key>
<value> <string>UTF-8</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>DC Workflow</string> </value>
</item>
<item>
<key> <string>unicode_mode</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>update_action</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>update_action_title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ListBox" module="Products.ERP5Form.ListBox"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>id</string> </key>
<value> <string>listbox</string> </value>
</item>
<item>
<key> <string>message_values</string> </key>
<value>
<dictionary>
<item>
<key> <string>external_validator_failed</string> </key>
<value> <string>The input failed the external validator.</string> </value>
</item>
<item>
<key> <string>required_not_found</string> </key>
<value> <string>Input is required but no input given.</string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>overrides</string> </key>
<value>
<dictionary>
<item>
<key> <string>all_columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>alternate_name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>anchor</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>count_method</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>css_class</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>default_display_style</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>default_params</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>display_style_list</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>domain_root_list</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>domain_tree</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>editable</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>editable_columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>enabled</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>external_validator</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>global_attributes</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>global_search_column</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>hidden</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>hide_rows_on_no_search_criterion</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>lines</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>list_action</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>list_method</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>meta_types</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>page_navigation_template</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>page_template</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>portal_types</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>report_root_list</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>report_tree</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>row_css_method</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>search</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>search_columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>select</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>selection_name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>sort</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>sort_columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>stat_columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>stat_method</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>style_columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>untranslatable_columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>url_columns</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>tales</string> </key>
<value>
<dictionary>
<item>
<key> <string>all_columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>alternate_name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>anchor</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>count_method</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>css_class</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>default_display_style</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>default_params</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>display_style_list</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>domain_root_list</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>domain_tree</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>editable</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>editable_columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>enabled</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>external_validator</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>global_attributes</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>global_search_column</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>hidden</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>hide_rows_on_no_search_criterion</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>lines</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>list_action</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>list_method</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>meta_types</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>page_navigation_template</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>page_template</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>portal_types</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>report_root_list</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>report_tree</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>row_css_method</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>search</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>search_columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>select</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>selection_name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>sort</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>sort_columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>stat_columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>stat_method</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>style_columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>untranslatable_columns</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>url_columns</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>values</string> </key>
<value>
<dictionary>
<item>
<key> <string>all_columns</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>alternate_name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>anchor</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>columns</string> </key>
<value>
<list>
<tuple>
<string>id</string>
<string>ID</string>
</tuple>
<tuple>
<string>title_or_id</string>
<string>Title</string>
</tuple>
</list>
</value>
</item>
<item>
<key> <string>count_method</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>css_class</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>default_display_style</string> </key>
<value> <string>table</string> </value>
</item>
<item>
<key> <string>default_params</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>display_style_list</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>domain_root_list</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>domain_tree</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>editable</string> </key>
<value> <int>1</int> </value>
</item>
<item>
<key> <string>editable_columns</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>enabled</string> </key>
<value> <int>1</int> </value>
</item>
<item>
<key> <string>external_validator</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>global_attributes</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>global_search_column</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>hidden</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>hide_rows_on_no_search_criterion</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>lines</string> </key>
<value> <int>20</int> </value>
</item>
<item>
<key> <string>list_action</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>list_method</string> </key>
<value>
<persistent> <string encoding="base64">AAAAAAAAAAI=</string> </persistent>
</value>
</item>
<item>
<key> <string>meta_types</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>page_navigation_template</string> </key>
<value> <string>ListBox_viewSliderPageNavigationRenderer</string> </value>
</item>
<item>
<key> <string>page_template</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>portal_types</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>report_root_list</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>report_tree</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>row_css_method</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>search</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>search_columns</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>select</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>selection_name</string> </key>
<value> <string>dc_workflow_script_selection</string> </value>
</item>
<item>
<key> <string>sort</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>sort_columns</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>stat_columns</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>stat_method</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>style_columns</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>Scripts</string> </value>
</item>
<item>
<key> <string>untranslatable_columns</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>url_columns</string> </key>
<value>
<list/>
</value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</pickle>
</record>
<record id="2" aka="AAAAAAAAAAI=">
<pickle>
<global name="Method" module="Products.Formulator.MethodField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>method_name</string> </key>
<value> <string>DCWorkflow_getScriptList</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="TextAreaField" module="Products.Formulator.StandardFields"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>id</string> </key>
<value> <string>my_description</string> </value>
</item>
<item>
<key> <string>message_values</string> </key>
<value>
<dictionary>
<item>
<key> <string>external_validator_failed</string> </key>
<value> <string>The input failed the external validator.</string> </value>
</item>
<item>
<key> <string>line_too_long</string> </key>
<value> <string>A line was too long.</string> </value>
</item>
<item>
<key> <string>required_not_found</string> </key>
<value> <string>Input is required but no input given.</string> </value>
</item>
<item>
<key> <string>too_long</string> </key>
<value> <string>You entered too many characters.</string> </value>
</item>
<item>
<key> <string>too_many_lines</string> </key>
<value> <string>You entered too many lines.</string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>overrides</string> </key>
<value>
<dictionary>
<item>
<key> <string>alternate_name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>css_class</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>default</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>editable</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>enabled</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>external_validator</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>extra</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>height</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>hidden</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>max_length</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>max_linelength</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>max_lines</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>required</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>unicode</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>whitespace_preserve</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>width</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>tales</string> </key>
<value>
<dictionary>
<item>
<key> <string>alternate_name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>css_class</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>default</string> </key>
<value>
<persistent> <string encoding="base64">AAAAAAAAAAI=</string> </persistent>
</value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>editable</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>enabled</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>external_validator</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>extra</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>height</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>hidden</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>max_length</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>max_linelength</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>max_lines</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>required</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>unicode</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>whitespace_preserve</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>width</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>values</string> </key>
<value>
<dictionary>
<item>
<key> <string>alternate_name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>css_class</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>default</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>editable</string> </key>
<value> <int>1</int> </value>
</item>
<item>
<key> <string>enabled</string> </key>
<value> <int>1</int> </value>
</item>
<item>
<key> <string>external_validator</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>extra</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>height</string> </key>
<value> <int>5</int> </value>
</item>
<item>
<key> <string>hidden</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>max_length</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>max_linelength</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>max_lines</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>required</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>Description</string> </value>
</item>
<item>
<key> <string>unicode</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>whitespace_preserve</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>width</string> </key>
<value> <int>40</int> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</pickle>
</record>
<record id="2" aka="AAAAAAAAAAI=">
<pickle>
<global name="TALESMethod" module="Products.Formulator.TALESField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_text</string> </key>
<value> <string>context/description</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="GadgetField" module="Products.ERP5Form.GadgetField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>id</string> </key>
<value> <string>my_jsplumb_graph</string> </value>
</item>
<item>
<key> <string>message_values</string> </key>
<value>
<dictionary>
<item>
<key> <string>external_validator_failed</string> </key>
<value> <string>The input failed the external validator.</string> </value>
</item>
<item>
<key> <string>required_not_found</string> </key>
<value> <string>Input is required but no input given.</string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>overrides</string> </key>
<value>
<dictionary>
<item>
<key> <string>alternate_name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>css_class</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>default</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>display_maxwidth</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>display_width</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>editable</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>enabled</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>external_validator</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>extra</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>gadget_url</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>hidden</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>js_sandbox</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>required</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>tales</string> </key>
<value>
<dictionary>
<item>
<key> <string>alternate_name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>css_class</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>data_url</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>default</string> </key>
<value>
<persistent> <string encoding="base64">AAAAAAAAAAI=</string> </persistent>
</value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>display_maxwidth</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>display_width</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>editable</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>enabled</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>external_validator</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>extra</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>gadget_url</string> </key>
<value>
<persistent> <string encoding="base64">AAAAAAAAAAM=</string> </persistent>
</value>
</item>
<item>
<key> <string>hidden</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>js_sandbox</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>required</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>values</string> </key>
<value>
<dictionary>
<item>
<key> <string>alternate_name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>css_class</string> </key>
<value> <string>page</string> </value>
</item>
<item>
<key> <string>data_url</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>default</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>display_maxwidth</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>display_width</string> </key>
<value> <int>20</int> </value>
</item>
<item>
<key> <string>editable</string> </key>
<value> <int>1</int> </value>
</item>
<item>
<key> <string>enabled</string> </key>
<value> <int>1</int> </value>
</item>
<item>
<key> <string>external_validator</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>extra</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>gadget_url</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>hidden</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>js_sandbox</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>required</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>Graph</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</pickle>
</record>
<record id="2" aka="AAAAAAAAAAI=">
<pickle>
<global name="TALESMethod" module="Products.Formulator.TALESField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_text</string> </key>
<value> <string>context/DCWorkflow_getGraph</string> </value>
</item>
</dictionary>
</pickle>
</record>
<record id="3" aka="AAAAAAAAAAM=">
<pickle>
<global name="TALESMethod" module="Products.Formulator.TALESField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_text</string> </key>
<value> <string>python: context.getPortalObject().restrictedTraverse(\'dream_graph_editor/jsplumb/index.html\').absolute_url()</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ProxyField" module="Products.ERP5Form.ProxyField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>delegated_list</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>my_title</string> </value>
</item>
<item>
<key> <string>message_values</string> </key>
<value>
<dictionary>
<item>
<key> <string>external_validator_failed</string> </key>
<value> <string>The input failed the external validator.</string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>overrides</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>tales</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>values</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string>my_view_mode_title</string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string>Base_viewTradeFieldLibrary</string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string>Click to edit the target</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Folder" module="OFS.Folder"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>dream_graph_editor</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Folder" module="OFS.Folder"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>dream</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts31681349.46</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>mixin_promise.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
/// FIXME: merge into the gadget using these utilities and remove this file\n
\n
/*global RSVP, FileReader */\n
/*jslint unparam: true */\n
(function(window, RSVP, FileReader) {\n
"use strict";\n
window.loopEventListener = function(target, type, useCapture, callback, allowDefault) {\n
//////////////////////////\n
// Infinite event listener (promise is never resolved)\n
// eventListener is removed when promise is cancelled/rejected\n
//////////////////////////\n
var handle_event_callback, callback_promise;\n
function cancelResolver() {\n
if (callback_promise !== undefined && typeof callback_promise.cancel === "function") {\n
callback_promise.cancel();\n
}\n
}\n
function canceller() {\n
if (handle_event_callback !== undefined) {\n
target.removeEventListener(type, handle_event_callback, useCapture);\n
}\n
cancelResolver();\n
}\n
function itsANonResolvableTrap(resolve, reject) {\n
handle_event_callback = function(evt) {\n
evt.stopPropagation();\n
if (allowDefault !== true) {\n
evt.preventDefault();\n
}\n
cancelResolver();\n
callback_promise = new RSVP.Queue().push(function() {\n
return callback(evt);\n
}).push(undefined, function(error) {\n
if (!(error instanceof RSVP.CancellationError)) {\n
canceller();\n
reject(error);\n
}\n
});\n
};\n
target.addEventListener(type, handle_event_callback, useCapture);\n
}\n
return new RSVP.Promise(itsANonResolvableTrap, canceller);\n
};\n
window.promiseEventListener = function(target, type, useCapture) {\n
//////////////////////////\n
// Resolve the promise as soon as the event is triggered\n
// eventListener is removed when promise is cancelled/resolved/rejected\n
//////////////////////////\n
var handle_event_callback;\n
function canceller() {\n
target.removeEventListener(type, handle_event_callback, useCapture);\n
}\n
function resolver(resolve) {\n
handle_event_callback = function(evt) {\n
canceller();\n
evt.stopPropagation();\n
evt.preventDefault();\n
resolve(evt);\n
return false;\n
};\n
target.addEventListener(type, handle_event_callback, useCapture);\n
}\n
return new RSVP.Promise(resolver, canceller);\n
};\n
window.promiseReadAsText = function(file) {\n
return new RSVP.Promise(function(resolve, reject) {\n
var reader = new FileReader();\n
reader.onload = function(evt) {\n
resolve(evt.target.result);\n
};\n
reader.onerror = function(evt) {\n
reject(evt);\n
};\n
reader.readAsText(file);\n
});\n
};\n
})(window, RSVP, FileReader);
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>3072</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Folder" module="OFS.Folder"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>fieldset</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts31677468.99</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>fieldset.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
/*global rJS, RSVP, jQuery, Handlebars,\n
promiseEventListener */\n
/*jslint nomen: true */\n
(function(window, rJS, RSVP, Handlebars) {\n
"use strict";\n
/////////////////////////////////////////////////////////////////\n
// Handlebars\n
/////////////////////////////////////////////////////////////////\n
// Precompile the templates while loading the first gadget instance\n
var gadget_klass = rJS(window),\n
source = gadget_klass.__template_element.getElementById("label-template").innerHTML,\n
label_template = Handlebars.compile(source);\n
\n
gadget_klass.ready(function (g) {\n
g.props = {};\n
})\n
.ready(function (g) {\n
return g.getElement().push(function (element) {\n
g.props.element = element;\n
});\n
})\n
.declareMethod("render", function(options, node_id) {\n
// XXX node_id is added like a property so that one can change the node\n
// id\n
var gadget = this,\n
queue;\n
gadget.props.key = options.key;\n
// used for recursive fieldsets\n
gadget.props.field_gadget_list = [];\n
\n
function addField(property_id, property_definition, value) {\n
var sub_gadget;\n
//console.log("addField", property_id, property_definition, value);\n
queue.push(function() {\n
gadget.props.fieldset_element.insertAdjacentHTML("beforeend", label_template({\n
"for": property_id,\n
name: property_definition.name || property_definition.description || property_id\n
}));\n
\n
if (property_definition.type === "object") {\n
// Create a recursive fieldset for this key.\n
return gadget.declareGadget("../fieldset/index.html");\n
}\n
if (property_definition.type === "number") {\n
return gadget.declareGadget("../number_field/index.html");\n
}\n
if (property_definition[\'enum\']) {\n
return gadget.declareGadget("../list_field/index.html");\n
}\n
return gadget.declareGadget("../string_field/index.html");\n
}).push(function(gg) {\n
sub_gadget = gg;\n
return sub_gadget.render({\n
key: property_id,\n
value: value,\n
property_definition: property_definition\n
});\n
}).push(function() {\n
return sub_gadget.getElement();\n
}).push(function(sub_element) {\n
gadget.props.fieldset_element.appendChild(sub_element);\n
gadget.props.field_gadget_list.push(sub_gadget);\n
});\n
}\n
queue = new RSVP.Queue().push(function() {\n
//gadget.props.fieldset_element = document.createElement("fieldset");\n
//gadget.props.element.appendChild(gadget.props.fieldset_element);\n
gadget.props.fieldset_element = gadget.props.element;\n
if (gadget.props.key) {\n
// style only recursive fieldsets\n
gadget.props.fieldset_element.style["border-width"] = "1px";\n
}\n
if (node_id) {\n
addField("id", {\n
type: "string"\n
}, node_id);\n
}\n
Object.keys(options.property_definition.properties).forEach(function(property_name) {\n
var property_definition = options.property_definition.properties[property_name],\n
value = (options.value || {})[property_name] === undefined ? property_definition[\'default\'] : options.value[property_name];\n
// XXX some properties are not editable\n
// XXX should not be defined here\n
if (property_name !== "coordinate" && property_name !== "_class" && property_name !== "id") {\n
addField(property_name, property_definition, value);\n
}\n
});\n
});\n
return queue;\n
}).declareMethod("startService", function() { // TODO: maybe we can remove this now\n
var i, gadget = this,\n
promise_list = [];\n
for (i = 0; i < gadget.props.field_gadget_list.length; i += 1) {\n
if (gadget.props.field_gadget_list[i].startService) {\n
promise_list.push(gadget.props.field_gadget_list[i].startService());\n
}\n
}\n
return RSVP.all(promise_list);\n
}).declareMethod("getContent", function() {\n
var i, promise_list = [],\n
gadget = this;\n
for (i = 0; i < this.props.field_gadget_list.length; i += 1) {\n
promise_list.push(this.props.field_gadget_list[i].getContent());\n
}\n
return RSVP.Queue().push(function() {\n
return RSVP.all(promise_list);\n
}).push(function(result_list) {\n
var name, result = {},\n
content = result;\n
if (gadget.props.key) {\n
content = result[gadget.props.key] = {};\n
}\n
for (i = 0; i < result_list.length; i += 1) {\n
for (name in result_list[i]) {\n
if (result_list[i].hasOwnProperty(name)) {\n
content[name] = result_list[i][name];\n
}\n
}\n
}\n
return result;\n
});\n
});\n
})(window, rJS, RSVP, Handlebars);
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>4694</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts31677560.85</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>index.html</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>text/html</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
<!DOCTYPE html>\n
<html>\n
<head>\n
<meta charset="utf-8">\n
<meta name="viewport" content="width=device-width, initial-scale=1">\n
<title>Fieldset</title>\n
<!--\n
<script src="rsvp.js" type="text/javascript"></script>\n
<script src="renderjs.js" type="text/javascript"></script>\n
-->\n
<script src="../lib/handlebars.min.js" type="text/javascript"></script>\n
<script src="../lib/jquery.js" type="text/javascript"></script>\n
\n
<script id="label-template" type="text/x-handlebars-template">\n
<label for="{{for}}">{{name}}</label>\n
</script>\n
\n
<script src="fieldset.js" type="text/javascript"></script>\n
</head>\n
<body>\n
</body>\n
</html>\n
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>662</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Folder" module="OFS.Folder"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>jsplumb</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts31679155.69</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>index.html</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>text/html</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
<!doctype html>\n
<html>\n
<head>\n
<meta charset="utf-8">\n
<link rel="stylesheet" href="../lib/jquery-ui.css">\n
<link rel="stylesheet" href="jsplumb.css">\n
<!--\n
FIXME: renderjs fails if we include renderjs.js twice (this one has a different URL from ERP5\'s one)\n
<script src="renderjs.js" type="text/javascript"></script>\n
<script src="rsvp.js" type="text/javascript"></script>\n
-->\n
<script src="../lib/jquery.js" type="text/javascript"></script>\n
<script src="../lib/jquery-ui.js" type="text/javascript"></script>\n
<script src="../lib/jquery.jsplumb.js" type="text/javascript"></script>\n
<script src="../lib/handlebars.min.js" type="text/javascript"></script>\n
\n
<script src="../dream/mixin_promise.js" type="text/javascript"></script>\n
<script src="jsplumb.js" type="text/javascript"></script>\n
\n
<script id="node-template" type="text/x-handlebars-template">\n
<div class="window {{class}}"\n
id="{{element_id}}"\n
title="{{title}}">\n
{{name}}\n
<div class="ep"></div>\n
</div>\n
</script>\n
<script id="popup-edit-template" type="text/x-handlebars-template">\n
<div id="edit-popup" data-position-to="origin">\n
<div data-role="header" data-theme="a">\n
<h1 class="node_class">Edit properties</h1>\n
<!-- XXX add this for jquery mobile version.\n
<a href="#" data-rel="back" class="ui-btn ui-corner-all ui-shadow ui-btn-a ui-icon-delete ui-btn-icon-notext ui-btn-right">Close</a>\n
-->\n
</div>\n
<br/>\n
<form class="ui-content">\n
<fieldset></fieldset>\n
<input type="button" value="Delete" class="graph_editor_delete_button">\n
<input type="submit" value="Validate" class="graph_editor_validate_button">\n
</form>\n
</div>\n
</script>\n
</head>\n
<body>\n
<div class="graph_container"></div>\n
<div class="dummy_window"></div>\n
</body>\n
</html>\n
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>1927</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts31928725.88</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>jsplumb.css</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>text/css</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string>.graph_container {\n
position: relative;\n
font-size: 80%;\n
border: 1px solid #999;\n
\n
min-width: 400px;\n
min-height: 400px;\n
\n
overflow: hidden;\n
background-color: #eaedef;\n
text-align: center;\n
}\n
\n
.selected {\n
color: #bd0b0b!important\n
}\n
\n
.window,\n
.label {\n
background-color: #fff;\n
text-align: center;\n
z-index: 23;\n
cursor: pointer;\n
box-shadow: 2px 2px 19px #aaa;\n
-o-box-shadow: 2px 2px 19px #aaa;\n
-webkit-box-shadow: 2px 2px 19px #aaa;\n
-moz-box-shadow: 2px 2px 19px #aaa\n
}\n
path,\n
._jsPlumb_endpoint {\n
cursor: pointer\n
}\n
._jsPlumb_endpoint_drop_allowed {\n
border: 4px solid #123456;\n
box-shadow: 6px 6px 19px #444;\n
-o-box-shadow: 6px 6px 19px #444;\n
-webkit-box-shadow: 6px 6px 19px #444;\n
-moz-box-shadow: 6px 6px 19px #444\n
}\n
._jsPlumb_connector {\n
z-index: 18\n
}\n
._jsPlumb_endpoint {\n
z-index: 19\n
}\n
._jsPlumb_overlay {\n
z-index: 23\n
}\n
._jsPlumb_connector._jsPlumb_hover {\n
z-index: 21!important\n
}\n
._jsPlumb_endpoint._jsPlumb_hover {\n
z-index: 22!important\n
}\n
._jsPlumb_overlay {\n
border: 1px solid #346789;\n
opacity: .8;\n
filter: alpha(opacity=80);\n
background-color: #fff;\n
color: #000;\n
font-family: helvetica;\n
padding: .5em\n
}\n
.window,\n
.dummy_window {\n
border: 1px solid #d3d3d3;\n
width: 80px;\n
height: 80px;\n
box-sizing: border-box;\n
position: absolute;\n
color: #000;\n
font-family: serif;\n
font-style: italic;\n
padding-top: .9em;\n
font-size: .9em;\n
cursor: move;\n
font-size: 11px;\n
-webkit-transition: background-color .1s ease-in;\n
-moz-transition: background-color .1s ease-in;\n
transition: background-color .1s ease-in;\n
border-radius: 5px\n
}\n
.window:hover {\n
background-color: #5c96bc;\n
background-image: none;\n
color: #fff\n
}\n
.dummy_window {\n
position: absolute;\n
top: 0;\n
left: 0;\n
visibility: hidden\n
}\n
.ep {\n
position: absolute;\n
bottom: 37%;\n
right: 5px;\n
width: 1em;\n
height: 1em;\n
background-color: orange;\n
cursor: pointer;\n
box-shadow: 0 0 2px #000;\n
-webkit-transition: -webkit-box-shadow .25s ease-in;\n
-moz-transition: -moz-box-shadow .25s ease-in;\n
transition: box-shadow .25s ease-in\n
}\n
._jsPlumb_source_hover,\n
._jsPlumb_target_hover,\n
.dragHover {\n
background-color: #1e8151;\n
background-image: none;\n
color: #fff\n
}\n
path {\n
cursor: pointer\n
}</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>2379</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts31928462.63</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>jsplumb.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
/* ===========================================================================\n
* Copyright 2013-2015 Nexedi SA and Contributors\n
*\n
* This file is part of DREAM.\n
*\n
* DREAM is free software: you can redistribute it and/or modify\n
* it under the terms of the GNU Lesser General Public License as published by\n
* the Free Software Foundation, either version 3 of the License, or\n
* (at your option) any later version.\n
*\n
* DREAM is distributed in the hope that it will be useful,\n
* but WITHOUT ANY WARRANTY; without even the implied warranty of\n
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n
* GNU Lesser General Public License for more details.\n
*\n
* You should have received a copy of the GNU Lesser General Public License\n
* along with DREAM. If not, see <http://www.gnu.org/licenses/>.\n
* ==========================================================================*/\n
/*global console, window, RSVP, rJS, $, jsPlumb, Handlebars,\n
loopEventListener, promiseEventListener, DOMParser */\n
/*jslint unparam: true todo: true */\n
(function(RSVP, rJS, $, jsPlumb, Handlebars, loopEventListener, promiseEventListener, DOMParser) {\n
"use strict";\n
/* TODO:\n
* less dependancies ( promise event listner ? )\n
* no more handlebars\n
* auto springy layout\n
* id should not always be modifiable\n
* drop zoom level\n
* rename draggable()\n
* factorize node & edge popup edition\n
*/\n
/*jslint nomen: true */\n
var gadget_klass = rJS(window),\n
domParser = new DOMParser(),\n
node_template_source = gadget_klass.__template_element.getElementById("node-template").innerHTML,\n
node_template = Handlebars.compile(node_template_source),\n
popup_edit_template = gadget_klass.__template_element.getElementById("popup-edit-template").innerHTML;\n
\n
function loopJsplumbBind(gadget, type, callback) {\n
//////////////////////////\n
// Infinite event listener (promise is never resolved)\n
// eventListener is removed when promise is cancelled/rejected\n
//////////////////////////\n
var handle_event_callback, callback_promise, jsplumb_instance = gadget.props.jsplumb_instance;\n
\n
function cancelResolver() {\n
if (callback_promise !== undefined && typeof callback_promise.cancel === "function") {\n
callback_promise.cancel();\n
}\n
}\n
\n
function canceller() {\n
if (handle_event_callback !== undefined) {\n
jsplumb_instance.unbind(type);\n
}\n
cancelResolver();\n
}\n
\n
function resolver(resolve, reject) {\n
handle_event_callback = function() {\n
var args = arguments;\n
cancelResolver();\n
callback_promise = new RSVP.Queue().push(function() {\n
return callback.apply(jsplumb_instance, args);\n
}).push(undefined, function(error) {\n
if (!(error instanceof RSVP.CancellationError)) {\n
canceller();\n
reject(error);\n
}\n
});\n
};\n
jsplumb_instance.bind(type, handle_event_callback);\n
}\n
return new RSVP.Promise(resolver, canceller);\n
}\n
\n
function getNodeId(gadget, element_id) {\n
// returns the ID of the node in the graph from its DOM element id\n
var node_id;\n
$.each(gadget.props.node_id_to_dom_element_id, function(k, v) {\n
if (v === element_id) {\n
node_id = k;\n
return false;\n
}\n
});\n
return node_id;\n
}\n
\n
function generateNodeId(gadget, element) {\n
// Generate a node id\n
var n = 1,\n
class_def = gadget.props.data.class_definition[element._class],\n
id = class_def.short_id || element._class;\n
while (gadget.props.data.graph.node[id + n] !== undefined) {\n
n += 1;\n
}\n
return id + n;\n
}\n
\n
function generateDomElementId(gadget_element) {\n
// Generate a probably unique DOM element ID.\n
var n = 1;\n
while ($(gadget_element).find("#DreamNode_" + n).length > 0) {\n
n += 1;\n
}\n
return "DreamNode_" + n;\n
}\n
\n
function getDefaultEdgeClass(gadget) {\n
var class_definition = gadget.props.data.class_definition;\n
for (var key in class_definition) {\n
if (class_definition.hasOwnProperty(key) && class_definition[key]._class === \'edge\') {\n
return key;\n
}\n
}\n
return "Dream.Edge";\n
}\n
\n
function updateConnectionData(gadget, connection, remove) {\n
if (connection.ignoreEvent) {\n
// this hack is for edge edition. Maybe there I missed one thing and\n
// there is a better way.\n
return;\n
}\n
if (remove) {\n
delete gadget.props.data.graph.edge[connection.id];\n
} else {\n
var edge_data = gadget.props.data.graph.edge[connection.id] || {\n
_class: getDefaultEdgeClass(gadget)\n
};\n
edge_data.source = getNodeId(gadget, connection.sourceId);\n
edge_data.destination = getNodeId(gadget, connection.targetId);\n
gadget.props.data.graph.edge[connection.id] = edge_data;\n
}\n
gadget.notifyDataChanged();\n
}\n
\n
function convertToAbsolutePosition(gadget, x, y) {\n
var zoom_level = gadget.props.zoom_level,\n
canvas_size_x = $(gadget.props.main).width(),\n
canvas_size_y = $(gadget.props.main).height(),\n
size_x = $(gadget.props.element).find(".dummy_window").width() * zoom_level,\n
size_y = $(gadget.props.element).find(".dummy_window").height() * zoom_level,\n
top = Math.floor(y * (canvas_size_y - size_y)) + "px",\n
left = Math.floor(x * (canvas_size_x - size_x)) + "px";\n
return [left, top];\n
}\n
\n
function convertToRelativePosition(gadget, x, y) {\n
var zoom_level = gadget.props.zoom_level,\n
canvas_size_x = $(gadget.props.main).width(),\n
canvas_size_y = $(gadget.props.main).height(),\n
size_x = $(gadget.props.element).find(".dummy_window").width() * zoom_level,\n
size_y = $(gadget.props.element).find(".dummy_window").height() * zoom_level,\n
top = Math.max(Math.min(y.replace("px", "") / (canvas_size_y - size_y), 1), 0),\n
left = Math.max(Math.min(x.replace("px", "") / (canvas_size_x - size_x), 1), 0);\n
return [left, top];\n
}\n
\n
function updateElementCoordinate(gadget, node_id, coordinate) {\n
var element_id = gadget.props.node_id_to_dom_element_id[node_id],\n
element,\n
relative_position;\n
if (coordinate === undefined) {\n
element = $(gadget.props.element).find("#" + element_id);\n
relative_position = convertToRelativePosition(gadget, element.css("left"), element.css("top"));\n
coordinate = {\n
left: relative_position[0],\n
top: relative_position[1]\n
};\n
}\n
gadget.props.data.graph.node[node_id].coordinate = coordinate;\n
gadget.notifyDataChanged();\n
return coordinate;\n
}\n
\n
function draggable(gadget) {\n
var jsplumb_instance = gadget.props.jsplumb_instance,\n
stop = function(element) {\n
updateElementCoordinate(gadget, getNodeId(gadget, element.target.id));\n
};\n
\n
// XXX This function should only touch the node element that we just added.\n
jsplumb_instance.draggable(jsplumb_instance.getSelector(".window"), {\n
containment: "parent",\n
grid: [10, 10],\n
stop: stop\n
});\n
jsplumb_instance.makeSource(jsplumb_instance.getSelector(".window"), {\n
filter: ".ep",\n
anchor: "Continuous",\n
connector: ["StateMachine", {\n
curviness: 20\n
}],\n
connectorStyle: {\n
strokeStyle: "#5c96bc",\n
lineWidth: 2,\n
outlineColor: "transparent",\n
outlineWidth: 4\n
}\n
});\n
jsplumb_instance.makeTarget(jsplumb_instance.getSelector(".window"), {\n
dropOptions: {\n
hoverClass: "dragHover"\n
},\n
anchor: "Continuous"\n
});\n
}\n
\n
function updateNodeStyle(gadget, element_id) {\n
// Update node size according to the zoom level\n
// XXX does nothing for now\n
var zoom_level = gadget.props.zoom_level,\n
element = $(gadget.props.element).find("#" + element_id),\n
new_value;\n
$.each(gadget.props.style_attr_list, function(i, j) {\n
new_value = element.css(j).replace("px", "") * zoom_level + "px";\n
element.css(j, new_value);\n
});\n
}\n
// function positionGraph(gadget) {\n
// $.ajax(\n
// \'/positionGraph\',\n
// {\n
// data: JSON.stringify(getData()),\n
// contentType: \'application/json\',\n
// type: \'POST\',\n
// success: function (data, textStatus, jqXHR) {\n
// $.each(data, function (node, pos) {\n
// convertToAbsolutePosition(\n
// gadget,\n
// pos.left,\n
// pos.top\n
// );\n
// updateElementCoordinate(gadget, node, {\n
// top: pos.top,\n
// left: pos.left\n
// });\n
// });\n
// redraw(gadget);\n
// }\n
// }\n
// );\n
// }\n
\n
function removeElement(gadget, node_id) {\n
var element_id = gadget.props.node_id_to_dom_element_id[node_id];\n
gadget.props.jsplumb_instance.removeAllEndpoints($(gadget.props.element).find("#" + element_id));\n
$(gadget.props.element).find("#" + element_id).remove();\n
delete gadget.props.data.graph.node[node_id];\n
delete gadget.props.node_id_to_dom_element_id[node_id];\n
$.each(gadget.props.data.graph.edge, function(k, v) {\n
if (node_id === v.source || node_id === v.destination) {\n
delete gadget.props.data.graph.edge[k];\n
}\n
});\n
gadget.notifyDataChanged();\n
}\n
\n
function updateElementData(gadget, node_id, data) {\n
var element_id = gadget.props.node_id_to_dom_element_id[node_id],\n
new_id = data.id || data.data.id;\n
$(gadget.props.element).find("#" + element_id).text(data.data.name || new_id)\n
.attr("title", data.data.name || new_id)\n
.append(\'<div class="ep"></div></div>\');\n
\n
delete data.id;\n
\n
$.extend(gadget.props.data.graph.node[node_id], data.data);\n
if (new_id && new_id !== node_id) {\n
gadget.props.data.graph.node[new_id] = gadget.props.data.graph.node[node_id];\n
delete gadget.props.data.graph.node[node_id];\n
\n
gadget.props.node_id_to_dom_element_id[new_id] = gadget.props.node_id_to_dom_element_id[node_id];\n
delete gadget.props.node_id_to_dom_element_id[node_id];\n
\n
delete gadget.props.data.graph.node[new_id].id;\n
$.each(gadget.props.data.graph.edge, function (k, v) {\n
if (v.source === node_id) {\n
v.source = new_id;\n
}\n
if (v.destination === node_id) {\n
v.destination = new_id;\n
}\n
});\n
}\n
gadget.notifyDataChanged();\n
}\n
\n
\n
function addEdge(gadget, edge_id, edge_data) {\n
var overlays = [],\n
connection;\n
if (edge_data.name) {\n
overlays = [\n
["Label", {\n
cssClass: "l1 component label",\n
label: edge_data.name\n
}]\n
];\n
}\n
if (gadget.props.data.graph.node[edge_data.source] === undefined) {\n
throw new Error("Edge Source " + edge_data.source + " does not exist");\n
}\n
if (gadget.props.data.graph.node[edge_data.source] === undefined) {\n
throw new Error("Edge Destination " + edge_data.source + " does not exist");\n
}\n
// If an edge has this data:\n
// { _class: \'Edge\',\n
// source: \'N1\',\n
// destination: \'N2\',\n
// jsplumb_source_endpoint: \'BottomCenter\',\n
// jsplumb_destination_endpoint: \'LeftMiddle\',\n
// jsplumb_connector: \'Flowchart\' }\n
// Then it is rendered using a flowchart connector. The difficulty is that\n
// jsplumb does not let you configure the connector type on the edge, but\n
// on the source endpoint. One solution seem to create all types of\n
// endpoints on nodes.\n
if (edge_data.jsplumb_connector === "Flowchart") {\n
connection = gadget.props.jsplumb_instance.connect({\n
uuids: [edge_data.source + ".flowChart" + edge_data.jsplumb_source_endpoint,\n
edge_data.destination + ".flowChart" + edge_data.jsplumb_destination_endpoint\n
],\n
overlays: overlays\n
});\n
} else {\n
connection = gadget.props.jsplumb_instance.connect({\n
source: gadget.props.node_id_to_dom_element_id[edge_data.source],\n
target: gadget.props.node_id_to_dom_element_id[edge_data.destination],\n
Connector: ["Bezier", {\n
curviness: 75\n
}],\n
overlays: overlays\n
});\n
}\n
// set data for \'connection\' event that will be called "later"\n
gadget.props.data.graph.edge[edge_id] = edge_data;\n
// jsplumb assigned an id, but we are controlling ids ourselves.\n
connection.id = edge_id;\n
}\n
\n
function expandSchema(class_definition, full_schema) {\n
// minimal expanding of json schema, supports merging allOf and $ref\n
// references\n
// XXX this should probably be moved to fieldset ( and not handle\n
// class_definition here)\n
\n
function resolveReference(ref, schema) {\n
// 2 here is for #/\n
var i, ref_path = ref.substr(2, ref.length),\n
parts = ref_path.split("/");\n
for (i = 0; i < parts.length; i += 1) {\n
schema = schema[parts[i]];\n
}\n
return schema;\n
}\n
\n
function clone(obj) {\n
return JSON.parse(JSON.stringify(obj));\n
}\n
\n
var referenced,\n
i,\n
property,\n
expanded_class_definition = clone(class_definition) || {};\n
\n
\n
if (!expanded_class_definition.properties) {\n
expanded_class_definition.properties = {};\n
}\n
// expand direct ref\n
if (class_definition.$ref) {\n
referenced = expandSchema(resolveReference(class_definition.$ref, full_schema.class_definition), full_schema);\n
$.extend(expanded_class_definition, referenced);\n
delete expanded_class_definition.$ref;\n
}\n
// expand ref in properties\n
for (property in class_definition.properties) {\n
if (class_definition.properties.hasOwnProperty(property)) {\n
if (class_definition.properties[property].$ref) {\n
referenced = expandSchema(resolveReference(class_definition.properties[property].$ref, full_schema.class_definition), full_schema);\n
$.extend(expanded_class_definition.properties[property], referenced);\n
delete expanded_class_definition.properties[property].$ref;\n
} else {\n
if (class_definition.properties[property].type === "object") {\n
// no reference, but we expand anyway because we need to recurse in case there is a ref in an object property\n
referenced = expandSchema(class_definition.properties[property], full_schema);\n
$.extend(expanded_class_definition.properties[property], referenced);\n
}\n
}\n
}\n
}\n
if (class_definition.oneOf) {\n
expanded_class_definition.oneOf = [];\n
for (i = 0; i < class_definition.oneOf.length; i += 1) {\n
expanded_class_definition.oneOf.push(expandSchema(class_definition.oneOf[i], full_schema));\n
}\n
}\n
if (class_definition.allOf) {\n
for (i = 0; i < class_definition.allOf.length; i += 1) {\n
referenced = expandSchema(class_definition.allOf[i], full_schema);\n
if (referenced.properties) {\n
$.extend(expanded_class_definition.properties, referenced.properties);\n
delete referenced.properties;\n
}\n
$.extend(expanded_class_definition, referenced);\n
}\n
if (expanded_class_definition.allOf) {\n
delete expanded_class_definition.allOf;\n
}\n
}\n
if (expanded_class_definition.$ref) {\n
delete expanded_class_definition.$ref;\n
}\n
return clone(expanded_class_definition);\n
}\n
\n
function openEdgeEditionDialog(gadget, connection) {\n
var edge_id = connection.id,\n
edge_data = gadget.props.data.graph.edge[edge_id],\n
edit_popup = $(gadget.props.element).find("#popup-edit-template"),\n
schema,\n
fieldset_element,\n
delete_promise;\n
schema = expandSchema(gadget.props.data.class_definition[edge_data._class], gadget.props.data);\n
// We do not edit source & destination on edge this way.\n
delete schema.properties.source;\n
delete schema.properties.destination;\n
gadget.props.element.insertAdjacentHTML("beforeend", popup_edit_template);\n
edit_popup = $(gadget.props.element).find("#edit-popup");\n
edit_popup.find(".node_class").text(connection.name || connection._class);\n
fieldset_element = edit_popup.find("fieldset")[0];\n
edit_popup.dialog();\n
edit_popup.show();\n
\n
function save_promise(fieldset_gadget, edge_id) {\n
return RSVP.Queue().push(function() {\n
return promiseEventListener(edit_popup.find(".graph_editor_validate_button")[0], "click", false);\n
}).push(function(evt) {\n
var data = {\n
id: $(evt.target[1]).val(),\n
data: {}\n
};\n
return fieldset_gadget.getContent().then(function(r) {\n
$.extend(data.data, gadget.props.data.graph.edge[connection.id]);\n
$.extend(data.data, r);\n
// to redraw, we remove the edge and add again.\n
// but we want to disable events on connection, since event\n
// handling promise are executed asynchronously in undefined order,\n
// we cannot just remove and /then/ add, because the new edge is\n
// added before the old is removed.\n
connection.ignoreEvent = true;\n
gadget.props.jsplumb_instance.detach(connection);\n
addEdge(gadget, r.id, data.data);\n
});\n
});\n
}\n
delete_promise = new RSVP.Queue().push(function() {\n
return promiseEventListener(edit_popup.find(".graph_editor_delete_button")[0], "click", false);\n
}).push(function() {\n
// connectionDetached event will remove the edge from data\n
gadget.props.jsplumb_instance.detach(connection);\n
});\n
return gadget.declareGadget("../fieldset/index.html", {\n
element: fieldset_element,\n
scope: "fieldset"\n
}).push(function(fieldset_gadget) {\n
return RSVP.all([fieldset_gadget, fieldset_gadget.render({\n
value: edge_data,\n
property_definition: schema\n
}, edge_id)]);\n
}).push(function(fieldset_gadget) {\n
edit_popup.dialog("open");\n
return fieldset_gadget[0];\n
}).push(function(fieldset_gadget) {\n
fieldset_gadget.startService(); // XXX\n
return fieldset_gadget;\n
}).push(function(fieldset_gadget) {\n
// Expose the dialog handling promise so that we can wait for it in\n
// test.\n
gadget.props.dialog_promise = RSVP.any([save_promise(fieldset_gadget, edge_id), delete_promise]);\n
return gadget.props.dialog_promise;\n
}).push(function() {\n
edit_popup.dialog("close");\n
edit_popup.remove();\n
delete gadget.props.dialog_promise;\n
});\n
}\n
\n
function openNodeEditionDialog(gadget, element) {\n
var node_id = getNodeId(gadget, element.id),\n
node_data = gadget.props.data.graph.node[node_id],\n
node_edit_popup = $(gadget.props.element).find("#popup-edit-template"),\n
schema,\n
fieldset_element,\n
delete_promise;\n
// If we have no definition for this, we do not allow edition.\n
// XXX incorrect, we need to display this dialog to be able\n
// to delete a node\n
if (gadget.props.data.class_definition[node_data._class] === undefined) {\n
return;\n
}\n
schema = expandSchema(gadget.props.data.class_definition[node_data._class], gadget.props.data);\n
if (node_edit_popup.length !== 0) {\n
node_edit_popup.remove();\n
}\n
gadget.props.element.insertAdjacentHTML("beforeend", popup_edit_template);\n
node_edit_popup = $(gadget.props.element).find("#edit-popup");\n
// Set the name of the popup to the node class\n
node_edit_popup.find(".node_class").text(node_data.name || node_data._class);\n
fieldset_element = node_edit_popup.find("fieldset")[0];\n
node_edit_popup.dialog();\n
node_data.id = node_id;\n
\n
function save_promise(fieldset_gadget, node_id) {\n
return RSVP.Queue().push(function() {\n
return promiseEventListener(node_edit_popup.find(".graph_editor_validate_button")[0], "click", false);\n
}).push(function(evt) {\n
var data = {\n
// XXX id should not be handled differently ...\n
id: $(evt.target[1]).val(),\n
data: {}\n
};\n
return fieldset_gadget.getContent().then(function(r) {\n
$.extend(data.data, r);\n
updateElementData(gadget, node_id, data);\n
});\n
});\n
}\n
delete_promise = new RSVP.Queue().push(function() {\n
return promiseEventListener(node_edit_popup.find(".graph_editor_delete_button")[0], "click", false);\n
}).push(function() {\n
return removeElement(gadget, node_id);\n
});\n
return gadget.declareGadget("../fieldset/index.html", {\n
element: fieldset_element,\n
scope: "fieldset"\n
}).push(function(fieldset_gadget) {\n
return RSVP.all([fieldset_gadget, fieldset_gadget.render({\n
value: node_data,\n
property_definition: schema\n
}, node_id)]);\n
}).push(function(fieldset_gadget) {\n
node_edit_popup.dialog("open");\n
return fieldset_gadget[0];\n
}).push(function(fieldset_gadget) {\n
fieldset_gadget.startService(); // XXX this should not be needed anymore.\n
return fieldset_gadget;\n
}).push(function(fieldset_gadget) {\n
// Expose the dialog handling promise so that we can wait for it in\n
// test.\n
gadget.props.dialog_promise = RSVP.any([save_promise(fieldset_gadget, node_id), delete_promise]);\n
return gadget.props.dialog_promise;\n
}).push(function() {\n
node_edit_popup.dialog("close");\n
node_edit_popup.remove();\n
delete gadget.props.dialog_promise;\n
});\n
}\n
\n
function waitForNodeClick(gadget, node) {\n
gadget.props.nodes_click_monitor.monitor(loopEventListener(node, "dblclick", false, openNodeEditionDialog.bind(null, gadget, node)));\n
}\n
\n
function waitForConnection(gadget) {\n
return loopJsplumbBind(gadget, "connection", function(info, originalEvent) {\n
updateConnectionData(gadget, info.connection, false);\n
});\n
}\n
\n
function waitForConnectionDetached(gadget) {\n
return loopJsplumbBind(gadget, "connectionDetached", function(info, originalEvent) {\n
updateConnectionData(gadget, info.connection, true);\n
});\n
}\n
\n
function waitForConnectionClick(gadget) {\n
return loopJsplumbBind(gadget, "click", function(connection) {\n
return openEdgeEditionDialog(gadget, connection);\n
});\n
}\n
\n
function addNode(gadget, node_id, node_data) {\n
var render_element = $(gadget.props.main),\n
class_definition = gadget.props.data.class_definition[node_data._class],\n
coordinate = node_data.coordinate,\n
dom_element_id,\n
box,\n
absolute_position,\n
domElement;\n
\n
dom_element_id = generateDomElementId(gadget.props.element);\n
gadget.props.node_id_to_dom_element_id[node_id] = dom_element_id;\n
node_data.name = node_data.name || class_definition.name;\n
gadget.props.data.graph.node[node_id] = node_data;\n
if (coordinate === undefined) {\n
coordinate = {\n
top: 0,\n
left: 0\n
};\n
}\n
node_data.coordinate = updateElementCoordinate(gadget, node_id, coordinate);\n
/*jslint nomen: true*/\n
domElement = domParser.parseFromString(node_template({\n
"class": node_data._class.replace(".", "-"),\n
element_id: dom_element_id,\n
title: node_data.name || node_data.id,\n
name: node_data.name || node_data.id\n
}), "text/html").querySelector(".window");\n
render_element.append(domElement);\n
waitForNodeClick(gadget, domElement);\n
box = $(gadget.props.element).find("#" + dom_element_id);\n
absolute_position = convertToAbsolutePosition(gadget, coordinate.left, coordinate.top);\n
if (class_definition && class_definition.css) {\n
box.css(class_definition.css);\n
}\n
box.css("top", absolute_position[1]);\n
box.css("left", absolute_position[0]);\n
updateNodeStyle(gadget, dom_element_id);\n
draggable(gadget);\n
// XXX make only this element draggable.\n
// Add some flowchart endpoints\n
// TODO: add them all !\n
gadget.props.jsplumb_instance.addEndpoint(dom_element_id, {\n
isSource: true,\n
maxConnections: -1,\n
connector: ["Flowchart", {\n
stub: [40, 60],\n
gap: 10,\n
cornerRadius: 5,\n
alwaysRespectStubs: true\n
}]\n
}, {\n
anchor: "BottomCenter",\n
uuid: node_id + ".flowchartBottomCenter"\n
});\n
gadget.props.jsplumb_instance.addEndpoint(dom_element_id, {\n
isTarget: true,\n
maxConnections: -1\n
}, {\n
anchor: "LeftMiddle",\n
uuid: node_id + ".flowChartLeftMiddle"\n
});\n
gadget.notifyDataChanged();\n
}\n
\n
function waitForDrop(gadget) {\n
var callback;\n
\n
function canceller() {\n
if (callback !== undefined) {\n
gadget.props.main.removeEventListener("drop", callback, false);\n
}\n
}\n
/*jslint unparam: true*/\n
function resolver(resolve, reject) {\n
callback = function(evt) {\n
try {\n
var class_name, offset = $(gadget.props.main).offset(),\n
relative_position = convertToRelativePosition(gadget, evt.clientX - offset.left + "px", evt.clientY - offset.top + "px");\n
try {\n
// html5 compliant browser\n
class_name = JSON.parse(evt.dataTransfer.getData("application/json"));\n
} catch (e) {\n
// internet explorer\n
class_name = JSON.parse(evt.dataTransfer.getData("text"));\n
}\n
addNode(gadget, generateNodeId(gadget, {\n
_class: class_name\n
}), {\n
coordinate: {\n
left: relative_position[0],\n
top: relative_position[1]\n
},\n
_class: class_name\n
});\n
} catch (e) {\n
reject(e);\n
}\n
};\n
gadget.props.main.addEventListener("drop", callback, false);\n
}\n
return new RSVP.all([ // loopEventListener adds an event listener that will prevent default for\n
// dragover\n
loopEventListener(gadget.props.main, "dragover", false, function() {\n
return undefined;\n
}), RSVP.Promise(resolver, canceller)\n
]);\n
}\n
\n
gadget_klass.ready(function (g) {\n
g.props = {};\n
})\n
.ready(function (g) {\n
return g.getElement().push(function (element) {\n
g.props.element = element;\n
});\n
})\n
.ready(function(g) {\n
g.props.node_id_to_dom_element_id = {};\n
g.props.zoom_level = 1;\n
g.props.style_attr_list = ["width", "height", "padding-top", "line-height"];\n
g.getElement().then(function(element) {\n
g.props.element = element;\n
});\n
})\n
.declareAcquiredMethod("notifyDataChanged", "notifyDataChanged")\n
.declareMethod("render", function(data) {\n
var gadget = this, jsplumb_instance;\n
\n
this.props.data = {};\n
if (data.key) {\n
// Gadget embedded in ERP5\n
this.props.erp5_key = data.key;\n
data = data.value;\n
}\n
\n
this.props.main = this.props.element.querySelector(".graph_container");\n
/*\n
$(this.props.main).resizable({\n
resize : function(event, ui) {\n
jsplumb_instance.repaint(ui.helper);\n
}\n
});\n
*/\n
if (data) {\n
this.props.data = JSON.parse(data);\n
// load the data\n
$.each(this.props.data.graph.node, function(key, value) {\n
addNode(gadget, key, value);\n
});\n
$.each(this.props.data.graph.edge, function(key, value) {\n
addEdge(gadget, key, value);\n
});\n
}\n
})\n
.declareMethod("getContent", function() {\n
var ret = {};\n
if (this.props.erp5_key) {\n
// ERP5\n
ret[this.props.erp5_key] = JSON.stringify(this.props.data);\n
return ret;\n
}\n
return JSON.stringify(this.props.data);\n
})\n
.declareService(function() {\n
var gadget = this, jsplumb_instance;\n
this.props.main = this.props.element.querySelector(".graph_container");\n
this.props.jsplumb_instance = jsplumb_instance = jsPlumb.getInstance();\n
if (this.props.data) {\n
// load the data\n
$.each(this.props.data.graph.node, function(key, value) {\n
addNode(gadget, key, value);\n
});\n
$.each(this.props.data.graph.edge, function(key, value) {\n
addEdge(gadget, key, value);\n
});\n
}\n
jsplumb_instance.setRenderMode(jsplumb_instance.SVG);\n
jsplumb_instance.importDefaults({\n
HoverPaintStyle: {\n
strokeStyle: "#1e8151",\n
lineWidth: 2\n
},\n
Endpoint: ["Dot", {\n
radius: 2\n
}],\n
ConnectionOverlays: [\n
["Arrow", {\n
location: 1,\n
id: "arrow",\n
length: 14,\n
foldback: 0.8\n
}]\n
],\n
Container: this.props.main\n
});\n
draggable(gadget);\n
\n
this.props.nodes_click_monitor = RSVP.Monitor();\n
return RSVP.all([waitForDrop(gadget),\n
waitForConnection(gadget),\n
waitForConnectionDetached(gadget),\n
waitForConnectionClick(gadget),\n
gadget.props.nodes_click_monitor\n
]);\n
});\n
\n
})(RSVP, rJS, $, jsPlumb, Handlebars, loopEventListener, promiseEventListener, DOMParser);
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>29366</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts31664812.47</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>test.html</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>text/html</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
<!doctype html>\n
<html>\n
<head>\n
<meta charset="utf-8">\n
<link rel="stylesheet" href="../lib/qunit.css">\n
\n
<script src="rsvp.js" type="text/javascript"></script>\n
<script src="renderjs.js" type="text/javascript"></script>\n
\n
<script src="../lib/qunit.js"></script>\n
<script src="../lib/jquery.js"></script>\n
<script src="../lib/jquery.simulate.js"></script>\n
<script src="test.js"></script>\n
</head>\n
\n
<body>\n
<div id="qunit"></div>\n
<div id="qunit-fixture"></div>\n
</body>\n
</html>\n
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>514</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts31928229.99</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>test.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
/*global window, document, rJS, JSON, QUnit, jQuery, RSVP, console, setTimeout\n
\n
*/\n
(function(rJS, JSON, QUnit, RSVP, $) {\n
"use strict";\n
var start = QUnit.start,\n
stop = QUnit.stop,\n
test = QUnit.test,\n
equal = QUnit.equal,\n
ok = QUnit.ok,\n
error_handler = function(e) {\n
window.console.error(e);\n
ok(false, e);\n
},\n
sample_class_definition = {\n
edge: {\n
description: "Base definition for edge",\n
properties: {\n
_class: {\n
type: "string"\n
},\n
destination: {\n
type: "string"\n
},\n
name: {\n
type: "string"\n
},\n
required: [ "name", "_class", "source", "destination" ],\n
source: {\n
type: "string"\n
}\n
},\n
type: "object"\n
},\n
"Example.Edge": {\n
_class: "edge",\n
allOf: [ {\n
$ref: "#/edge"\n
}, {\n
properties: {\n
color: {\n
"enum": [ "red", "green", "blue" ]\n
}\n
}\n
} ],\n
description: "An example edge with a color property"\n
},\n
"Example.Node": {\n
_class: "node",\n
allOf: [ {\n
$ref: "#/node"\n
}, {\n
properties: {\n
shape: {\n
type: "string"\n
}\n
}\n
} ],\n
description: "An example node with a shape property"\n
},\n
node: {\n
description: "Base definition for node",\n
properties: {\n
_class: {\n
type: "string"\n
},\n
coordinate: {\n
properties: {\n
left: "number",\n
top: "number"\n
},\n
type: "object"\n
},\n
name: {\n
type: "string"\n
},\n
required: [ "name", "_class" ]\n
},\n
type: "object"\n
}\n
}, sample_graph = {\n
edge: {\n
edge1: {\n
_class: "Example.Edge",\n
source: "N1",\n
destination: "N2",\n
color: "blue"\n
}\n
},\n
node: {\n
N1: {\n
_class: "Example.Node",\n
name: "Node 1",\n
coordinate: {\n
top: 0,\n
left: 0\n
},\n
shape: "square"\n
},\n
N2: {\n
_class: "Example.Node",\n
name: "Node 2",\n
shape: "circle",\n
coordinate: {\n
top: 0.3,\n
left: 0.4\n
}\n
}\n
}\n
}, sample_graph_not_connected = {\n
edge: {},\n
node: {\n
N1: {\n
_class: "Example.Node",\n
name: "Node 1",\n
shape: "square"\n
},\n
N2: {\n
_class: "Example.Node",\n
name: "Node 2",\n
shape: "circle"\n
}\n
}\n
}, sample_data_graph = JSON.stringify({\n
class_definition: sample_class_definition,\n
graph: sample_graph\n
}), sample_data_graph_not_connected = JSON.stringify({\n
class_definition: sample_class_definition,\n
graph: sample_graph_not_connected\n
}), sample_data_empty_graph = JSON.stringify({\n
class_definition: sample_class_definition,\n
graph: {\n
node: {},\n
edge: {}\n
}\n
});\n
QUnit.config.testTimeout = 60000;\n
rJS(window).ready(function(g) {\n
test("Sample graph can be loaded and output is equal to input", function() {\n
var jsplumb_gadget;\n
stop();\n
g.declareGadget("./index.html", {\n
element: document.querySelector("#qunit-fixture")\n
}).then(function(new_gadget) {\n
jsplumb_gadget = new_gadget;\n
return jsplumb_gadget.render(sample_data_graph);\n
}).then(function() {\n
return jsplumb_gadget.getContent();\n
}).then(function(content) {\n
equal(content, sample_data_graph);\n
}).fail(error_handler).always(start);\n
});\n
test("New node can be drag & dropped", function() {\n
var jsplumb_gadget;\n
stop();\n
function runTest() {\n
// XXX here I used getContent to have a promise, but there must be a\n
// more elegant way.\n
return jsplumb_gadget.getContent().then(function() {\n
// fake a drop event\n
var e = new window.Event("drop");\n
e.dataTransfer = {\n
getData: function(type) {\n
// make sure we are called properly\n
equal("application/json", type, "The drag&dropped element must have data type application/json");\n
return JSON.stringify("Example.Node");\n
}\n
};\n
jsplumb_gadget.props.main.dispatchEvent(e);\n
}).then(function() {\n
return jsplumb_gadget.getContent();\n
}).then(function(content) {\n
var node, graph = JSON.parse(content).graph;\n
equal(1, Object.keys(graph.node).length, "There is one new node class");\n
node = graph.node[Object.keys(graph.node)[0]];\n
equal("Example.Node", node._class, "Node class is set to Example.?ode");\n
});\n
}\n
g.declareGadget("./index.html", {\n
element: document.querySelector("#qunit-fixture")\n
}).then(function(new_gadget) {\n
jsplumb_gadget = new_gadget;\n
jsplumb_gadget.render(sample_data_empty_graph);\n
}).then(runTest).fail(error_handler).always(start);\n
});\n
test("Node can be dragged", function() {\n
var jsplumb_gadget;\n
stop();\n
function runTest() {\n
return jsplumb_gadget.getContent().then(function() {\n
// 100 and 60 are about 10% of the .graph_container div ( set by css, so this\n
// might change )\n
$("div[title=\'Node 1\']").simulate("drag", {\n
dx: 100,\n
dy: 60\n
});\n
}).then(function() {\n
return jsplumb_gadget.getContent();\n
}).then(function(content) {\n
var graph = JSON.parse(content).graph, node_coordinate = graph.node.N1.coordinate;\n
// Since original coordinates where 0,0 we are now about 0.1,0.1\n
// as we moved 10%\n
ok(node_coordinate.top - .1 < .1, "Top is ok");\n
ok(node_coordinate.left - .1 < .1, "Left is ok");\n
});\n
}\n
g.declareGadget("./index.html", {\n
element: document.querySelector("#qunit-fixture")\n
}).then(function(new_gadget) {\n
jsplumb_gadget = new_gadget;\n
jsplumb_gadget.render(sample_data_graph);\n
}).then(runTest).fail(error_handler).always(start);\n
});\n
test("Node properties can be edited", function() {\n
var jsplumb_gadget;\n
stop();\n
function runTest() {\n
return jsplumb_gadget.getContent().then(function() {\n
// click on a node to see display the popup\n
$("div[title=\'Node 1\']").simulate("dblclick");\n
// Promises that handle the dialog actions are not available\n
// immediately after clicking.\n
var promise = RSVP.Promise(function(resolve) {\n
var fillDialog = function() {\n
if (!jsplumb_gadget.props.dialog_promise) {\n
// Dialog not ready. Let\'s retry later.\n
// XXX this condition is actually incorrect. We need to wait\n
// for the event listener to have been registered for the\n
// dialog buttons. This setTimeout is good enough for now.\n
return setTimeout(fillDialog, 1e3);\n
}\n
// check displayed values\n
equal($("input[name=\'id\']").val(), "N1");\n
equal($("input[name=\'name\']").val(), "Node 1");\n
equal($("input[name=\'shape\']").val(), "square");\n
// change the name\n
$("input[name=\'name\']").val("Modified Name");\n
equal(1, $("input[value=\'Validate\']").length, "There should be one validate button");\n
// and save\n
$("input[value=\'Validate\']").click();\n
// resolve our test promise once the dialog handling promise is\n
// finished.\n
jsplumb_gadget.props.dialog_promise.then(resolve);\n
};\n
fillDialog();\n
});\n
return promise.then(function() {\n
return jsplumb_gadget.getContent().then(function(content) {\n
var graph = JSON.parse(content).graph, node = graph.node.N1;\n
equal("Modified Name", node.name, "Data is modified");\n
equal("Modified Name", $("div#" + jsplumb_gadget.props.node_id_to_dom_element_id.N1).text(), "DOM is modified");\n
equal(1, $("div[title=\'Modified Name\']").length, "DOM title attribute is modified");\n
});\n
});\n
});\n
}\n
g.declareGadget("./index.html", {\n
element: document.querySelector("#qunit-fixture")\n
}).then(function(new_gadget) {\n
jsplumb_gadget = new_gadget;\n
jsplumb_gadget.render(sample_data_graph);\n
}).then(runTest).fail(error_handler).always(start);\n
});\n
test("Node can be connected", function() {\n
var jsplumb_gadget;\n
stop();\n
function runTest() {\n
return jsplumb_gadget.getContent().then(function(content) {\n
var node1 = jsplumb_gadget.props.main.querySelector("div[title=\'Node 1\']"), node2 = jsplumb_gadget.props.main.querySelector("div[title=\'Node 2\']");\n
equal(0, Object.keys(JSON.parse(content).graph.edge).length, "There are no edge at the beginning");\n
jsplumb_gadget.props.jsplumb_instance.connect({\n
source: node1.id,\n
target: node2.id\n
});\n
}).then(function() {\n
return jsplumb_gadget.getContent();\n
}).then(function(content) {\n
var edge, graph = JSON.parse(content).graph;\n
equal(2, Object.keys(graph.node).length, "We still have 2 nodes");\n
equal(1, Object.keys(graph.edge).length, "We have 1 edge");\n
edge = graph.edge[Object.keys(graph.edge)[0]];\n
// XXX how edge class would be set ? the first one from schema ? Yes ! TODO: update test\n
//equal("Example.Edge", edge._class, "Edge class is correct");\n
equal("N1", edge.source, "edge source is correct");\n
equal("N2", edge.destination, "edge destination is correct");\n
});\n
}\n
g.declareGadget("./index.html", {\n
element: document.querySelector("#qunit-fixture")\n
}).then(function(new_gadget) {\n
jsplumb_gadget = new_gadget;\n
jsplumb_gadget.render(sample_data_graph_not_connected);\n
}).then(runTest).fail(error_handler).always(start);\n
});\n
test("Node can be deleted", function() {\n
var jsplumb_gadget;\n
stop();\n
function runTest() {\n
return jsplumb_gadget.getContent().then(function() {\n
equal(1, $("div[title=\'Node 1\']").length, "node 1 is visible");\n
equal(1, $("._jsPlumb_connector").length, "there is 1 connection");\n
// click on node 1 to see display the popup\n
$("div[title=\'Node 1\']").simulate("dblclick");\n
// Promises that handle the dialog actions are not available\n
// immediately after clicking.\n
var promise = RSVP.Promise(function(resolve) {\n
var waitForDialogAndDelete = function() {\n
if (!jsplumb_gadget.props.dialog_promise) {\n
// Dialog not ready. Let\'s retry later.\n
// XXX this condition is actually incorrect. We need to wait\n
// for the event listener to have been registered for the\n
// dialog buttons. This setTimeout is good enough for now.\n
return setTimeout(waitForDialogAndDelete, 1e3);\n
}\n
equal(1, $("input[value=\'Delete\']").length, "There should be one delete button");\n
$("input[value=\'Delete\']").click();\n
// resolve our test promise once the dialog handling promise is\n
// finished.\n
jsplumb_gadget.props.dialog_promise.then(resolve);\n
};\n
waitForDialogAndDelete();\n
});\n
return promise.then(function() {\n
return jsplumb_gadget.getContent().then(function(content) {\n
var graph = JSON.parse(content).graph;\n
equal(1, Object.keys(graph.node).length, "node is removed from data");\n
equal(0, Object.keys(graph.edge).length, "edge referencing this node is also removed");\n
equal(0, $("div[title=\'Node 1\']").length, "DOM element for node is removed");\n
equal(0, $("._jsPlumb_connector").length, "DOM element for edge is removed");\n
});\n
});\n
});\n
}\n
g.declareGadget("./index.html", {\n
element: document.querySelector("#qunit-fixture")\n
}).then(function(new_gadget) {\n
jsplumb_gadget = new_gadget;\n
jsplumb_gadget.render(sample_data_graph);\n
}).then(runTest).fail(error_handler).always(start);\n
});\n
test("Node id can be changed (connections are updated and node can be edited afterwards)", function() {\n
var jsplumb_gadget;\n
stop();\n
function runTest() {\n
return jsplumb_gadget.getContent().then(function() {\n
// click on a node to see display the popup\n
$("div[title=\'Node 1\']").simulate("dblclick");\n
// Promises that handle the dialog actions are not available\n
// immediately after clicking.\n
var promise = RSVP.Promise(function(resolve) {\n
var fillDialog = function() {\n
if (!jsplumb_gadget.props.dialog_promise) {\n
// Dialog not ready. Let\'s retry later.\n
// XXX this condition is actually incorrect. We need to wait\n
// for the event listener to have been registered for the\n
// dialog buttons. This setTimeout is good enough for now.\n
return setTimeout(fillDialog, 1e3);\n
}\n
equal($("input[name=\'id\']").val(), "N1");\n
// change the id\n
$("input[name=\'id\']").val("N1b");\n
equal(1, $("input[value=\'Validate\']").length, "There should be one validate button");\n
$("input[value=\'Validate\']").click();\n
// resolve our test promise once the dialog handling promise is\n
// finished.\n
jsplumb_gadget.props.dialog_promise.then(resolve);\n
};\n
fillDialog();\n
});\n
return promise.then(function() {\n
return jsplumb_gadget.getContent().then(function(content) {\n
var graph = JSON.parse(content).graph;\n
equal(2, Object.keys(graph.node).length, "We still have two nodes");\n
ok(graph.node.N1b !== undefined, "Node Id changed");\n
equal(1, Object.keys(graph.edge).length, "We still have one connection");\n
equal("N1b", graph.edge.edge1.source, "Connection source has been updated");\n
});\n
});\n
});\n
}\n
g.declareGadget("./index.html", {\n
element: document.querySelector("#qunit-fixture")\n
}).then(function(new_gadget) {\n
jsplumb_gadget = new_gadget;\n
jsplumb_gadget.render(sample_data_graph);\n
}).then(runTest).fail(error_handler).always(start);\n
});\n
test("New node can be edited", function() {\n
var jsplumb_gadget, node_id;\n
stop();\n
function runTest() {\n
// XXX here I used getContent to have a promise, but there must be a\n
// more elegant way.\n
return jsplumb_gadget.getContent().then(function() {\n
// fake a drop event\n
var e = new window.Event("drop");\n
e.dataTransfer = {\n
getData: function(type) {\n
// make sure we are called properly\n
equal("application/json", type, "The drag&dropped element must have data type application/json");\n
return JSON.stringify("Example.Node");\n
}\n
};\n
jsplumb_gadget.props.main.dispatchEvent(e);\n
}).then(function() {\n
return jsplumb_gadget.getContent();\n
}).then(function(content) {\n
var node, graph = JSON.parse(content).graph;\n
equal(1, Object.keys(graph.node).length);\n
node_id = Object.keys(graph.node)[0];\n
node = graph.node[node_id];\n
equal("Example.Node", node._class);\n
}).then(function() {\n
// click the new node to see display the popup\n
// XXX at the moment nodes have class window\n
equal(1, $("div.window").length, "We have a new node");\n
$("div.window").simulate("dblclick");\n
// Promises that handle the dialog actions are not available\n
// immediately after clicking.\n
var promise = RSVP.Promise(function(resolve) {\n
var fillDialog = function() {\n
if (!jsplumb_gadget.props.dialog_promise) {\n
// Dialog not ready. Let\'s retry later.\n
// XXX this condition is actually incorrect. We need to wait\n
// for the event listener to have been registered for the\n
// dialog buttons. This setTimeout is good enough for now.\n
return setTimeout(fillDialog, 1e3);\n
}\n
// check displayed values\n
equal($("input[name=\'id\']").val(), node_id);\n
equal($("input[name=\'name\']").val(), "");\n
equal($("input[name=\'shape\']").val(), "");\n
// change the name\n
$("input[name=\'name\']").val("Modified Name");\n
equal(1, $("input[value=\'Validate\']").length, "There should be one validate button");\n
// and save\n
$("input[value=\'Validate\']").click();\n
// resolve our test promise once the dialog handling promise is\n
// finished.\n
jsplumb_gadget.props.dialog_promise.then(resolve);\n
};\n
fillDialog();\n
});\n
return promise.then(function() {\n
return jsplumb_gadget.getContent().then(function(content) {\n
var graph = JSON.parse(content).graph, node = graph.node[node_id];\n
equal("Modified Name", node.name, "Data is modified");\n
equal("Modified Name", $("div.window").text(), "DOM is modified");\n
});\n
});\n
});\n
}\n
g.declareGadget("./index.html", {\n
element: document.querySelector("#qunit-fixture")\n
}).then(function(new_gadget) {\n
jsplumb_gadget = new_gadget;\n
jsplumb_gadget.render(sample_data_empty_graph);\n
}).then(runTest).fail(error_handler).always(start);\n
});\n
test("New node can be deleted", function() {\n
var jsplumb_gadget, node_id;\n
stop();\n
function runTest() {\n
// XXX here I used getContent to have a promise, but there must be a\n
// more elegant way.\n
return jsplumb_gadget.getContent().then(function() {\n
// fake a drop event\n
var e = new window.Event("drop");\n
e.dataTransfer = {\n
getData: function(type) {\n
// make sure we are called properly\n
equal("application/json", type, "The drag&dropped element must have data type application/json");\n
return JSON.stringify("Example.Node");\n
}\n
};\n
jsplumb_gadget.props.main.dispatchEvent(e);\n
}).then(function() {\n
return jsplumb_gadget.getContent();\n
}).then(function(content) {\n
var node, graph = JSON.parse(content).graph;\n
equal(1, Object.keys(graph.node).length);\n
node_id = Object.keys(graph.node)[0];\n
node = graph.node[node_id];\n
equal("Example.Node", node._class);\n
}).then(function() {\n
// click the new node to see display the popup\n
// XXX at the moment nodes have class window\n
equal(1, $("div.window").length, "We have a new node");\n
$("div.window").simulate("dblclick");\n
// Promises that handle the dialog actions are not available\n
// immediately after clicking.\n
var promise = RSVP.Promise(function(resolve) {\n
var waitForDialogAndDelete = function() {\n
if (!jsplumb_gadget.props.dialog_promise) {\n
// Dialog not ready. Let\'s retry later.\n
// XXX this condition is actually incorrect. We need to wait\n
// for the event listener to have been registered for the\n
// dialog buttons. This setTimeout is good enough for now.\n
return setTimeout(waitForDialogAndDelete, 1e3);\n
}\n
equal(1, $("input[value=\'Delete\']").length, "There should be one delete button");\n
$("input[value=\'Delete\']").click();\n
// resolve our test promise once the dialog handling promise is\n
// finished.\n
jsplumb_gadget.props.dialog_promise.then(resolve);\n
};\n
waitForDialogAndDelete();\n
});\n
return promise.then(function() {\n
return jsplumb_gadget.getContent().then(function(content) {\n
var graph = JSON.parse(content).graph;\n
equal(0, Object.keys(graph.node).length, "node is removed from data");\n
equal(0, $("div.window").length, "DOM is modified");\n
});\n
});\n
});\n
}\n
g.declareGadget("./index.html", {\n
element: document.querySelector("#qunit-fixture")\n
}).then(function(new_gadget) {\n
jsplumb_gadget = new_gadget;\n
jsplumb_gadget.render(sample_data_empty_graph);\n
}).then(runTest).fail(error_handler).always(start);\n
});\n
});\n
})(rJS, JSON, QUnit, RSVP, jQuery);
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>26016</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Folder" module="OFS.Folder"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>lib</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570788.33</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>handlebars.min.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
/*!\n
\n
handlebars v2.0.0-alpha.4\n
\n
Copyright (C) 2011-2014 by Yehuda Katz\n
\n
Permission is hereby granted, free of charge, to any person obtaining a copy\n
of this software and associated documentation files (the "Software"), to deal\n
in the Software without restriction, including without limitation the rights\n
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell\n
copies of the Software, and to permit persons to whom the Software is\n
furnished to do so, subject to the following conditions:\n
\n
The above copyright notice and this permission notice shall be included in\n
all copies or substantial portions of the Software.\n
\n
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\n
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN\n
THE SOFTWARE.\n
\n
@license\n
*/\n
this.Handlebars=function(){var a=function(){"use strict";function a(a){this.string=a}var b;return a.prototype.toString=function(){return""+this.string},b=a}(),b=function(a){"use strict";function b(a){return i[a]||"&amp;"}function c(a){for(var b=1;b<arguments.length;b++)for(var c in arguments[b])Object.prototype.hasOwnProperty.call(arguments[b],c)&&(a[c]=arguments[b][c]);return a}function d(a){return a instanceof h?a.toString():a||0===a?(a=""+a,k.test(a)?a.replace(j,b):a):""}function e(a){return a||0===a?n(a)&&0===a.length?!0:!1:!0}function f(a,b){return(a?a+".":"")+b}var g={},h=a,i={"&":"&amp;","<":"&lt;",">":"&gt;",\'"\':"&quot;","\'":"&#x27;","`":"&#x60;"},j=/[&<>"\'`]/g,k=/[&<>"\'`]/;g.extend=c;var l=Object.prototype.toString;g.toString=l;var m=function(a){return"function"==typeof a};m(/x/)&&(m=function(a){return"function"==typeof a&&"[object Function]"===l.call(a)});var m;g.isFunction=m;var n=Array.isArray||function(a){return a&&"object"==typeof a?"[object Array]"===l.call(a):!1};return g.isArray=n,g.escapeExpression=d,g.isEmpty=e,g.appendContextPath=f,g}(a),c=function(){"use strict";function a(a,b){var d;b&&b.firstLine&&(d=b.firstLine,a+=" - "+d+":"+b.firstColumn);for(var e=Error.prototype.constructor.call(this,a),f=0;f<c.length;f++)this[c[f]]=e[c[f]];d&&(this.lineNumber=d,this.column=b.firstColumn)}var b,c=["description","fileName","lineNumber","message","name","number","stack"];return a.prototype=new Error,b=a}(),d=function(a,b){"use strict";function c(a,b){this.helpers=a||{},this.partials=b||{},d(this)}function d(a){a.registerHelper("helperMissing",function(){if(1===arguments.length)return void 0;throw new h("Missing helper: \'"+arguments[arguments.length-1].name+"\'")}),a.registerHelper("blockHelperMissing",function(b,c){var d=c.inverse||function(){},e=c.fn;if(m(b)&&(b=b.call(this)),b===!0)return e(this);if(b===!1||null==b)return d(this);if(l(b))return b.length>0?(c.ids&&(c.ids=[c.name]),a.helpers.each(b,c)):d(this);if(c.data&&c.ids){var f=q(c.data);f.contextPath=g.appendContextPath(c.data.contextPath,c.name),c={data:f}}return e(b,c)}),a.registerHelper("each",function(a,b){b||(b=a,a=this);var c,d,e=b.fn,f=b.inverse,h=0,i="";if(b.data&&b.ids&&(d=g.appendContextPath(b.data.contextPath,b.ids[0])+"."),m(a)&&(a=a.call(this)),b.data&&(c=q(b.data)),a&&"object"==typeof a)if(l(a))for(var j=a.length;j>h;h++)c&&(c.index=h,c.first=0===h,c.last=h===a.length-1,d&&(c.contextPath=d+h)),i+=e(a[h],{data:c});else for(var k in a)a.hasOwnProperty(k)&&(c&&(c.key=k,c.index=h,c.first=0===h,d&&(c.contextPath=d+k)),i+=e(a[k],{data:c}),h++);return 0===h&&(i=f(this)),i}),a.registerHelper("if",function(a,b){return m(a)&&(a=a.call(this)),!b.hash.includeZero&&!a||g.isEmpty(a)?b.inverse(this):b.fn(this)}),a.registerHelper("unless",function(b,c){return a.helpers["if"].call(this,b,{fn:c.inverse,inverse:c.fn,hash:c.hash})}),a.registerHelper("with",function(a,b){m(a)&&(a=a.call(this));var c=b.fn;if(!g.isEmpty(a)){if(b.data&&b.ids){var d=q(b.data);d.contextPath=g.appendContextPath(b.data.contextPath,b.ids[0]),b={data:d}}return c(a,b)}}),a.registerHelper("log",function(b,c){var d=c.data&&null!=c.data.level?parseInt(c.data.level,10):1;a.log(d,b)}),a.registerHelper("lookup",function(a,b){return a&&a[b]})}function e(a,b){p.log(a,b)}var f={},g=a,h=b,i="2.0.0-alpha.4";f.VERSION=i;var j=5;f.COMPILER_REVISION=j;var k={1:"<= 1.0.rc.2",2:"== 1.0.0-rc.3",3:"== 1.0.0-rc.4",4:"== 1.x.x",5:">= 2.0.0"};f.REVISION_CHANGES=k;var l=g.isArray,m=g.isFunction,n=g.toString,o="[object Object]";f.HandlebarsEnvironment=c,c.prototype={constructor:c,logger:p,log:e,registerHelper:function(a,b,c){if(n.call(a)===o){if(c||b)throw new h("Arg not supported with multiple helpers");g.extend(this.helpers,a)}else c&&(b.not=c),this.helpers[a]=b},unregisterHelper:function(a){delete this.helpers[a]},registerPartial:function(a,b){n.call(a)===o?g.extend(this.partials,a):this.partials[a]=b},unregisterPartial:function(a){delete this.partials[a]}};var p={methodMap:{0:"debug",1:"info",2:"warn",3:"error"},DEBUG:0,INFO:1,WARN:2,ERROR:3,level:3,log:function(a,b){if(p.level<=a){var c=p.methodMap[a];"undefined"!=typeof console&&console[c]&&console[c].call(console,b)}}};f.logger=p,f.log=e;var q=function(a){var b=g.extend({},a);return b._parent=a,b};return f.createFrame=q,f}(b,c),e=function(a,b,c){"use strict";function d(a){var b=a&&a[0]||1,c=n;if(b!==c){if(c>b){var d=o[c],e=o[b];throw new m("Template was precompiled with an older version of Handlebars than the current runtime. Please update your precompiler to a newer version ("+d+") or downgrade your runtime to an older version ("+e+").")}throw new m("Template was precompiled with a newer version of Handlebars than the current runtime. Please update your runtime to a newer version ("+a[1]+").")}}function e(a,b){if(!b)throw new m("No environment passed to template");b.VM.checkRevision(a.compiler);var c=function(a,c,d,e,f,g,h){e&&(d=l.extend({},d,e));var i=b.VM.invokePartial.call(this,a,c,d,f,g,h);if(null!=i)return i;if(b.compile){var j={helpers:f,partials:g,data:h};return g[c]=b.compile(a,{data:void 0!==h},b),g[c](d,j)}throw new m("The partial "+c+" could not be compiled when running in runtime-only mode")},d={escapeExpression:l.escapeExpression,invokePartial:c,fn:function(b){return a[b]},programs:[],program:function(a,b){var c=this.programs[a],d=this.fn(a);return b?c=g(this,a,d,b):c||(c=this.programs[a]=g(this,a,d)),c},programWithDepth:b.VM.programWithDepth,data:function(a,b){for(;a&&b--;)a=a._parent;return a},merge:function(a,b){var c=a||b;return a&&b&&a!==b&&(c=l.extend({},b,a)),c},noop:b.VM.noop,compilerInfo:a.compiler},e=function(b,c){c=c||{};var f=c.data;return e._setup(c),!c.partial&&a.useData&&(f=j(b,f)),a.main.call(d,b,d.helpers,d.partials,f)};return e._setup=function(c){c.partial?(d.helpers=c.helpers,d.partials=c.partials):(d.helpers=d.merge(c.helpers,b.helpers),a.usePartial&&(d.partials=d.merge(c.partials,b.partials)))},e._child=function(a){return d.programWithDepth(a)},e}function f(a,b){var c=Array.prototype.slice.call(arguments,2),d=this,e=d.fn(a),f=function(a,f){return f=f||{},e.apply(d,[a,d.helpers,d.partials,f.data||b].concat(c))};return f.program=a,f.depth=c.length,f}function g(a,b,c,d){var e=function(b,e){return e=e||{},c.call(a,b,a.helpers,a.partials,e.data||d)};return e.program=b,e.depth=0,e}function h(a,b,c,d,e,f){var g={partial:!0,helpers:d,partials:e,data:f};if(void 0===a)throw new m("The partial "+b+" could not be found");return a instanceof Function?a(c,g):void 0}function i(){return""}function j(a,b){return b&&"root"in b||(b=b?p(b):{},b.root=a),b}var k={},l=a,m=b,n=c.COMPILER_REVISION,o=c.REVISION_CHANGES,p=c.createFrame;return k.checkRevision=d,k.template=e,k.programWithDepth=f,k.program=g,k.invokePartial=h,k.noop=i,k}(b,c,d),f=function(a,b,c,d,e){"use strict";var f,g=a,h=b,i=c,j=d,k=e,l=function(){var a=new g.HandlebarsEnvironment;return j.extend(a,g),a.SafeString=h,a.Exception=i,a.Utils=j,a.VM=k,a.template=function(b){return k.template(b,a)},a},m=l();return m.create=l,f=m}(d,a,c,b,e),g=function(a){"use strict";function b(a){a=a||{},this.firstLine=a.first_line,this.firstColumn=a.first_column,this.lastColumn=a.last_column,this.lastLine=a.last_line}var c,d=a,e={ProgramNode:function(a,c,d,f){var g,h;3===arguments.length?(f=d,d=null):2===arguments.length&&(f=c,c=null),b.call(this,f),this.type="program",this.statements=a,this.strip={},d?(h=d[0],h?(g={first_line:h.firstLine,last_line:h.lastLine,last_column:h.lastColumn,first_column:h.firstColumn},this.inverse=new e.ProgramNode(d,c,g)):this.inverse=new e.ProgramNode(d,c),this.strip.right=c.left):c&&(this.strip.left=c.right)},MustacheNode:function(a,c,d,f,g){if(b.call(this,g),this.type="mustache",this.strip=f,null!=d&&d.charAt){var h=d.charAt(3)||d.charAt(2);this.escaped="{"!==h&&"&"!==h}else this.escaped=!!d;this.sexpr=a instanceof e.SexprNode?a:new e.SexprNode(a,c),this.sexpr.isRoot=!0,this.id=this.sexpr.id,this.params=this.sexpr.params,this.hash=this.sexpr.hash,this.eligibleHelper=this.sexpr.eligibleHelper,this.isHelper=this.sexpr.isHelper},SexprNode:function(a,c,d){b.call(this,d),this.type="sexpr",this.hash=c;var e=this.id=a[0],f=this.params=a.slice(1);this.isHelper=!(!f.length&&!c),this.eligibleHelper=this.isHelper||e.isSimple},PartialNode:function(a,c,d,e,f){b.call(this,f),this.type="partial",this.partialName=a,this.context=c,this.hash=d,this.strip=e},BlockNode:function(a,c,e,f,g){if(b.call(this,g),a.sexpr.id.original!==f.path.original)throw new d(a.sexpr.id.original+" doesn\'t match "+f.path.original,this);this.type="block",this.mustache=a,this.program=c,this.inverse=e,this.strip={left:a.strip.left,right:f.strip.right},(c||e).strip.left=a.strip.right,(e||c).strip.right=f.strip.left,e&&!c&&(this.isInverse=!0)},RawBlockNode:function(a,c,f,g){if(b.call(this,g),a.sexpr.id.original!==f)throw new d(a.sexpr.id.original+" doesn\'t match "+f,this);c=new e.ContentNode(c,g),this.type="block",this.mustache=a,this.program=new e.ProgramNode([c],g)},ContentNode:function(a,c){b.call(this,c),this.type="content",this.string=a},HashNode:function(a,c){b.call(this,c),this.type="hash",this.pairs=a},IdNode:function(a,c){b.call(this,c),this.type="ID";for(var e="",f=[],g=0,h="",i=0,j=a.length;j>i;i++){var k=a[i].part;if(e+=(a[i].separator||"")+k,".."===k||"."===k||"this"===k){if(f.length>0)throw new d("Invalid path: "+e,this);".."===k?(g++,h+="../"):this.isScoped=!0}else f.push(k)}this.original=e,this.parts=f,this.string=f.join("."),this.depth=g,this.idName=h+this.string,this.isSimple=1===a.length&&!this.isScoped&&0===g,this.stringModeValue=this.string},PartialNameNode:function(a,c){b.call(this,c),this.type="PARTIAL_NAME",this.name=a.original},DataNode:function(a,c){b.call(this,c),this.type="DATA",this.id=a,this.stringModeValue=a.stringModeValue,this.idName="@"+a.stringModeValue},StringNode:function(a,c){b.call(this,c),this.type="STRING",this.original=this.string=this.stringModeValue=a},NumberNode:function(a,c){b.call(this,c),this.type="NUMBER",this.original=this.number=a,this.stringModeValue=Number(a)},BooleanNode:function(a,c){b.call(this,c),this.type="BOOLEAN",this.bool=a,this.stringModeValue="true"===a},CommentNode:function(a,c){b.call(this,c),this.type="comment",this.comment=a}};return c=e}(c),h=function(){"use strict";var a,b=function(){function a(a,b){return{left:"~"===a.charAt(2),right:"~"===b.charAt(0)||"~"===b.charAt(1)}}function b(){this.yy={}}var c={trace:function(){},yy:{},symbols_:{error:2,root:3,statements:4,EOF:5,program:6,simpleInverse:7,statement:8,openRawBlock:9,CONTENT:10,END_RAW_BLOCK:11,openInverse:12,closeBlock:13,openBlock:14,mustache:15,partial:16,COMMENT:17,OPEN_RAW_BLOCK:18,sexpr:19,CLOSE_RAW_BLOCK:20,OPEN_BLOCK:21,CLOSE:22,OPEN_INVERSE:23,OPEN_ENDBLOCK:24,path:25,OPEN:26,OPEN_UNESCAPED:27,CLOSE_UNESCAPED:28,OPEN_PARTIAL:29,partialName:30,param:31,partial_option0:32,partial_option1:33,sexpr_repetition0:34,sexpr_option0:35,dataName:36,STRING:37,NUMBER:38,BOOLEAN:39,OPEN_SEXPR:40,CLOSE_SEXPR:41,hash:42,hash_repetition_plus0:43,hashSegment:44,ID:45,EQUALS:46,DATA:47,pathSegments:48,SEP:49,$accept:0,$end:1},terminals_:{2:"error",5:"EOF",10:"CONTENT",11:"END_RAW_BLOCK",17:"COMMENT",18:"OPEN_RAW_BLOCK",20:"CLOSE_RAW_BLOCK",21:"OPEN_BLOCK",22:"CLOSE",23:"OPEN_INVERSE",24:"OPEN_ENDBLOCK",26:"OPEN",27:"OPEN_UNESCAPED",28:"CLOSE_UNESCAPED",29:"OPEN_PARTIAL",37:"STRING",38:"NUMBER",39:"BOOLEAN",40:"OPEN_SEXPR",41:"CLOSE_SEXPR",45:"ID",46:"EQUALS",47:"DATA",49:"SEP"},productions_:[0,[3,2],[3,1],[6,2],[6,3],[6,2],[6,1],[6,1],[6,0],[4,1],[4,2],[8,3],[8,3],[8,3],[8,1],[8,1],[8,1],[8,1],[9,3],[14,3],[12,3],[13,3],[15,3],[15,3],[16,5],[16,4],[7,2],[19,3],[19,1],[31,1],[31,1],[31,1],[31,1],[31,1],[31,3],[42,1],[44,3],[30,1],[30,1],[30,1],[36,2],[25,1],[48,3],[48,1],[32,0],[32,1],[33,0],[33,1],[34,0],[34,2],[35,0],[35,1],[43,1],[43,2]],performAction:function(b,c,d,e,f,g){var h=g.length-1;switch(f){case 1:return new e.ProgramNode(g[h-1],this._$);case 2:return new e.ProgramNode([],this._$);case 3:this.$=new e.ProgramNode([],g[h-1],g[h],this._$);break;case 4:this.$=new e.ProgramNode(g[h-2],g[h-1],g[h],this._$);break;case 5:this.$=new e.ProgramNode(g[h-1],g[h],[],this._$);break;case 6:this.$=new e.ProgramNode(g[h],this._$);break;case 7:this.$=new e.ProgramNode([],this._$);break;case 8:this.$=new e.ProgramNode([],this._$);break;case 9:this.$=[g[h]];break;case 10:g[h-1].push(g[h]),this.$=g[h-1];break;case 11:this.$=new e.RawBlockNode(g[h-2],g[h-1],g[h],this._$);break;case 12:this.$=new e.BlockNode(g[h-2],g[h-1].inverse,g[h-1],g[h],this._$);break;case 13:this.$=new e.BlockNode(g[h-2],g[h-1],g[h-1].inverse,g[h],this._$);break;case 14:this.$=g[h];break;case 15:this.$=g[h];break;case 16:this.$=new e.ContentNode(g[h],this._$);break;case 17:this.$=new e.CommentNode(g[h],this._$);break;case 18:this.$=new e.MustacheNode(g[h-1],null,"","",this._$);break;case 19:this.$=new e.MustacheNode(g[h-1],null,g[h-2],a(g[h-2],g[h]),this._$);break;case 20:this.$=new e.MustacheNode(g[h-1],null,g[h-2],a(g[h-2],g[h]),this._$);break;case 21:this.$={path:g[h-1],strip:a(g[h-2],g[h])};break;case 22:this.$=new e.MustacheNode(g[h-1],null,g[h-2],a(g[h-2],g[h]),this._$);break;case 23:this.$=new e.MustacheNode(g[h-1],null,g[h-2],a(g[h-2],g[h]),this._$);break;case 24:this.$=new e.PartialNode(g[h-3],g[h-2],g[h-1],a(g[h-4],g[h]),this._$);break;case 25:this.$=new e.PartialNode(g[h-2],void 0,g[h-1],a(g[h-3],g[h]),this._$);break;case 26:this.$=a(g[h-1],g[h]);break;case 27:this.$=new e.SexprNode([g[h-2]].concat(g[h-1]),g[h],this._$);break;case 28:this.$=new e.SexprNode([g[h]],null,this._$);break;case 29:this.$=g[h];break;case 30:this.$=new e.StringNode(g[h],this._$);break;case 31:this.$=new e.NumberNode(g[h],this._$);break;case 32:this.$=new e.BooleanNode(g[h],this._$);break;case 33:this.$=g[h];break;case 34:g[h-1].isHelper=!0,this.$=g[h-1];break;case 35:this.$=new e.HashNode(g[h],this._$);break;case 36:this.$=[g[h-2],g[h]];break;case 37:this.$=new e.PartialNameNode(g[h],this._$);break;case 38:this.$=new e.PartialNameNode(new e.StringNode(g[h],this._$),this._$);break;case 39:this.$=new e.PartialNameNode(new e.NumberNode(g[h],this._$));break;case 40:this.$=new e.DataNode(g[h],this._$);break;case 41:this.$=new e.IdNode(g[h],this._$);break;case 42:g[h-2].push({part:g[h],separator:g[h-1]}),this.$=g[h-2];break;case 43:this.$=[{part:g[h]}];break;case 48:this.$=[];break;case 49:g[h-1].push(g[h]);break;case 52:this.$=[g[h]];break;case 53:g[h-1].push(g[h])}},table:[{3:1,4:2,5:[1,3],8:4,9:5,10:[1,10],12:6,14:7,15:8,16:9,17:[1,11],18:[1,12],21:[1,14],23:[1,13],26:[1,15],27:[1,16],29:[1,17]},{1:[3]},{5:[1,18],8:19,9:5,10:[1,10],12:6,14:7,15:8,16:9,17:[1,11],18:[1,12],21:[1,14],23:[1,13],26:[1,15],27:[1,16],29:[1,17]},{1:[2,2]},{5:[2,9],10:[2,9],17:[2,9],18:[2,9],21:[2,9],23:[2,9],24:[2,9],26:[2,9],27:[2,9],29:[2,9]},{10:[1,20]},{4:23,6:21,7:22,8:4,9:5,10:[1,10],12:6,14:7,15:8,16:9,17:[1,11],18:[1,12],21:[1,14],23:[1,24],24:[2,8],26:[1,15],27:[1,16],29:[1,17]},{4:23,6:25,7:22,8:4,9:5,10:[1,10],12:6,14:7,15:8,16:9,17:[1,11],18:[1,12],21:[1,14],23:[1,24],24:[2,8],26:[1,15],27:[1,16],29:[1,17]},{5:[2,14],10:[2,14],17:[2,14],18:[2,14],21:[2,14],23:[2,14],24:[2,14],26:[2,14],27:[2,14],29:[2,14]},{5:[2,15],10:[2,15],17:[2,15],18:[2,15],21:[2,15],23:[2,15],24:[2,15],26:[2,15],27:[2,15],29:[2,15]},{5:[2,16],10:[2,16],17:[2,16],18:[2,16],21:[2,16],23:[2,16],24:[2,16],26:[2,16],27:[2,16],29:[2,16]},{5:[2,17],10:[2,17],17:[2,17],18:[2,17],21:[2,17],23:[2,17],24:[2,17],26:[2,17],27:[2,17],29:[2,17]},{19:26,25:27,36:28,45:[1,31],47:[1,30],48:29},{19:32,25:27,36:28,45:[1,31],47:[1,30],48:29},{19:33,25:27,36:28,45:[1,31],47:[1,30],48:29},{19:34,25:27,36:28,45:[1,31],47:[1,30],48:29},{19:35,25:27,36:28,45:[1,31],47:[1,30],48:29},{25:37,30:36,37:[1,38],38:[1,39],45:[1,31],48:29},{1:[2,1]},{5:[2,10],10:[2,10],17:[2,10],18:[2,10],21:[2,10],23:[2,10],24:[2,10],26:[2,10],27:[2,10],29:[2,10]},{11:[1,40]},{13:41,24:[1,42]},{4:43,8:4,9:5,10:[1,10],12:6,14:7,15:8,16:9,17:[1,11],18:[1,12],21:[1,14],23:[1,13],24:[2,7],26:[1,15],27:[1,16],29:[1,17]},{7:44,8:19,9:5,10:[1,10],12:6,14:7,15:8,16:9,17:[1,11],18:[1,12],21:[1,14],23:[1,24],24:[2,6],26:[1,15],27:[1,16],29:[1,17]},{19:32,22:[1,45],25:27,36:28,45:[1,31],47:[1,30],48:29},{13:46,24:[1,42]},{20:[1,47]},{20:[2,48],22:[2,48],28:[2,48],34:48,37:[2,48],38:[2,48],39:[2,48],40:[2,48],41:[2,48],45:[2,48],47:[2,48]},{20:[2,28],22:[2,28],28:[2,28],41:[2,28]},{20:[2,41],22:[2,41],28:[2,41],37:[2,41],38:[2,41],39:[2,41],40:[2,41],41:[2,41],45:[2,41],47:[2,41],49:[1,49]},{25:50,45:[1,31],48:29},{20:[2,43],22:[2,43],28:[2,43],37:[2,43],38:[2,43],39:[2,43],40:[2,43],41:[2,43],45:[2,43],47:[2,43],49:[2,43]},{22:[1,51]},{22:[1,52]},{22:[1,53]},{28:[1,54]},{22:[2,46],25:57,31:55,33:56,36:61,37:[1,58],38:[1,59],39:[1,60],40:[1,62],42:63,43:64,44:66,45:[1,65],47:[1,30],48:29},{22:[2,37],37:[2,37],38:[2,37],39:[2,37],40:[2,37],45:[2,37],47:[2,37]},{22:[2,38],37:[2,38],38:[2,38],39:[2,38],40:[2,38],45:[2,38],47:[2,38]},{22:[2,39],37:[2,39],38:[2,39],39:[2,39],40:[2,39],45:[2,39],47:[2,39]},{5:[2,11],10:[2,11],17:[2,11],18:[2,11],21:[2,11],23:[2,11],24:[2,11],26:[2,11],27:[2,11],29:[2,11]},{5:[2,12],10:[2,12],17:[2,12],18:[2,12],21:[2,12],23:[2,12],24:[2,12],26:[2,12],27:[2,12],29:[2,12]},{25:67,45:[1,31],48:29},{8:19,9:5,10:[1,10],12:6,14:7,15:8,16:9,17:[1,11],18:[1,12],21:[1,14],23:[1,13],24:[2,3],26:[1,15],27:[1,16],29:[1,17]},{4:68,8:4,9:5,10:[1,10],12:6,14:7,15:8,16:9,17:[1,11],18:[1,12],21:[1,14],23:[1,13],24:[2,5],26:[1,15],27:[1,16],29:[1,17]},{10:[2,26],17:[2,26],18:[2,26],21:[2,26],23:[2,26],24:[2,26],26:[2,26],27:[2,26],29:[2,26]},{5:[2,13],10:[2,13],17:[2,13],18:[2,13],21:[2,13],23:[2,13],24:[2,13],26:[2,13],27:[2,13],29:[2,13]},{10:[2,18]},{20:[2,50],22:[2,50],25:57,28:[2,50],31:70,35:69,36:61,37:[1,58],38:[1,59],39:[1,60],40:[1,62],41:[2,50],42:71,43:64,44:66,45:[1,65],47:[1,30],48:29},{45:[1,72]},{20:[2,40],22:[2,40],28:[2,40],37:[2,40],38:[2,40],39:[2,40],40:[2,40],41:[2,40],45:[2,40],47:[2,40]},{10:[2,20],17:[2,20],18:[2,20],21:[2,20],23:[2,20],24:[2,20],26:[2,20],27:[2,20],29:[2,20]},{10:[2,19],17:[2,19],18:[2,19],21:[2,19],23:[2,19],24:[2,19],26:[2,19],27:[2,19],29:[2,19]},{5:[2,22],10:[2,22],17:[2,22],18:[2,22],21:[2,22],23:[2,22],24:[2,22],26:[2,22],27:[2,22],29:[2,22]},{5:[2,23],10:[2,23],17:[2,23],18:[2,23],21:[2,23],23:[2,23],24:[2,23],26:[2,23],27:[2,23],29:[2,23]},{22:[2,44],32:73,42:74,43:64,44:66,45:[1,75]},{22:[1,76]},{20:[2,29],22:[2,29],28:[2,29],37:[2,29],38:[2,29],39:[2,29],40:[2,29],41:[2,29],45:[2,29],47:[2,29]},{20:[2,30],22:[2,30],28:[2,30],37:[2,30],38:[2,30],39:[2,30],40:[2,30],41:[2,30],45:[2,30],47:[2,30]},{20:[2,31],22:[2,31],28:[2,31],37:[2,31],38:[2,31],39:[2,31],40:[2,31],41:[2,31],45:[2,31],47:[2,31]},{20:[2,32],22:[2,32],28:[2,32],37:[2,32],38:[2,32],39:[2,32],40:[2,32],41:[2,32],45:[2,32],47:[2,32]},{20:[2,33],22:[2,33],28:[2,33],37:[2,33],38:[2,33],39:[2,33],40:[2,33],41:[2,33],45:[2,33],47:[2,33]},{19:77,25:27,36:28,45:[1,31],47:[1,30],48:29},{22:[2,47]},{20:[2,35],22:[2,35],28:[2,35],41:[2,35],44:78,45:[1,75]},{20:[2,43],22:[2,43],28:[2,43],37:[2,43],38:[2,43],39:[2,43],40:[2,43],41:[2,43],45:[2,43],46:[1,79],47:[2,43],49:[2,43]},{20:[2,52],22:[2,52],28:[2,52],41:[2,52],45:[2,52]},{22:[1,80]},{8:19,9:5,10:[1,10],12:6,14:7,15:8,16:9,17:[1,11],18:[1,12],21:[1,14],23:[1,13],24:[2,4],26:[1,15],27:[1,16],29:[1,17]},{20:[2,27],22:[2,27],28:[2,27],41:[2,27]},{20:[2,49],22:[2,49],28:[2,49],37:[2,49],38:[2,49],39:[2,49],40:[2,49],41:[2,49],45:[2,49],47:[2,49]},{20:[2,51],22:[2,51],28:[2,51],41:[2,51]},{20:[2,42],22:[2,42],28:[2,42],37:[2,42],38:[2,42],39:[2,42],40:[2,42],41:[2,42],45:[2,42],47:[2,42],49:[2,42]},{22:[1,81]},{22:[2,45]},{46:[1,79]},{5:[2,25],10:[2,25],17:[2,25],18:[2,25],21:[2,25],23:[2,25],24:[2,25],26:[2,25],27:[2,25],29:[2,25]},{41:[1,82]},{20:[2,53],22:[2,53],28:[2,53],41:[2,53],45:[2,53]},{25:57,31:83,36:61,37:[1,58],38:[1,59],39:[1,60],40:[1,62],45:[1,31],47:[1,30],48:29},{5:[2,21],10:[2,21],17:[2,21],18:[2,21],21:[2,21],23:[2,21],24:[2,21],26:[2,21],27:[2,21],29:[2,21]},{5:[2,24],10:[2,24],17:[2,24],18:[2,24],21:[2,24],23:[2,24],24:[2,24],26:[2,24],27:[2,24],29:[2,24]},{20:[2,34],22:[2,34],28:[2,34],37:[2,34],38:[2,34],39:[2,34],40:[2,34],41:[2,34],45:[2,34],47:[2,34]},{20:[2,36],22:[2,36],28:[2,36],41:[2,36],45:[2,36]}],defaultActions:{3:[2,2],18:[2,1],47:[2,18],63:[2,47],74:[2,45]},parseError:function(a){throw new Error(a)},parse:function(a){function b(){var a;return a=c.lexer.lex()||1,"number"!=typeof a&&(a=c.symbols_[a]||a),a}var c=this,d=[0],e=[null],f=[],g=this.table,h="",i=0,j=0,k=0;this.lexer.setInput(a),this.lexer.yy=this.yy,this.yy.lexer=this.lexer,this.yy.parser=this,"undefined"==typeof this.lexer.yylloc&&(this.lexer.yylloc={});var l=this.lexer.yylloc;f.push(l);var m=this.lexer.options&&this.lexer.options.ranges;"function"==typeof this.yy.parseError&&(this.parseError=this.yy.parseError);for(var n,o,p,q,r,s,t,u,v,w={};;){if(p=d[d.length-1],this.defaultActions[p]?q=this.defaultActions[p]:((null===n||"undefined"==typeof n)&&(n=b()),q=g[p]&&g[p][n]),"undefined"==typeof q||!q.length||!q[0]){var x="";if(!k){v=[];for(s in g[p])this.terminals_[s]&&s>2&&v.push("\'"+this.terminals_[s]+"\'");x=this.lexer.showPosition?"Parse error on line "+(i+1)+":\\n"+this.lexer.showPosition()+"\\nExpecting "+v.join(", ")+", got \'"+(this.terminals_[n]||n)+"\'":"Parse error on line "+(i+1)+": Unexpected "+(1==n?"end of input":"\'"+(this.terminals_[n]||n)+"\'"),this.parseError(x,{text:this.lexer.match,token:this.terminals_[n]||n,line:this.lexer.yylineno,loc:l,expected:v})}}if(q[0]instanceof Array&&q.length>1)throw new Error("Parse Error: multiple actions possible at state: "+p+", token: "+n);switch(q[0]){case 1:d.push(n),e.push(this.lexer.yytext),f.push(this.lexer.yylloc),d.push(q[1]),n=null,o?(n=o,o=null):(j=this.lexer.yyleng,h=this.lexer.yytext,i=this.lexer.yylineno,l=this.lexer.yylloc,k>0&&k--);break;case 2:if(t=this.productions_[q[1]][1],w.$=e[e.length-t],w._$={first_line:f[f.length-(t||1)].first_line,last_line:f[f.length-1].last_line,first_column:f[f.length-(t||1)].first_column,last_column:f[f.length-1].last_column},m&&(w._$.range=[f[f.length-(t||1)].range[0],f[f.length-1].range[1]]),r=this.performAction.call(w,h,j,i,this.yy,q[1],e,f),"undefined"!=typeof r)return r;t&&(d=d.slice(0,-1*t*2),e=e.slice(0,-1*t),f=f.slice(0,-1*t)),d.push(this.productions_[q[1]][0]),e.push(w.$),f.push(w._$),u=g[d[d.length-2]][d[d.length-1]],d.push(u);break;case 3:return!0}}return!0}},d=function(){var a={EOF:1,parseError:function(a,b){if(!this.yy.parser)throw new Error(a);this.yy.parser.parseError(a,b)},setInput:function(a){return this._input=a,this._more=this._less=this.done=!1,this.yylineno=this.yyleng=0,this.yytext=this.matched=this.match="",this.conditionStack=["INITIAL"],this.yylloc={first_line:1,first_column:0,last_line:1,last_column:0},this.options.ranges&&(this.yylloc.range=[0,0]),this.offset=0,this},input:function(){var a=this._input[0];this.yytext+=a,this.yyleng++,this.offset++,this.match+=a,this.matched+=a;var b=a.match(/(?:\\r\\n?|\\n).*/g);return b?(this.yylineno++,this.yylloc.last_line++):this.yylloc.last_column++,this.options.ranges&&this.yylloc.range[1]++,this._input=this._input.slice(1),a},unput:function(a){var b=a.length,c=a.split(/(?:\\r\\n?|\\n)/g);this._input=a+this._input,this.yytext=this.yytext.substr(0,this.yytext.length-b-1),this.offset-=b;var d=this.match.split(/(?:\\r\\n?|\\n)/g);this.match=this.match.substr(0,this.match.length-1),this.matched=this.matched.substr(0,this.matched.length-1),c.length-1&&(this.yylineno-=c.length-1);var e=this.yylloc.range;return this.yylloc={first_line:this.yylloc.first_line,last_line:this.yylineno+1,first_column:this.yylloc.first_column,last_column:c?(c.length===d.length?this.yylloc.first_column:0)+d[d.length-c.length].length-c[0].length:this.yylloc.first_column-b},this.options.ranges&&(this.yylloc.range=[e[0],e[0]+this.yyleng-b]),this},more:function(){return this._more=!0,this},less:function(a){this.unput(this.match.slice(a))},pastInput:function(){var a=this.matched.substr(0,this.matched.length-this.match.length);return(a.length>20?"...":"")+a.substr(-20).replace(/\\n/g,"")},upcomingInput:function(){var a=this.match;return a.length<20&&(a+=this._input.substr(0,20-a.length)),(a.substr(0,20)+(a.length>20?"...":"")).replace(/\\n/g,"")},showPosition:function(){var a=this.pastInput(),b=new Array(a.length+1).join("-");return a+this.upcomingInput()+"\\n"+b+"^"},next:function(){if(this.done)return this.EOF;this._input||(this.done=!0);var a,b,c,d,e;this._more||(this.yytext="",this.match="");for(var f=this._currentRules(),g=0;g<f.length&&(c=this._input.match(this.rules[f[g]]),!c||b&&!(c[0].length>b[0].length)||(b=c,d=g,this.options.flex));g++);return b?(e=b[0].match(/(?:\\r\\n?|\\n).*/g),e&&(this.yylineno+=e.length),this.yylloc={first_line:this.yylloc.last_line,last_line:this.yylineno+1,first_column:this.yylloc.last_column,last_column:e?e[e.length-1].length-e[e.length-1].match(/\\r?\\n?/)[0].length:this.yylloc.last_column+b[0].length},this.yytext+=b[0],this.match+=b[0],this.matches=b,this.yyleng=this.yytext.length,this.options.ranges&&(this.yylloc.range=[this.offset,this.offset+=this.yyleng]),this._more=!1,this._input=this._input.slice(b[0].length),this.matched+=b[0],a=this.performAction.call(this,this.yy,this,f[d],this.conditionStack[this.conditionStack.length-1]),this.done&&this._input&&(this.done=!1),a?a:void 0):""===this._input?this.EOF:this.parseError("Lexical error on line "+(this.yylineno+1)+". Unrecognized text.\\n"+this.showPosition(),{text:"",token:null,line:this.yylineno})},lex:function(){var a=this.next();return"undefined"!=typeof a?a:this.lex()},begin:function(a){this.conditionStack.push(a)},popState:function(){return this.conditionStack.pop()},_currentRules:function(){return this.conditions[this.conditionStack[this.conditionStack.length-1]].rules},topState:function(){return this.conditionStack[this.conditionStack.length-2]},pushState:function(a){this.begin(a)}};return a.options={},a.performAction=function(a,b,c,d){function e(a,c){return b.yytext=b.yytext.substr(a,b.yyleng-c)}switch(c){case 0:if("\\\\\\\\"===b.yytext.slice(-2)?(e(0,1),this.begin("mu")):"\\\\"===b.yytext.slice(-1)?(e(0,1),this.begin("emu")):this.begin("mu"),b.yytext)return 10;break;case 1:return 10;case 2:return this.popState(),10;case 3:return b.yytext=b.yytext.substr(5,b.yyleng-9),this.popState(),11;case 4:return 10;case 5:return e(0,4),this.popState(),17;case 6:return 40;case 7:return 41;case 8:return 18;case 9:return this.popState(),this.begin("raw"),20;case 10:return b.yytext=b.yytext.substr(4,b.yyleng-8),this.popState(),"RAW_BLOCK";case 11:return 29;case 12:return 21;case 13:return 24;case 14:return 23;case 15:return 23;case 16:return 27;case 17:return 26;case 18:this.popState(),this.begin("com");break;case 19:return e(3,5),this.popState(),17;case 20:return 26;case 21:return 46;case 22:return 45;case 23:return 45;case 24:return 49;case 25:break;case 26:return this.popState(),28;case 27:return this.popState(),22;case 28:return b.yytext=e(1,2).replace(/\\\\"/g,\'"\'),37;case 29:return b.yytext=e(1,2).replace(/\\\\\'/g,"\'"),37;case 30:return 47;case 31:return 39;case 32:return 39;case 33:return 38;case 34:return 45;case 35:return b.yytext=e(1,2),45;case 36:return"INVALID";case 37:return 5}},a.rules=[/^(?:[^\\x00]*?(?=(\\{\\{)))/,/^(?:[^\\x00]+)/,/^(?:[^\\x00]{2,}?(?=(\\{\\{|\\\\\\{\\{|\\\\\\\\\\{\\{|$)))/,/^(?:\\{\\{\\{\\{\\/[^\\s!"#%-,\\.\\/;->@\\[-\\^`\\{-~]+(?=[=}\\s\\/.])\\}\\}\\}\\})/,/^(?:[^\\x00]*?(?=(\\{\\{\\{\\{\\/)))/,/^(?:[\\s\\S]*?--\\}\\})/,/^(?:\\()/,/^(?:\\))/,/^(?:\\{\\{\\{\\{)/,/^(?:\\}\\}\\}\\})/,/^(?:\\{\\{\\{\\{[^\\x00]*\\}\\}\\}\\})/,/^(?:\\{\\{(~)?>)/,/^(?:\\{\\{(~)?#)/,/^(?:\\{\\{(~)?\\/)/,/^(?:\\{\\{(~)?\\^)/,/^(?:\\{\\{(~)?\\s*else\\b)/,/^(?:\\{\\{(~)?\\{)/,/^(?:\\{\\{(~)?&)/,/^(?:\\{\\{!--)/,/^(?:\\{\\{![\\s\\S]*?\\}\\})/,/^(?:\\{\\{(~)?)/,/^(?:=)/,/^(?:\\.\\.)/,/^(?:\\.(?=([=~}\\s\\/.)])))/,/^(?:[\\/.])/,/^(?:\\s+)/,/^(?:\\}(~)?\\}\\})/,/^(?:(~)?\\}\\})/,/^(?:"(\\\\["]|[^"])*")/,/^(?:\'(\\\\[\']|[^\'])*\')/,/^(?:@)/,/^(?:true(?=([~}\\s)])))/,/^(?:false(?=([~}\\s)])))/,/^(?:-?[0-9]+(?:\\.[0-9]+)?(?=([~}\\s)])))/,/^(?:([^\\s!"#%-,\\.\\/;->@\\[-\\^`\\{-~]+(?=([=~}\\s\\/.)]))))/,/^(?:\\[[^\\]]*\\])/,/^(?:.)/,/^(?:$)/],a.conditions={mu:{rules:[6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37],inclusive:!1},emu:{rules:[2],inclusive:!1},com:{rules:[5],inclusive:!1},raw:{rules:[3,4],inclusive:!1},INITIAL:{rules:[0,1,37],inclusive:!0}},a}();return c.lexer=d,b.prototype=c,c.Parser=b,new b}();return a=b}(),i=function(a,b){"use strict";function c(a){return a.constructor===f.ProgramNode?a:(e.yy=f,e.parse(a))}var d={},e=a,f=b;return d.parser=e,d.parse=c,d}(h,g),j=function(a){"use strict";function b(){}function c(a,b,c){if(null==a||"string"!=typeof a&&a.constructor!==c.AST.ProgramNode)throw new f("You must pass a string or Handlebars AST to Handlebars.precompile. You passed "+a);b=b||{},"data"in b||(b.data=!0);var d=c.parse(a),e=(new c.Compiler).compile(d,b);return(new c.JavaScriptCompiler).compile(e,b)}function d(a,b,c){function d(){var d=c.parse(a),e=(new c.Compiler).compile(d,b),f=(new c.JavaScriptCompiler).compile(e,b,void 0,!0);return c.template(f)}if(null==a||"string"!=typeof a&&a.constructor!==c.AST.ProgramNode)throw new f("You must pass a string or Handlebars AST to Handlebars.compile. You passed "+a);b=b||{},"data"in b||(b.data=!0);var e,g=function(a,b){return e||(e=d()),e.call(this,a,b)};return g._setup=function(a){return e||(e=d()),e._setup(a)},g._child=function(a){return e||(e=d()),e._child(a)},g}var e={},f=a;return e.Compiler=b,b.prototype={compiler:b,disassemble:function(){for(var a,b,c,d=this.opcodes,e=[],f=0,g=d.length;g>f;f++)if(a=d[f],"DECLARE"===a.opcode)e.push("DECLARE "+a.name+"="+a.value);else{b=[];for(var h=0;h<a.args.length;h++)c=a.args[h],"string"==typeof c&&(c=\'"\'+c.replace("\\n","\\\\n")+\'"\'),b.push(c);e.push(a.opcode+" "+b.join(" "))}return e.join("\\n")},equals:function(a){var b=this.opcodes.length;if(a.opcodes.length!==b)return!1;for(var c=0;b>c;c++){var d=this.opcodes[c],e=a.opcodes[c];if(d.opcode!==e.opcode||d.args.length!==e.args.length)return!1;for(var f=0;f<d.args.length;f++)if(d.args[f]!==e.args[f])return!1}if(b=this.children.length,a.children.length!==b)return!1;for(c=0;b>c;c++)if(!this.children[c].equals(a.children[c]))return!1;return!0},guid:0,compile:function(a,b){this.opcodes=[],this.children=[],this.depths={list:[]},this.options=b,this.stringParams=b.stringParams,this.trackIds=b.trackIds;var c=this.options.knownHelpers;if(this.options.knownHelpers={helperMissing:!0,blockHelperMissing:!0,each:!0,"if":!0,unless:!0,"with":!0,log:!0,lookup:!0},c)for(var d in c)this.options.knownHelpers[d]=c[d];return this.accept(a)},accept:function(a){var b,c=a.strip||{};return c.left&&this.opcode("strip"),b=this[a.type](a),c.right&&this.opcode("strip"),b},program:function(a){for(var b=a.statements,c=0,d=b.length;d>c;c++)this.accept(b[c]);return this.isSimple=1===d,this.depths.list=this.depths.list.sort(function(a,b){return a-b}),this},compileProgram:function(a){var b,c=(new this.compiler).compile(a,this.options),d=this.guid++;this.usePartial=this.usePartial||c.usePartial,this.children[d]=c;for(var e=0,f=c.depths.list.length;f>e;e++)b=c.depths.list[e],2>b||this.addDepth(b-1);return d},block:function(a){var b=a.mustache,c=a.program,d=a.inverse;c&&(c=this.compileProgram(c)),d&&(d=this.compileProgram(d));var e=b.sexpr,f=this.classifySexpr(e);"helper"===f?this.helperSexpr(e,c,d):"simple"===f?(this.simpleSexpr(e),this.opcode("pushProgram",c),this.opcode("pushProgram",d),this.opcode("emptyHash"),this.opcode("blockValue",e.id.original)):(this.ambiguousSexpr(e,c,d),this.opcode("pushProgram",c),this.opcode("pushProgram",d),this.opcode("emptyHash"),this.opcode("ambiguousBlockValue")),this.opcode("append")},hash:function(a){var b,c,d=a.pairs;for(this.opcode("pushHash"),b=0,c=d.length;c>b;b++)this.pushParam(d[b][1]);for(;b--;)this.opcode("assignToHash",d[b][0]);this.opcode("popHash")},partial:function(a){var b=a.partialName;this.usePartial=!0,a.hash?this.accept(a.hash):this.opcode("push","undefined"),a.context?this.accept(a.context):this.opcode("push","depth0"),this.opcode("invokePartial",b.name),this.opcode("append")\n
},content:function(a){this.opcode("appendContent",a.string)},mustache:function(a){this.sexpr(a.sexpr),a.escaped&&!this.options.noEscape?this.opcode("appendEscaped"):this.opcode("append")},ambiguousSexpr:function(a,b,c){var d=a.id,e=d.parts[0],f=null!=b||null!=c;this.opcode("getContext",d.depth),this.opcode("pushProgram",b),this.opcode("pushProgram",c),this.opcode("invokeAmbiguous",e,f)},simpleSexpr:function(a){var b=a.id;"DATA"===b.type?this.DATA(b):b.parts.length?this.ID(b):(this.addDepth(b.depth),this.opcode("getContext",b.depth),this.opcode("pushContext")),this.opcode("resolvePossibleLambda")},helperSexpr:function(a,b,c){var d=this.setupFullMustacheParams(a,b,c),e=a.id,g=e.parts[0];if(this.options.knownHelpers[g])this.opcode("invokeKnownHelper",d.length,g);else{if(this.options.knownHelpersOnly)throw new f("You specified knownHelpersOnly, but used the unknown helper "+g,a);this.ID(e),this.opcode("invokeHelper",d.length,e.original,a.isRoot)}},sexpr:function(a){var b=this.classifySexpr(a);"simple"===b?this.simpleSexpr(a):"helper"===b?this.helperSexpr(a):this.ambiguousSexpr(a)},ID:function(a){this.addDepth(a.depth),this.opcode("getContext",a.depth);var b=a.parts[0];b?this.opcode("lookupOnContext",a.parts[0]):this.opcode("pushContext");for(var c=1,d=a.parts.length;d>c;c++)this.opcode("lookup",a.parts[c])},DATA:function(a){this.options.data=!0,this.opcode("lookupData",a.id.depth);for(var b=a.id.parts,c=0,d=b.length;d>c;c++)this.opcode("lookup",b[c])},STRING:function(a){this.opcode("pushString",a.string)},NUMBER:function(a){this.opcode("pushLiteral",a.number)},BOOLEAN:function(a){this.opcode("pushLiteral",a.bool)},comment:function(){},opcode:function(a){this.opcodes.push({opcode:a,args:[].slice.call(arguments,1)})},declare:function(a,b){this.opcodes.push({opcode:"DECLARE",name:a,value:b})},addDepth:function(a){0!==a&&(this.depths[a]||(this.depths[a]=!0,this.depths.list.push(a)))},classifySexpr:function(a){var b=a.isHelper,c=a.eligibleHelper,d=this.options;if(c&&!b){var e=a.id.parts[0];d.knownHelpers[e]?b=!0:d.knownHelpersOnly&&(c=!1)}return b?"helper":c?"ambiguous":"simple"},pushParams:function(a){for(var b=0,c=a.length;c>b;b++)this.pushParam(a[b])},pushParam:function(a){this.stringParams?(a.depth&&this.addDepth(a.depth),this.opcode("getContext",a.depth||0),this.opcode("pushStringParam",a.stringModeValue,a.type),"sexpr"===a.type&&this.sexpr(a)):(this.trackIds&&this.opcode("pushId",a.type,a.idName||a.stringModeValue),this.accept(a))},setupFullMustacheParams:function(a,b,c){var d=a.params;return this.pushParams(d),this.opcode("pushProgram",b),this.opcode("pushProgram",c),a.hash?this.hash(a.hash):this.opcode("emptyHash"),d}},e.precompile=c,e.compile=d,e}(c),k=function(a,b){"use strict";function c(a){this.value=a}function d(){}var e,f=a.COMPILER_REVISION,g=a.REVISION_CHANGES,h=a.log,i=b;d.prototype={nameLookup:function(a,b){var c,e;return 0===a.indexOf("depth")&&(c=!0),e=d.isValidJavaScriptVariableName(b)?a+"."+b:a+"[\'"+b+"\']",c?"("+a+" && "+e+")":e},compilerInfo:function(){var a=f,b=g[a];return[a,b]},appendToBuffer:function(a){return this.environment.isSimple?"return "+a+";":{appendToBuffer:!0,content:a,toString:function(){return"buffer += "+a+";"}}},initializeBuffer:function(){return this.quotedString("")},namespace:"Handlebars",compile:function(a,b,c,d){this.environment=a,this.options=b||{},this.stringParams=this.options.stringParams,this.trackIds=this.options.trackIds,this.precompile=!d,h("debug",this.environment.disassemble()+"\\n\\n"),this.name=this.environment.name,this.isChild=!!c,this.context=c||{programs:[],environments:[]},this.preamble(),this.stackSlot=0,this.stackVars=[],this.aliases={},this.registers={list:[]},this.hashes=[],this.compileStack=[],this.inlineStack=[],this.compileChildren(a,b);var e,f,g,j=a.opcodes;for(f=0,g=j.length;g>f;f++)e=j[f],"DECLARE"===e.opcode?this[e.name]=e.value:this[e.opcode].apply(this,e.args),e.opcode!==this.stripNext&&(this.stripNext=!1);if(this.pushSource(""),this.stackSlot||this.inlineStack.length||this.compileStack.length)throw new i("Compile completed with content left on stack");var k=this.createFunctionContext(d);if(this.isChild)return k;var l={compiler:this.compilerInfo(),main:k},m=this.context.programs;for(f=0,g=m.length;g>f;f++)m[f]&&(l[f]=m[f]);return this.environment.usePartial&&(l.usePartial=!0),this.options.data&&(l.useData=!0),d||(l.compiler=JSON.stringify(l.compiler),l=this.objectLiteral(l)),l},preamble:function(){this.lastContext=0,this.source=[]},createFunctionContext:function(a){var b="",c=this.stackVars.concat(this.registers.list);c.length>0&&(b+=", "+c.join(", "));for(var d in this.aliases)this.aliases.hasOwnProperty(d)&&(b+=", "+d+"="+this.aliases[d]);for(var e=["depth0","helpers","partials","data"],f=0,g=this.environment.depths.list.length;g>f;f++)e.push("depth"+this.environment.depths.list[f]);var h=this.mergeSource(b);return a?(e.push(h),Function.apply(this,e)):"function("+e.join(",")+") {\\n "+h+"}"},mergeSource:function(a){for(var b,c,d="",e=!this.forceBuffer,f=0,g=this.source.length;g>f;f++){var h=this.source[f];h.appendToBuffer?b=b?b+"\\n + "+h.content:h.content:(b&&(d?d+="buffer += "+b+";\\n ":(c=!0,d=b+";\\n "),b=void 0),d+=h+"\\n ",this.environment.isSimple||(e=!1))}return e?(b||!d)&&(d+="return "+(b||\'""\')+";\\n"):(a+=", buffer = "+(c?"":this.initializeBuffer()),d+=b?"return buffer + "+b+";\\n":"return buffer;\\n"),a&&(d="var "+a.substring(2)+(c?"":";\\n ")+d),d},blockValue:function(a){this.aliases.blockHelperMissing="helpers.blockHelperMissing";var b=["depth0"];this.setupParams(a,0,b),this.replaceStack(function(a){return b.splice(1,0,a),"blockHelperMissing.call("+b.join(", ")+")"})},ambiguousBlockValue:function(){this.aliases.blockHelperMissing="helpers.blockHelperMissing";var a=["depth0"];this.setupParams("",0,a,!0),this.flushInline();var b=this.topStack();a.splice(1,0,b),this.pushSource("if (!"+this.lastHelper+") { "+b+" = blockHelperMissing.call("+a.join(", ")+"); }")},appendContent:function(a){this.pendingContent&&(a=this.pendingContent+a),this.stripNext&&(a=a.replace(/^\\s+/,"")),this.pendingContent=a},strip:function(){this.pendingContent&&(this.pendingContent=this.pendingContent.replace(/\\s+$/,"")),this.stripNext="strip"},append:function(){this.flushInline();var a=this.popStack();this.pushSource("if("+a+" || "+a+" === 0) { "+this.appendToBuffer(a)+" }"),this.environment.isSimple&&this.pushSource("else { "+this.appendToBuffer("\'\'")+" }")},appendEscaped:function(){this.aliases.escapeExpression="this.escapeExpression",this.pushSource(this.appendToBuffer("escapeExpression("+this.popStack()+")"))},getContext:function(a){this.lastContext!==a&&(this.lastContext=a)},lookupOnContext:function(a){this.push(this.nameLookup("depth"+this.lastContext,a,"context"))},pushContext:function(){this.pushStackLiteral("depth"+this.lastContext)},resolvePossibleLambda:function(){this.aliases.functionType=\'"function"\',this.replaceStack(function(a){return"typeof "+a+" === functionType ? "+a+".apply(depth0) : "+a})},lookup:function(a){this.replaceStack(function(b){return b+" == null || "+b+" === false ? "+b+" : "+this.nameLookup(b,a,"context")})},lookupData:function(a){a?this.pushStackLiteral("this.data(data, "+a+")"):this.pushStackLiteral("data")},pushStringParam:function(a,b){this.pushStackLiteral("depth"+this.lastContext),this.pushString(b),"sexpr"!==b&&("string"==typeof a?this.pushString(a):this.pushStackLiteral(a))},emptyHash:function(){this.pushStackLiteral("{}"),this.trackIds&&this.push("{}"),this.stringParams&&(this.push("{}"),this.push("{}"))},pushHash:function(){this.hash&&this.hashes.push(this.hash),this.hash={values:[],types:[],contexts:[],ids:[]}},popHash:function(){var a=this.hash;this.hash=this.hashes.pop(),this.trackIds&&this.push("{"+a.ids.join(",")+"}"),this.stringParams&&(this.push("{"+a.contexts.join(",")+"}"),this.push("{"+a.types.join(",")+"}")),this.push("{\\n "+a.values.join(",\\n ")+"\\n }")},pushString:function(a){this.pushStackLiteral(this.quotedString(a))},push:function(a){return this.inlineStack.push(a),a},pushLiteral:function(a){this.pushStackLiteral(a)},pushProgram:function(a){null!=a?this.pushStackLiteral(this.programExpression(a)):this.pushStackLiteral(null)},invokeHelper:function(a,b,c){this.aliases.helperMissing="helpers.helperMissing",this.useRegister("helper");var d=this.popStack(),e=this.setupHelper(a,b),f="helper = "+e.name+" || "+d+" || helperMissing";e.paramsInit&&(f+=","+e.paramsInit),this.push("("+f+",helper.call("+e.callParams+"))"),c||this.flushInline()},invokeKnownHelper:function(a,b){var c=this.setupHelper(a,b);this.push(c.name+".call("+c.callParams+")")},invokeAmbiguous:function(a,b){this.aliases.functionType=\'"function"\',this.useRegister("helper"),this.emptyHash();var c=this.setupHelper(0,a,b),d=this.lastHelper=this.nameLookup("helpers",a,"helper"),e=this.nameLookup("depth"+this.lastContext,a,"context");this.push("((helper = "+d+" || "+e+(c.paramsInit?"),("+c.paramsInit:"")+"),(typeof helper === functionType ? helper.call("+c.callParams+") : helper))")},invokePartial:function(a){var b=[this.nameLookup("partials",a,"partial"),"\'"+a+"\'",this.popStack(),this.popStack(),"helpers","partials"];this.options.data&&b.push("data"),this.push("this.invokePartial("+b.join(", ")+")")},assignToHash:function(a){var b,c,d,e=this.popStack();this.trackIds&&(d=this.popStack()),this.stringParams&&(c=this.popStack(),b=this.popStack());var f=this.hash;b&&f.contexts.push("\'"+a+"\': "+b),c&&f.types.push("\'"+a+"\': "+c),d&&f.ids.push("\'"+a+"\': "+d),f.values.push("\'"+a+"\': ("+e+")")},pushId:function(a,b){"ID"===a||"DATA"===a?this.pushString(b):"sexpr"===a?this.pushStackLiteral("true"):this.pushStackLiteral("null")},compiler:d,compileChildren:function(a,b){for(var c,d,e=a.children,f=0,g=e.length;g>f;f++){c=e[f],d=new this.compiler;var h=this.matchExistingProgram(c);null==h?(this.context.programs.push(""),h=this.context.programs.length,c.index=h,c.name="program"+h,this.context.programs[h]=d.compile(c,b,this.context,!this.precompile),this.context.environments[h]=c):(c.index=h,c.name="program"+h)}},matchExistingProgram:function(a){for(var b=0,c=this.context.environments.length;c>b;b++){var d=this.context.environments[b];if(d&&d.equals(a))return b}},programExpression:function(a){if(null==a)return"this.noop";for(var b,c=this.environment.children[a],d=c.depths.list,e=[c.index,"data"],f=0,g=d.length;g>f;f++)b=d[f],e.push("depth"+(b-1));return(0===d.length?"this.program(":"this.programWithDepth(")+e.join(", ")+")"},register:function(a,b){this.useRegister(a),this.pushSource(a+" = "+b+";")},useRegister:function(a){this.registers[a]||(this.registers[a]=!0,this.registers.list.push(a))},pushStackLiteral:function(a){return this.push(new c(a))},pushSource:function(a){this.pendingContent&&(this.source.push(this.appendToBuffer(this.quotedString(this.pendingContent))),this.pendingContent=void 0),a&&this.source.push(a)},pushStack:function(a){this.flushInline();var b=this.incrStack();return a&&this.pushSource(b+" = "+a+";"),this.compileStack.push(b),b},replaceStack:function(a){var b,d,e,f="",g=this.isInline();if(g){var h=this.popStack(!0);if(h instanceof c)b=h.value,e=!0;else{d=!this.stackSlot;var i=d?this.incrStack():this.topStackName();f="("+this.push(i)+" = "+h+"),",b=this.topStack()}}else b=this.topStack();var j=a.call(this,b);return g?(e||this.popStack(),d&&this.stackSlot--,this.push("("+f+j+")")):(/^stack/.test(b)||(b=this.nextStack()),this.pushSource(b+" = ("+f+j+");")),b},nextStack:function(){return this.pushStack()},incrStack:function(){return this.stackSlot++,this.stackSlot>this.stackVars.length&&this.stackVars.push("stack"+this.stackSlot),this.topStackName()},topStackName:function(){return"stack"+this.stackSlot},flushInline:function(){var a=this.inlineStack;if(a.length){this.inlineStack=[];for(var b=0,d=a.length;d>b;b++){var e=a[b];e instanceof c?this.compileStack.push(e):this.pushStack(e)}}},isInline:function(){return this.inlineStack.length},popStack:function(a){var b=this.isInline(),d=(b?this.inlineStack:this.compileStack).pop();if(!a&&d instanceof c)return d.value;if(!b){if(!this.stackSlot)throw new i("Invalid stack pop");this.stackSlot--}return d},topStack:function(a){var b=this.isInline()?this.inlineStack:this.compileStack,d=b[b.length-1];return!a&&d instanceof c?d.value:d},quotedString:function(a){return\'"\'+a.replace(/\\\\/g,"\\\\\\\\").replace(/"/g,\'\\\\"\').replace(/\\n/g,"\\\\n").replace(/\\r/g,"\\\\r").replace(/\\u2028/g,"\\\\u2028").replace(/\\u2029/g,"\\\\u2029")+\'"\'},objectLiteral:function(a){var b=[];for(var c in a)a.hasOwnProperty(c)&&b.push(this.quotedString(c)+":"+a[c]);return"{"+b.join(",")+"}"},setupHelper:function(a,b,c){var d=[],e=this.setupParams(b,a,d,c),f=this.nameLookup("helpers",b,"helper");return{params:d,paramsInit:e,name:f,callParams:["depth0"].concat(d).join(", ")}},setupOptions:function(a,b,c){var d,e,f,g={},h=[],i=[],j=[];g.name=this.quotedString(a),g.hash=this.popStack(),this.trackIds&&(g.hashIds=this.popStack()),this.stringParams&&(g.hashTypes=this.popStack(),g.hashContexts=this.popStack()),e=this.popStack(),f=this.popStack(),(f||e)&&(f||(f="this.noop"),e||(e="this.noop"),g.fn=f,g.inverse=e);for(var k=b;k--;)d=this.popStack(),c[k]=d,this.trackIds&&(j[k]=this.popStack()),this.stringParams&&(i[k]=this.popStack(),h[k]=this.popStack());return this.trackIds&&(g.ids="["+j.join(",")+"]"),this.stringParams&&(g.types="["+i.join(",")+"]",g.contexts="["+h.join(",")+"]"),this.options.data&&(g.data="data"),g},setupParams:function(a,b,c,d){var e=this.objectLiteral(this.setupOptions(a,b,c));return d?(this.useRegister("options"),c.push("options"),"options="+e):(c.push(e),"")}};for(var j="break else new var case finally return void catch for switch while continue function this with default if throw delete in try do instanceof typeof abstract enum int short boolean export interface static byte extends long super char final native synchronized class float package throws const goto private transient debugger implements protected volatile double import public let yield".split(" "),k=d.RESERVED_WORDS={},l=0,m=j.length;m>l;l++)k[j[l]]=!0;return d.isValidJavaScriptVariableName=function(a){return!d.RESERVED_WORDS[a]&&/^[a-zA-Z_$][0-9a-zA-Z_$]*$/.test(a)},e=d}(d,c),l=function(a,b,c,d,e){"use strict";var f,g=a,h=b,i=c.parser,j=c.parse,k=d.Compiler,l=d.compile,m=d.precompile,n=e,o=g.create,p=function(){var a=o();return a.compile=function(b,c){return l(b,c,a)},a.precompile=function(b,c){return m(b,c,a)},a.AST=h,a.Compiler=k,a.JavaScriptCompiler=n,a.Parser=i,a.parse=j,a};return g=p(),g.create=p,f=g}(f,g,i,j,k);return l}();
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>47711</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Folder" module="OFS.Folder"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>images</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570622.72</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>ajax-loader.gif</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/gif</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="base64">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
cp529CLVyZCqPo7WiAAAOw==</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>7825</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570622.6</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>animated-overlay.gif</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/gif</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="base64">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
JvjWKcnoGQpqyPlpOhr3aElaqrq56Bq7VAAAOw==</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>1738</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570622.49</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>ui-bg_flat_0_aaaaaa_40x100.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="base64">iVBORw0KGgoAAAANSUhEUgAAACgAAABkCAYAAAD0ZHJ6AAAAe0lEQVRoge3OMQHAIBAAMcC/kjdZ
JHTI0A4XBdkz86wfO18H3hRUBVVBVVAVVAVVQVVQFVQFVUFVUBVUBVVBVVAVVAVVQVVQFVQFVUFV
UBVUBVVBVVAVVAVVQVVQFVQFVUFVUBVUBVVBVVAVVAVVQVVQFVQFVUFVUBVUF8O8A8WdY6opAAAA
AElFTkSuQmCC</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>180</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570621.08</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>ui-bg_flat_75_ffffff_40x100.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="base64">iVBORw0KGgoAAAANSUhEUgAAACgAAABkCAYAAAD0ZHJ6AAAAeUlEQVRoge3OMQHAIBAAsVL/nh8J
DDfAkCjImpn5HvbfDpwIVoKVYCVYCVaClWAlWAlWgpVgJVgJVoKVYCVYCVaClWAlWAlWgpVgJVgJ
VoKVYCVYCVaClWAlWAlWgpVgJVgJVoKVYCVYCVaClWAlWAlWgpVgJVgJVhtqiwTEKTLXTgAAAABJ
RU5ErkJggg==</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>178</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570621.21</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>ui-bg_glass_55_fbf9ee_1x400.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="base64">iVBORw0KGgoAAAANSUhEUgAAAAEAAAGQCAYAAABvWArbAAAAP0lEQVQ4je3PMQrAMABC0a/3v2zX
0mCXNkOgc6C4PARd5DqPGKCU8luS8SbAQhiCQRgJE56kZTfbbP9RSvnkBsWcEAZRWcgqAAAAAElF
TkSuQmCC</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>120</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570621.33</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>ui-bg_glass_65_ffffff_1x400.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="base64">iVBORw0KGgoAAAANSUhEUgAAAAEAAAGQCAYAAABvWArbAAAAMElEQVQ4je3LIQ4AIBTD0O3f/8wr
FgmKhMy8pKJKwkhSKeVbbGuAPU9f4PIopTxgAeS0DRtI4yK0AAAAAElFTkSuQmCC</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>105</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570621.44</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>ui-bg_glass_75_dadada_1x400.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="base64">iVBORw0KGgoAAAANSUhEUgAAAAEAAAGQCAYAAABvWArbAAAANklEQVQ4jWN48uTJfyYGBgaGUWKU
GCWGLfHt2zcoi5GREYNgYmJCZiG42IiB98woMUqMEtgIAMdjCdyg+eEBAAAAAElFTkSuQmCC</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>111</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570621.55</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>ui-bg_glass_75_e6e6e6_1x400.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="base64">iVBORw0KGgoAAAANSUhEUgAAAAEAAAGQCAYAAABvWArbAAAANUlEQVQ4je3LMQoAIBADwb38/6t5
wFXaWAiCtUiaYZvF9hBACOFbuntVVe11B0CSjjeE8BwThQIJ8dhEl0YAAAAASUVORK5CYII=</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>110</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570621.67</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>ui-bg_glass_95_fef1ec_1x400.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="base64">iVBORw0KGgoAAAANSUhEUgAAAAEAAAGQCAYAAABvWArbAAAAPklEQVQ4je3PMQqAMABD0Z/c/7aC
IAXjJIhD10LJ8vgZw30eMUApZV/GhZNgSTjoLYElY/hNMJ/S6gullCkPiCIPCr4NiEwAAAAASUVO
RK5CYII=</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>119</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570621.78</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>ui-bg_highlight-soft_75_cccccc_1x100.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="base64">iVBORw0KGgoAAAANSUhEUgAAAAEAAABkCAYAAABHLFpgAAAALElEQVQYlWN49OjRfyYGBgaGIUT8
//8fSqBx0Yh///4RL8vAwAAVQ2MNOwIAl6g6KkOJwk8AAAAASUVORK5CYII=</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>101</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570621.89</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>ui-icons_222222_256x240.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="base64">iVBORw0KGgoAAAANSUhEUgAAAQAAAADwCAMAAADYSUr5AAAA7VBMVEUiIiIiIiIiIiIiIiIiIiIi
IiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIi
IiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIi
IiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIi
IiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiJdmhHzAAAA
TnRSTlMAGBAyBAhQv4OZLiJUcEBmYBoSzQwgPBZCSEoeWiYwUiyFNIeBw2rJz8c4RBy9uXyrtaWN
qa2zKP2fJO8KBgKPo2KVoa9s351GPm5+kWho0kj9AAAPhUlEQVR4nO1djWLbthEGyUiq5YSSLXtp
7FpLOmfzkmxr126tmi2p03RJ1/Xe/3EGgARxPyAgRbIk2/hkSz4CJO4+HsE7AJSVysjI2AMUUOxa
hZ2iANhzBtZWr4BoIRSYAVN5u4QwDwQDRbcwfUi5KS3wFuDmFnQLa4Dtb//cqktwD5QEFFwfUs7P
oCCA7y4bEJVFizcIob8KmhAplwwqVjt+9FBl3uINQniwEiryEyw9JHqGpQdEFNi+B4QQ7QOiHhys
IPoAxUqxvdvvA9K42bsAv4S2fxfYOe57IJSRkZGRkZGxx7jxSHDHcRBXQMTyIjInBgHwBJ/bEx8P
EANC+uhbpSSggCBAVODVabpI1S/k4WLZpTn6NpMhoX9Y40hxYERFpMcqUs4AloCtDQdID1YhnyXZ
2hLjAYWiO9Dy1PDB7tPhIqLx+uMB8grZaR+Qxl2/C2RkZGRkZGRk7A7rBf7J0DR5/LUTjzUPIPSP
GvQJiVJiB7kcQCiUOJrcFNtDZIf2xarQ3aGvLNxAVIFAabz90BFiBIlycTBhgWwOWCH0FLYHlPqw
HaCvcIn2ZbosCevfPTRiFFcgvHukCjWwrc3GrGh1fsAof8EaUReKXkCB4/MzFNo97qLpFiKFYv/k
NR5YQxQbQEofkZ2OuEOHqqT6gFTpru8CN7x/+jaZkZGRkZGRcV+x/rLUNcMMqUAscgnFocmpqkTz
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</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>4369</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570622.02</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>ui-icons_2e83ff_256x240.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="base64">iVBORw0KGgoAAAANSUhEUgAAAQAAAADwCAMAAADYSUr5AAAA7VBMVEUug/8ug/8ug/8ug/8ug/8u
g/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8u
g/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8u
g/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8u
g/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8ug/8lgcyYAAAA
TnRSTlMAGBAyBAhQv4OZLiJUcEBmYBoSzQwgPBZCSEoeWiYwUiyFNIeBw2rJz8c4RBy9uXyrtaWN
qa2zKP2fJO8KBgKPo2KVoa9s351GPm5+kWho0kj9AAAPhUlEQVR4nO1djWLbthEGyUiq5YSSLXtp
7FpLOmfzkmxr126tmi2p03RJ1/Xe/3EGgARxPyAgRbIk2/hkSz4CJO4+HsE7AJSVysjI2AMUUOxa
hZ2iANhzBtZWr4BoIRSYAVN5u4QwDwQDRbcwfUi5KS3wFuDmFnQLa4Dtb//cqktwD5QEFFwfUs7P
oCCA7y4bEJVFizcIob8KmhAplwwqVjt+9FBl3uINQniwEiryEyw9JHqGpQdEFNi+B4QQ7QOiHhys
IPoAxUqxvdvvA9K42bsAv4S2fxfYOe57IJSRkZGRkZGxx7jxSHDHcRBXQMTyIjInBgHwBJ/bEx8P
EANC+uhbpSSggCBAVODVabpI1S/k4WLZpTn6NpMhoX9Y40hxYERFpMcqUs4AloCtDQdID1YhnyXZ
2hLjAYWiO9Dy1PDB7tPhIqLx+uMB8grZaR+Qxl2/C2RkZGRkZGRk7A7rBf7J0DR5/LUTjzUPIPSP
GvQJiVJiB7kcQCiUOJrcFNtDZIf2xarQ3aGvLNxAVIFAabz90BFiBIlycTBhgWwOWCH0FLYHlPqw
HaCvcIn2ZbosCevfPTRiFFcgvHukCjWwrc3GrGh1fsAof8EaUReKXkCB4/MzFNo97qLpFiKFYv/k
NR5YQxQbQEofkZ2OuEOHqqT6gFTpru8CN7x/+jaZkZGRkZGRcV+x/rLUNcMMqUAscgnFocmpqkTz
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</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>4369</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570622.15</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>ui-icons_454545_256x240.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="base64">iVBORw0KGgoAAAANSUhEUgAAAQAAAADwCAMAAADYSUr5AAAA7VBMVEVFRUVFRUVFRUVFRUVFRUVF
RUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVF
RUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVF
RUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVF
RUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUVFRUWG2rLCAAAA
TnRSTlMAGBAyBAhQv4OZLiJUcEBmYBoSzQwgPBZCSEoeWiYwUiyFNIeBw2rJz8c4RBy9uXyrtaWN
qa2zKP2fJO8KBgKPo2KVoa9s351GPm5+kWho0kj9AAAPhUlEQVR4nO1djWLbthEGyUiq5YSSLXtp
7FpLOmfzkmxr126tmi2p03RJ1/Xe/3EGgARxPyAgRbIk2/hkSz4CJO4+HsE7AJSVysjI2AMUUOxa
hZ2iANhzBtZWr4BoIRSYAVN5u4QwDwQDRbcwfUi5KS3wFuDmFnQLa4Dtb//cqktwD5QEFFwfUs7P
oCCA7y4bEJVFizcIob8KmhAplwwqVjt+9FBl3uINQniwEiryEyw9JHqGpQdEFNi+B4QQ7QOiHhys
IPoAxUqxvdvvA9K42bsAv4S2fxfYOe57IJSRkZGRkZGxx7jxSHDHcRBXQMTyIjInBgHwBJ/bEx8P
EANC+uhbpSSggCBAVODVabpI1S/k4WLZpTn6NpMhoX9Y40hxYERFpMcqUs4AloCtDQdID1YhnyXZ
2hLjAYWiO9Dy1PDB7tPhIqLx+uMB8grZaR+Qxl2/C2RkZGRkZGRk7A7rBf7J0DR5/LUTjzUPIPSP
GvQJiVJiB7kcQCiUOJrcFNtDZIf2xarQ3aGvLNxAVIFAabz90BFiBIlycTBhgWwOWCH0FLYHlPqw
HaCvcIn2ZbosCevfPTRiFFcgvHukCjWwrc3GrGh1fsAof8EaUReKXkCB4/MzFNo97qLpFiKFYv/k
NR5YQxQbQEofkZ2OuEOHqqT6gFTpru8CN7x/+jaZkZGRkZGRcV+x/rLUNcMMqUAscgnFocmpqkTz
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</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>4369</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570622.26</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>ui-icons_888888_256x240.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="base64">iVBORw0KGgoAAAANSUhEUgAAAQAAAADwCAMAAADYSUr5AAAA7VBMVEWIiIiIiIiIiIiIiIiIiIiI
iIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiI
iIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiI
iIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiI
iIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIiIighcp7AAAA
TnRSTlMAGBAyBAhQv4OZLiJUcEBmYBoSzQwgPBZCSEoeWiYwUiyFNIeBw2rJz8c4RBy9uXyrtaWN
qa2zKP2fJO8KBgKPo2KVoa9s351GPm5+kWho0kj9AAAPhUlEQVR4nO1djWLbthEGyUiq5YSSLXtp
7FpLOmfzkmxr126tmi2p03RJ1/Xe/3EGgARxPyAgRbIk2/hkSz4CJO4+HsE7AJSVysjI2AMUUOxa
hZ2iANhzBtZWr4BoIRSYAVN5u4QwDwQDRbcwfUi5KS3wFuDmFnQLa4Dtb//cqktwD5QEFFwfUs7P
oCCA7y4bEJVFizcIob8KmhAplwwqVjt+9FBl3uINQniwEiryEyw9JHqGpQdEFNi+B4QQ7QOiHhys
IPoAxUqxvdvvA9K42bsAv4S2fxfYOe57IJSRkZGRkZGxx7jxSHDHcRBXQMTyIjInBgHwBJ/bEx8P
EANC+uhbpSSggCBAVODVabpI1S/k4WLZpTn6NpMhoX9Y40hxYERFpMcqUs4AloCtDQdID1YhnyXZ
2hLjAYWiO9Dy1PDB7tPhIqLx+uMB8grZaR+Qxl2/C2RkZGRkZGRk7A7rBf7J0DR5/LUTjzUPIPSP
GvQJiVJiB7kcQCiUOJrcFNtDZIf2xarQ3aGvLNxAVIFAabz90BFiBIlycTBhgWwOWCH0FLYHlPqw
HaCvcIn2ZbosCevfPTRiFFcgvHukCjWwrc3GrGh1fsAof8EaUReKXkCB4/MzFNo97qLpFiKFYv/k
NR5YQxQbQEofkZ2OuEOHqqT6gFTpru8CN7x/+jaZkZGRkZGRcV+x/rLUNcMMqUAscgnFocmpqkTz
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</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>4369</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570622.38</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>ui-icons_cd0a0a_256x240.png</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>image/png</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="base64">iVBORw0KGgoAAAANSUhEUgAAAQAAAADwCAMAAADYSUr5AAAA7VBMVEXNCgrNCgrNCgrNCgrNCgrN
CgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrN
CgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrN
CgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrN
CgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrNCgrqN5j8AAAA
TnRSTlMAGBAyBAhQv4OZLiJUcEBmYBoSzQwgPBZCSEoeWiYwUiyFNIeBw2rJz8c4RBy9uXyrtaWN
qa2zKP2fJO8KBgKPo2KVoa9s351GPm5+kWho0kj9AAAPhUlEQVR4nO1djWLbthEGyUiq5YSSLXtp
7FpLOmfzkmxr126tmi2p03RJ1/Xe/3EGgARxPyAgRbIk2/hkSz4CJO4+HsE7AJSVysjI2AMUUOxa
hZ2iANhzBtZWr4BoIRSYAVN5u4QwDwQDRbcwfUi5KS3wFuDmFnQLa4Dtb//cqktwD5QEFFwfUs7P
oCCA7y4bEJVFizcIob8KmhAplwwqVjt+9FBl3uINQniwEiryEyw9JHqGpQdEFNi+B4QQ7QOiHhys
IPoAxUqxvdvvA9K42bsAv4S2fxfYOe57IJSRkZGRkZGxx7jxSHDHcRBXQMTyIjInBgHwBJ/bEx8P
EANC+uhbpSSggCBAVODVabpI1S/k4WLZpTn6NpMhoX9Y40hxYERFpMcqUs4AloCtDQdID1YhnyXZ
2hLjAYWiO9Dy1PDB7tPhIqLx+uMB8grZaR+Qxl2/C2RkZGRkZGRk7A7rBf7J0DR5/LUTjzUPIPSP
GvQJiVJiB7kcQCiUOJrcFNtDZIf2xarQ3aGvLNxAVIFAabz90BFiBIlycTBhgWwOWCH0FLYHlPqw
HaCvcIn2ZbosCevfPTRiFFcgvHukCjWwrc3GrGh1fsAof8EaUReKXkCB4/MzFNo97qLpFiKFYv/k
NR5YQxQbQEofkZ2OuEOHqqT6gFTpru8CN7x/+jaZkZGRkZGRcV+x/rLUNcMMqUAscgnFocmpqkTz
qymwVAPxfJ5PnIUUQOUKT04tEdWZyv3JCQSn96WS4pD97QfyW25A7NhSAbyhmVj0FEltA4vdiygB
ibXhoUYgykCUP7HwPTDeEqAIcHVMkZg7Zx4k0uFANs63hPQXCoRLAwdgGsr9Az7Qv7sgQGgg1aPl
/BJLExBWgG4RFRLFImGmIquPC/klEGyCG0AuAXaJJC+B8FVe9NYQDEcXB8g6AQcjYJ1goJIggHWC
rFR0S6kRHN5+4BzFi8NaoN35NRxUvL+JJdZr7PV4wK6fj8nIyMjIyNhr3OxdXAYq7FHZwB6bDSzS
h4sF0utChqo0NAvaT1hLzXwFinmCzmeDucEQK18TTaQoFgP7bNC+RZ4OT4T6gQogDFYk+1QxQlj1
9QGSAWKiLYp8P0Ag1Gbz1ULfWHLg9iUnQNK5QQJcukm04blKLH2GgEJCY+HzXAZWCvHKco3Bp6MI
aCjSXXRJyOxeqhnzEaF93MfFGW/O16ZvDL5TM4MJIjujz/cHypkQuuzRwWJ93BKdIt+wCRAPl9kp
e2Ikkb2mFgGlxh/i40d3EHfdvoyMjIyMu43ylt/IAmGHnN5iIt7wKfbv01RAcJqFRl9lcjYQSnbQ
qKgC4fYOwSJt6N6trE0twZ9kN/PqNpTQeICvr4TLsDYC06U7BMjshS+v1/aT7IwQYD5LcgRQXMT2
FrBfBLjZ6151jDElk9tPFfpUgk2yregusX25BJbwAFEfM+YI6vGAti4bTtizB+TjfQCrERyhKb2X
8D6A9wX75P4t4neBYJeP6pdhg/gQl8MWvytzeSTjgOQBynQdh/iXKdxOrGJ/RkZGRsb9QmXihGr5
+g8GGg9uTh+KoVZuNIzV+CwRucFBEyr1mVjx4irOxwM1BhirB6Q+2eNQi4eqR+aF6mELtoMzCR7V
9RAFe/ZvQogNiyY8FPSUTFsLp8TeTmMui5mtw7bcaT0Yw2AA4wFRQIlkgq+1DQrNhkmoxS5Jq+u6
bMAIGRECEANgXHTgWzwgBOhDH2l0oTQ4D8D5NMktBgNywAEMjo8rwATMZrPY7JGxBoJCkIBDQiAY
09EGTUiBCWkUpISfGPR5AAwBfZiG2z7Ayc1yeKTxid39xBNwfHr4O0LA48ePFTvhYrF1r4tyAoz9
n2MCqEuBtp/6GDR0oAYfG/R6wJExHYZHfhygsv7fEWCOj4bYmsP5A+pL4MkTfAnMlD4F+r3bobKv
TyTA2P/w7PN+Agq2QW8piqMCpTBwenoKvX0AHGkGtP2YAPvTEWA7QUTAudn7/NxtOG46wWNmDtpB
EkBzN7rBEvAFHp+YTB/q97qPAN4gHFqgBi8uLsC7qPCA6mg41G/+ErByPwEXDdoNxRhOx+M5jPEz
QugS0ht+b1/Y3gEnYMAIAOIBE29/hIDucE8tmMsNOgK4B1RHFu4UCRlMHzv0xzcajcfdXWDs2h8T
ArBCkoDUJYDLmz6w7ip3BFS0ve5wTRwAn6keMA9I3QYbfSZ0DKbyt+7OXjGI1idPcfNyAyfAMlCr
zaGqphYrxHocLHRJVycnfGUcbtT+jIyMjIw9x7Nn8fJSzG0TmFtO8rZT+XT3S3ub+tKJbbLd5diT
Vp50+zahyeHSslJ/YPrU0fuazrZO2CZ92/ZCCVXlGRiZKPJyPPRxyIFWeXLQBXJBKiq/3divEAN6
ZwM200Qjm7EJBZeWm/PRWVCbYK7s7u2l4XaCz+lzgOfMfhMonXr7TWzeZb98dbgIzBT8Ub8eYYUq
fZ4rVJ/MDbIDgPqTulJ/xvntWAtjIisqnwxOkGz0n077FARoY79GdA6HPE4rOy196NiMWHTZlSSA
pcOgXpy/fHV2joaNKu3ffsAnRcBf4K/6NcIG6tIxk3HyoXPjASqfUgXbYN5PzpL2njkR9QMjeDTV
HDTCgRuxOegjoO0FvKzP/t/gmVdI24+G7NIe8JX6Wv3dDyldMA+4YB5wwTygtd+dwRqaTqrLb1l7
3zTSN52CNpnHuQOYPsDblybgxfkXh/oVtr+N1DEBJdhRJyd/Bd/q1z+cbNrD17iVKyajcnv9arhO
kRPgsruuD6DmNPwpDNrLw2CoTgHni4yALr0L29+tiKAEIPn868ejx//8rpWP3OEOl5On9OwpcQm0
MhafP/ey8f1uvDNIgGLQG8z4YO99ENgg95etwv4uYJYY8fUGHYH6j6fscHFZMftlAl9i+9XL73X3
N/n+ZStOzfVfRvYXhrbdKOpEgVQTg/wsDuDD3kwOfQNMTJ5y+/ltUDWLunyxnRF46IqlBzGMY4X7
inggREFioIyMjIyMHWCIB6ZNKAcXseo3vLTQTkVE7348dlwJJSz0+wLfmi8BhZqfw3D4ww/wHVLn
Ed5/fgYvXsDZ3MlsvYUbbnDjDZ3MN3TJG4+bxjAaDl8TBri9qxEw1ccao2wTNAMLHo2f+sjrXwb/
9qHoYqgPMBXJTVfOpmrZH23y6uvo0LHSyY6fHGwKfHJlAuMFvObjDYrIqxBgQi20h7Hd/nYVLmno
+eaNUm/eeH2GCuopntnhBJAlI2AHo9CCh1I1QxUdAbqqGY9BBLwyc3W4wYVhvY8A4BoIc1l5M7vn
PWphZW9/Ses3n37y9a0uGqFwFQZsQQbd386DogpgEk+dzynsAZMJXq8+ns9NeukJ0PYrNATGGefJ
QlhkLo7DTXr+y3bNiOsDvrXTz/C2q1DXZH84iRNwrP88Nj+u2DjYEE6RBxD9Knj16ujVHC67A742
2o02RwD3gB+t7EblWvu9geOFxSnd3ROmT+nJyQkhoPlsxVONc/3TEdBos+jtA+ZzcwHgTvD1cDja
YCcItA8w9i88A8b+mqSjc6Pvqd998QguEQPmQMeo23ODN86+p0/bn1buBkT6+oBhNZ/PYY4ZAHYb
3PRd4LkZmPX68NRtMZn4ASvdA+qf0jMA5MP9eeg28Nug9QiLnj5A33U1MAES6xHAUNpz/9zFAYE1
gqQDMT3G6xI9pwdw/aIgKoHCS1YGlRnSq9yCjdXjgN3j+N27YyROHxmuNAeNKPpYuXIyIyMjYy0M
8eros59MF/PT2c602T7eA7zvhJ9dr/vzDjXaLp4Yc5+0wllzxzHv3gdmMMM7/CcQzKgVBqYTmFn+
Z+mKm8J7k0A5F/jgCfjQ1WBhQyiOqD0lYuqBb+AyzMw9Ha2G3m6c8qQx+AlqnIceQp+Sb6i9UyQW
bhr54+AjnZ0VzW2TAN0DmBT6PWmc6jDBE2PK2u+nF43dyP7Q0t1pOcX2fdRvH0mF2Q4JqN35rnHj
VIeaXfIAVyUuw/aHCCiJy9iF5l1621zweI8KZrPZ9iJdb7DXJ3US0OSrtZ10imt7wHY7QesAzUMz
1oZ3noB3qFJ/H18j97FYuw8QDN4oeKf30osvcSW2ExLo+VcbuAuo/sUIm8fMG9xocO3Ea19J9gFY
ivnHJ2KnyfovZlgW3v6ySx32abQiIyMjIyPjhlFDTLxpwIgFMnTp6A3g4IDKNY+stkwAMAoIAbas
xBXqUWneSAWTMjt50lTqT29rFjvXohjsDNm2YPXDFlICmrJOZ3t6tHm8AiEAl0sCeLIIorIRt+cF
bew/QRsoAXb4o1XSfoywzm0FTMAoYBNvLyFu8v8HpLBtD1iKgC17wHb7AI6d9wFbvguAIGTHd4E9
wG7jgIyMjIyM+434c2R3HeV/Ffx6jtZu6ijl8h59T655jhR+rdHzDOP6beABCheb8O8/WFXeOyzg
f5oAhVYnKxP7CwaAf1afJu8bSrhS6tdaXeGnrRenOqOlz9d6QwYnA/3TLd+GE7qe3chA5YF5DfY0
vK3adfOX/gyNp2BW25MHdxAB9qvRiiP3/XpQQFGYDU4+Mi///XumXG8pjvaUAOsBGlf4jJt+YYEz
eEzAdw06F19R3juM7D1wita86GR0CKfDHgLuXCc4Bri6vMLdfjMc4VNSUNsdodo2xu/1+Xl/K5+a
z8jIyMhYG/z5gJTMF1GtKq/a3rpyCvz5gJTMl9GtKq/a3rpyCmfQ4WwZmS+kXFVetb115ST48wEf
/AGcfG1iw+tWbpbS2vJ3nQxcVr3lH3z5h972FUTLzYpOVk7l5hD+eYcYwDcAnewOotrZ4OtrPDuc
qi/LRX0/RR4qx7Nn4U8g+qjffvuN6Gf+nC85vwauHjaYyubqvWYKY4VEfSUMitdnBCT1Ue63R543
9m+OgCn6DroAAaHPVQxKth/wkJgHmG8bmQMsT0D6EjDfvhVRKO3ywOQUgRA7nmL1uawZmHf1k+DP
BwQ6NdcJ+k6Md1LA5f5ONdhJ8vZ5J0vLHT99srkGOjmJbd/G1r2Nriqnse1AZt1AalU5jW2HsuuG
0qvKGRkZGRkZGRG0gcONyXsP9v8D0/IdJADiBNiXl3327WRGgOL/9HC/0XwlIURkRhC4tz6Z/fu7
fUf2gHvfB9z3u0BGRkZGRkbGplHcnkgguQoSqtUXuhbs/wPtMwqV0HUJAvj5vk32b8IDuL23yn7q
AXZ5u32hbRX7d3o82Df1FZXvbh9QOfhyxldr/+3xgXU9oKmvsHyr7F/XA269/eveBXrsv7N9QALe
/tvjA0kPWAXGbvebkbHn+D/J5nMcHzx1UAAAAABJRU5ErkJggg==</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>4369</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570616.66</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>jquery-ui.css</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>text/css</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string>/*! jQuery UI - v1.11.0-beta.1 - 2014-04-24\n
* http://jqueryui.com\n
* Includes: core.css, accordion.css, autocomplete.css, button.css, datepicker.css, dialog.css, draggable.css, menu.css, progressbar.css, resizable.css, selectable.css, slider.css, sortable.css, spinner.css, tabs.css, tooltip.css, theme.css\n
* Copyright 2014 jQuery Foundation and other contributors; Licensed MIT */\n
\n
/* Layout helpers\n
----------------------------------*/\n
.ui-helper-hidden {\n
\tdisplay: none;\n
}\n
.ui-helper-hidden-accessible {\n
\tborder: 0;\n
\tclip: rect(0 0 0 0);\n
\theight: 1px;\n
\tmargin: -1px;\n
\toverflow: hidden;\n
\tpadding: 0;\n
\tposition: absolute;\n
\twidth: 1px;\n
}\n
.ui-helper-reset {\n
\tmargin: 0;\n
\tpadding: 0;\n
\tborder: 0;\n
\toutline: 0;\n
\tline-height: 1.3;\n
\ttext-decoration: none;\n
\tfont-size: 100%;\n
\tlist-style: none;\n
}\n
.ui-helper-clearfix:before,\n
.ui-helper-clearfix:after {\n
\tcontent: "";\n
\tdisplay: table;\n
\tborder-collapse: collapse;\n
}\n
.ui-helper-clearfix:after {\n
\tclear: both;\n
}\n
.ui-helper-clearfix {\n
\tmin-height: 0; /* support: IE7 */\n
}\n
.ui-helper-zfix {\n
\twidth: 100%;\n
\theight: 100%;\n
\ttop: 0;\n
\tleft: 0;\n
\tposition: absolute;\n
\topacity: 0;\n
\tfilter:Alpha(Opacity=0);\n
}\n
\n
.ui-front {\n
\tz-index: 100;\n
}\n
\n
\n
/* Interaction Cues\n
----------------------------------*/\n
.ui-state-disabled {\n
\tcursor: default !important;\n
}\n
\n
\n
/* Icons\n
----------------------------------*/\n
\n
/* states and images */\n
.ui-icon {\n
\tdisplay: block;\n
\ttext-indent: -99999px;\n
\toverflow: hidden;\n
\tbackground-repeat: no-repeat;\n
}\n
\n
\n
/* Misc visuals\n
----------------------------------*/\n
\n
/* Overlays */\n
.ui-widget-overlay {\n
\tposition: fixed;\n
\ttop: 0;\n
\tleft: 0;\n
\twidth: 100%;\n
\theight: 100%;\n
}\n
.ui-accordion .ui-accordion-header {\n
\tdisplay: block;\n
\tcursor: pointer;\n
\tposition: relative;\n
\tmargin: 2px 0 0 0;\n
\tpadding: .5em .5em .5em .7em;\n
\tmin-height: 0; /* support: IE7 */\n
\tfont-size: 100%;\n
}\n
.ui-accordion .ui-accordion-icons {\n
\tpadding-left: 2.2em;\n
}\n
.ui-accordion .ui-accordion-icons .ui-accordion-icons {\n
\tpadding-left: 2.2em;\n
}\n
.ui-accordion .ui-accordion-header .ui-accordion-header-icon {\n
\tposition: absolute;\n
\tleft: .5em;\n
\ttop: 50%;\n
\tmargin-top: -8px;\n
}\n
.ui-accordion .ui-accordion-content {\n
\tpadding: 1em 2.2em;\n
\tborder-top: 0;\n
\toverflow: auto;\n
}\n
.ui-autocomplete {\n
\tposition: absolute;\n
\ttop: 0;\n
\tleft: 0;\n
\tcursor: default;\n
}\n
.ui-button {\n
\tdisplay: inline-block;\n
\tposition: relative;\n
\tpadding: 0;\n
\tline-height: normal;\n
\tmargin-right: .1em;\n
\tcursor: pointer;\n
\tvertical-align: middle;\n
\ttext-align: center;\n
\toverflow: visible; /* removes extra width in IE */\n
}\n
.ui-button,\n
.ui-button:link,\n
.ui-button:visited,\n
.ui-button:hover,\n
.ui-button:active {\n
\ttext-decoration: none;\n
}\n
/* to make room for the icon, a width needs to be set here */\n
.ui-button-icon-only {\n
\twidth: 2.2em;\n
}\n
/* button elements seem to need a little more width */\n
button.ui-button-icon-only {\n
\twidth: 2.4em;\n
}\n
.ui-button-icons-only {\n
\twidth: 3.4em;\n
}\n
button.ui-button-icons-only {\n
\twidth: 3.7em;\n
}\n
\n
/* button text element */\n
.ui-button .ui-button-text {\n
\tdisplay: block;\n
\tline-height: normal;\n
}\n
.ui-button-text-only .ui-button-text {\n
\tpadding: .4em 1em;\n
}\n
.ui-button-icon-only .ui-button-text,\n
.ui-button-icons-only .ui-button-text {\n
\tpadding: .4em;\n
\ttext-indent: -9999999px;\n
}\n
.ui-button-text-icon-primary .ui-button-text,\n
.ui-button-text-icons .ui-button-text {\n
\tpadding: .4em 1em .4em 2.1em;\n
}\n
.ui-button-text-icon-secondary .ui-button-text,\n
.ui-button-text-icons .ui-button-text {\n
\tpadding: .4em 2.1em .4em 1em;\n
}\n
.ui-button-text-icons .ui-button-text {\n
\tpadding-left: 2.1em;\n
\tpadding-right: 2.1em;\n
}\n
/* no icon support for input elements, provide padding by default */\n
input.ui-button {\n
\tpadding: .4em 1em;\n
}\n
\n
/* button icon element(s) */\n
.ui-button-icon-only .ui-icon,\n
.ui-button-text-icon-primary .ui-icon,\n
.ui-button-text-icon-secondary .ui-icon,\n
.ui-button-text-icons .ui-icon,\n
.ui-button-icons-only .ui-icon {\n
\tposition: absolute;\n
\ttop: 50%;\n
\tmargin-top: -8px;\n
}\n
.ui-button-icon-only .ui-icon {\n
\tleft: 50%;\n
\tmargin-left: -8px;\n
}\n
.ui-button-text-icon-primary .ui-button-icon-primary,\n
.ui-button-text-icons .ui-button-icon-primary,\n
.ui-button-icons-only .ui-button-icon-primary {\n
\tleft: .5em;\n
}\n
.ui-button-text-icon-secondary .ui-button-icon-secondary,\n
.ui-button-text-icons .ui-button-icon-secondary,\n
.ui-button-icons-only .ui-button-icon-secondary {\n
\tright: .5em;\n
}\n
\n
/* button sets */\n
.ui-buttonset {\n
\tmargin-right: 7px;\n
}\n
.ui-buttonset .ui-button {\n
\tmargin-left: 0;\n
\tmargin-right: -.3em;\n
}\n
\n
/* workarounds */\n
/* reset extra padding in Firefox, see h5bp.com/l */\n
input.ui-button::-moz-focus-inner,\n
button.ui-button::-moz-focus-inner {\n
\tborder: 0;\n
\tpadding: 0;\n
}\n
.ui-datepicker {\n
\twidth: 17em;\n
\tpadding: .2em .2em 0;\n
\tdisplay: none;\n
}\n
.ui-datepicker .ui-datepicker-header {\n
\tposition: relative;\n
\tpadding: .2em 0;\n
}\n
.ui-datepicker .ui-datepicker-prev,\n
.ui-datepicker .ui-datepicker-next {\n
\tposition: absolute;\n
\ttop: 2px;\n
\twidth: 1.8em;\n
\theight: 1.8em;\n
}\n
.ui-datepicker .ui-datepicker-prev-hover,\n
.ui-datepicker .ui-datepicker-next-hover {\n
\ttop: 1px;\n
}\n
.ui-datepicker .ui-datepicker-prev {\n
\tleft: 2px;\n
}\n
.ui-datepicker .ui-datepicker-next {\n
\tright: 2px;\n
}\n
.ui-datepicker .ui-datepicker-prev-hover {\n
\tleft: 1px;\n
}\n
.ui-datepicker .ui-datepicker-next-hover {\n
\tright: 1px;\n
}\n
.ui-datepicker .ui-datepicker-prev span,\n
.ui-datepicker .ui-datepicker-next span {\n
\tdisplay: block;\n
\tposition: absolute;\n
\tleft: 50%;\n
\tmargin-left: -8px;\n
\ttop: 50%;\n
\tmargin-top: -8px;\n
}\n
.ui-datepicker .ui-datepicker-title {\n
\tmargin: 0 2.3em;\n
\tline-height: 1.8em;\n
\ttext-align: center;\n
}\n
.ui-datepicker .ui-datepicker-title select {\n
\tfont-size: 1em;\n
\tmargin: 1px 0;\n
}\n
.ui-datepicker select.ui-datepicker-month,\n
.ui-datepicker select.ui-datepicker-year {\n
\twidth: 49%;\n
}\n
.ui-datepicker table {\n
\twidth: 100%;\n
\tfont-size: .9em;\n
\tborder-collapse: collapse;\n
\tmargin: 0 0 .4em;\n
}\n
.ui-datepicker th {\n
\tpadding: .7em .3em;\n
\ttext-align: center;\n
\tfont-weight: bold;\n
\tborder: 0;\n
}\n
.ui-datepicker td {\n
\tborder: 0;\n
\tpadding: 1px;\n
}\n
.ui-datepicker td span,\n
.ui-datepicker td a {\n
\tdisplay: block;\n
\tpadding: .2em;\n
\ttext-align: right;\n
\ttext-decoration: none;\n
}\n
.ui-datepicker .ui-datepicker-buttonpane {\n
\tbackground-image: none;\n
\tmargin: .7em 0 0 0;\n
\tpadding: 0 .2em;\n
\tborder-left: 0;\n
\tborder-right: 0;\n
\tborder-bottom: 0;\n
}\n
.ui-datepicker .ui-datepicker-buttonpane button {\n
\tfloat: right;\n
\tmargin: .5em .2em .4em;\n
\tcursor: pointer;\n
\tpadding: .2em .6em .3em .6em;\n
\twidth: auto;\n
\toverflow: visible;\n
}\n
.ui-datepicker .ui-datepicker-buttonpane button.ui-datepicker-current {\n
\tfloat: left;\n
}\n
\n
/* with multiple calendars */\n
.ui-datepicker.ui-datepicker-multi {\n
\twidth: auto;\n
}\n
.ui-datepicker-multi .ui-datepicker-group {\n
\tfloat: left;\n
}\n
.ui-datepicker-multi .ui-datepicker-group table {\n
\twidth: 95%;\n
\tmargin: 0 auto .4em;\n
}\n
.ui-datepicker-multi-2 .ui-datepicker-group {\n
\twidth: 50%;\n
}\n
.ui-datepicker-multi-3 .ui-datepicker-group {\n
\twidth: 33.3%;\n
}\n
.ui-datepicker-multi-4 .ui-datepicker-group {\n
\twidth: 25%;\n
}\n
.ui-datepicker-multi .ui-datepicker-group-last .ui-datepicker-header,\n
.ui-datepicker-multi .ui-datepicker-group-middle .ui-datepicker-header {\n
\tborder-left-width: 0;\n
}\n
.ui-datepicker-multi .ui-datepicker-buttonpane {\n
\tclear: left;\n
}\n
.ui-datepicker-row-break {\n
\tclear: both;\n
\twidth: 100%;\n
\tfont-size: 0;\n
}\n
\n
/* RTL support */\n
.ui-datepicker-rtl {\n
\tdirection: rtl;\n
}\n
.ui-datepicker-rtl .ui-datepicker-prev {\n
\tright: 2px;\n
\tleft: auto;\n
}\n
.ui-datepicker-rtl .ui-datepicker-next {\n
\tleft: 2px;\n
\tright: auto;\n
}\n
.ui-datepicker-rtl .ui-datepicker-prev:hover {\n
\tright: 1px;\n
\tleft: auto;\n
}\n
.ui-datepicker-rtl .ui-datepicker-next:hover {\n
\tleft: 1px;\n
\tright: auto;\n
}\n
.ui-datepicker-rtl .ui-datepicker-buttonpane {\n
\tclear: right;\n
}\n
.ui-datepicker-rtl .ui-datepicker-buttonpane button {\n
\tfloat: left;\n
}\n
.ui-datepicker-rtl .ui-datepicker-buttonpane button.ui-datepicker-current,\n
.ui-datepicker-rtl .ui-datepicker-group {\n
\tfloat: right;\n
}\n
.ui-datepicker-rtl .ui-datepicker-group-last .ui-datepicker-header,\n
.ui-datepicker-rtl .ui-datepicker-group-middle .ui-datepicker-header {\n
\tborder-right-width: 0;\n
\tborder-left-width: 1px;\n
}\n
.ui-dialog {\n
\toverflow: hidden;\n
\tposition: absolute;\n
\ttop: 0;\n
\tleft: 0;\n
\tpadding: .2em;\n
\toutline: 0;\n
}\n
.ui-dialog .ui-dialog-titlebar {\n
\tpadding: .4em 1em;\n
\tposition: relative;\n
}\n
.ui-dialog .ui-dialog-title {\n
\tfloat: left;\n
\tmargin: .1em 0;\n
\twhite-space: nowrap;\n
\twidth: 90%;\n
\toverflow: hidden;\n
\ttext-overflow: ellipsis;\n
}\n
.ui-dialog .ui-dialog-titlebar-close {\n
\tposition: absolute;\n
\tright: .3em;\n
\ttop: 50%;\n
\twidth: 20px;\n
\tmargin: -10px 0 0 0;\n
\tpadding: 1px;\n
\theight: 20px;\n
}\n
.ui-dialog .ui-dialog-content {\n
\tposition: relative;\n
\tborder: 0;\n
\tpadding: .5em 1em;\n
\tbackground: none;\n
\toverflow: auto;\n
}\n
.ui-dialog .ui-dialog-buttonpane {\n
\ttext-align: left;\n
\tborder-width: 1px 0 0 0;\n
\tbackground-image: none;\n
\tmargin-top: .5em;\n
\tpadding: .3em 1em .5em .4em;\n
}\n
.ui-dialog .ui-dialog-buttonpane .ui-dialog-buttonset {\n
\tfloat: right;\n
}\n
.ui-dialog .ui-dialog-buttonpane button {\n
\tmargin: .5em .4em .5em 0;\n
\tcursor: pointer;\n
}\n
.ui-dialog .ui-resizable-se {\n
\twidth: 12px;\n
\theight: 12px;\n
\tright: -5px;\n
\tbottom: -5px;\n
\tbackground-position: 16px 16px;\n
}\n
.ui-draggable .ui-dialog-titlebar {\n
\tcursor: move;\n
}\n
.ui-draggable-handle {\n
\t-ms-touch-action: none;\n
\ttouch-action: none;\n
}\n
.ui-menu {\n
\tlist-style: none;\n
\tpadding: 0;\n
\tmargin: 0;\n
\tdisplay: block;\n
\toutline: none;\n
}\n
.ui-menu .ui-menu {\n
\tposition: absolute;\n
}\n
.ui-menu .ui-menu-item {\n
\tmargin: 0;\n
\tdisplay: block;\n
\tpadding: 3px .4em;\n
\tcursor: pointer;\n
\tmin-height: 0; /* support: IE7 */\n
\t/* support: IE10, see #8844 */\n
\tlist-style-image: url("data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7");\n
}\n
.ui-menu .ui-menu-divider {\n
\tmargin: 5px 0;\n
\theight: 0;\n
\tfont-size: 0;\n
\tline-height: 0;\n
\tborder-width: 1px 0 0 0;\n
}\n
.ui-menu .ui-state-focus,\n
.ui-menu .ui-state-active {\n
\tmargin: -1px;\n
}\n
\n
/* icon support */\n
.ui-menu-icons {\n
\tposition: relative;\n
}\n
.ui-menu-icons .ui-menu-item {\n
\tposition: relative;\n
\tpadding-left: 2em;\n
}\n
\n
/* left-aligned */\n
.ui-menu .ui-icon {\n
\tposition: absolute;\n
\ttop: .2em;\n
\tleft: .2em;\n
}\n
\n
/* right-aligned */\n
.ui-menu .ui-menu-icon {\n
\tposition: relative;\n
\ttop: -.2em;\n
\tfloat: right;\n
}\n
.ui-progressbar {\n
\theight: 2em;\n
\ttext-align: left;\n
\toverflow: hidden;\n
}\n
.ui-progressbar .ui-progressbar-value {\n
\tmargin: -1px;\n
\theight: 100%;\n
}\n
.ui-progressbar .ui-progressbar-overlay {\n
\tbackground: url("images/animated-overlay.gif");\n
\theight: 100%;\n
\tfilter: alpha(opacity=25);\n
\topacity: 0.25;\n
}\n
.ui-progressbar-indeterminate .ui-progressbar-value {\n
\tbackground-image: none;\n
}\n
.ui-resizable {\n
\tposition: relative;\n
}\n
.ui-resizable-handle {\n
\tposition: absolute;\n
\tfont-size: 0.1px;\n
\tdisplay: block;\n
\t-ms-touch-action: none;\n
\ttouch-action: none;\n
}\n
.ui-resizable-disabled .ui-resizable-handle,\n
.ui-resizable-autohide .ui-resizable-handle {\n
\tdisplay: none;\n
}\n
.ui-resizable-n {\n
\tcursor: n-resize;\n
\theight: 7px;\n
\twidth: 100%;\n
\ttop: -5px;\n
\tleft: 0;\n
}\n
.ui-resizable-s {\n
\tcursor: s-resize;\n
\theight: 7px;\n
\twidth: 100%;\n
\tbottom: -5px;\n
\tleft: 0;\n
}\n
.ui-resizable-e {\n
\tcursor: e-resize;\n
\twidth: 7px;\n
\tright: -5px;\n
\ttop: 0;\n
\theight: 100%;\n
}\n
.ui-resizable-w {\n
\tcursor: w-resize;\n
\twidth: 7px;\n
\tleft: -5px;\n
\ttop: 0;\n
\theight: 100%;\n
}\n
.ui-resizable-se {\n
\tcursor: se-resize;\n
\twidth: 12px;\n
\theight: 12px;\n
\tright: 1px;\n
\tbottom: 1px;\n
}\n
.ui-resizable-sw {\n
\tcursor: sw-resize;\n
\twidth: 9px;\n
\theight: 9px;\n
\tleft: -5px;\n
\tbottom: -5px;\n
}\n
.ui-resizable-nw {\n
\tcursor: nw-resize;\n
\twidth: 9px;\n
\theight: 9px;\n
\tleft: -5px;\n
\ttop: -5px;\n
}\n
.ui-resizable-ne {\n
\tcursor: ne-resize;\n
\twidth: 9px;\n
\theight: 9px;\n
\tright: -5px;\n
\ttop: -5px;\n
}\n
.ui-selectable {\n
\t-ms-touch-action: none;\n
\ttouch-action: none;\n
}\n
.ui-selectable-helper {\n
\tposition: absolute;\n
\tz-index: 100;\n
\tborder: 1px dotted black;\n
}\n
.ui-slider {\n
\tposition: relative;\n
\ttext-align: left;\n
}\n
.ui-slider .ui-slider-handle {\n
\tposition: absolute;\n
\tz-index: 2;\n
\twidth: 1.2em;\n
\theight: 1.2em;\n
\tcursor: default;\n
\t-ms-touch-action: none;\n
\ttouch-action: none;\n
}\n
.ui-slider .ui-slider-range {\n
\tposition: absolute;\n
\tz-index: 1;\n
\tfont-size: .7em;\n
\tdisplay: block;\n
\tborder: 0;\n
\tbackground-position: 0 0;\n
}\n
\n
/* For IE8 - See #6727 */\n
.ui-slider.ui-state-disabled .ui-slider-handle,\n
.ui-slider.ui-state-disabled .ui-slider-range {\n
\tfilter: inherit;\n
}\n
\n
.ui-slider-horizontal {\n
\theight: .8em;\n
}\n
.ui-slider-horizontal .ui-slider-handle {\n
\ttop: -.3em;\n
\tmargin-left: -.6em;\n
}\n
.ui-slider-horizontal .ui-slider-range {\n
\ttop: 0;\n
\theight: 100%;\n
}\n
.ui-slider-horizontal .ui-slider-range-min {\n
\tleft: 0;\n
}\n
.ui-slider-horizontal .ui-slider-range-max {\n
\tright: 0;\n
}\n
\n
.ui-slider-vertical {\n
\twidth: .8em;\n
\theight: 100px;\n
}\n
.ui-slider-vertical .ui-slider-handle {\n
\tleft: -.3em;\n
\tmargin-left: 0;\n
\tmargin-bottom: -.6em;\n
}\n
.ui-slider-vertical .ui-slider-range {\n
\tleft: 0;\n
\twidth: 100%;\n
}\n
.ui-slider-vertical .ui-slider-range-min {\n
\tbottom: 0;\n
}\n
.ui-slider-vertical .ui-slider-range-max {\n
\ttop: 0;\n
}\n
.ui-sortable-handle {\n
\t-ms-touch-action: none;\n
\ttouch-action: none;\n
}\n
.ui-spinner {\n
\tposition: relative;\n
\tdisplay: inline-block;\n
\toverflow: hidden;\n
\tpadding: 0;\n
\tvertical-align: middle;\n
}\n
.ui-spinner-input {\n
\tborder: none;\n
\tbackground: none;\n
\tcolor: inherit;\n
\tpadding: 0;\n
\tmargin: .2em 0;\n
\tvertical-align: middle;\n
\tmargin-left: .4em;\n
\tmargin-right: 22px;\n
}\n
.ui-spinner-button {\n
\twidth: 16px;\n
\theight: 50%;\n
\tfont-size: .5em;\n
\tpadding: 0;\n
\tmargin: 0;\n
\ttext-align: center;\n
\tposition: absolute;\n
\tcursor: default;\n
\tdisplay: block;\n
\toverflow: hidden;\n
\tright: 0;\n
}\n
/* more specificity required here to override default borders */\n
.ui-spinner a.ui-spinner-button {\n
\tborder-top: none;\n
\tborder-bottom: none;\n
\tborder-right: none;\n
}\n
/* vertically center icon */\n
.ui-spinner .ui-icon {\n
\tposition: absolute;\n
\tmargin-top: -8px;\n
\ttop: 50%;\n
\tleft: 0;\n
}\n
.ui-spinner-up {\n
\ttop: 0;\n
}\n
.ui-spinner-down {\n
\tbottom: 0;\n
}\n
\n
/* TR overrides */\n
.ui-spinner .ui-icon-triangle-1-s {\n
\t/* need to fix icons sprite */\n
\tbackground-position: -65px -16px;\n
}\n
.ui-tabs {\n
\tposition: relative;/* position: relative prevents IE scroll bug (element with position: relative inside container with overflow: auto appear as "fixed") */\n
\tpadding: .2em;\n
}\n
.ui-tabs .ui-tabs-nav {\n
\tmargin: 0;\n
\tpadding: .2em .2em 0;\n
}\n
.ui-tabs .ui-tabs-nav li {\n
\tlist-style: none;\n
\tfloat: left;\n
\tposition: relative;\n
\ttop: 0;\n
\tmargin: 1px .2em 0 0;\n
\tborder-bottom-width: 0;\n
\tpadding: 0;\n
\twhite-space: nowrap;\n
}\n
.ui-tabs .ui-tabs-nav .ui-tabs-anchor {\n
\tfloat: left;\n
\tpadding: .5em 1em;\n
\ttext-decoration: none;\n
}\n
.ui-tabs .ui-tabs-nav li.ui-tabs-active {\n
\tmargin-bottom: -1px;\n
\tpadding-bottom: 1px;\n
}\n
.ui-tabs .ui-tabs-nav li.ui-tabs-active .ui-tabs-anchor,\n
.ui-tabs .ui-tabs-nav li.ui-state-disabled .ui-tabs-anchor,\n
.ui-tabs .ui-tabs-nav li.ui-tabs-loading .ui-tabs-anchor {\n
\tcursor: text;\n
}\n
.ui-tabs-collapsible .ui-tabs-nav li.ui-tabs-active .ui-tabs-anchor {\n
\tcursor: pointer;\n
}\n
.ui-tabs .ui-tabs-panel {\n
\tdisplay: block;\n
\tborder-width: 0;\n
\tpadding: 1em 1.4em;\n
\tbackground: none;\n
}\n
.ui-tooltip {\n
\tpadding: 8px;\n
\tposition: absolute;\n
\tz-index: 9999;\n
\tmax-width: 300px;\n
\t-webkit-box-shadow: 0 0 5px #aaa;\n
\tbox-shadow: 0 0 5px #aaa;\n
}\n
body .ui-tooltip {\n
\tborder-width: 2px;\n
}\n
\n
/* Component containers\n
----------------------------------*/\n
.ui-widget {\n
\tfont-family: Verdana,Arial,sans-serif/*{ffDefault}*/;\n
\tfont-size: 1.1em/*{fsDefault}*/;\n
}\n
.ui-widget .ui-widget {\n
\tfont-size: 1em;\n
}\n
.ui-widget input,\n
.ui-widget select,\n
.ui-widget textarea,\n
.ui-widget button {\n
\tfont-family: Verdana,Arial,sans-serif/*{ffDefault}*/;\n
\tfont-size: 1em;\n
}\n
.ui-widget-content {\n
\tborder: 1px solid #aaaaaa/*{borderColorContent}*/;\n
\tbackground: #ffffff/*{bgColorContent}*/ url("images/ui-bg_flat_75_ffffff_40x100.png")/*{bgImgUrlContent}*/ 50%/*{bgContentXPos}*/ 50%/*{bgContentYPos}*/ repeat-x/*{bgContentRepeat}*/;\n
\tcolor: #222222/*{fcContent}*/;\n
}\n
.ui-widget-content a {\n
\tcolor: #222222/*{fcContent}*/;\n
}\n
.ui-widget-header {\n
\tborder: 1px solid #aaaaaa/*{borderColorHeader}*/;\n
\tbackground: #cccccc/*{bgColorHeader}*/ url("images/ui-bg_highlight-soft_75_cccccc_1x100.png")/*{bgImgUrlHeader}*/ 50%/*{bgHeaderXPos}*/ 50%/*{bgHeaderYPos}*/ repeat-x/*{bgHeaderRepeat}*/;\n
\tcolor: #222222/*{fcHeader}*/;\n
\tfont-weight: bold;\n
}\n
.ui-widget-header a {\n
\tcolor: #222222/*{fcHeader}*/;\n
}\n
\n
/* Interaction states\n
----------------------------------*/\n
.ui-state-default,\n
.ui-widget-content .ui-state-default,\n
.ui-widget-header .ui-state-default {\n
\tborder: 1px solid #d3d3d3/*{borderColorDefault}*/;\n
\tbackground: #e6e6e6/*{bgColorDefault}*/ url("images/ui-bg_glass_75_e6e6e6_1x400.png")/*{bgImgUrlDefault}*/ 50%/*{bgDefaultXPos}*/ 50%/*{bgDefaultYPos}*/ repeat-x/*{bgDefaultRepeat}*/;\n
\tfont-weight: normal/*{fwDefault}*/;\n
\tcolor: #555555/*{fcDefault}*/;\n
}\n
.ui-state-default a,\n
.ui-state-default a:link,\n
.ui-state-default a:visited {\n
\tcolor: #555555/*{fcDefault}*/;\n
\ttext-decoration: none;\n
}\n
.ui-state-hover,\n
.ui-widget-content .ui-state-hover,\n
.ui-widget-header .ui-state-hover,\n
.ui-state-focus,\n
.ui-widget-content .ui-state-focus,\n
.ui-widget-header .ui-state-focus {\n
\tborder: 1px solid #999999/*{borderColorHover}*/;\n
\tbackground: #dadada/*{bgColorHover}*/ url("images/ui-bg_glass_75_dadada_1x400.png")/*{bgImgUrlHover}*/ 50%/*{bgHoverXPos}*/ 50%/*{bgHoverYPos}*/ repeat-x/*{bgHoverRepeat}*/;\n
\tfont-weight: normal/*{fwDefault}*/;\n
\tcolor: #212121/*{fcHover}*/;\n
}\n
.ui-state-hover a,\n
.ui-state-hover a:hover,\n
.ui-state-hover a:link,\n
.ui-state-hover a:visited,\n
.ui-state-focus a,\n
.ui-state-focus a:hover,\n
.ui-state-focus a:link,\n
.ui-state-focus a:visited {\n
\tcolor: #212121/*{fcHover}*/;\n
\ttext-decoration: none;\n
}\n
.ui-state-active,\n
.ui-widget-content .ui-state-active,\n
.ui-widget-header .ui-state-active {\n
\tborder: 1px solid #aaaaaa/*{borderColorActive}*/;\n
\tbackground: #ffffff/*{bgColorActive}*/ url("images/ui-bg_glass_65_ffffff_1x400.png")/*{bgImgUrlActive}*/ 50%/*{bgActiveXPos}*/ 50%/*{bgActiveYPos}*/ repeat-x/*{bgActiveRepeat}*/;\n
\tfont-weight: normal/*{fwDefault}*/;\n
\tcolor: #212121/*{fcActive}*/;\n
}\n
.ui-state-active a,\n
.ui-state-active a:link,\n
.ui-state-active a:visited {\n
\tcolor: #212121/*{fcActive}*/;\n
\ttext-decoration: none;\n
}\n
\n
/* Interaction Cues\n
----------------------------------*/\n
.ui-state-highlight,\n
.ui-widget-content .ui-state-highlight,\n
.ui-widget-header .ui-state-highlight {\n
\tborder: 1px solid #fcefa1/*{borderColorHighlight}*/;\n
\tbackground: #fbf9ee/*{bgColorHighlight}*/ url("images/ui-bg_glass_55_fbf9ee_1x400.png")/*{bgImgUrlHighlight}*/ 50%/*{bgHighlightXPos}*/ 50%/*{bgHighlightYPos}*/ repeat-x/*{bgHighlightRepeat}*/;\n
\tcolor: #363636/*{fcHighlight}*/;\n
}\n
.ui-state-highlight a,\n
.ui-widget-content .ui-state-highlight a,\n
.ui-widget-header .ui-state-highlight a {\n
\tcolor: #363636/*{fcHighlight}*/;\n
}\n
.ui-state-error,\n
.ui-widget-content .ui-state-error,\n
.ui-widget-header .ui-state-error {\n
\tborder: 1px solid #cd0a0a/*{borderColorError}*/;\n
\tbackground: #fef1ec/*{bgColorError}*/ url("images/ui-bg_glass_95_fef1ec_1x400.png")/*{bgImgUrlError}*/ 50%/*{bgErrorXPos}*/ 50%/*{bgErrorYPos}*/ repeat-x/*{bgErrorRepeat}*/;\n
\tcolor: #cd0a0a/*{fcError}*/;\n
}\n
.ui-state-error a,\n
.ui-widget-content .ui-state-error a,\n
.ui-widget-header .ui-state-error a {\n
\tcolor: #cd0a0a/*{fcError}*/;\n
}\n
.ui-state-error-text,\n
.ui-widget-content .ui-state-error-text,\n
.ui-widget-header .ui-state-error-text {\n
\tcolor: #cd0a0a/*{fcError}*/;\n
}\n
.ui-priority-primary,\n
.ui-widget-content .ui-priority-primary,\n
.ui-widget-header .ui-priority-primary {\n
\tfont-weight: bold;\n
}\n
.ui-priority-secondary,\n
.ui-widget-content .ui-priority-secondary,\n
.ui-widget-header .ui-priority-secondary {\n
\topacity: .7;\n
\tfilter:Alpha(Opacity=70);\n
\tfont-weight: normal;\n
}\n
.ui-state-disabled,\n
.ui-widget-content .ui-state-disabled,\n
.ui-widget-header .ui-state-disabled {\n
\topacity: .35;\n
\tfilter:Alpha(Opacity=35);\n
\tbackground-image: none;\n
}\n
.ui-state-disabled .ui-icon {\n
\tfilter:Alpha(Opacity=35); /* For IE8 - See #6059 */\n
}\n
\n
/* Icons\n
----------------------------------*/\n
\n
/* states and images */\n
.ui-icon {\n
\twidth: 16px;\n
\theight: 16px;\n
}\n
.ui-icon,\n
.ui-widget-content .ui-icon {\n
\tbackground-image: url("images/ui-icons_222222_256x240.png")/*{iconsContent}*/;\n
}\n
.ui-widget-header .ui-icon {\n
\tbackground-image: url("images/ui-icons_222222_256x240.png")/*{iconsHeader}*/;\n
}\n
.ui-state-default .ui-icon {\n
\tbackground-image: url("images/ui-icons_888888_256x240.png")/*{iconsDefault}*/;\n
}\n
.ui-state-hover .ui-icon,\n
.ui-state-focus .ui-icon {\n
\tbackground-image: url("images/ui-icons_454545_256x240.png")/*{iconsHover}*/;\n
}\n
.ui-state-active .ui-icon {\n
\tbackground-image: url("images/ui-icons_454545_256x240.png")/*{iconsActive}*/;\n
}\n
.ui-state-highlight .ui-icon {\n
\tbackground-image: url("images/ui-icons_2e83ff_256x240.png")/*{iconsHighlight}*/;\n
}\n
.ui-state-error .ui-icon,\n
.ui-state-error-text .ui-icon {\n
\tbackground-image: url("images/ui-icons_cd0a0a_256x240.png")/*{iconsError}*/;\n
}\n
\n
/* positioning */\n
.ui-icon-blank { background-position: 16px 16px; }\n
.ui-icon-carat-1-n { background-position: 0 0; }\n
.ui-icon-carat-1-ne { background-position: -16px 0; }\n
.ui-icon-carat-1-e { background-position: -32px 0; }\n
.ui-icon-carat-1-se { background-position: -48px 0; }\n
.ui-icon-carat-1-s { background-position: -64px 0; }\n
.ui-icon-carat-1-sw { background-position: -80px 0; }\n
.ui-icon-carat-1-w { background-position: -96px 0; }\n
.ui-icon-carat-1-nw { background-position: -112px 0; }\n
.ui-icon-carat-2-n-s { background-position: -128px 0; }\n
.ui-icon-carat-2-e-w { background-position: -144px 0; }\n
.ui-icon-triangle-1-n { background-position: 0 -16px; }\n
.ui-icon-triangle-1-ne { background-position: -16px -16px; }\n
.ui-icon-triangle-1-e { background-position: -32px -16px; }\n
.ui-icon-triangle-1-se { background-position: -48px -16px; }\n
.ui-icon-triangle-1-s { background-position: -64px -16px; }\n
.ui-icon-triangle-1-sw { background-position: -80px -16px; }\n
.ui-icon-triangle-1-w { background-position: -96px -16px; }\n
.ui-icon-triangle-1-nw { background-position: -112px -16px; }\n
.ui-icon-triangle-2-n-s { background-position: -128px -16px; }\n
.ui-icon-triangle-2-e-w { background-position: -144px -16px; }\n
.ui-icon-arrow-1-n { background-position: 0 -32px; }\n
.ui-icon-arrow-1-ne { background-position: -16px -32px; }\n
.ui-icon-arrow-1-e { background-position: -32px -32px; }\n
.ui-icon-arrow-1-se { background-position: -48px -32px; }\n
.ui-icon-arrow-1-s { background-position: -64px -32px; }\n
.ui-icon-arrow-1-sw { background-position: -80px -32px; }\n
.ui-icon-arrow-1-w { background-position: -96px -32px; }\n
.ui-icon-arrow-1-nw { background-position: -112px -32px; }\n
.ui-icon-arrow-2-n-s { background-position: -128px -32px; }\n
.ui-icon-arrow-2-ne-sw { background-position: -144px -32px; }\n
.ui-icon-arrow-2-e-w { background-position: -160px -32px; }\n
.ui-icon-arrow-2-se-nw { background-position: -176px -32px; }\n
.ui-icon-arrowstop-1-n { background-position: -192px -32px; }\n
.ui-icon-arrowstop-1-e { background-position: -208px -32px; }\n
.ui-icon-arrowstop-1-s { background-position: -224px -32px; }\n
.ui-icon-arrowstop-1-w { background-position: -240px -32px; }\n
.ui-icon-arrowthick-1-n { background-position: 0 -48px; }\n
.ui-icon-arrowthick-1-ne { background-position: -16px -48px; }\n
.ui-icon-arrowthick-1-e { background-position: -32px -48px; }\n
.ui-icon-arrowthick-1-se { background-position: -48px -48px; }\n
.ui-icon-arrowthick-1-s { background-position: -64px -48px; }\n
.ui-icon-arrowthick-1-sw { background-position: -80px -48px; }\n
.ui-icon-arrowthick-1-w { background-position: -96px -48px; }\n
.ui-icon-arrowthick-1-nw { background-position: -112px -48px; }\n
.ui-icon-arrowthick-2-n-s { background-position: -128px -48px; }\n
.ui-icon-arrowthick-2-ne-sw { background-position: -144px -48px; }\n
.ui-icon-arrowthick-2-e-w { background-position: -160px -48px; }\n
.ui-icon-arrowthick-2-se-nw { background-position: -176px -48px; }\n
.ui-icon-arrowthickstop-1-n { background-position: -192px -48px; }\n
.ui-icon-arrowthickstop-1-e { background-position: -208px -48px; }\n
.ui-icon-arrowthickstop-1-s { background-position: -224px -48px; }\n
.ui-icon-arrowthickstop-1-w { background-position: -240px -48px; }\n
.ui-icon-arrowreturnthick-1-w { background-position: 0 -64px; }\n
.ui-icon-arrowreturnthick-1-n { background-position: -16px -64px; }\n
.ui-icon-arrowreturnthick-1-e { background-position: -32px -64px; }\n
.ui-icon-arrowreturnthick-1-s { background-position: -48px -64px; }\n
.ui-icon-arrowreturn-1-w { background-position: -64px -64px; }\n
.ui-icon-arrowreturn-1-n { background-position: -80px -64px; }\n
.ui-icon-arrowreturn-1-e { background-position: -96px -64px; }\n
.ui-icon-arrowreturn-1-s { background-position: -112px -64px; }\n
.ui-icon-arrowrefresh-1-w { background-position: -128px -64px; }\n
.ui-icon-arrowrefresh-1-n { background-position: -144px -64px; }\n
.ui-icon-arrowrefresh-1-e { background-position: -160px -64px; }\n
.ui-icon-arrowrefresh-1-s { background-position: -176px -64px; }\n
.ui-icon-arrow-4 { background-position: 0 -80px; }\n
.ui-icon-arrow-4-diag { background-position: -16px -80px; }\n
.ui-icon-extlink { background-position: -32px -80px; }\n
.ui-icon-newwin { background-position: -48px -80px; }\n
.ui-icon-refresh { background-position: -64px -80px; }\n
.ui-icon-shuffle { background-position: -80px -80px; }\n
.ui-icon-transfer-e-w { background-position: -96px -80px; }\n
.ui-icon-transferthick-e-w { background-position: -112px -80px; }\n
.ui-icon-folder-collapsed { background-position: 0 -96px; }\n
.ui-icon-folder-open { background-position: -16px -96px; }\n
.ui-icon-document { background-position: -32px -96px; }\n
.ui-icon-document-b { background-position: -48px -96px; }\n
.ui-icon-note { background-position: -64px -96px; }\n
.ui-icon-mail-closed { background-position: -80px -96px; }\n
.ui-icon-mail-open { background-position: -96px -96px; }\n
.ui-icon-suitcase { background-position: -112px -96px; }\n
.ui-icon-comment { background-position: -128px -96px; }\n
.ui-icon-person { background-position: -144px -96px; }\n
.ui-icon-print { background-position: -160px -96px; }\n
.ui-icon-trash { background-position: -176px -96px; }\n
.ui-icon-locked { background-position: -192px -96px; }\n
.ui-icon-unlocked { background-position: -208px -96px; }\n
.ui-icon-bookmark { background-position: -224px -96px; }\n
.ui-icon-tag { background-position: -240px -96px; }\n
.ui-icon-home { background-position: 0 -112px; }\n
.ui-icon-flag { background-position: -16px -112px; }\n
.ui-icon-calendar { background-position: -32px -112px; }\n
.ui-icon-cart { background-position: -48px -112px; }\n
.ui-icon-pencil { background-position: -64px -112px; }\n
.ui-icon-clock { background-position: -80px -112px; }\n
.ui-icon-disk { background-position: -96px -112px; }\n
.ui-icon-calculator { background-position: -112px -112px; }\n
.ui-icon-zoomin { background-position: -128px -112px; }\n
.ui-icon-zoomout { background-position: -144px -112px; }\n
.ui-icon-search { background-position: -160px -112px; }\n
.ui-icon-wrench { background-position: -176px -112px; }\n
.ui-icon-gear { background-position: -192px -112px; }\n
.ui-icon-heart { background-position: -208px -112px; }\n
.ui-icon-star { background-position: -224px -112px; }\n
.ui-icon-link { background-position: -240px -112px; }\n
.ui-icon-cancel { background-position: 0 -128px; }\n
.ui-icon-plus { background-position: -16px -128px; }\n
.ui-icon-plusthick { background-position: -32px -128px; }\n
.ui-icon-minus { background-position: -48px -128px; }\n
.ui-icon-minusthick { background-position: -64px -128px; }\n
.ui-icon-close { background-position: -80px -128px; }\n
.ui-icon-closethick { background-position: -96px -128px; }\n
.ui-icon-key { background-position: -112px -128px; }\n
.ui-icon-lightbulb { background-position: -128px -128px; }\n
.ui-icon-scissors { background-position: -144px -128px; }\n
.ui-icon-clipboard { background-position: -160px -128px; }\n
.ui-icon-copy { background-position: -176px -128px; }\n
.ui-icon-contact { background-position: -192px -128px; }\n
.ui-icon-image { background-position: -208px -128px; }\n
.ui-icon-video { background-position: -224px -128px; }\n
.ui-icon-script { background-position: -240px -128px; }\n
.ui-icon-alert { background-position: 0 -144px; }\n
.ui-icon-info { background-position: -16px -144px; }\n
.ui-icon-notice { background-position: -32px -144px; }\n
.ui-icon-help { background-position: -48px -144px; }\n
.ui-icon-check { background-position: -64px -144px; }\n
.ui-icon-bullet { background-position: -80px -144px; }\n
.ui-icon-radio-on { background-position: -96px -144px; }\n
.ui-icon-radio-off { background-position: -112px -144px; }\n
.ui-icon-pin-w { background-position: -128px -144px; }\n
.ui-icon-pin-s { background-position: -144px -144px; }\n
.ui-icon-play { background-position: 0 -160px; }\n
.ui-icon-pause { background-position: -16px -160px; }\n
.ui-icon-seek-next { background-position: -32px -160px; }\n
.ui-icon-seek-prev { background-position: -48px -160px; }\n
.ui-icon-seek-end { background-position: -64px -160px; }\n
.ui-icon-seek-start { background-position: -80px -160px; }\n
/* ui-icon-seek-first is deprecated, use ui-icon-seek-start instead */\n
.ui-icon-seek-first { background-position: -80px -160px; }\n
.ui-icon-stop { background-position: -96px -160px; }\n
.ui-icon-eject { background-position: -112px -160px; }\n
.ui-icon-volume-off { background-position: -128px -160px; }\n
.ui-icon-volume-on { background-position: -144px -160px; }\n
.ui-icon-power { background-position: 0 -176px; }\n
.ui-icon-signal-diag { background-position: -16px -176px; }\n
.ui-icon-signal { background-position: -32px -176px; }\n
.ui-icon-battery-0 { background-position: -48px -176px; }\n
.ui-icon-battery-1 { background-position: -64px -176px; }\n
.ui-icon-battery-2 { background-position: -80px -176px; }\n
.ui-icon-battery-3 { background-position: -96px -176px; }\n
.ui-icon-circle-plus { background-position: 0 -192px; }\n
.ui-icon-circle-minus { background-position: -16px -192px; }\n
.ui-icon-circle-close { background-position: -32px -192px; }\n
.ui-icon-circle-triangle-e { background-position: -48px -192px; }\n
.ui-icon-circle-triangle-s { background-position: -64px -192px; }\n
.ui-icon-circle-triangle-w { background-position: -80px -192px; }\n
.ui-icon-circle-triangle-n { background-position: -96px -192px; }\n
.ui-icon-circle-arrow-e { background-position: -112px -192px; }\n
.ui-icon-circle-arrow-s { background-position: -128px -192px; }\n
.ui-icon-circle-arrow-w { background-position: -144px -192px; }\n
.ui-icon-circle-arrow-n { background-position: -160px -192px; }\n
.ui-icon-circle-zoomin { background-position: -176px -192px; }\n
.ui-icon-circle-zoomout { background-position: -192px -192px; }\n
.ui-icon-circle-check { background-position: -208px -192px; }\n
.ui-icon-circlesmall-plus { background-position: 0 -208px; }\n
.ui-icon-circlesmall-minus { background-position: -16px -208px; }\n
.ui-icon-circlesmall-close { background-position: -32px -208px; }\n
.ui-icon-squaresmall-plus { background-position: -48px -208px; }\n
.ui-icon-squaresmall-minus { background-position: -64px -208px; }\n
.ui-icon-squaresmall-close { background-position: -80px -208px; }\n
.ui-icon-grip-dotted-vertical { background-position: 0 -224px; }\n
.ui-icon-grip-dotted-horizontal { background-position: -16px -224px; }\n
.ui-icon-grip-solid-vertical { background-position: -32px -224px; }\n
.ui-icon-grip-solid-horizontal { background-position: -48px -224px; }\n
.ui-icon-gripsmall-diagonal-se { background-position: -64px -224px; }\n
.ui-icon-grip-diagonal-se { background-position: -80px -224px; }\n
\n
\n
/* Misc visuals\n
----------------------------------*/\n
\n
/* Corner radius */\n
.ui-corner-all,\n
.ui-corner-top,\n
.ui-corner-left,\n
.ui-corner-tl {\n
\tborder-top-left-radius: 4px/*{cornerRadius}*/;\n
}\n
.ui-corner-all,\n
.ui-corner-top,\n
.ui-corner-right,\n
.ui-corner-tr {\n
\tborder-top-right-radius: 4px/*{cornerRadius}*/;\n
}\n
.ui-corner-all,\n
.ui-corner-bottom,\n
.ui-corner-left,\n
.ui-corner-bl {\n
\tborder-bottom-left-radius: 4px/*{cornerRadius}*/;\n
}\n
.ui-corner-all,\n
.ui-corner-bottom,\n
.ui-corner-right,\n
.ui-corner-br {\n
\tborder-bottom-right-radius: 4px/*{cornerRadius}*/;\n
}\n
\n
/* Overlays */\n
.ui-widget-overlay {\n
\tbackground: #aaaaaa/*{bgColorOverlay}*/ url("images/ui-bg_flat_0_aaaaaa_40x100.png")/*{bgImgUrlOverlay}*/ 50%/*{bgOverlayXPos}*/ 50%/*{bgOverlayYPos}*/ repeat-x/*{bgOverlayRepeat}*/;\n
\topacity: .3/*{opacityOverlay}*/;\n
\tfilter: Alpha(Opacity=30)/*{opacityFilterOverlay}*/;\n
}\n
.ui-widget-shadow {\n
\tmargin: -8px/*{offsetTopShadow}*/ 0 0 -8px/*{offsetLeftShadow}*/;\n
\tpadding: 8px/*{thicknessShadow}*/;\n
\tbackground: #aaaaaa/*{bgColorShadow}*/ url("images/ui-bg_flat_0_aaaaaa_40x100.png")/*{bgImgUrlShadow}*/ 50%/*{bgShadowXPos}*/ 50%/*{bgShadowYPos}*/ repeat-x/*{bgShadowRepeat}*/;\n
\topacity: .3/*{opacityShadow}*/;\n
\tfilter: Alpha(Opacity=30)/*{opacityFilterShadow}*/;\n
\tborder-radius: 8px/*{cornerRadiusShadow}*/;\n
}\n
</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>32251</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
This source diff could not be displayed because it is too large. You can view the blob instead.
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570616.72</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>jquery.simulate.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
/*\n
* jquery.simulate - simulate browser mouse and keyboard events\n
*\n
* Copyright (c) 2009 Eduardo Lundgren (eduardolundgren@gmail.com)\n
* and Richard D. Worth (rdworth@gmail.com)\n
*\n
* Dual licensed under the MIT (http://www.opensource.org/licenses/mit-license.php) \n
* and GPL (http://www.opensource.org/licenses/gpl-license.php) licenses.\n
*\n
*/\n
\n
;(function($) {\n
\n
$.fn.extend({\n
\tsimulate: function(type, options) {\n
\t\treturn this.each(function() {\n
\t\t\tvar opt = $.extend({}, $.simulate.defaults, options || {});\n
\t\t\tnew $.simulate(this, type, opt);\n
\t\t});\n
\t}\n
});\n
\n
$.simulate = function(el, type, options) {\n
\tthis.target = el;\n
\tthis.options = options;\n
\n
\tif (/^drag$/.test(type)) {\n
\t\tthis[type].apply(this, [this.target, options]);\n
\t} else {\n
\t\tthis.simulateEvent(el, type, options);\n
\t}\n
};\n
\n
$.extend($.simulate.prototype, {\n
\tsimulateEvent: function(el, type, options) {\n
\t\tvar evt = this.createEvent(type, options);\n
\t\tthis.dispatchEvent(el, type, evt, options);\n
\t\treturn evt;\n
\t},\n
\tcreateEvent: function(type, options) {\n
\t\tif (/^mouse(over|out|down|up|move)|(dbl)?click$/.test(type)) {\n
\t\t\treturn this.mouseEvent(type, options);\n
\t\t} else if (/^key(up|down|press)$/.test(type)) {\n
\t\t\treturn this.keyboardEvent(type, options);\n
\t\t}\n
\t},\n
\tmouseEvent: function(type, options) {\n
\t\tvar evt;\n
\t\tvar e = $.extend({\n
\t\t\tbubbles: true, cancelable: (type != "mousemove"), view: window, detail: 0,\n
\t\t\tscreenX: 0, screenY: 0, clientX: 0, clientY: 0,\n
\t\t\tctrlKey: false, altKey: false, shiftKey: false, metaKey: false,\n
\t\t\tbutton: 0, relatedTarget: undefined\n
\t\t}, options);\n
\n
\t\tvar relatedTarget = $(e.relatedTarget)[0];\n
\n
\t\tif ($.isFunction(document.createEvent)) {\n
\t\t\tevt = document.createEvent("MouseEvents");\n
\t\t\tevt.initMouseEvent(type, e.bubbles, e.cancelable, e.view, e.detail,\n
\t\t\t\te.screenX, e.screenY, e.clientX, e.clientY,\n
\t\t\t\te.ctrlKey, e.altKey, e.shiftKey, e.metaKey,\n
\t\t\t\te.button, e.relatedTarget || document.body.parentNode);\n
\t\t} else if (document.createEventObject) {\n
\t\t\tevt = document.createEventObject();\n
\t\t\t$.extend(evt, e);\n
\t\t\tevt.button = { 0:1, 1:4, 2:2 }[evt.button] || evt.button;\n
\t\t}\n
\t\treturn evt;\n
\t},\n
\tkeyboardEvent: function(type, options) {\n
\t\tvar evt;\n
\n
\t\tvar e = $.extend({ bubbles: true, cancelable: true, view: window,\n
\t\t\tctrlKey: false, altKey: false, shiftKey: false, metaKey: false,\n
\t\t\tkeyCode: 0, charCode: 0\n
\t\t}, options);\n
\n
\t\tif ($.isFunction(document.createEvent)) {\n
\t\t\ttry {\n
\t\t\t\tevt = document.createEvent("KeyEvents");\n
\t\t\t\tevt.initKeyEvent(type, e.bubbles, e.cancelable, e.view,\n
\t\t\t\t\te.ctrlKey, e.altKey, e.shiftKey, e.metaKey,\n
\t\t\t\t\te.keyCode, e.charCode);\n
\t\t\t} catch(err) {\n
\t\t\t\tevt = document.createEvent("Events");\n
\t\t\t\tevt.initEvent(type, e.bubbles, e.cancelable);\n
\t\t\t\t$.extend(evt, { view: e.view,\n
\t\t\t\t\tctrlKey: e.ctrlKey, altKey: e.altKey, shiftKey: e.shiftKey, metaKey: e.metaKey,\n
\t\t\t\t\tkeyCode: e.keyCode, charCode: e.charCode\n
\t\t\t\t});\n
\t\t\t}\n
\t\t} else if (document.createEventObject) {\n
\t\t\tevt = document.createEventObject();\n
\t\t\t$.extend(evt, e);\n
\t\t}\n
\t\tif (($.browser !== undefined) && ($.browser.msie || $.browser.opera)) {\n
\t\t\tevt.keyCode = (e.charCode > 0) ? e.charCode : e.keyCode;\n
\t\t\tevt.charCode = undefined;\n
\t\t}\n
\t\treturn evt;\n
\t},\n
\n
\tdispatchEvent: function(el, type, evt) {\n
\t\tif (el.dispatchEvent) {\n
\t\t\tel.dispatchEvent(evt);\n
\t\t} else if (el.fireEvent) {\n
\t\t\tel.fireEvent(\'on\' + type, evt);\n
\t\t}\n
\t\treturn evt;\n
\t},\n
\n
\tdrag: function(el) {\n
\t\tvar self = this, center = this.findCenter(this.target), \n
\t\t\toptions = this.options,\tx = Math.floor(center.x), y = Math.floor(center.y), \n
\t\t\tdx = options.dx || 0, dy = options.dy || 0, target = this.target;\n
\t\tvar coord = { clientX: x, clientY: y };\n
\t\tthis.simulateEvent(target, "mousedown", coord);\n
\t\tcoord = { clientX: x + 1, clientY: y + 1 };\n
\t\tthis.simulateEvent(document, "mousemove", coord);\n
\t\tcoord = { clientX: x + dx, clientY: y + dy };\n
\t\tthis.simulateEvent(document, "mousemove", coord);\n
\t\tthis.simulateEvent(document, "mousemove", coord);\n
\t\tthis.simulateEvent(target, "mouseup", coord);\n
\t},\n
\tfindCenter: function(el) {\n
\t\tvar el = $(this.target), o = el.offset();\n
\t\treturn {\n
\t\t\tx: o.left + el.outerWidth() / 2,\n
\t\t\ty: o.top + el.outerHeight() / 2\n
\t\t};\n
\t}\n
});\n
\n
$.extend($.simulate, {\n
\tdefaults: {\n
\t\tspeed: \'sync\'\n
\t},\n
\tVK_TAB: 9,\n
\tVK_ENTER: 13,\n
\tVK_ESC: 27,\n
\tVK_PGUP: 33,\n
\tVK_PGDN: 34,\n
\tVK_END: 35,\n
\tVK_HOME: 36,\n
\tVK_LEFT: 37,\n
\tVK_UP: 38,\n
\tVK_RIGHT: 39,\n
\tVK_DOWN: 40\n
});\n
\n
})(jQuery);\n
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>4340</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570623.34</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>qunit.css</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>text/css</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
/*!\n
* QUnit 1.17.1\n
* http://qunitjs.com/\n
*\n
* Copyright jQuery Foundation and other contributors\n
* Released under the MIT license\n
* http://jquery.org/license\n
*\n
* Date: 2015-01-20T19:39Z\n
*/\n
\n
/** Font Family and Sizes */\n
\n
#qunit-tests, #qunit-header, #qunit-banner, #qunit-testrunner-toolbar, #qunit-userAgent, #qunit-testresult {\n
\tfont-family: "Helvetica Neue Light", "HelveticaNeue-Light", "Helvetica Neue", Calibri, Helvetica, Arial, sans-serif;\n
}\n
\n
#qunit-testrunner-toolbar, #qunit-userAgent, #qunit-testresult, #qunit-tests li { font-size: small; }\n
#qunit-tests { font-size: smaller; }\n
\n
\n
/** Resets */\n
\n
#qunit-tests, #qunit-header, #qunit-banner, #qunit-userAgent, #qunit-testresult, #qunit-modulefilter {\n
\tmargin: 0;\n
\tpadding: 0;\n
}\n
\n
\n
/** Header */\n
\n
#qunit-header {\n
\tpadding: 0.5em 0 0.5em 1em;\n
\n
\tcolor: #8699A4;\n
\tbackground-color: #0D3349;\n
\n
\tfont-size: 1.5em;\n
\tline-height: 1em;\n
\tfont-weight: 400;\n
\n
\tborder-radius: 5px 5px 0 0;\n
}\n
\n
#qunit-header a {\n
\ttext-decoration: none;\n
\tcolor: #C2CCD1;\n
}\n
\n
#qunit-header a:hover,\n
#qunit-header a:focus {\n
\tcolor: #FFF;\n
}\n
\n
#qunit-testrunner-toolbar label {\n
\tdisplay: inline-block;\n
\tpadding: 0 0.5em 0 0.1em;\n
}\n
\n
#qunit-banner {\n
\theight: 5px;\n
}\n
\n
#qunit-testrunner-toolbar {\n
\tpadding: 0.5em 1em 0.5em 1em;\n
\tcolor: #5E740B;\n
\tbackground-color: #EEE;\n
\toverflow: hidden;\n
}\n
\n
#qunit-userAgent {\n
\tpadding: 0.5em 1em 0.5em 1em;\n
\tbackground-color: #2B81AF;\n
\tcolor: #FFF;\n
\ttext-shadow: rgba(0, 0, 0, 0.5) 2px 2px 1px;\n
}\n
\n
#qunit-modulefilter-container {\n
\tfloat: right;\n
\tpadding: 0.2em;\n
}\n
\n
.qunit-url-config {\n
\tdisplay: inline-block;\n
\tpadding: 0.1em;\n
}\n
\n
.qunit-filter {\n
\tdisplay: block;\n
\tfloat: right;\n
\tmargin-left: 1em;\n
}\n
\n
/** Tests: Pass/Fail */\n
\n
#qunit-tests {\n
\tlist-style-position: inside;\n
}\n
\n
#qunit-tests li {\n
\tpadding: 0.4em 1em 0.4em 1em;\n
\tborder-bottom: 1px solid #FFF;\n
\tlist-style-position: inside;\n
}\n
\n
#qunit-tests > li {\n
\tdisplay: none;\n
}\n
\n
#qunit-tests li.running,\n
#qunit-tests li.pass,\n
#qunit-tests li.fail,\n
#qunit-tests li.skipped {\n
\tdisplay: list-item;\n
}\n
\n
#qunit-tests.hidepass li.running,\n
#qunit-tests.hidepass li.pass {\n
\tdisplay: none;\n
}\n
\n
#qunit-tests li strong {\n
\tcursor: pointer;\n
}\n
\n
#qunit-tests li.skipped strong {\n
\tcursor: default;\n
}\n
\n
#qunit-tests li a {\n
\tpadding: 0.5em;\n
\tcolor: #C2CCD1;\n
\ttext-decoration: none;\n
}\n
#qunit-tests li a:hover,\n
#qunit-tests li a:focus {\n
\tcolor: #000;\n
}\n
\n
#qunit-tests li .runtime {\n
\tfloat: right;\n
\tfont-size: smaller;\n
}\n
\n
.qunit-assert-list {\n
\tmargin-top: 0.5em;\n
\tpadding: 0.5em;\n
\n
\tbackground-color: #FFF;\n
\n
\tborder-radius: 5px;\n
}\n
\n
.qunit-collapsed {\n
\tdisplay: none;\n
}\n
\n
#qunit-tests table {\n
\tborder-collapse: collapse;\n
\tmargin-top: 0.2em;\n
}\n
\n
#qunit-tests th {\n
\ttext-align: right;\n
\tvertical-align: top;\n
\tpadding: 0 0.5em 0 0;\n
}\n
\n
#qunit-tests td {\n
\tvertical-align: top;\n
}\n
\n
#qunit-tests pre {\n
\tmargin: 0;\n
\twhite-space: pre-wrap;\n
\tword-wrap: break-word;\n
}\n
\n
#qunit-tests del {\n
\tbackground-color: #E0F2BE;\n
\tcolor: #374E0C;\n
\ttext-decoration: none;\n
}\n
\n
#qunit-tests ins {\n
\tbackground-color: #FFCACA;\n
\tcolor: #500;\n
\ttext-decoration: none;\n
}\n
\n
/*** Test Counts */\n
\n
#qunit-tests b.counts { color: #000; }\n
#qunit-tests b.passed { color: #5E740B; }\n
#qunit-tests b.failed { color: #710909; }\n
\n
#qunit-tests li li {\n
\tpadding: 5px;\n
\tbackground-color: #FFF;\n
\tborder-bottom: none;\n
\tlist-style-position: inside;\n
}\n
\n
/*** Passing Styles */\n
\n
#qunit-tests li li.pass {\n
\tcolor: #3C510C;\n
\tbackground-color: #FFF;\n
\tborder-left: 10px solid #C6E746;\n
}\n
\n
#qunit-tests .pass { color: #528CE0; background-color: #D2E0E6; }\n
#qunit-tests .pass .test-name { color: #366097; }\n
\n
#qunit-tests .pass .test-actual,\n
#qunit-tests .pass .test-expected { color: #999; }\n
\n
#qunit-banner.qunit-pass { background-color: #C6E746; }\n
\n
/*** Failing Styles */\n
\n
#qunit-tests li li.fail {\n
\tcolor: #710909;\n
\tbackground-color: #FFF;\n
\tborder-left: 10px solid #EE5757;\n
\twhite-space: pre;\n
}\n
\n
#qunit-tests > li:last-child {\n
\tborder-radius: 0 0 5px 5px;\n
}\n
\n
#qunit-tests .fail { color: #000; background-color: #EE5757; }\n
#qunit-tests .fail .test-name,\n
#qunit-tests .fail .module-name { color: #000; }\n
\n
#qunit-tests .fail .test-actual { color: #EE5757; }\n
#qunit-tests .fail .test-expected { color: #008000; }\n
\n
#qunit-banner.qunit-fail { background-color: #EE5757; }\n
\n
/*** Skipped tests */\n
\n
#qunit-tests .skipped {\n
\tbackground-color: #EBECE9;\n
}\n
\n
#qunit-tests .qunit-skipped-label {\n
\tbackground-color: #F4FF77;\n
\tdisplay: inline-block;\n
\tfont-style: normal;\n
\tcolor: #366097;\n
\tline-height: 1.8em;\n
\tpadding: 0 0.5em;\n
\tmargin: -0.4em 0.4em -0.4em 0;\n
}\n
\n
/** Result */\n
\n
#qunit-testresult {\n
\tpadding: 0.5em 1em 0.5em 1em;\n
\n
\tcolor: #2B81AF;\n
\tbackground-color: #D2E0E6;\n
\n
\tborder-bottom: 1px solid #FFF;\n
}\n
#qunit-testresult .module-name {\n
\tfont-weight: 700;\n
}\n
\n
/** Fixture */\n
\n
#qunit-fixture {\n
\tposition: absolute;\n
\ttop: -10000px;\n
\tleft: -10000px;\n
\twidth: 1000px;\n
\theight: 1000px;\n
}\n
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>4991</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570623.48</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>qunit.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value>
<persistent> <string encoding="base64">AAAAAAAAAAI=</string> </persistent>
</value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>71721</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
<record id="2" aka="AAAAAAAAAAI=">
<pickle>
<global name="Pdata" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
/*!\n
* QUnit 1.17.1\n
* http://qunitjs.com/\n
*\n
* Copyright jQuery Foundation and other contributors\n
* Released under the MIT license\n
* http://jquery.org/license\n
*\n
* Date: 2015-01-20T19:39Z\n
*/\n
\n
(function( window ) {\n
\n
var QUnit,\n
\tconfig,\n
\tonErrorFnPrev,\n
\tloggingCallbacks = {},\n
\tfileName = ( sourceFromStacktrace( 0 ) || "" ).replace( /(:\\d+)+\\)?/, "" ).replace( /.+\\//, "" ),\n
\ttoString = Object.prototype.toString,\n
\thasOwn = Object.prototype.hasOwnProperty,\n
\t// Keep a local reference to Date (GH-283)\n
\tDate = window.Date,\n
\tnow = Date.now || function() {\n
\t\treturn new Date().getTime();\n
\t},\n
\tglobalStartCalled = false,\n
\trunStarted = false,\n
\tsetTimeout = window.setTimeout,\n
\tclearTimeout = window.clearTimeout,\n
\tdefined = {\n
\t\tdocument: window.document !== undefined,\n
\t\tsetTimeout: window.setTimeout !== undefined,\n
\t\tsessionStorage: (function() {\n
\t\t\tvar x = "qunit-test-string";\n
\t\t\ttry {\n
\t\t\t\tsessionStorage.setItem( x, x );\n
\t\t\t\tsessionStorage.removeItem( x );\n
\t\t\t\treturn true;\n
\t\t\t} catch ( e ) {\n
\t\t\t\treturn false;\n
\t\t\t}\n
\t\t}())\n
\t},\n
\t/**\n
\t * Provides a normalized error string, correcting an issue\n
\t * with IE 7 (and prior) where Error.prototype.toString is\n
\t * not properly implemented\n
\t *\n
\t * Based on http://es5.github.com/#x15.11.4.4\n
\t *\n
\t * @param {String|Error} error\n
\t * @return {String} error message\n
\t */\n
\terrorString = function( error ) {\n
\t\tvar name, message,\n
\t\t\terrorString = error.toString();\n
\t\tif ( errorString.substring( 0, 7 ) === "[object" ) {\n
\t\t\tname = error.name ? error.name.toString() : "Error";\n
\t\t\tmessage = error.message ? error.message.toString() : "";\n
\t\t\tif ( name && message ) {\n
\t\t\t\treturn name + ": " + message;\n
\t\t\t} else if ( name ) {\n
\t\t\t\treturn name;\n
\t\t\t} else if ( message ) {\n
\t\t\t\treturn message;\n
\t\t\t} else {\n
\t\t\t\treturn "Error";\n
\t\t\t}\n
\t\t} else {\n
\t\t\treturn errorString;\n
\t\t}\n
\t},\n
\t/**\n
\t * Makes a clone of an object using only Array or Object as base,\n
\t * and copies over the own enumerable properties.\n
\t *\n
\t * @param {Object} obj\n
\t * @return {Object} New object with only the own properties (recursively).\n
\t */\n
\tobjectValues = function( obj ) {\n
\t\tvar key, val,\n
\t\t\tvals = QUnit.is( "array", obj ) ? [] : {};\n
\t\tfor ( key in obj ) {\n
\t\t\tif ( hasOwn.call( obj, key ) ) {\n
\t\t\t\tval = obj[ key ];\n
\t\t\t\tvals[ key ] = val === Object( val ) ? objectValues( val ) : val;\n
\t\t\t}\n
\t\t}\n
\t\treturn vals;\n
\t};\n
\n
QUnit = {};\n
\n
/**\n
* Config object: Maintain internal state\n
* Later exposed as QUnit.config\n
* `config` initialized at top of scope\n
*/\n
config = {\n
\t// The queue of tests to run\n
\tqueue: [],\n
\n
\t// block until document ready\n
\tblocking: true,\n
\n
\t// by default, run previously failed tests first\n
\t// very useful in combination with "Hide passed tests" checked\n
\treorder: true,\n
\n
\t// by default, modify document.title when suite is done\n
\taltertitle: true,\n
\n
\t// by default, scroll to top of the page when suite is done\n
\tscrolltop: true,\n
\n
\t// when enabled, all tests must call expect()\n
\trequireExpects: false,\n
\n
\t// add checkboxes that are persisted in the query-string\n
\t// when enabled, the id is set to `true` as a `QUnit.config` property\n
\turlConfig: [\n
\t\t{\n
\t\t\tid: "hidepassed",\n
\t\t\tlabel: "Hide passed tests",\n
\t\t\ttooltip: "Only show tests and assertions that fail. Stored as query-strings."\n
\t\t},\n
\t\t{\n
\t\t\tid: "noglobals",\n
\t\t\tlabel: "Check for Globals",\n
\t\t\ttooltip: "Enabling this will test if any test introduces new properties on the " +\n
\t\t\t\t"`window` object. Stored as query-strings."\n
\t\t},\n
\t\t{\n
\t\t\tid: "notrycatch",\n
\t\t\tlabel: "No try-catch",\n
\t\t\ttooltip: "Enabling this will run tests outside of a try-catch block. Makes debugging " +\n
\t\t\t\t"exceptions in IE reasonable. Stored as query-strings."\n
\t\t}\n
\t],\n
\n
\t// Set of all modules.\n
\tmodules: [],\n
\n
\t// The first unnamed module\n
\tcurrentModule: {\n
\t\tname: "",\n
\t\ttests: []\n
\t},\n
\n
\tcallbacks: {}\n
};\n
\n
// Push a loose unnamed module to the modules collection\n
config.modules.push( config.currentModule );\n
\n
// Initialize more QUnit.config and QUnit.urlParams\n
(function() {\n
\tvar i, current,\n
\t\tlocation = window.location || { search: "", protocol: "file:" },\n
\t\tparams = location.search.slice( 1 ).split( "&" ),\n
\t\tlength = params.length,\n
\t\turlParams = {};\n
\n
\tif ( params[ 0 ] ) {\n
\t\tfor ( i = 0; i < length; i++ ) {\n
\t\t\tcurrent = params[ i ].split( "=" );\n
\t\t\tcurrent[ 0 ] = decodeURIComponent( current[ 0 ] );\n
\n
\t\t\t// allow just a key to turn on a flag, e.g., test.html?noglobals\n
\t\t\tcurrent[ 1 ] = current[ 1 ] ? decodeURIComponent( current[ 1 ] ) : true;\n
\t\t\tif ( urlParams[ current[ 0 ] ] ) {\n
\t\t\t\turlParams[ current[ 0 ] ] = [].concat( urlParams[ current[ 0 ] ], current[ 1 ] );\n
\t\t\t} else {\n
\t\t\t\turlParams[ current[ 0 ] ] = current[ 1 ];\n
\t\t\t}\n
\t\t}\n
\t}\n
\n
\tif ( urlParams.filter === true ) {\n
\t\tdelete urlParams.filter;\n
\t}\n
\n
\tQUnit.urlParams = urlParams;\n
\n
\t// String search anywhere in moduleName+testName\n
\tconfig.filter = urlParams.filter;\n
\n
\tconfig.testId = [];\n
\tif ( urlParams.testId ) {\n
\n
\t\t// Ensure that urlParams.testId is an array\n
\t\turlParams.testId = [].concat( urlParams.testId );\n
\t\tfor ( i = 0; i < urlParams.testId.length; i++ ) {\n
\t\t\tconfig.testId.push( urlParams.testId[ i ] );\n
\t\t}\n
\t}\n
\n
\t// Figure out if we\'re running the tests from a server or not\n
\tQUnit.isLocal = location.protocol === "file:";\n
}());\n
\n
// Root QUnit object.\n
// `QUnit` initialized at top of scope\n
extend( QUnit, {\n
\n
\t// call on start of module test to prepend name to all tests\n
\tmodule: function( name, testEnvironment ) {\n
\t\tvar currentModule = {\n
\t\t\tname: name,\n
\t\t\ttestEnvironment: testEnvironment,\n
\t\t\ttests: []\n
\t\t};\n
\n
\t\t// DEPRECATED: handles setup/teardown functions,\n
\t\t// beforeEach and afterEach should be used instead\n
\t\tif ( testEnvironment && testEnvironment.setup ) {\n
\t\t\ttestEnvironment.beforeEach = testEnvironment.setup;\n
\t\t\tdelete testEnvironment.setup;\n
\t\t}\n
\t\tif ( testEnvironment && testEnvironment.teardown ) {\n
\t\t\ttestEnvironment.afterEach = testEnvironment.teardown;\n
\t\t\tdelete testEnvironment.teardown;\n
\t\t}\n
\n
\t\tconfig.modules.push( currentModule );\n
\t\tconfig.currentModule = currentModule;\n
\t},\n
\n
\t// DEPRECATED: QUnit.asyncTest() will be removed in QUnit 2.0.\n
\tasyncTest: function( testName, expected, callback ) {\n
\t\tif ( arguments.length === 2 ) {\n
\t\t\tcallback = expected;\n
\t\t\texpected = null;\n
\t\t}\n
\n
\t\tQUnit.test( testName, expected, callback, true );\n
\t},\n
\n
\ttest: function( testName, expected, callback, async ) {\n
\t\tvar test;\n
\n
\t\tif ( arguments.length === 2 ) {\n
\t\t\tcallback = expected;\n
\t\t\texpected = null;\n
\t\t}\n
\n
\t\ttest = new Test({\n
\t\t\ttestName: testName,\n
\t\t\texpected: expected,\n
\t\t\tasync: async,\n
\t\t\tcallback: callback\n
\t\t});\n
\n
\t\ttest.queue();\n
\t},\n
\n
\tskip: function( testName ) {\n
\t\tvar test = new Test({\n
\t\t\ttestName: testName,\n
\t\t\tskip: true\n
\t\t});\n
\n
\t\ttest.queue();\n
\t},\n
\n
\t// DEPRECATED: The functionality of QUnit.start() will be altered in QUnit 2.0.\n
\t// In QUnit 2.0, invoking it will ONLY affect the `QUnit.config.autostart` blocking behavior.\n
\tstart: function( count ) {\n
\t\tvar globalStartAlreadyCalled = globalStartCalled;\n
\n
\t\tif ( !config.current ) {\n
\t\t\tglobalStartCalled = true;\n
\n
\t\t\tif ( runStarted ) {\n
\t\t\t\tthrow new Error( "Called start() outside of a test context while already started" );\n
\t\t\t} else if ( globalStartAlreadyCalled || count > 1 ) {\n
\t\t\t\tthrow new Error( "Called start() outside of a test context too many times" );\n
\t\t\t} else if ( config.autostart ) {\n
\t\t\t\tthrow new Error( "Called start() outside of a test context when " +\n
\t\t\t\t\t"QUnit.config.autostart was true" );\n
\t\t\t} else if ( !config.pageLoaded ) {\n
\n
\t\t\t\t// The page isn\'t completely loaded yet, so bail out and let `QUnit.load` handle it\n
\t\t\t\tconfig.autostart = true;\n
\t\t\t\treturn;\n
\t\t\t}\n
\t\t} else {\n
\n
\t\t\t// If a test is running, adjust its semaphore\n
\t\t\tconfig.current.semaphore -= count || 1;\n
\n
\t\t\t// Don\'t start until equal number of stop-calls\n
\t\t\tif ( config.current.semaphore > 0 ) {\n
\t\t\t\treturn;\n
\t\t\t}\n
\n
\t\t\t// throw an Error if start is called more often than stop\n
\t\t\tif ( config.current.semaphore < 0 ) {\n
\t\t\t\tconfig.current.semaphore = 0;\n
\n
\t\t\t\tQUnit.pushFailure(\n
\t\t\t\t\t"Called start() while already started (test\'s semaphore was 0 already)",\n
\t\t\t\t\tsourceFromStacktrace( 2 )\n
\t\t\t\t);\n
\t\t\t\treturn;\n
\t\t\t}\n
\t\t}\n
\n
\t\tresumeProcessing();\n
\t},\n
\n
\t// DEPRECATED: QUnit.stop() will be removed in QUnit 2.0.\n
\tstop: function( count ) {\n
\n
\t\t// If there isn\'t a test running, don\'t allow QUnit.stop() to be called\n
\t\tif ( !config.current ) {\n
\t\t\tthrow new Error( "Called stop() outside of a test context" );\n
\t\t}\n
\n
\t\t// If a test is running, adjust its semaphore\n
\t\tconfig.current.semaphore += count || 1;\n
\n
\t\tpauseProcessing();\n
\t},\n
\n
\tconfig: config,\n
\n
\t// Safe object type checking\n
\tis: function( type, obj ) {\n
\t\treturn QUnit.objectType( obj ) === type;\n
\t},\n
\n
\tobjectType: function( obj ) {\n
\t\tif ( typeof obj === "undefined" ) {\n
\t\t\treturn "undefined";\n
\t\t}\n
\n
\t\t// Consider: typeof null === object\n
\t\tif ( obj === null ) {\n
\t\t\treturn "null";\n
\t\t}\n
\n
\t\tvar match = toString.call( obj ).match( /^\\[object\\s(.*)\\]$/ ),\n
\t\t\ttype = match && match[ 1 ] || "";\n
\n
\t\tswitch ( type ) {\n
\t\t\tcase "Number":\n
\t\t\t\tif ( isNaN( obj ) ) {\n
\t\t\t\t\treturn "nan";\n
\t\t\t\t}\n
\t\t\t\treturn "number";\n
\t\t\tcase "String":\n
\t\t\tcase "Boolean":\n
\t\t\tcase "Array":\n
\t\t\tcase "Date":\n
\t\t\tcase "RegExp":\n
\t\t\tcase "Function":\n
\t\t\t\treturn type.toLowerCase();\n
\t\t}\n
\t\tif ( typeof obj === "object" ) {\n
\t\t\treturn "object";\n
\t\t}\n
\t\treturn undefined;\n
\t},\n
\n
\textend: extend,\n
\n
\tload: function() {\n
\t\tconfig.pageLoaded = true;\n
\n
\t\t// Initialize the configuration options\n
\t\textend( config, {\n
\t\t\tstats: { all: 0, bad: 0 },\n
\t\t\tmoduleStats: { all: 0, bad: 0 },\n
\t\t\tstarted: 0,\n
\t\t\tupdateRate: 1000,\n
\t\t\tautostart: true,\n
\t\t\tfilter: ""\n
\t\t}, true );\n
\n
\t\tconfig.blocking = false;\n
\n
\t\tif ( config.autostart ) {\n
\t\t\tresumeProcessing();\n
\t\t}\n
\t}\n
});\n
\n
// Register logging callbacks\n
(function() {\n
\tvar i, l, key,\n
\t\tcallbacks = [ "begin", "done", "log", "testStart", "testDone",\n
\t\t\t"moduleStart", "moduleDone" ];\n
\n
\tfunction registerLoggingCallback( key ) {\n
\t\tvar loggingCallback = function( callback ) {\n
\t\t\tif ( QUnit.objectType( callback ) !== "function" ) {\n
\t\t\t\tthrow new Error(\n
\t\t\t\t\t"QUnit logging methods require a callback function as their first parameters."\n
\t\t\t\t);\n
\t\t\t}\n
\n
\t\t\tconfig.callbacks[ key ].push( callback );\n
\t\t};\n
\n
\t\t// DEPRECATED: This will be removed on QUnit 2.0.0+\n
\t\t// Stores the registered functions allowing restoring\n
\t\t// at verifyLoggingCallbacks() if modified\n
\t\tloggingCallbacks[ key ] = loggingCallback;\n
\n
\t\treturn loggingCallback;\n
\t}\n
\n
\tfor ( i = 0, l = callbacks.length; i < l; i++ ) {\n
\t\tkey = callbacks[ i ];\n
\n
\t\t// Initialize key collection of logging callback\n
\t\tif ( QUnit.objectType( config.callbacks[ key ] ) === "undefined" ) {\n
\t\t\tconfig.callbacks[ key ] = [];\n
\t\t}\n
\n
\t\tQUnit[ key ] = registerLoggingCallback( key );\n
\t}\n
})();\n
\n
// `onErrorFnPrev` initialized at top of scope\n
// Preserve other handlers\n
onErrorFnPrev = window.onerror;\n
\n
// Cover uncaught exceptions\n
// Returning true will suppress the default browser handler,\n
// returning false will let it run.\n
window.onerror = function( error, filePath, linerNr ) {\n
\tvar ret = false;\n
\tif ( onErrorFnPrev ) {\n
\t\tret = onErrorFnPrev( error, filePath, linerNr );\n
\t}\n
\n
\t// Treat return value as window.onerror itself does,\n
\t// Only do our handling if not suppressed.\n
\tif ( ret !== true ) {\n
\t\tif ( QUnit.config.current ) {\n
\t\t\tif ( QUnit.config.current.ignoreGlobalErrors ) {\n
\t\t\t\treturn true;\n
\t\t\t}\n
\t\t\tQUnit.pushFailure( error, filePath + ":" + linerNr );\n
\t\t} else {\n
\t\t\tQUnit.test( "global failure", extend(function() {\n
\t\t\t\tQUnit.pushFailure( error, filePath + ":" + linerNr );\n
\t\t\t}, { validTest: true } ) );\n
\t\t}\n
\t\treturn false;\n
\t}\n
\n
\treturn ret;\n
};\n
\n
function done() {\n
\tvar runtime, passed;\n
\n
\tconfig.autorun = true;\n
\n
\t// Log the last module results\n
\tif ( config.previousModule ) {\n
\t\trunLoggingCallbacks( "moduleDone", {\n
\t\t\tname: config.previousModule.name,\n
\t\t\ttests: config.previousModule.tests,\n
\t\t\tfailed: config.moduleStats.bad,\n
\t\t\tpassed: config.moduleStats.all - config.moduleStats.bad,\n
\t\t\ttotal: config.moduleStats.all,\n
\t\t\truntime: now() - config.moduleStats.started\n
\t\t});\n
\t}\n
\tdelete config.previousModule;\n
\n
\truntime = now() - config.started;\n
\tpassed = config.stats.all - config.stats.bad;\n
\n
\trunLoggingCallbacks( "done", {\n
\t\tfailed: config.stats.bad,\n
\t\tpassed: passed,\n
\t\ttotal: config.stats.all,\n
\t\truntime: runtime\n
\t});\n
}\n
\n
// Doesn\'t support IE6 to IE9\n
// See also https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Error/Stack\n
function extractStacktrace( e, offset ) {\n
\toffset = offset === undefined ? 4 : offset;\n
\n
\tvar stack, include, i;\n
\n
\tif ( e.stacktrace ) {\n
\n
\t\t// Opera 12.x\n
\t\treturn e.stacktrace.split( "\\n" )[ offset + 3 ];\n
\t} else if ( e.stack ) {\n
\n
\t\t// Firefox, Chrome, Safari 6+, IE10+, PhantomJS and Node\n
\t\tstack = e.stack.split( "\\n" );\n
\t\tif ( /^error$/i.test( stack[ 0 ] ) ) {\n
\t\t\tstack.shift();\n
\t\t}\n
\t\tif ( fileName ) {\n
\t\t\tinclude = [];\n
\t\t\tfor ( i = offset; i < stack.length; i++ ) {\n
\t\t\t\tif ( stack[ i ].indexOf( fileName ) !== -1 ) {\n
\t\t\t\t\tbreak;\n
\t\t\t\t}\n
\t\t\t\tinclude.push( stack[ i ] );\n
\t\t\t}\n
\t\t\tif ( include.length ) {\n
\t\t\t\treturn include.join( "\\n" );\n
\t\t\t}\n
\t\t}\n
\t\treturn stack[ offset ];\n
\t} else if ( e.sourceURL ) {\n
\n
\t\t// Safari < 6\n
\t\t// exclude useless self-reference for generated Error objects\n
\t\tif ( /qunit.js$/.test( e.sourceURL ) ) {\n
\t\t\treturn;\n
\t\t}\n
\n
\t\t// for actual exceptions, this is useful\n
\t\treturn e.sourceURL + ":" + e.line;\n
\t}\n
}\n
\n
function sourceFromStacktrace( offset ) {\n
\tvar e = new Error();\n
\tif ( !e.stack ) {\n
\t\ttry {\n
\t\t\tthrow e;\n
\t\t} catch ( err ) {\n
\t\t\t// This should already be true in most browsers\n
\t\t\te = err;\n
\t\t}\n
\t}\n
\treturn extractStacktrace( e, offset );\n
}\n
\n
function synchronize( callback, last ) {\n
\tif ( QUnit.objectType( callback ) === "array" ) {\n
\t\twhile ( callback.length ) {\n
\t\t\tsynchronize( callback.shift() );\n
\t\t}\n
\t\treturn;\n
\t}\n
\tconfig.queue.push( callback );\n
\n
\tif ( config.autorun && !config.blocking ) {\n
\t\tprocess( last );\n
\t}\n
}\n
\n
function process( last ) {\n
\tfunction next() {\n
\t\tprocess( last );\n
\t}\n
\tvar start = now();\n
\tconfig.depth = ( config.depth || 0 ) + 1;\n
\n
\twhile ( config.queue.length && !config.blocking ) {\n
\t\tif ( !defined.setTimeout || config.updateRate <= 0 ||\n
\t\t\t\t( ( now() - start ) < config.updateRate ) ) {\n
\t\t\tif ( config.current ) {\n
\n
\t\t\t\t// Reset async tracking for each phase of the Test lifecycle\n
\t\t\t\tconfig.current.usedAsync = false;\n
\t\t\t}\n
\t\t\tconfig.queue.shift()();\n
\t\t} else {\n
\t\t\tsetTimeout( next, 13 );\n
\t\t\tbreak;\n
\t\t}\n
\t}\n
\tconfig.depth--;\n
\tif ( last && !config.blocking && !config.queue.length && config.depth === 0 ) {\n
\t\tdone();\n
\t}\n
}\n
\n
function begin() {\n
\tvar i, l,\n
\t\tmodulesLog = [];\n
\n
\t// If the test run hasn\'t officially begun yet\n
\tif ( !config.started ) {\n
\n
\t\t// Record the time of the test run\'s beginning\n
\t\tconfig.started = now();\n
\n
\t\tverifyLoggingCallbacks();\n
\n
\t\t// Delete the loose unnamed module if unused.\n
\t\tif ( config.modules[ 0 ].name === "" && config.modules[ 0 ].tests.length === 0 ) {\n
\t\t\tconfig.modules.shift();\n
\t\t}\n
\n
\t\t// Avoid unnecessary information by not logging modules\' test environments\n
\t\tfor ( i = 0, l = config.modules.length; i < l; i++ ) {\n
\t\t\tmodulesLog.push({\n
\t\t\t\tname: config.modules[ i ].name,\n
\t\t\t\ttests: config.modules[ i ].tests\n
\t\t\t});\n
\t\t}\n
\n
\t\t// The test run is officially beginning now\n
\t\trunLoggingCallbacks( "begin", {\n
\t\t\ttotalTests: Test.count,\n
\t\t\tmodules: modulesLog\n
\t\t});\n
\t}\n
\n
\tconfig.blocking = false;\n
\tprocess( true );\n
}\n
\n
function resumeProcessing() {\n
\trunStarted = true;\n
\n
\t// A slight delay to allow this iteration of the event loop to finish (more assertions, etc.)\n
\tif ( defined.setTimeout ) {\n
\t\tsetTimeout(function() {\n
\t\t\tif ( config.current && config.current.semaphore > 0 ) {\n
\t\t\t\treturn;\n
\t\t\t}\n
\t\t\tif ( config.timeout ) {\n
\t\t\t\tclearTimeout( config.timeout );\n
\t\t\t}\n
\n
\t\t\tbegin();\n
\t\t}, 13 );\n
\t} else {\n
\t\tbegin();\n
\t}\n
}\n
\n
function pauseProcessing() {\n
\tconfig.blocking = true;\n
\n
\tif ( config.testTimeout && defined.setTimeout ) {\n
\t\tclearTimeout( config.timeout );\n
\t\tconfig.timeout = setTimeout(function() {\n
\t\t\tif ( config.current ) {\n
\t\t\t\tconfig.current.semaphore = 0;\n
\t\t\t\tQUnit.pushFailure( "Test timed out", sourceFromStacktrace( 2 ) );\n
\t\t\t} else {\n
\t\t\t\tthrow new Error( "Test timed out" );\n
\t\t\t}\n
\t\t\tresumeProcessing();\n
\t\t}, config.testTimeout );\n
\t}\n
}\n
\n
function saveGlobal() {\n
\tconfig.pollution = [];\n
\n
\tif ( config.noglobals ) {\n
\t\tfor ( var key in window ) {\n
\t\t\tif ( hasOwn.call( window, key ) ) {\n
\t\t\t\t// in Opera sometimes DOM element ids show up here, ignore them\n
\t\t\t\tif ( /^qunit-test-output/.test( key ) ) {\n
\t\t\t\t\tcontinue;\n
\t\t\t\t}\n
\t\t\t\tconfig.pollution.push( key );\n
\t\t\t}\n
\t\t}\n
\t}\n
}\n
\n
function checkPollution() {\n
\tvar newGlobals,\n
\t\tdeletedGlobals,\n
\t\told = config.pollution;\n
\n
\tsaveGlobal();\n
\n
\tnewGlobals = diff( config.pollution, old );\n
\tif ( newGlobals.length > 0 ) {\n
\t\tQUnit.pushFailure( "Introduced global variable(s): " + newGlobals.join( ", " ) );\n
\t}\n
\n
\tdeletedGlobals = diff( old, config.pollution );\n
\tif ( deletedGlobals.length > 0 ) {\n
\t\tQUnit.pushFailure( "Deleted global variable(s): " + deletedGlobals.join( ", " ) );\n
\t}\n
}\n
\n
// returns a new Array with the elements that are in a but not in b\n
function diff( a, b ) {\n
\tvar i, j,\n
\t\tresult = a.slice();\n
\n
\tfor ( i = 0; i < result.length; i++ ) {\n
\t\tfor ( j = 0; j < b.length; j++ ) {\n
\t\t\tif ( result[ i ] === b[ j ] ) {\n
\t\t\t\tresult.splice( i, 1 );\n
\t\t\t\ti--;\n
\t\t\t\tbreak;\n
\t\t\t}\n
\t\t}\n
\t}\n
\treturn result;\n
}\n
\n
function extend( a, b, undefOnly ) {\n
\tfor ( var prop in b ) {\n
\t\tif ( hasOwn.call( b, prop ) ) {\n
\n
\t\t\t// Avoid "Member not found" error in IE8 caused by messing with window.constructor\n
\t\t\tif ( !( prop === "constructor" && a === window ) ) {\n
\t\t\t\tif ( b[ prop ] === undefined ) {\n
\t\t\t\t\tdelete a[ prop ];\n
\t\t\t\t} else if ( !( undefOnly && typeof a[ prop ] !== "undefined" ) ) {\n
\t\t\t\t\ta[ prop ] = b[ prop ];\n
\t\t\t\t}\n
\t\t\t}\n
\t\t}\n
\t}\n
\n
\treturn a;\n
}\n
\n
function runLoggingCallbacks( key, args ) {\n
\tvar i, l, callbacks;\n
\n
\tcallbacks = config.callbacks[ key ];\n
\tfor ( i = 0, l = callbacks.length; i < l; i++ ) {\n
\t\tcallbacks[ i ]( args );\n
\t}\n
}\n
\n
// DEPRECATED: This will be removed on 2.0.0+\n
// This function verifies if the loggingCallbacks were modified by the user\n
// If so, it will restore it, assign the given callback and print a console warning\n
function verifyLoggingCallbacks() {\n
\tvar loggingCallback, userCallback;\n
\n
\tfor ( loggingCallback in loggingCallbacks ) {\n
\t\tif ( QUnit[ loggingCallback ] !== loggingCallbacks[ loggingCallback ] ) {\n
\n
\t\t\tuserCallback = QUnit[ loggingCallback ];\n
\n
\t\t\t// Restore the callback function\n
\t\t\tQUnit[ loggingCallback ] = loggingCallbacks[ loggingCallback ];\n
\n
\t\t\t// Assign the deprecated given callback\n
\t\t\tQUnit[ loggingCallback ]( userCallback );\n
\n
\t\t\tif ( window.console && window.console.warn ) {\n
\t\t\t\twindow.console.warn(\n
\t\t\t\t\t"QUnit." + loggingCallback + " was replaced with a new value.\\n" +\n
\t\t\t\t\t"Please, check out the documentation on how to apply logging callbacks.\\n" +\n
\t\t\t\t\t"Reference: http://api.qunitjs.com/category/callbacks/"\n
\t\t\t\t);\n
\t\t\t}\n
\t\t}\n
\t}\n
}\n
\n
// from jquery.js\n
function inArray( elem, array ) {\n
\tif ( array.indexOf ) {\n
\t\treturn array.indexOf( elem );\n
\t}\n
\n
\tfor ( var i = 0, length = array.length; i < length; i++ ) {\n
\t\tif ( array[ i ] === elem ) {\n
\t\t\treturn i;\n
\t\t}\n
\t}\n
\n
\treturn -1;\n
}\n
\n
function Test( settings ) {\n
\tvar i, l;\n
\n
\t++Test.count;\n
\n
\textend( this, settings );\n
\tthis.assertions = [];\n
\tthis.semaphore = 0;\n
\tthis.usedAsync = false;\n
\tthis.module = config.currentModule;\n
\tthis.stack = sourceFromStacktrace( 3 );\n
\n
\t// Register unique strings\n
\tfor ( i = 0, l = this.module.tests; i < l.length; i++ ) {\n
\t\tif ( this.module.tests[ i ].name === this.testName ) {\n
\t\t\tthis.testName += " ";\n
\t\t}\n
\t}\n
\n
\tthis.testId = generateHash( this.module.name, this.testName );\n
\n
\tthis.module.tests.push({\n
\t\tname: this.testName,\n
\t\ttestId: this.testId\n
\t});\n
\n
\tif ( settings.skip ) {\n
\n
\t\t// Skipped tests will fully ignore any sent callback\n
\t\tthis.callback = function() {};\n
\t\tthis.async = false;\n
\t\tthis.expected = 0;\n
\t} else {\n
\t\tthis.assert = new Assert( this );\n
\t}\n
}\n
\n
Test.count = 0;\n
\n
Test.prototype = {\n
\tbefore: function() {\n
\t\tif (\n
\n
\t\t\t// Emit moduleStart when we\'re switching from one module to another\n
\t\t\tthis.module !== config.previousModule ||\n
\n
\t\t\t\t// They could be equal (both undefined) but if the previousModule property doesn\'t\n
\t\t\t\t// yet exist it means this is the first test in a suite that isn\'t wrapped in a\n
\t\t\t\t// module, in which case we\'ll just emit a moduleStart event for \'undefined\'.\n
\t\t\t\t// Without this, reporters can get testStart before moduleStart which is a problem.\n
\t\t\t\t!hasOwn.call( config, "previousModule" )\n
\t\t) {\n
\t\t\tif ( hasOwn.call( config, "previousModule" ) ) {\n
\t\t\t\trunLoggingCallbacks( "moduleDone", {\n
\t\t\t\t\tname: config.previousModule.name,\n
\t\t\t\t\ttests: config.previousModule.tests,\n
\t\t\t\t\tfailed: config.moduleStats.bad,\n
\t\t\t\t\tpassed: config.moduleStats.all - config.moduleStats.bad,\n
\t\t\t\t\ttotal: config.moduleStats.all,\n
\t\t\t\t\truntime: now() - config.moduleStats.started\n
\t\t\t\t});\n
\t\t\t}\n
\t\t\tconfig.previousModule = this.module;\n
\t\t\tconfig.moduleStats = { all: 0, bad: 0, started: now() };\n
\t\t\trunLoggingCallbacks( "moduleStart", {\n
\t\t\t\tname: this.module.name,\n
\t\t\t\ttests: this.module.tests\n
\t\t\t});\n
\t\t}\n
\n
\t\tconfig.current = this;\n
\n
\t\tthis.testEnvironment = extend( {}, this.module.testEnvironment );\n
\t\tdelete this.testEnvironment.beforeEach;\n
\t\tdelete this.testEnvironment.afterEach;\n
\n
\t\tthis.started = now();\n
\t\trunLoggingCallbacks( "testStart", {\n
\t\t\tname: this.testName,\n
\t\t\tmodule: this.module.name,\n
\t\t\ttestId: this.testId\n
\t\t});\n
\n
\t\tif ( !config.pollution ) {\n
\t\t\tsaveGlobal();\n
\t\t}\n
\t},\n
\n
\trun: function() {\n
\t\tvar promise;\n
\n
\t\tconfig.current = this;\n
\n
\t\tif ( this.async ) {\n
\t\t\tQUnit.stop();\n
\t\t}\n
\n
\t\tthis.callbackStarted = now();\n
\n
\t\tif ( config.notrycatch ) {\n
\t\t\tpromise = this.callback.call( this.testEnvironment, this.assert );\n
\t\t\tthis.resolvePromise( promise );\n
\t\t\treturn;\n
\t\t}\n
\n
\t\ttry {\n
\t\t\tpromise = this.callback.call( this.testEnvironment, this.assert );\n
\t\t\tthis.resolvePromise( promise );\n
\t\t} catch ( e ) {\n
\t\t\tthis.pushFailure( "Died on test #" + ( this.assertions.length + 1 ) + " " +\n
\t\t\t\tthis.stack + ": " + ( e.message || e ), extractStacktrace( e, 0 ) );\n
\n
\t\t\t// else next test will carry the responsibility\n
\t\t\tsaveGlobal();\n
\n
\t\t\t// Restart the tests if they\'re blocking\n
\t\t\tif ( config.blocking ) {\n
\t\t\t\tQUnit.start();\n
\t\t\t}\n
\t\t}\n
\t},\n
\n
\tafter: function() {\n
\t\tcheckPollution();\n
\t},\n
\n
\tqueueHook: function( hook, hookName ) {\n
\t\tvar promise,\n
\t\t\ttest = this;\n
\t\treturn function runHook() {\n
\t\t\tconfig.current = test;\n
\t\t\tif ( config.notrycatch ) {\n
\t\t\t\tpromise = hook.call( test.testEnvironment, test.assert );\n
\t\t\t\ttest.resolvePromise( promise, hookName );\n
\t\t\t\treturn;\n
\t\t\t}\n
\t\t\ttry {\n
\t\t\t\tpromise = hook.call( test.testEnvironment, test.assert );\n
\t\t\t\ttest.resolvePromise( promise, hookName );\n
\t\t\t} catch ( error ) {\n
\t\t\t\ttest.pushFailure( hookName + " failed on " + test.testName + ": " +\n
\t\t\t\t\t( error.message || error ), extractStacktrace( error, 0 ) );\n
\t\t\t}\n
\t\t};\n
\t},\n
\n
\t// Currently only used for module level hooks, can be used to add global level ones\n
\thooks: function( handler ) {\n
\t\tvar hooks = [];\n
\n
\t\t// Hooks are ignored on skipped tests\n
\t\tif ( this.skip ) {\n
\t\t\treturn hooks;\n
\t\t}\n
\n
\t\tif ( this.module.testEnvironment &&\n
\t\t\t\tQUnit.objectType( this.module.testEnvironment[ handler ] ) === "function" ) {\n
\t\t\thooks.push( this.queueHook( this.module.testEnvironment[ handler ], handler ) );\n
\t\t}\n
\n
\t\treturn hooks;\n
\t},\n
\n
\tfinish: function() {\n
\t\tconfig.current = this;\n
\t\tif ( config.requireExpects && this.expected === null ) {\n
\t\t\tthis.pushFailure( "Expected number of assertions to be defined, but expect() was " +\n
\t\t\t\t"not called.", this.stack );\n
\t\t} else if ( this.expected !== null && this.expected !== this.assertions.length ) {\n
\t\t\tthis.pushFailure( "Expected " + this.expected + " assertions, but " +\n
\t\t\t\tthis.assertions.length + " were run", this.stack );\n
\t\t} else if ( this.expected === null && !this.assertions.length ) {\n
\t\t\tthis.pushFailure( "Expected at least one assertion, but none were run - call " +\n
\t\t\t\t"expect(0) to accept zero assertions.", this.stack );\n
\t\t}\n
\n
\t\tvar i,\n
\t\t\tbad = 0;\n
\n
\t\tthis.runtime = now() - this.started;\n
\t\tconfig.stats.all += this.assertions.length;\n
\t\tconfig.moduleStats.all += this.assertions.length;\n
\n
\t\tfor ( i = 0; i < this.assertions.length; i++ ) {\n
\t\t\tif ( !this.assertions[ i ].result ) {\n
\t\t\t\tbad++;\n
\t\t\t\tconfig.stats.bad++;\n
\t\t\t\tconfig.moduleStats.bad++;\n
\t\t\t}\n
\t\t}\n
\n
\t\trunLoggingCallbacks( "testDone", {\n
\t\t\tname: this.testName,\n
\t\t\tmodule: this.module.name,\n
\t\t\tskipped: !!this.skip,\n
\t\t\tfailed: bad,\n
\t\t\tpassed: this.assertions.length - bad,\n
\t\t\ttotal: this.assertions.length,\n
\t\t\truntime: this.runtime,\n
\n
\t\t\t// HTML Reporter use\n
\t\t\tassertions: this.assertions,\n
\t\t\ttestId: this.testId,\n
\n
\t\t\t// DEPRECATED: this property will be removed in 2.0.0, use runtime instead\n
\t\t\tduration: this.runtime\n
\t\t});\n
\n
\t\t// QUnit.reset() is deprecated and will be replaced for a new\n
\t\t// fixture reset function on QUnit 2.0/2.1.\n
\t\t// It\'s still called here for backwards compatibility handling\n
\t\tQUnit.reset();\n
\n
\t\tconfig.current = undefined;\n
\t},\n
\n
\tqueue: function() {\n
\t\tvar bad,\n
\t\t\ttest = this;\n
\n
\t\tif ( !this.valid() ) {\n
\t\t\treturn;\n
\t\t}\n
\n
\t\tfunction run() {\n
\n
\t\t\t// each of these can by async\n
\t\t\tsynchronize([\n
\t\t\t\tfunction() {\n
\t\t\t\t\ttest.before();\n
\t\t\t\t},\n
\n
\t\t\t\ttest.hooks( "beforeEach" ),\n
\n
\t\t\t\tfunction() {\n
\t\t\t\t\ttest.run();\n
\t\t\t\t},\n
\n
\t\t\t\ttest.hooks( "afterEach" ).reverse(),\n
\n
\t\t\t\tfunction() {\n
\t\t\t\t\ttest.after();\n
\t\t\t\t},\n
\t\t\t\tfunction() {\n
\t\t\t\t\ttest.finish();\n
\t\t\t\t}\n
\t\t\t]);\n
\t\t}\n
\n
\t\t// `bad` initialized at top of scope\n
\t\t// defer when previous test run passed, if storage is available\n
\t\tbad = QUnit.config.reorder && defined.sessionStorage &&\n
\t\t\t\t+sessionStorage.getItem( "qunit-test-" + this.module.name + "-" + this.testName );\n
\n
\t\tif ( bad ) {\n
\t\t\trun();\n
\t\t} else {\n
\t\t\tsynchronize( run, true );\n
\t\t}\n
\t},\n
\n
\tpush: function( result, actual, expected, message ) {\n
\t\tvar source,\n
\t\t\tdetails = {\n
\t\t\t\tmodule: this.module.name,\n
\t\t\t\tname: this.testName,\n
\t\t\t\tresult: result,\n
\t\t\t\tmessage: message,\n
\t\t\t\tactual: actual,\n
\t\t\t\texpected: expected,\n
\t\t\t\ttestId: this.testId,\n
\t\t\t\truntime: now() - this.started\n
\t\t\t};\n
\n
\t\tif ( !result ) {\n
\t\t\tsource = sourceFromStacktrace();\n
\n
\t\t\tif ( source ) {\n
\t\t\t\tdetails.source = source;\n
\t\t\t}\n
\t\t}\n
\n
\t\trunLoggingCallbacks( "log", details );\n
\n
\t\tthis.assertions.push({\n
\t\t\tresult: !!result,\n
\t\t\tmessage: message\n
\t\t});\n
\t},\n
\n
\tpushFailure: function( message, source, actual ) {\n
\t\tif ( !this instanceof Test ) {\n
\t\t\tthrow new Error( "pushFailure() assertion outside test context, was " +\n
\t\t\t\tsourceFromStacktrace( 2 ) );\n
\t\t}\n
\n
\t\tvar details = {\n
\t\t\t\tmodule: this.module.name,\n
\t\t\t\tname: this.testName,\n
\t\t\t\tresult: false,\n
\t\t\t\tmessage: message || "error",\n
\t\t\t\tactual: actual || null,\n
\t\t\t\ttestId: this.testId,\n
\t\t\t\truntime: now() - this.started\n
\t\t\t};\n
\n
\t\tif ( source ) {\n
\t\t\tdetails.source = source;\n
\t\t}\n
\n
\t\trunLoggingCallbacks( "log", details );\n
\n
\t\tthis.assertions.push({\n
\t\t\tresult: false,\n
\t\t\tmessage: message\n
\t\t});\n
\t},\n
\n
\tresolvePromise: function( promise, phase ) {\n
\t\tvar then, message,\n
\t\t\ttest = this;\n
\t\tif ( promise != null ) {\n
\t\t\tthen = promise.then;\n
\t\t\tif ( QUnit.objectType( then ) === "function" ) {\n
\t\t\t\tQUnit.stop();\n
\t\t\t\tthen.call(\n
\t\t\t\t\tpromise,\n
\t\t\t\t\tQUnit.start,\n
\t\t\t\t\tfunction( error ) {\n
\t\t\t\t\t\tmessage = "Promise rejected " +\n
\t\t\t\t\t\t\t( !phase ? "during" : phase.replace( /Each$/, "" ) ) +\n
\t\t\t\t\t\t\t" " + test.testName + ": " + ( error.message || error );\n
\t\t\t\t\t\ttest.pushFailure( message, extractStacktrace( error, 0 ) );\n
\n
\t\t\t\t\t\t// else next test will carry the responsibility\n
\t\t\t\t\t\tsaveGlobal();\n
\n
\t\t\t\t\t\t// Unblock\n
\t\t\t\t\t\tQUnit.start();\n
\t\t\t\t\t}\n
\t\t\t\t);\n
\t\t\t}\n
\t\t}\n
\t},\n
\n
\tvalid: function() {\n
\t\tvar include,\n
\t\t\tfilter = config.filter,\n
\t\t\tmodule = QUnit.urlParams.module && QUnit.urlParams.module.toLowerCase(),\n
\t\t\tfullName = ( this.module.name + ": " + this.testName ).toLowerCase();\n
\n
\t\t// Internally-generated tests are always valid\n
\t\tif ( this.callback && this.callback.validTest ) {\n
\t\t\treturn true;\n
\t\t}\n
\n
\t\tif ( config.testId.length > 0 && inArray( this.testId, config.testId ) < 0 ) {\n
\t\t\treturn false;\n
\t\t}\n
\n
\t\tif ( module && ( !this.module.name || this.module.name.toLowerCase() !== module ) ) {\n
\t\t\treturn false;\n
\t\t}\n
\n
\t\tif ( !filter ) {\n
\t\t\treturn true;\n
\t\t}\n
\n
\t\tinclude = filter.charAt( 0 ) !== "!";\n
\t\tif ( !include ) {\n
\t\t\tfilter = filter.toLowerCase().slice( 1 );\n
\t\t}\n
\n
\t\t// If the filter matches, we need to honour include\n
\t\tif ( fullName.indexOf( filter ) !== -1 ) {\n
\t\t\treturn include;\n
\t\t}\n
\n
\t\t// Otherwise, do the opposite\n
\t\treturn !include;\n
\t}\n
\n
};\n
\n
// Resets the test setup. Useful for tests that modify the DOM.\n
/*\n
DEPRECATED: Use multiple tests instead of resetting inside a test.\n
Use testStart or testDone for custom cleanup.\n
This method will throw an error in 2.0, and will be removed in 2.1\n
*/\n
QUnit.reset = function() {\n
\n
\t// Return on non-browser environments\n
\t// This is necessary to not break on node tests\n
\tif ( typeof window === "undefined" ) {\n
\t\treturn;\n
\t}\n
\n
\tvar fixture = defined.document && document.getElementById &&\n
\t\t\tdocument.getElementById( "qunit-fixture" );\n
\n
\tif ( fixture ) {\n
\t\tfixture.innerHTML = config.fixture;\n
\t}\n
};\n
\n
QUnit.pushFailure = function() {\n
\tif ( !QUnit.config.current ) {\n
\t\tthrow new Error( "pushFailure() assertion outside test context, in " +\n
\t\t\tsourceFromStacktrace( 2 ) );\n
\t}\n
\n
\t// Gets current test obj\n
\tvar currentTest = QUnit.config.current;\n
\n
\treturn currentTest.pushFailure.apply( currentTest, arguments );\n
};\n
\n
// Based on Java\'s String.hashCode, a simple but not\n
// rigorously collision resistant hashing function\n
function generateHash( module, testName ) {\n
\tvar hex,\n
\t\ti = 0,\n
\t\thash = 0,\n
\t\tstr = module + "\\x1C" + testName,\n
\t\tlen = str.length;\n
\n
\tfor ( ; i < len; i++ ) {\n
\t\thash = ( ( hash << 5 ) - hash ) + str.charCodeAt( i );\n
\t\thash |= 0;\n
\t}\n
\n
\t// Convert the possibly negative integer hash code into an 8 character hex string, which isn\'t\n
\t// strictly necessary but increases user understanding that the id is a SHA-like hash\n
\thex = ( 0x100000000 + hash ).toString( 16 );\n
\tif ( hex.length < 8 ) {\n
\t\thex = "0000000" + hex;\n
\t}\n
\n
\treturn hex.slice( -8 );\n
}\n
\n
function Assert( testContext ) {\n
\tthis.test = testContext;\n
}\n
\n
// Assert helpers\n
QUnit.assert = Assert.prototype = {\n
\n
\t// Specify the number of expected assertions to guarantee that failed test\n
\t// (no assertions are run at all) don\'t slip through.\n
\texpect: function( asserts ) {\n
\t\tif ( arguments.length === 1 ) {\n
\t\t\tthis.test.expected = asserts;\n
\t\t} else {\n
\t\t\treturn this.test.expected;\n
\t\t}\n
\t},\n
\n
\t// Increment this Test\'s semaphore counter, then return a single-use function that\n
\t// decrements that counter a maximum of once.\n
\tasync: function() {\n
\t\tvar test = this.test,\n
\t\t\tpopped = false;\n
\n
\t\ttest.semaphore += 1;\n
\t\ttest.usedAsync = true;\n
\t\tpauseProcessing();\n
\n
\t\treturn function done() {\n
\t\t\tif ( !popped ) {\n
\t\t\t\ttest.semaphore -= 1;\n
\t\t\t\tpopped = true;\n
\t\t\t\tresumeProcessing();\n
\t\t\t} else {\n
\t\t\t\ttest.pushFailure( "Called the callback returned from `assert.async` more than once",\n
\t\t\t\t\tsourceFromStacktrace( 2 ) );\n
\t\t\t}\n
\t\t};\n
\t},\n
\n
\t// Exports test.push() to the user API\n
\tpush: function( /* result, actual, expected, message */ ) {\n
\t\tvar assert = this,\n
\t\t\tcurrentTest = ( assert instanceof Assert && assert.test ) || QUnit.config.current;\n
\n
\t\t// Backwards compatibility fix.\n
\t\t// Allows the direct use of global exported assertions and QUnit.assert.*\n
\t\t// Although, it\'s use is not recommended as it can leak assertions\n
\t\t// to other tests from async tests, because we only get a reference to the current test,\n
\t\t// not exactly the test where assertion were intended to be called.\n
\t\tif ( !currentTest ) {\n
\t\t\tthrow new Error( "assertion outside test context, in " + sourceFromStacktrace( 2 ) );\n
\t\t}\n
\n
\t\tif ( currentTest.usedAsync === true && currentTest.semaphore === 0 ) {\n
\t\t\tcurrentTest.pushFailure( "Assertion after the final `assert.async` was resolved",\n
\t\t\t\tsourceFromStacktrace( 2 ) );\n
\n
\t\t\t// Allow this assertion to continue running anyway...\n
\t\t}\n
\n
\t\tif ( !( assert instanceof Assert ) ) {\n
\t\t\tassert = currentTest.assert;\n
\t\t}\n
\t\treturn assert.test.push.apply( assert.test, arguments );\n
\t},\n
\n
\t/**\n
\t * Asserts rough true-ish result.\n
\t * @name ok\n
\t * @function\n
\t * @example ok( "asdfasdf".length > 5, "There must be at least 5 chars" );\n
\t */\n
\tok: function( result, message ) {\n
\t\tmessage = message || ( result ? "okay" : "failed, expected argument to be truthy, was: " +\n
\t\t\tQUnit.dump.parse( result ) );\n
\t\tthis.push( !!result, result, true, message );\n
\t},\n
\n
\t/**\n
\t * Assert that the first two arguments are equal, with an optional message.\n
\t * Prints out both actual and expected values.\n
\t * @name equal\n
\t * @function\n
\t * @example equal( format( "{0} bytes.", 2), "2 bytes.", "replaces {0} with next argument" );\n
\t */\n
\tequal: function( actual, expected, message ) {\n
\t\t/*jshint eqeqeq:false */\n
\t\tthis.push( expected == actual, actual, expected, message );\n
\t},\n
\n
\t/**\n
\t * @name notEqual\n
\t * @function\n
\t */\n
\tnotEqual: function( actual, expected, message ) {\n
\t\t/*jshint eqeqeq:false */\n
\t\tthis.push( expected != actual, actual, expected, message );\n
\t},\n
\n
\t/**\n
\t * @name propEqual\n
\t * @function\n
\t */\n
\tpropEqual: function( actual, expected, message ) {\n
\t\tactual = objectValues( actual );\n
\t\texpected = objectValues( expected );\n
\t\tthis.push( QUnit.equiv( actual, expected ), actual, expected, message );\n
\t},\n
\n
\t/**\n
\t * @name notPropEqual\n
\t * @function\n
\t */\n
\tnotPropEqual: function( actual, expected, message ) {\n
\t\tactual = objectValues( actual );\n
\t\texpected = objectValues( expected );\n
\t\tthis.push( !QUnit.equiv( actual, expected ), actual, expected, message );\n
\t},\n
\n
\t/**\n
\t * @name deepEqual\n
\t * @function\n
\t */\n
\tdeepEqual: function( actual, expected, message ) {\n
\t\tthis.push( QUnit.equiv( actual, expected ), actual, expected, message );\n
\t},\n
\n
\t/**\n
\t * @name notDeepEqual\n
\t * @function\n
\t */\n
\tnotDeepEqual: function( actual, expected, message ) {\n
\t\tthis.push( !QUnit.equiv( actual, expected ), actual, expected, message );\n
\t},\n
\n
\t/**\n
\t * @name strictEqual\n
\t * @function\n
\t */\n
\tstrictEqual: function( actual, expected, message ) {\n
\t\tthis.push( expected === actual, actual, expected, message );\n
\t},\n
\n
\t/**\n
\t * @name notStrictEqual\n
\t * @function\n
\t */\n
\tnotStrictEqual: function( actual, expected, message ) {\n
\t\tthis.push( expected !== actual, actual, expected, message );\n
\t},\n
\n
\t"throws": function( block, expected, message ) {\n
\t\tvar actual, expectedType,\n
\t\t\texpectedOutput = expected,\n
\t\t\tok = false;\n
\n
\t\t// \'expected\' is optional unless doing string comparison\n
\t\tif ( message == null && typeof expected === "string" ) {\n
\t\t\tmessage = expected;\n
\t\t\texpected = null;\n
\t\t}\n
\n
\t\tthis.test.ignoreGlobalErrors = true;\n
\t\ttry {\n
\t\t\tblock.call( this.test.testEnvironment );\n
\t\t} catch (e) {\n
\t\t\tactual = e;\n
\t\t}\n
\t\tthis.test.ignoreGlobalErrors = false;\n
\n
\t\tif ( actual ) {\n
\t\t\texpectedType = QUnit.objectType( expected );\n
\n
\t\t\t// we don\'t want to validate thrown error\n
\t\t\tif ( !expected ) {\n
\t\t\t\tok = true;\n
\t\t\t\texpectedOutput = null;\n
\n
\t\t\t// expected is a regexp\n
\t\t\t} else if ( expectedType === "regexp" ) {\n
\t\t\t\tok = expected.test( errorString( actual ) );\n
\n
\t\t\t// expected is a string\n
\t\t\t} else if ( expectedType === "string" ) {\n
\t\t\t\tok = expected === errorString( actual );\n
\n
\t\t\t// expected is a constructor, maybe an Error constructor\n
\t\t\t} else if ( expectedType === "function" && actual instanceof expected ) {\n
\t\t\t\tok = true;\n
\n
\t\t\t// expected is an Error object\n
\t\t\t} else if ( expectedType === "object" ) {\n
\t\t\t\tok = actual instanceof expected.constructor &&\n
\t\t\t\t\tactual.name === expected.name &&\n
\t\t\t\t\tactual.message === expected.message;\n
\n
\t\t\t// expected is a validation function which returns true if validation passed\n
\t\t\t} else if ( expectedType === "function" && expected.call( {}, actual ) === true ) {\n
\t\t\t\texpectedOutput = null;\n
\t\t\t\tok = true;\n
\t\t\t}\n
\n
\t\t\tthis.push( ok, actual, expectedOutput, message );\n
\t\t} else {\n
\t\t\tthis.test.pushFailure( message, null, "No exception was thrown." );\n
\t\t}\n
\t}\n
};\n
\n
// Provide an alternative to assert.throws(), for enviroments that consider throws a reserved word\n
// Known to us are: Closure Compiler, Narwhal\n
(function() {\n
\t/*jshint sub:true */\n
\tAssert.prototype.raises = Assert.prototype[ "throws" ];\n
}());\n
\n
// Test for equality any JavaScript type.\n
// Author: Philippe Rathé <prathe@gmail.com>\n
QUnit.equiv = (function() {\n
\n
\t// Call the o related callback with the given arguments.\n
\tfunction bindCallbacks( o, callbacks, args ) {\n
\t\tvar prop = QUnit.objectType( o );\n
\t\tif ( prop ) {\n
\t\t\tif ( QUnit.objectType( callbacks[ prop ] ) === "function" ) {\n
\t\t\t\treturn callbacks[ prop ].apply( callbacks, args );\n
\t\t\t} else {\n
\t\t\t\treturn callbacks[ prop ]; // or undefined\n
\t\t\t}\n
\t\t}\n
\t}\n
\n
\t// the real equiv function\n
\tvar innerEquiv,\n
\n
\t\t// stack to decide between skip/abort functions\n
\t\tcallers = [],\n
\n
\t\t// stack to avoiding loops from circular referencing\n
\t\tparents = [],\n
\t\tparentsB = [],\n
\n
\t\tgetProto = Object.getPrototypeOf || function( obj ) {\n
\t\t\t/* jshint camelcase: false, proto: true */\n
\t\t\treturn obj.__proto__;\n
\t\t},\n
\t\tcallbacks = (function() {\n
\n
\t\t\t// for string, boolean, number and null\n
\t\t\tfunction useStrictEquality( b, a ) {\n
\n
\t\t\t\t/*jshint eqeqeq:false */\n
\t\t\t\tif ( b instanceof a.constructor || a instanceof b.constructor ) {\n
\n
\t\t\t\t\t// to catch short annotation VS \'new\' annotation of a\n
\t\t\t\t\t// declaration\n
\t\t\t\t\t// e.g. var i = 1;\n
\t\t\t\t\t// var j = new Number(1);\n
\t\t\t\t\treturn a == b;\n
\t\t\t\t} else {\n
\t\t\t\t\treturn a === b;\n
\t\t\t\t}\n
\t\t\t}\n
\n
\t\t\treturn {\n
\t\t\t\t"string": useStrictEquality,\n
\t\t\t\t"boolean": useStrictEquality,\n
\t\t\t\t"number": useStrictEquality,\n
\t\t\t\t"null": useStrictEquality,\n
\t\t\t\t"undefined": useStrictEquality,\n
\n
\t\t\t\t"nan": function( b ) {\n
\t\t\t\t\treturn isNaN( b );\n
\t\t\t\t},\n
\n
\t\t\t\t"date": function( b, a ) {\n
\t\t\t\t\treturn QUnit.objectType( b ) === "date" && a.valueOf() === b.valueOf();\n
\t\t\t\t},\n
\n
\t\t\t\t"regexp": function( b, a ) {\n
\t\t\t\t\treturn QUnit.objectType( b ) === "regexp" &&\n
\n
\t\t\t\t\t\t// the regex itself\n
\t\t\t\t\t\ta.source === b.source &&\n
\n
\t\t\t\t\t\t// and its modifiers\n
\t\t\t\t\t\ta.global === b.global &&\n
\n
\t\t\t\t\t\t// (gmi) ...\n
\t\t\t\t\t\ta.ignoreCase === b.ignoreCase &&\n
\t\t\t\t\t\ta.multiline === b.multiline &&\n
\t\t\t\t\t\ta.sticky === b.sticky;\n
\t\t\t\t},\n
\n
\t\t\t\t// - skip when the property is a method of an instance (OOP)\n
\t\t\t\t// - abort otherwise,\n
\t\t\t\t// initial === would have catch identical references anyway\n
\t\t\t\t"function": function() {\n
\t\t\t\t\tvar caller = callers[ callers.length - 1 ];\n
\t\t\t\t\treturn caller !== Object && typeof caller !== "undefined";\n
\t\t\t\t},\n
\n
\t\t\t\t"array": function( b, a ) {\n
\t\t\t\t\tvar i, j, len, loop, aCircular, bCircular;\n
\n
\t\t\t\t\t// b could be an object literal here\n
\t\t\t\t\tif ( QUnit.objectType( b ) !== "array" ) {\n
\t\t\t\t\t\treturn false;\n
\t\t\t\t\t}\n
\n
\t\t\t\t\tlen = a.length;\n
\t\t\t\t\tif ( len !== b.length ) {\n
\t\t\t\t\t\t// safe and faster\n
\t\t\t\t\t\treturn false;\n
\t\t\t\t\t}\n
\n
\t\t\t\t\t// track reference to avoid circular references\n
\t\t\t\t\tparents.push( a );\n
\t\t\t\t\tparentsB.push( b );\n
\t\t\t\t\tfor ( i = 0; i < len; i++ ) {\n
\t\t\t\t\t\tloop = false;\n
\t\t\t\t\t\tfor ( j = 0; j < parents.length; j++ ) {\n
\t\t\t\t\t\t\taCircular = parents[ j ] === a[ i ];\n
\t\t\t\t\t\t\tbCircular = parentsB[ j ] === b[ i ];\n
\t\t\t\t\t\t\tif ( aCircular || bCircular ) {\n
\t\t\t\t\t\t\t\tif ( a[ i ] === b[ i ] || aCircular && bCircular ) {\n
\t\t\t\t\t\t\t\t\tloop = true;\n
\t\t\t\t\t\t\t\t} else {\n
\t\t\t\t\t\t\t\t\tparents.pop();\n
\t\t\t\t\t\t\t\t\tparentsB.pop();\n
\t\t\t\t\t\t\t\t\treturn false;\n
\t\t\t\t\t\t\t\t}\n
\t\t\t\t\t\t\t}\n
\t\t\t\t\t\t}\n
\t\t\t\t\t\tif ( !loop && !innerEquiv( a[ i ], b[ i ] ) ) {\n
\t\t\t\t\t\t\tparents.pop();\n
\t\t\t\t\t\t\tparentsB.pop();\n
\t\t\t\t\t\t\treturn false;\n
\t\t\t\t\t\t}\n
\t\t\t\t\t}\n
\t\t\t\t\tparents.pop();\n
\t\t\t\t\tparentsB.pop();\n
\t\t\t\t\treturn true;\n
\t\t\t\t},\n
\n
\t\t\t\t"object": function( b, a ) {\n
\n
\t\t\t\t\t/*jshint forin:false */\n
\t\t\t\t\tvar i, j, loop, aCircular, bCircular,\n
\t\t\t\t\t\t// Default to true\n
\t\t\t\t\t\teq = true,\n
\t\t\t\t\t\taProperties = [],\n
\t\t\t\t\t\tbProperties = [];\n
\n
\t\t\t\t\t// comparing constructors is more strict than using\n
\t\t\t\t\t// instanceof\n
\t\t\t\t\tif ( a.constructor !== b.constructor ) {\n
\n
\t\t\t\t\t\t// Allow objects with no prototype to be equivalent to\n
\t\t\t\t\t\t// objects with Object as their constructor.\n
\t\t\t\t\t\tif ( !( ( getProto( a ) === null && getProto( b ) === Object.prototype ) ||\n
\t\t\t\t\t\t\t( getProto( b ) === null && getProto( a ) === Object.prototype ) ) ) {\n
\t\t\t\t\t\t\treturn false;\n
\t\t\t\t\t\t}\n
\t\t\t\t\t}\n
\n
\t\t\t\t\t// stack constructor before traversing properties\n
\t\t\t\t\tcallers.push( a.constructor );\n
\n
\t\t\t\t\t// track reference to avoid circular references\n
\t\t\t\t\tparents.push( a );\n
\t\t\t\t\tparentsB.push( b );\n
\n
\t\t\t\t\t// be strict: don\'t ensure hasOwnProperty and go deep\n
\t\t\t\t\tfor ( i in a ) {\n
\t\t\t\t\t\tloop = false;\n
\t\t\t\t\t\tfor ( j = 0; j < parents.length; j++ ) {\n
\t\t\t\t\t\t\taCircular = parents[ j ] === a[ i ];\n
\t\t\t\t\t\t\tbCircular = parentsB[ j ] === b[ i ];\n
\t\t\t\t\t\t\tif ( aCircular || bCircular ) {\n
\t\t\t\t\t\t\t\tif ( a[ i ] === b[ i ] || aCircular && bCircular ) {\n
\t\t\t\t\t\t\t\t\tloop = true;\n
\t\t\t\t\t\t\t\t} else {\n
\t\t\t\t\t\t\t\t\teq = false;\n
\t\t\t\t\t\t\t\t\tbreak;\n
\t\t\t\t\t\t\t\t}\n
\t\t\t\t\t\t\t}\n
\t\t\t\t\t\t}\n
\t\t\t\t\t\taProperties.push( i );\n
\t\t\t\t\t\tif ( !loop && !innerEquiv( a[ i ], b[ i ] ) ) {\n
\t\t\t\t\t\t\teq = false;\n
\t\t\t\t\t\t\tbreak;\n
\t\t\t\t\t\t}\n
\t\t\t\t\t}\n
\n
\t\t\t\t\tparents.pop();\n
\t\t\t\t\tparentsB.pop();\n
\t\t\t\t\tcallers.pop(); // unstack, we are done\n
\n
\t\t\t\t\tfor ( i in b ) {\n
\t\t\t\t\t\tbProperties.push( i ); // collect b\'s properties\n
\t\t\t\t\t}\n
\n
\t\t\t\t\t// Ensures identical properties name\n
\t\t\t\t\treturn eq && innerEquiv( aProperties.sort(), bProperties.sort() );\n
\t\t\t\t}\n
\t\t\t};\n
\t\t}());\n
\n
\tinnerEquiv = function() { // can take multiple arguments\n
\t\tvar args = [].slice.apply( arguments );\n
\t\tif ( args.length < 2 ) {\n
\t\t\treturn true; // end transition\n
\t\t}\n
\n
\t\treturn ( (function( a, b ) {\n
\t\t\tif ( a === b ) {\n
\t\t\t\treturn true; // catch the most you can\n
\t\t\t} else if ( a === null || b === null || typeof a === "undefined" ||\n
\t\t\t\t\ttypeof b === "undefined" ||\n
\t\t\t\t\tQUnit.objectType( a ) !== QUnit.objectType( b ) ) {\n
\n
\t\t\t\t// don\'t lose time with error prone cases\n
\t\t\t\treturn false;\n
\t\t\t} else {\n
\t\t\t\treturn bindCallbacks( a, callbacks, [ b, a ] );\n
\t\t\t}\n
\n
\t\t\t// apply transition with (1..n) arguments\n
\t\t}( args[ 0 ], args[ 1 ] ) ) &&\n
\t\t\tinnerEquiv.apply( this, args.splice( 1, args.length - 1 ) ) );\n
\t};\n
\n
\treturn innerEquiv;\n
}());\n
\n
// Based on jsDump by Ariel Flesler\n
// http://flesler.blogspot.com/2008/05/jsdump-pretty-dump-of-any-javascript.html\n
QUnit.dump = (function() {\n
\tfunction quote( str ) {\n
\t\treturn "\\"" + str.toString().replace( /"/g, "\\\\\\"" ) + "\\"";\n
\t}\n
\tfunction literal( o ) {\n
\t\treturn o + "";\n
\t}\n
\tfunction join( pre, arr, post ) {\n
\t\tvar s = dump.separator(),\n
\t\t\tbase = dump.indent(),\n
\t\t\tinner = dump.indent( 1 );\n
\t\tif ( arr.join ) {\n
\t\t\tarr = arr.join( "," + s + inner );\n
\t\t}\n
\t\tif ( !arr ) {\n
\t\t\treturn pre + post;\n
\t\t}\n
\t\treturn [ pre, inner + arr, base + post ].join( s );\n
\t}\n
\tfunction array( arr, stack ) {\n
\t\tvar i = arr.length,\n
\t\t\tret = new Array( i );\n
\n
\t\tif ( dump.maxDepth && dump.depth > dump.maxDepth ) {\n
\t\t\treturn "[object Array]";\n
\t\t}\n
\n
\t\tthis.up();\n
\t\twhile ( i-- ) {\n
\t\t\tret[ i ] = this.parse( arr[ i ], undefined, stack );\n
\t\t}\n
\t\tthis.down();\n
\t\treturn join( "[", ret, "]" );\n
\t}\n
\n
\tvar reName = /^function (\\w+)/,\n
\t\tdump = {\n
\n
\t\t\t// objType is used mostly internally, you can fix a (custom) type in advance\n
\t\t\tparse: function( obj, objType, stack ) {\n
\t\t\t\tstack = stack || [];\n
\t\t\t\tvar res, parser, parserType,\n
\t\t\t\t\tinStack = inArray( obj, stack );\n
\n
\t\t\t\tif ( inStack !== -1 ) {\n
\t\t\t\t\treturn "recursion(" + ( inStack - stack.length ) + ")";\n
\t\t\t\t}\n
\n
\t\t\t\tobjType = objType || this.typeOf( obj );\n
\t\t\t\tparser = this.parsers[ objType ];\n
\t\t\t\tparserType = typeof parser;\n
\n
\t\t\t\tif ( parserType === "function" ) {\n
\t\t\t\t\tstack.push( obj );\n
\t\t\t\t\tres = parser.call( this, obj, stack );\n
\t\t\t\t\tstack.pop();\n
\t\t\t\t\treturn res;\n
\t\t\t\t}\n
\t\t\t\treturn ( parserType === "string" ) ? parser : this.parsers.error;\n
\t\t\t},\n
\t\t\ttypeOf: function( obj ) {\n
\t\t\t\tvar type;\n
\t\t\t\tif ( obj === null ) {\n
\t\t\t\t\ttype = "null";\n
\t\t\t\t} else if ( typeof obj === "undefined" ) {\n
\t\t\t\t\ttype = "undefined";\n
\t\t\t\t} else if ( QUnit.is( "regexp", obj ) ) {\n
\t\t\t\t\ttype = "regexp";\n
\t\t\t\t} else if ( QUnit.is( "date", obj ) ) {\n
\t\t\t\t\ttype = "date";\n
\t\t\t\t} else if ( QUnit.is( "function", obj ) ) {\n
\t\t\t\t\ttype = "function";\n
\t\t\t\t} else if ( obj.setInterval !== undefined &&\n
\t\t\t\t\t\tobj.document !== undefined &&\n
\t\t\t\t\t\tobj.nodeType === undefined ) {\n
\t\t\t\t\ttype = "window";\n
\t\t\t\t} else if ( obj.nodeType === 9 ) {\n
\t\t\t\t\ttype = "document";\n
\t\t\t\t} else if ( obj.nodeType ) {\n
\t\t\t\t\ttype = "node";\n
\t\t\t\t} else if (\n
\n
\t\t\t\t\t// native arrays\n
\t\t\t\t\ttoString.call( obj ) === "[object Array]" ||\n
\n
\t\t\t\t\t// NodeList objects\n
\t\t\t\t\t( typeof obj.length === "number" && obj.item !== undefined &&\n
\t\t\t\t\t( obj.length ? obj.item( 0 ) === obj[ 0 ] : ( obj.item( 0 ) === null &&\n
\t\t\t\t\tobj[ 0 ] === undefined ) ) )\n
\t\t\t\t) {\n
\t\t\t\t\ttype = "array";\n
\t\t\t\t} else if ( obj.constructor === Error.prototype.constructor ) {\n
\t\t\t\t\ttype = "error";\n
\t\t\t\t} else {\n
\t\t\t\t\ttype = typeof obj;\n
\t\t\t\t}\n
\t\t\t\treturn type;\n
\t\t\t},\n
\t\t\tseparator: function() {\n
\t\t\t\treturn this.multiline ? this.HTML ? "<br />" : "\\n" : this.HTML ? "&#160;" : " ";\n
\t\t\t},\n
\t\t\t// extra can be a number, shortcut for increasing-calling-decreasing\n
\t\t\tindent: function( extra ) {\n
\t\t\t\tif ( !this.multiline ) {\n
\t\t\t\t\treturn "";\n
\t\t\t\t}\n
\t\t\t\tvar chr = this.indentChar;\n
\t\t\t\tif ( this.HTML ) {\n
\t\t\t\t\tchr = chr.replace( /\\t/g, " " ).replace( / /g, "&#160;" );\n
\t\t\t\t}\n
\t\t\t\treturn new Array( this.depth + ( extra || 0 ) ).join( chr );\n
\t\t\t},\n
\t\t\tup: function( a ) {\n
\t\t\t\tthis.depth += a || 1;\n
\t\t\t},\n
\t\t\tdown: function( a ) {\n
\t\t\t\tthis.depth -= a || 1;\n
\t\t\t},\n
\t\t\tsetParser: function( name, parser ) {\n
\t\t\t\tthis.parsers[ name ] = parser;\n
\t\t\t},\n
\t\t\t// The next 3 are exposed so you can use them\n
\t\t\tquote: quote,\n
\t\t\tliteral: literal,\n
\t\t\tjoin: join,\n
\t\t\t//\n
\t\t\tdepth: 1,\n
\t\t\tmaxDepth: 5,\n
\n
\t\t\t// This is the list of parsers, to modify them, use dump.setParser\n
\t\t\tparsers: {\n
\t\t\t\twindow: "[Window]",\n
\t\t\t\tdocument: "[Document]",\n
\t\t\t\terror: function( error ) {\n
\t\t\t\t\treturn "Error(\\"" + error.message + "\\")";\n
\t\t\t\t},\n
\t\t\t\tunknown: "[Unknown]",\n
\t\t\t\t"null": "null",\n
\t\t\t\t"undefined": "undefined",\n
\t\t\t\t"function": function( fn ) {\n
\t\t\t\t\tvar ret = "function",\n
\n
\t\t\t\t\t\t// functions never have name in IE\n
\t\t\t\t\t\tname = "name" in fn ? fn.name : ( reName.exec( fn ) || [] )[ 1 ];\n
\n
\t\t\t\t\tif ( name ) {\n
\t\t\t\t\t\tret += " " + name;\n
\t\t\t\t\t}\n
\t\t\t\t\tret += "( ";\n
\n
\t\t\t\t\tret = [ ret, dump.parse( fn, "functionArgs" ), "){" ].join( "" );\n
\t\t\t\t\treturn join( ret, dump.parse( fn, "functionCode" ), "}" );\n
\t\t\t\t},\n
\t\t\t\tarray: array,\n
\t\t\t\tnodelist: array,\n
\t\t\t\t"arguments": array,\n
\t\t\t\tobject: function( map, stack ) {\n
\t\t\t\t\tvar keys, key, val, i, nonEnumerableProperties,\n
\t\t\t\t\t\tret = [];\n
\n
\t\t\t\t\tif ( dump.maxDepth && dump.depth > dump.maxDepth ) {\n
\t\t\t\t\t\treturn "[object Object]";\n
\t\t\t\t\t}\n
\n
\t\t\t\t\tdump.up();\n
\t\t\t\t\tkeys = [];\n
\t\t\t\t\tfor ( key in map ) {\n
\t\t\t\t\t\tkeys.push( key );\n
\t\t\t\t\t}\n
\n
\t\t\t\t\t// Some properties are not always enumerable on Error objects.\n
\t\t\t\t\tnonEnumerableProperties = [ "message", "name" ];\n
\t\t\t\t\tfor ( i in nonEnumerableProperties ) {\n
\t\t\t\t\t\tkey = nonEnumerableProperties[ i ];\n
\t\t\t\t\t\tif ( key in map && !( key in keys ) ) {\n
\t\t\t\t\t\t\tkeys.push( key );\n
\t\t\t\t\t\t}\n
\t\t\t\t\t}\n
\t\t\t\t\tkeys.sort();\n
\t\t\t\t\tfor ( i = 0; i < keys.length; i++ ) {\n
\t\t\t\t\t\tkey = keys[ i ];\n
\t\t\t\t\t\tval = map[ key ];\n
\t\t\t\t\t\tret.push( dump.parse( key, "key" ) + ": " +\n
\t\t\t\t\t\t\tdump.parse( val, undefined, stack ) );\n
\t\t\t\t\t}\n
\t\t\t\t\tdump.down();\n
\t\t\t\t\treturn join( "{", ret, "}" );\n
\t\t\t\t},\n
\t\t\t\tnode: function( node ) {\n
\t\t\t\t\tvar len, i, val,\n
\t\t\t\t\t\topen = dump.HTML ? "&lt;" : "<",\n
\t\t\t\t\t\tclose = dump.HTML ? "&gt;" : ">",\n
\t\t\t\t\t\ttag = node.nodeName.toLowerCase(),\n
\t\t\t\t\t\tret = open + tag,\n
\t\t\t\t\t\tattrs = node.attributes;\n
\n
\t\t\t\t\tif ( attrs ) {\n
\t\t\t\t\t\tfor ( i = 0, len = attrs.length; i < len; i++ ) {\n
\t\t\t\t\t\t\tval = attrs[ i ].nodeValue;\n
\n
\t\t\t\t\t\t\t// IE6 includes all attributes in .attributes, even ones not explicitly\n
\t\t\t\t\t\t\t// set. Those have values like undefined, null, 0, false, "" or\n
\t\t\t\t\t\t\t// "inherit".\n
\t\t\t\t\t\t\tif ( val && val !== "inherit" ) {\n
\t\t\t\t\t\t\t\tret += " " + attrs[ i ].nodeName + "=" +\n
\t\t\t\t\t\t\t\t\tdump.parse( val, "attribute" );\n
\t\t\t\t\t\t\t}\n
\t\t\t\t\t\t}\n
\t\t\t\t\t}\n
\t\t\t\t\tret += close;\n
\n
\t\t\t\t\t// Show content of TextNode or CDATASection\n
\t\t\t\t\tif ( node.nodeType === 3 || node.nodeType === 4 ) {\n
\t\t\t\t\t\tret += node.nodeValue;\n
\t\t\t\t\t}\n
\n
\t\t\t\t\treturn ret + open + "/" + tag + close;\n
\t\t\t\t},\n
\n
\t\t\t\t// function calls it internally, it\'s the arguments part of the function\n
\t\t\t\tfunctionArgs: function( fn ) {\n
\t\t\t\t\tvar args,\n
\t\t\t\t\t\tl = fn.length;\n
\n
\t\t\t\t\tif ( !l ) {\n
\t\t\t\t\t\treturn "";\n
\t\t\t\t\t}\n
\n
\t\t\t\t\targs = new Array( l );\n
\t\t\t\t\twhile ( l-- ) {\n
\n
\t\t\t\t\t\t// 97 is \'a\'\n
\t\t\t\t\t\targs[ l ] = String.fromCharCode( 97 + l );\n
\t\t\t\t\t}\n
\t\t\t\t\treturn " " + args.join( ", " ) + " ";\n
\t\t\t\t},\n
\t\t\t\t// object calls it internally, the key part of an item in a map\n
\t\t\t\tkey: quote,\n
\t\t\t\t// function calls it internally, it\'s the content of the function\n
\t\t\t\tfunctionCode: "[code]",\n
\t\t\t\t// node calls it internally, it\'s an html attribute value\n
\t\t\t\tattribute: quote,\n
\t\t\t\tstring: quote,\n
\t\t\t\tdate: quote,\n
\t\t\t\tregexp: literal,\n
\t\t\t\tnumber: literal,\n
\t\t\t\t"boolean": literal\n
\t\t\t},\n
\t\t\t// if true, entities are escaped ( <, >, \\t, space and \\n )\n
\t\t\tHTML: false,\n
\t\t\t// indentation unit\n
\t\t\tindentChar: " ",\n
\t\t\t// if true, items in a collection, are separated by a \\n, else just a space.\n
\t\t\tmultiline: true\n
\t\t};\n
\n
\treturn dump;\n
}());\n
\n
// back compat\n
QUnit.jsDump = QUnit.dump;\n
\n
// For browser, export only select globals\n
if ( typeof window !== "undefined" ) {\n
\n
\t// Deprecated\n
\t// Extend assert methods to QUnit and Global scope through Backwards compatibility\n
\t(function() {\n
\t\tvar i,\n
\t\t\tassertions = Assert.prototype;\n
\n
\t\tfunction applyCurrent( current ) {\n
\t\t\treturn function() {\n
\t\t\t\tvar assert = new Assert( QUnit.config.current );\n
\t\t\t\tcurrent.apply( assert, arguments );\n
\t\t\t};\n
\t\t}\n
\n
\t\tfor ( i in assertions ) {\n
\t\t\tQUnit[ i ] = applyCurrent( assertions[ i ] );\n
\t\t}\n
\t})();\n
\n
\t(function() {\n
\t\tvar i, l,\n
\t\t\tkeys = [\n
\t\t\t\t"test",\n
\t\t\t\t"module",\n
\t\t\t\t"expect",\n
\t\t\t\t"asyncTest",\n
\t\t\t\t"start",\n
\t\t\t\t"stop",\n
\t\t\t\t"ok",\n
\t\t\t\t"equal",\n
\t\t\t\t"notEqual",\n
\t\t\t\t"propEqual",\n
\t\t\t\t"notPropEqual",\n
\t\t\t\t"deepEqual",\n
\t\t\t\t"notDeepEqual",\n
\t\t\t\t"strictEqual",\n
\t\t\t\t"notStrictEqual",\n
\t\t\t\t"throws"\n
\t\t\t];\n
\n
\t\tfor ( i = 0, l = keys.length; i < l; i++ ) {\n
\t\t\twindow[ keys[ i ] ] = QUnit[ keys[ i ] ];\n
\t\t}\n
\t})();\n
\n
\twindow.QUnit = QUnit;\n
}\n
\n
// For nodejs\n
if ( typeof module !== "undefined" && module && module.exports ) {\n
\tmodule.exports = QUnit;\n
\n
\t// For consistency with CommonJS environments\' exports\n
\tmodule.exports.QUnit = QUnit;\n
}\n
\n
// For CommonJS with exports, but without module.exports, like Rhino\n
if ( typeof exports !== "undefined" && exports ) {\n
\texports.QUnit = QUnit;\n
}\n
\n
// Get a reference to the global object, like window in browsers\n
}( (function() {\n
\treturn this;\n
})() ));\n
\n
/*istanbul ignore next */\n
// jscs:disable maximumLineLength\n
/*\n
* Javascript Diff Algorithm\n
* By John Resig (http://ejohn.org/)\n
* Modified by Chu Alan "sprite"\n
*\n
* Released under the MIT license.\n
*\n
* More Info:\n
* http://ejohn.org/projects/javascript-diff-algorithm/\n
*\n
* Usage: QUnit.diff(expected, actual)\n
*\n
* QUnit.diff( "the quick brown fox jumped over", "the quick fox jumps over" ) == "the quick <del>brown </del> fox <del>jumped </del><ins>jumps </ins> over"\n
*/\n
QUnit.diff = (function() {\n
\tvar hasOwn = Object.prototype.hasOwnProperty;\n
\n
\t/*jshint eqeqeq:false, eqnull:true */\n
\tfunction diff( o, n ) {\n
\t\tvar i,\n
\t\t\tns = {},\n
\t\t\tos = {};\n
\n
\t\tfor ( i = 0; i < n.length; i++ ) {\n
\t\t\tif ( !hasOwn.call( ns, n[ i ] ) ) {\n
\t\t\t\tns[ n[ i ] ] = {\n
\t\t\t\t\trows: [],\n
\t\t\t\t\to: null\n
\t\t\t\t};\n
\t\t\t}\n
\t\t\tns[ n[ i ] ].rows.push( i );\n
\t\t}\n
\n
\t\tfor ( i = 0; i < o.length; i++ ) {\n
\t\t\tif ( !hasOwn.call( os, o[ i ] ) ) {\n
\t\t\t\tos[ o[ i ] ] = {\n
\t\t\t\t\trows: [],\n
\t\t\t\t\tn: null\n
\t\t\t\t};\n
\t\t\t}\n
\t\t\tos[ o[ i ] ].rows.push( i );\n
\t\t}\n
\n
\t\tfor ( i in ns ) {\n
\t\t\tif ( hasOwn.call( ns, i ) ) {\n
\t\t\t\tif ( ns[ i ].rows.length === 1 && hasOwn.call( os, i ) && os[ i ].rows.length === 1 ) {\n
\t\t\t\t\tn[ ns[ i ].rows[ 0 ] ] = {\n
\t\t\t\t\t\ttext: n[ ns[ i ].rows[ 0 ] ],\n
\t\t\t\t\t\trow: os[ i ].rows[ 0 ]\n
\t\t\t\t\t};\n
\t\t\t\t\to[ os[ i ].rows[ 0 ] ] = {\n
\t\t\t\t\t\ttext: o[ os[ i ].rows[ 0 ] ],\n
\t\t\t\t\t\trow: ns[ i ].rows[ 0 ]\n
\t\t\t\t\t};\n
\t\t\t\t}\n
\t\t\t}\n
\t\t}\n
\n
\t\tfor ( i = 0; i < n.length - 1; i++ ) {\n
\t\t\tif ( n[ i ].text != null && n[ i + 1 ].text == null && n[ i ].row + 1 < o.length && o[ n[ i ].row + 1 ].text == null &&\n
\t\t\t\tn[ i + 1 ] == o[ n[ i ].row + 1 ] ) {\n
\n
\t\t\t\tn[ i + 1 ] = {\n
\t\t\t\t\ttext: n[ i + 1 ],\n
\t\t\t\t\trow: n[ i ].row + 1\n
\t\t\t\t};\n
\t\t\t\to[ n[ i ].row + 1 ] = {\n
\t\t\t\t\ttext: o[ n[ i ].row + 1 ],\n
\t\t\t\t\trow: i + 1\n
\t\t\t\t};\n
\t\t\t}\n
\t\t}\n
\n
\t\tfor ( i = n.length - 1; i > 0; i-- ) {\n
\t\t\tif ( n[ i ].text != null && n[ i - 1 ].text == null && n[ i ].row > 0 && o[ n[ i ].row - 1 ].text == null &&\n
\t\t\t\tn[ i - 1 ] == o[ n[ i ].row - 1 ] ) {\n
\n
\t\t\t\tn[ i - 1 ] = {\n
\t\t\t\t\ttext: n[ i - 1 ],\n
\t\t\t\t\trow: n[ i ].row - 1\n
\t\t\t\t};\n
\t\t\t\to[ n[ i ].row - 1 ] = {\n
\t\t\t\t\ttext: o[ n[ i ].row - 1 ],\n
\t\t\t\t\trow: i - 1\n
\t\t\t\t};\n
\t\t\t}\n
\t\t}\n
\n
\t\treturn {\n
\t\t\to: o,\n
\t\t\tn: n\n
\t\t};\n
\t}\n
\n
\treturn function( o, n ) {\n
\t\to = o.replace( /\\s+$/, "" );\n
\t\tn = n.replace( /\\s+$/, "" );\n
\n
\t\tvar i, pre,\n
\t\t\tstr = "",\n
\t\t\tout = diff( o === "" ? [] : o.split( /\\s+/ ), n === "" ? [] : n.split( /\\s+/ ) ),\n
\t\t\toSpace = o.match( /\\s+/g ),\n
\t\t\tnSpace = n.match( /\\s+/g );\n
\n
\t\tif ( oSpace == null ) {\n
\t\t\toSpace = [ " " ];\n
\t\t} else {\n
\t\t\toSpace.push( " " );\n
\t\t}\n
\n
\t\tif ( nSpace == null ) {\n
\t\t\tnSpace = [ " " ];\n
\t\t} else {\n
\t\t\tnSpace.push( " " );\n
\t\t}\n
\n
\t\tif ( out.n.length === 0 ) {\n
\t\t\tfor ( i = 0; i < out.o.length; i++ ) {\n
\t\t\t\tstr += "<del>" + out.o[ i ] + oSpace[ i ] + "</del>";\n
\t\t\t}\n
\t\t} else {\n
\t\t\tif ( out.n[ 0 ].text == null ) {\n
\t\t\t\tfor ( n = 0; n < out.o.length && out.o[ n ].text == null; n++ ) {\n
\t\t\t\t\tstr += "<del>" + out.o[ n ] + oSpace[ n ] + "</del>";\n
\t\t\t\t}\n
\t\t\t}\n
\n
\t\t\tfor ( i = 0; i < out.n.length; i++ ) {\n
\t\t\t\tif ( out.n[ i ].text == null ) {\n
\t\t\t\t\tstr += "<ins>" + out.n[ i ] + nSpace[ i ] + "</ins>";\n
\t\t\t\t} else {\n
\n
\t\t\t\t\t// `pre` initialized at top of scope\n
\t\t\t\t\tpre = "";\n
\n
\t\t\t\t\tfor ( n = out.n[ i ].row + 1; n < out.o.length && out.o[ n ].text == null; n++ ) {\n
\t\t\t\t\t\tpre += "<del>" + out.o[ n ] + oSpace[ n ] + "</del>";\n
\t\t\t\t\t}\n
\t\t\t\t\tstr += " " + out.n[ i ].text + nSpace[ i ] + pre;\n
\t\t\t\t}\n
\t\t\t}\n
\t\t}\n
\n
\t\treturn str;\n
\t};\n
}());\n
// jscs:enable\n
\n
(function() {\n
\n
// Deprecated QUnit.init - Ref #530\n
// Re-initialize the configuration options\n
QUnit.init = function() {\n
\tvar tests, banner, result, qunit,\n
\t\tconfig = QUnit.config;\n
\n
\tconfig.stats = { all: 0, bad: 0 };\n
\tconfig.moduleStats = { all: 0, bad: 0 };\n
\tconfig.started = 0;\n
\tconfig.updateRate = 1000;\n
\tconfig.blocking = false;\n
\tconfig.autostart = true;\n
\tconfig.autorun = false;\n
\tconfig.filter = "";\n
\tconfig.queue = [];\n
\n
\t// Return on non-browser environments\n
\t// This is necessary to not break on node tests\n
\tif ( typeof window === "undefined" ) {\n
\t\treturn;\n
\t}\n
\n
\tqunit = id( "qunit" );\n
\tif ( qunit ) {\n
\t\tqunit.innerHTML =\n
\t\t\t"<h1 id=\'qunit-header\'>" + escapeText( document.title ) + "</h1>" +\n
\t\t\t"<h2 id=\'qunit-banner\'></h2>" +\n
\t\t\t"<div id=\'qunit-testrunner-toolbar\'></div>" +\n
\t\t\t"<h2 id=\'qunit-userAgent\'></h2>" +\n
\t\t\t"<ol id=\'qunit-tests\'></ol>";\n
\t}\n
\n
\ttests = id( "qunit-tests" );\n
\tbanner = id( "qunit-banner" );\n
\tresult = id( "qunit-testresult" );\n
\n
\tif ( tests ) {\n
\t\ttests.innerHTML = "";\n
\t}\n
\n
\tif ( banner ) {\n
\t\tbanner.className = "";\n
\t}\n
\n
\tif ( result ) {\n
\t\tresult.parentNode.removeChild( result );\n
\t}\n
\n
\tif ( tests ) {\n
\t\tresult = document.createElement( "p" );\n
\t\tresult.id = "qunit-testresult";\n
\t\tresult.className = "result";\n
\t\ttests.parentNode.insertBefore( result, tests );\n
\t\tresult.innerHTML = "Running...<br />&#160;";\n
\t}\n
};\n
\n
// Don\'t load the HTML Reporter on non-Browser environments\n
if ( typeof window === "undefined" ) {\n
\treturn;\n
}\n
\n
var config = QUnit.config,\n
\thasOwn = Object.prototype.hasOwnProperty,\n
\tdefined = {\n
\t\tdocument: window.document !== undefined,\n
\t\tsessionStorage: (function() {\n
\t\t\tvar x = "qunit-test-string";\n
\t\t\ttry {\n
\t\t\t\tsessionStorage.setItem( x, x );\n
\t\t\t\tsessionStorage.removeItem( x );\n
\t\t\t\treturn true;\n
\t\t\t} catch ( e ) {\n
\t\t\t\treturn false;\n
\t\t\t}\n
\t\t}())\n
\t},\n
\tmodulesList = [];\n
\n
/**\n
* Escape text for attribute or text content.\n
*/\n
function escapeText( s ) {\n
\tif ( !s ) {\n
\t\treturn "";\n
\t}\n
\ts = s + "";\n
\n
\t// Both single quotes and double quotes (for attributes)\n
\treturn s.replace( /[\'"<>&]/g, function( s ) {\n
\t\tswitch ( s ) {\n
\t\tcase "\'":\n
\t\t\treturn "&#039;";\n
\t\tcase "\\"":\n
\t\t\treturn "&quot;";\n
\t\tcase "<":\n
\t\t\treturn "&lt;";\n
\t\tcase ">":\n
\t\t\treturn "&gt;";\n
\t\tcase "&":\n
\t\t\treturn "&amp;";\n
\t\t}\n
\t});\n
}\n
\n
/**\n
* @param {HTMLElement} elem\n
* @param {string} type\n
* @param {Function} fn\n
*/\n
function addEvent( elem, type, fn ) {\n
\tif ( elem.addEventListener ) {\n
\n
\t\t// Standards-based browsers\n
\t\telem.addEventListener( type, fn, false );\n
\t} else if ( elem.attachEvent ) {\n
\n
\t\t// support: IE <9\n
\t\telem.attachEvent( "on" + type, fn );\n
\t}\n
}\n
\n
/**\n
* @param {Array|NodeList} elems\n
* @param {string} type\n
* @param {Function} fn\n
*/\n
function addEvents( elems, type, fn ) {\n
\tvar i = elems.length;\n
\twhile ( i-- ) {\n
\t\taddEvent( elems[ i ], type, fn );\n
\t}\n
}\n
\n
function hasClass( elem, name ) {\n
\treturn ( " " + elem.className + " " ).indexOf( " " + name + " " ) >= 0;\n
}\n
\n
function addClass( elem, name ) {\n
\tif ( !hasClass( elem, name ) ) {\n
\t\telem.className += ( elem.className ? " " : "" ) + name;\n
\t}\n
}\n
\n
function toggleClass( elem, name ) {\n
\tif ( hasClass( elem, name ) ) {\n
\t\tremoveClass( elem, name );\n
\t} else {\n
\t\taddClass( elem, name );\n
\t}\n
}\n
\n
function removeClass( elem, name ) {\n
\tvar set = " " + elem.className + " ";\n
\n
\t// Class name may appear multiple times\n
\twhile ( set.indexOf( " " + name + " " ) >= 0 ) {\n
\t\tset = set.replace( " " + name + " ", " " );\n
\t}\n
\n
\t// trim for prettiness\n
\telem.className = typeof set.trim === "function" ? set.trim() : set.replace( /^\\s+|\\s+$/g, "" );\n
}\n
\n
function id( name ) {\n
\treturn defined.document && document.getElementById && document.getElementById( name );\n
}\n
\n
function getUrlConfigHtml() {\n
\tvar i, j, val,\n
\t\tescaped, escapedTooltip,\n
\t\tselection = false,\n
\t\tlen = config.urlConfig.length,\n
\t\turlConfigHtml = "";\n
\n
\tfor ( i = 0; i < len; i++ ) {\n
\t\tval = config.urlConfig[ i ];\n
\t\tif ( typeof val === "string" ) {\n
\t\t\tval = {\n
\t\t\t\tid: val,\n
\t\t\t\tlabel: val\n
\t\t\t};\n
\t\t}\n
\n
\t\tescaped = escapeText( val.id );\n
\t\tescapedTooltip = escapeText( val.tooltip );\n
\n
\t\tif ( config[ val.id ] === undefined ) {\n
\t\t\tconfig[ val.id ] = QUnit.urlParams[ val.id ];\n
\t\t}\n
\n
\t\tif ( !val.value || typeof val.value === "string" ) {\n
\t\t\turlConfigHtml += "<input id=\'qunit-urlconfig-" + escaped +\n
\t\t\t\t"\' name=\'" + escaped + "\' type=\'checkbox\'" +\n
\t\t\t\t( val.value ? " value=\'" + escapeText( val.value ) + "\'" : "" ) +\n
\t\t\t\t( config[ val.id ] ? " checked=\'checked\'" : "" ) +\n
\t\t\t\t" title=\'" + escapedTooltip + "\' /><label for=\'qunit-urlconfig-" + escaped +\n
\t\t\t\t"\' title=\'" + escapedTooltip + "\'>" + val.label + "</label>";\n
\t\t} else {\n
\t\t\turlConfigHtml += "<label for=\'qunit-urlconfig-" + escaped +\n
\t\t\t\t"\' title=\'" + escapedTooltip + "\'>" + val.label +\n
\t\t\t\t": </label><select id=\'qunit-urlconfig-" + escaped +\n
\t\t\t\t"\' name=\'" + escaped + "\' title=\'" + escapedTooltip + "\'><option></option>";\n
\n
\t\t\tif ( QUnit.is( "array", val.value ) ) {\n
\t\t\t\tfor ( j = 0; j < val.value.length; j++ ) {\n
\t\t\t\t\tescaped = escapeText( val.value[ j ] );\n
\t\t\t\t\turlConfigHtml += "<option value=\'" + escaped + "\'" +\n
\t\t\t\t\t\t( config[ val.id ] === val.value[ j ] ?\n
\t\t\t\t\t\t\t( selection = true ) && " selected=\'selected\'" : "" ) +\n
\t\t\t\t\t\t">" + escaped + "</option>";\n
\t\t\t\t}\n
\t\t\t} else {\n
\t\t\t\tfor ( j in val.value ) {\n
\t\t\t\t\tif ( hasOwn.call( val.value, j ) ) {\n
\t\t\t\t\t\turlConfigHtml += "<option value=\'" + escapeText( j ) + "\'" +\n
\t\t\t\t\t\t\t( config[ val.id ] === j ?\n
\t\t\t\t\t\t\t\t( selection = true ) && " selected=\'selected\'" : "" ) +\n
\t\t\t\t\t\t\t">" + escapeText( val.value[ j ] ) + "</option>";\n
\t\t\t\t\t}\n
\t\t\t\t}\n
\t\t\t}\n
\t\t\tif ( config[ val.id ] && !selection ) {\n
\t\t\t\tescaped = escapeText( config[ val.id ] );\n
\t\t\t\turlConfigHtml += "<option value=\'" + escaped +\n
\t\t\t\t\t"\' selected=\'selected\' disabled=\'disabled\'>" + escaped + "</option>";\n
\t\t\t}\n
\t\t\turlConfigHtml += "</select>";\n
\t\t}\n
\t}\n
\n
\treturn urlConfigHtml;\n
}\n
\n
// Handle "click" events on toolbar checkboxes and "change" for select menus.\n
// Updates the URL with the new state of `config.urlConfig` values.\n
function toolbarChanged() {\n
\tvar updatedUrl, value,\n
\t\tfield = this,\n
\t\tparams = {};\n
\n
\t// Detect if field is a select menu or a checkbox\n
\tif ( "selectedIndex" in field ) {\n
\t\tvalue = field.options[ field.selectedIndex ].value || undefined;\n
\t} else {\n
\t\tvalue = field.checked ? ( field.defaultValue || true ) : undefined;\n
\t}\n
\n
\tparams[ field.name ] = value;\n
\tupdatedUrl = setUrl( params );\n
\n
\tif ( "hidepassed" === field.name && "replaceState" in window.history ) {\n
\t\tconfig[ field.name ] = value || false;\n
\t\tif ( value ) {\n
\t\t\taddClass( id( "qunit-tests" ), "hidepass" );\n
\t\t} else {\n
\t\t\tremoveClass( id( "qunit-tests" ), "hidepass" );\n
\t\t}\n
\n
\t\t// It is not necessary to refresh the whole page\n
\t\twindow.history.replaceState( null, "", updatedUrl );\n
\t} else {\n
\t\twindow.location = updatedUrl;\n
\t}\n
}\n
\n
function setUrl( params ) {\n
\tvar key,\n
\t\tquerystring = "?";\n
\n
\tparams = QUnit.extend( QUnit.extend( {}, QUnit.urlParams ), params );\n
\n
\tfor ( key in params ) {\n
\t\tif ( hasOwn.call( params, key ) ) {\n
\t\t\tif ( params[ key ] === undefined ) {\n
\t\t\t\tcontinue;\n
\t\t\t}\n
\t\t\tquerystring += encodeURIComponent( key );\n
\t\t\tif ( params[ key ] !== true ) {\n
\t\t\t\tquerystring += "=" + encodeURIComponent( params[ key ] );\n
\t\t\t}\n
\t\t\tquerystring += "&";\n
\t\t}\n
\t}\n
\treturn location.protocol + "//" + location.host +\n
\t\tlocation.pathname + querystring.slice( 0, -1 );\n
}\n
\n
function applyUrlParams() {\n
\tvar selectBox = id( "qunit-modulefilter" ),\n
\t\tselection = decodeURIComponent( selectBox.options[ selectBox.selectedIndex ].value ),\n
\t\tfilter = id( "qunit-filter-input" ).value;\n
\n
\twindow.location = setUrl({\n
\t\tmodule: ( selection === "" ) ? undefined : selection,\n
\t\tfilter: ( filter === "" ) ? undefined : filter,\n
\n
\t\t// Remove testId filter\n
\t\ttestId: undefined\n
\t});\n
}\n
\n
function toolbarUrlConfigContainer() {\n
\tvar urlConfigContainer = document.createElement( "span" );\n
\n
\turlConfigContainer.innerHTML = getUrlConfigHtml();\n
\taddClass( urlConfigContainer, "qunit-url-config" );\n
\n
\t// For oldIE support:\n
\t// * Add handlers to the individual elements instead of the container\n
\t// * Use "click" instead of "change" for checkboxes\n
\taddEvents( urlConfigContainer.getElementsByTagName( "input" ), "click", toolbarChanged );\n
\taddEvents( urlConfigContainer.getElementsByTagName( "select" ), "change", toolbarChanged );\n
\n
\treturn urlConfigContainer;\n
}\n
\n
function toolbarLooseFilter() {\n
\tvar filter = document.createElement( "form" ),\n
\t\tlabel = document.createElement( "label" ),\n
\t\tinput = document.createElement( "input" ),\n
\t\tbutton = document.createElement( "button" );\n
\n
\taddClass( filter, "qunit-filter" );\n
\n
\tlabel.innerHTML = "Filter: ";\n
\n
\tinput.type = "text";\n
\tinput.value = config.filter || "";\n
\tinput.name = "filter";\n
\tinput.id = "qunit-filter-input";\n
\n
\tbutton.innerHTML = "Go";\n
\n
\tlabel.appendChild( input );\n
\n
\tfilter.appendChild( label );\n
\tfilter.appendChild( button );\n
\taddEvent( filter, "submit", function( ev ) {\n
\t\tapplyUrlParams();\n
\n
\t\tif ( ev && ev.preventDefault ) {\n
\t\t\tev.preventDefault();\n
\t\t}\n
\n
\t\treturn false;\n
\t});\n
\n
\treturn filter;\n
}\n
\n
function toolbarModuleFilterHtml() {\n
\tvar i,\n
\t\tmoduleFilterHtml = "";\n
\n
\tif ( !modulesList.length ) {\n
\t\treturn false;\n
\t}\n
\n
\tmodulesList.sort(function( a, b ) {\n
\t\treturn a.localeCompare( b );\n
\t});\n
\n
\tmoduleFilterHtml += "<label for=\'qunit-modulefilter\'>Module: </label>" +\n
\t\t"<select id=\'qunit-modulefilter\' name=\'modulefilter\'><option value=\'\' " +\n
\t\t( QUnit.urlParams.module === undefined ? "selected=\'selected\'" : "" ) +\n
\t\t">< All Modules ></option>";\n
\n
\tfor ( i = 0; i < modulesList.length; i++ ) {\n
\t\tmoduleFilterHtml += "<option value=\'" +\n
\t\t\tescapeText( encodeURIComponent( modulesList[ i ] ) ) + "\' " +\n
\t\t\t( QUnit.urlParams.module === modulesList[ i ] ? "selected=\'selected\'" : "" ) +\n
\t\t\t">" + escapeText( modulesList[ i ] ) + "</option>";\n
\t}\n
\tmoduleFilterHtml += "</select>";\n
\n
\treturn moduleFilterHtml;\n
}\n
\n
function toolbarModuleFilter() {\n
\tvar toolbar = id( "qunit-testrunner-toolbar" ),\n
\t\tmoduleFilter = document.createElement( "span" ),\n
\t\tmoduleFilterHtml = toolbarModuleFilterHtml();\n
\n
\tif ( !toolbar || !moduleFilterHtml ) {\n
\t\treturn false;\n
\t}\n
\n
\tmoduleFilter.setAttribute( "id", "qunit-modulefilter-container" );\n
\tmoduleFilter.innerHTML = moduleFilterHtml;\n
\n
\taddEvent( moduleFilter.lastChild, "change", applyUrlParams );\n
\n
\ttoolbar.appendChild( moduleFilter );\n
}\n
\n
function appendToolbar() {\n
\tvar toolbar = id( "qunit-testrunner-toolbar" );\n
\n
\tif ( toolbar ) {\n
\t\ttoolbar.appendChild( toolbarUrlConfigContainer() );\n
\t\ttoolbar.appendChild( toolbarLooseFilter() );\n
\t}\n
}\n
\n
function appendHeader() {\n
\tvar header = id( "qunit-header" );\n
\n
\tif ( header ) {\n
\t\theader.innerHTML = "<a href=\'" +\n
\t\t\tsetUrl({ filter: undefined, module: undefined, testId: undefined }) +\n
\t\t\t"\'>" + header.innerHTML + "</a> ";\n
\t}\n
}\n
\n
function appendBanner() {\n
\tvar banner = id( "qunit-banner" );\n
\n
\tif ( banner ) {\n
\t\tbanner.className = "";\n
\t}\n
}\n
\n
function appendTestResults() {\n
\tvar tests = id( "qunit-tests" ),\n
\t\tresult = id( "qunit-testresult" );\n
\n
\tif ( result ) {\n
\t\tresult.parentNode.removeChild( result );\n
\t}\n
\n
\tif ( tests ) {\n
\t\ttests.innerHTML = "";\n
\t\tresult = document.createElement( "p" );\n
\t\tresult.id = "qunit-testresult";\n
\t\tresult.className = "result";\n
\t\ttests.parentNode.insertBefore( result, tests );\n
\t\tresult.innerHTML = "Running...<br />&#160;";\n
\t}\n
}\n
\n
function storeFixture() {\n
\tvar fixture = id( "qunit-fixture" );\n
\tif ( fixture ) {\n
\t\tconfig.fixture = fixture.innerHTML;\n
\t}\n
}\n
\n
function appendUserAgent() {\n
\tvar userAgent = id( "qunit-userAgent" );\n
\tif ( userAgent ) {\n
\t\tuserAgent.innerHTML = "";\n
\t\tuserAgent.appendChild( document.createTextNode( navigator.userAgent ) );\n
\t}\n
}\n
\n
function appendTestsList( modules ) {\n
\tvar i, l, x, z, test, moduleObj;\n
\n
\tfor ( i = 0, l = modules.length; i < l; i++ ) {\n
\t\tmoduleObj = modules[ i ];\n
\n
\t\tif ( moduleObj.name ) {\n
\t\t\tmodulesList.push( moduleObj.name );\n
\t\t}\n
\n
\t\tfor ( x = 0, z = moduleObj.tests.length; x < z; x++ ) {\n
\t\t\ttest = moduleObj.tests[ x ];\n
\n
\t\t\tappendTest( test.name, test.testId, moduleObj.name );\n
\t\t}\n
\t}\n
}\n
\n
function appendTest( name, testId, moduleName ) {\n
\tvar title, rerunTrigger, testBlock, assertList,\n
\t\ttests = id( "qunit-tests" );\n
\n
\tif ( !tests ) {\n
\t\treturn;\n
\t}\n
\n
\ttitle = document.createElement( "strong" );\n
\ttitle.innerHTML = getNameHtml( name, moduleName );\n
\n
\trerunTrigger = document.createElement( "a" );\n
\trerunTrigger.innerHTML = "Rerun";\n
\trerunTrigger.href = setUrl({ testId: testId });\n
\n
\ttestBlock = document.createElement( "li" );\n
\ttestBlock.appendChild( title );\n
\ttestBlock.appendChild( rerunTrigger );\n
\ttestBlock.id = "qunit-test-output-" + testId;\n
\n
\tassertList = document.createElement( "ol" );\n
\tassertList.className = "qunit-assert-list";\n
\n
\ttestBlock.appendChild( assertList );\n
\n
\ttests.appendChild( testBlock );\n
}\n
\n
// HTML Reporter initialization and load\n
QUnit.begin(function( details ) {\n
\tvar qunit = id( "qunit" );\n
\n
\t// Fixture is the only one necessary to run without the #qunit element\n
\tstoreFixture();\n
\n
\tif ( qunit ) {\n
\t\tqunit.innerHTML =\n
\t\t\t"<h1 id=\'qunit-header\'>" + escapeText( document.title ) + "</h1>" +\n
\t\t\t"<h2 id=\'qunit-banner\'></h2>" +\n
\t\t\t"<div id=\'qunit-testrunner-toolbar\'></div>" +\n
\t\t\t"<h2 id=\'qunit-userAgent\'></h2>" +\n
\t\t\t"<ol id=\'qunit-tests\'></ol>";\n
\t}\n
\n
\tappendHeader();\n
\tappendBanner();\n
\tappendTestResults();\n
\tappendUserAgent();\n
\tappendToolbar();\n
\tappendTestsList( details.modules );\n
\ttoolbarModuleFilter();\n
\n
\tif ( qunit && config.hidepassed ) {\n
\t\taddClass( qunit.lastChild, "hidepass" );\n
\t}\n
});\n
\n
QUnit.done(function( details ) {\n
\tvar i, key,\n
\t\tbanner = id( "qunit-banner" ),\n
\t\ttests = id( "qunit-tests" ),\n
\t\thtml = [\n
\t\t\t"Tests completed in ",\n
\t\t\tdetails.runtime,\n
\t\t\t" milliseconds.<br />",\n
\t\t\t"<span class=\'passed\'>",\n
\t\t\tdetails.passed,\n
\t\t\t"</span> assertions of <span class=\'total\'>",\n
\t\t\tdetails.total,\n
\t\t\t"</span> passed, <span class=\'failed\'>",\n
\t\t\tdetails.failed,\n
\t\t\t"</span> failed."\n
\t\t].join( "" );\n
\n
\tif ( banner ) {\n
\t\tbanner.className = details.failed ? "qunit-fail" : "qunit-pass";\n
\t}\n
\n
\tif ( tests ) {\n
\t\tid( "qunit-testresult" ).innerHTML = html;\n
\t}\n
\n
\tif ( config.altertitle && defined.document && document.title ) {\n
\n
\t\t// show ✖ for good, ✔ for bad suite result in title\n
\t\t// use escape sequences in case file gets loaded with non-utf-8-charset\n
\t\tdocument.title = [\n
\t\t\t( details.failed ? "\\u2716" : "\\u2714" ),\n
\t\t\tdocument.title.replace( /^[\\u2714\\u2716] /i, "" )\n
\t\t].join( " " );\n
\t}\n
\n
\t// clear own sessionStorage items if all tests passed\n
\tif ( config.reorder && defined.sessionStorage && details.failed === 0 ) {\n
\t\tfor ( i = 0; i < sessionStorage.length; i++ ) {\n
\t\t\tkey = sessionStorage.key( i++ );\n
\t\t\tif ( key.indexOf( "qunit-test-" ) === 0 ) {\n
\t\t\t\tsessionStorage.removeItem( key );\n
\t\t\t}\n
\t\t}\n
\t}\n
\n
\t// scroll back to top to show results\n
\tif ( config.scrolltop && window.scrollTo ) {\n
\t\twindow.scrollTo( 0, 0 );\n
\t}\n
});\n
\n
function getNameHtml( name, module ) {\n
\tvar nameHtml = "";\n
\n
\tif ( module ) {\n
\t\tnameHtml = "<span class=\'module-name\'>" + escapeText( module ) + "</span>: ";\n
\t}\n
\n
\tnameHtml += "<span class=\'test-name\'>" + escapeText( name ) + "</span>";\n
\n
\treturn nameHtml;\n
}\n
\n
QUnit.testStart(function( details ) {\n
\tvar running, testBlock;\n
\n
\ttestBlock = id( "qunit-test-output-" + details.testId );\n
\tif ( testBlock ) {\n
\t\ttestBlock.className = "running";\n
\t} else {\n
\n
\t\t// Report later registered tests\n
\t\tappendTest( details.name, details.testId, details.module );\n
\t}\n
\n
\trunning = id( "qunit-testresult" );\n
\tif ( running ) {\n
\t\trunning.innerHTML = "Running: <br />" + getNameHtml( details.name, details.module );\n
\t}\n
\n
});\n
\n
QUnit.log(function( details ) {\n
\tvar assertList, assertLi,\n
\t\tmessage, expected, actual,\n
\t\ttestItem = id( "qunit-test-output-" + details.testId );\n
\n
\tif ( !testItem ) {\n
\t\treturn;\n
\t}\n
\n
\tmessage = escapeText( details.message ) || ( details.result ? "okay" : "failed" );\n
\tmessage = "<span class=\'test-message\'>" + message + "</span>";\n
\tmessage += "<span class=\'runtime\'>@ " + details.runtime + " ms</span>";\n
\n
\t// pushFailure doesn\'t provide details.expected\n
\t// when it calls, it\'s implicit to also not show expected and diff stuff\n
\t// Also, we need to check details.expected existence, as it can exist and be undefined\n
\tif ( !details.result && hasOwn.call( details, "expected" ) ) {\n
\t\texpected = escapeText( QUnit.dump.parse( details.expected ) );\n
\t\tactual = escapeText( QUnit.dump.parse( details.actual ) );\n
\t\tmessage += "<table><tr class=\'test-expected\'><th>Expected: </th><td><pre>" +\n
\t\t\texpected +\n
\t\t\t"</pre></td></tr>";\n
\n
\t\tif ( actual !== expected ) {\n
\t\t\tmessage += "<tr class=\'test-actual\'><th>Result: </th><td><pre>" +\n
\t\t\t\tactual + "</pre></td></tr>" +\n
\t\t\t\t"<tr class=\'test-diff\'><th>Diff: </th><td><pre>" +\n
\t\t\t\tQUnit.diff( expected, actual ) + "</pre></td></tr>";\n
\t\t}\n
\n
\t\tif ( details.source ) {\n
\t\t\tmessage += "<tr class=\'test-source\'><th>Source: </th><td><pre>" +\n
\t\t\t\tescapeText( details.source ) + "</pre></td></tr>";\n
\t\t}\n
\n
\t\tmessage += "</table>";\n
\n
\t// this occours when pushFailure is set and we have an extracted stack trace\n
\t} else if ( !details.result && details.source ) {\n
\t\tmessage += "<table>" +\n
\t\t\t"<tr class=\'test-source\'><th>Source: </th><td><pre>" +\n
\t\t\tescapeText( details.source ) + "</pre></td></tr>" +\n
\t\t\t"</table>";\n
\t}\n
\n
\tassertList = testItem.getElementsByTagName( "ol" )[ 0 ];\n
\n
\tassertLi = document.createElement( "li" );\n
\tassertLi.className = details.result ? "pass" : "fail";\n
\tassertLi.innerHTML = message;\n
\tassertList.appendChild( assertLi );\n
});\n
\n
QUnit.testDone(function( details ) {\n
\tvar testTitle, time, testItem, assertList,\n
\t\tgood, bad, testCounts, skipped,\n
\t\ttests = id( "qunit-tests" );\n
\n
\tif ( !tests ) {\n
\t\treturn;\n
\t}\n
\n
\ttestItem = id( "qunit-test-output-" + details.testId );\n
\n
\tassertList = testItem.getElementsByTagName( "ol" )[ 0 ];\n
\n
\tgood = details.passed;\n
\tbad = details.failed;\n
\n
\t// store result when possible\n
\tif ( config.reorder && defined.sessionStorage ) {\n
\t\tif ( bad ) {\n
\t\t\tsessionStorage.setItem( "qunit-test-" + details.module + "-" + details.name, bad );\n
\t\t} else {\n
\t\t\tsessionStorage.removeItem( "qunit-test-" + details.module + "-" + details.name );\n
\t\t}\n
\t}\n
\n
\tif ( bad === 0 ) {\n
\t\taddClass( assertList, "qunit-collapsed" );\n
\t}\n
\n
\t// testItem.firstChild is the test name\n
\ttestTitle = testItem.firstChild;\n
\n
\ttestCounts = bad ?\n
\t\t"<b class=\'failed\'>" + bad + "</b>, " + "<b class=\'passed\'>" + good + "</b>, " :\n
\t\t"";\n
\n
\ttestTitle.innerHTML += " <b class=\'counts\'>(" + testCounts +\n
\t\tdetails.assertions.length + ")</b>";\n
\n
\tif ( details.skipped ) {\n
\t\ttestItem.className = "skipped";\n
\t\tskipped = document.createElement( "em" );\n
\t\tskipped.className = "qunit-skipped-label";\n
\t\tskipped.innerHTML = "skipped";\n
\t\ttestItem.insertBefore( skipped, testTitle );\n
\t} else {\n
\t\taddEvent( testTitle, "click", function() {\n
\t\t\ttoggleClass( assertList, "qunit-collapsed" );\n
\t\t});\n
\n
\t\ttestItem.className = bad ? "fail" : "pass";\n
\n
\t\ttime = document.createElement( "span" );\n
\t\ttime.className = "runtime";\n
\t\ttime.innerHTML = details.runtime + " ms";\n
\t\ttestItem.insertBefore( time, assertList );\n
\t}\n
});\n
\n
if ( !defined.document || document.readyState === "complete" ) {\n
\tconfig.pageLoaded = true;\n
\tconfig.autorun = true;\n
}\n
\n
if ( defined.document ) {\n
\taddEvent( window, "load", QUnit.load );\n
}\n
\n
})();\n
]]></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Folder" module="OFS.Folder"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>list_field</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts31677048.93</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>index.html</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>text/html</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
<!DOCTYPE html>\n
<html>\n
<head>\n
<meta http-equiv="Content-type" content="text/html; charset=utf-8" />\n
<meta name="viewport" content="width=device-width, user-scalable=no" />\n
<title>Listfield</title>\n
\n
<!-- renderjs -->\n
<!--\n
<script src="rsvp.js" type="text/javascript"></script>\n
<script src="renderjs.js" type="text/javascript"></script>\n
-->\n
<script src="../lib/handlebars.min.js" type="text/javascript"></script>\n
<!-- custom script -->\n
<script src="listfield.js" type="text/javascript"></script>\n
\n
<script id="option-template" type="text/x-handlebars-template">\n
<option value="{{value}}">{{text}}</option>\n
</script>\n
\n
<script id="selected-option-template" type="text/x-handlebars-template">\n
<option selected="selected" value="{{value}}">{{text}}</option>\n
</script>\n
\n
</head>\n
<body>\n
<select />\n
</body>\n
</html>\n
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>880</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570624.3</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>listfield.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
/*global window, rJS, Handlebars */\n
/*jslint nomen: true */\n
(function(window, rJS, Handlebars) {\n
"use strict";\n
/////////////////////////////////////////////////////////////////\n
// Handlebars\n
/////////////////////////////////////////////////////////////////\n
// Precompile the templates while loading the first gadget instance\n
var gadget_klass = rJS(window), option_source = gadget_klass.__template_element.getElementById("option-template").innerHTML, option_template = Handlebars.compile(option_source), selected_option_source = gadget_klass.__template_element.getElementById("selected-option-template").innerHTML, selected_option_template = Handlebars.compile(selected_option_source);\n
gadget_klass.ready(function(g) {\n
return g.getElement().push(function(element) {\n
g.element = element;\n
});\n
}).declareMethod("render", function(options) {\n
var select = this.element.getElementsByTagName("select")[0], i, template, tmp = "";\n
select.setAttribute("name", options.key);\n
for (i = 0; i < options.property_definition.enum.length; i += 1) {\n
if (options.property_definition.enum[i] === options.value) {\n
template = selected_option_template;\n
} else {\n
template = option_template;\n
}\n
// XXX value and text are always same in json schema\n
tmp += template({\n
value: options.property_definition.enum[i],\n
text: options.property_definition.enum[i]\n
});\n
}\n
select.innerHTML += tmp;\n
}).declareMethod("getContent", function() {\n
var select = this.element.getElementsByTagName("select")[0], result = {};\n
result[select.getAttribute("name")] = select.options[select.selectedIndex].value;\n
return result;\n
});\n
})(window, rJS, Handlebars);
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>1870</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Folder" module="OFS.Folder"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>number_field</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts31677061.83</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>index.html</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>text/html</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
<!DOCTYPE html>\n
<html>\n
<head>\n
<meta http-equiv="Content-type" content="text/html; charset=utf-8" />\n
<meta name="viewport" content="width=device-width, user-scalable=no" />\n
<title>Number field</title>\n
\n
<!-- renderjs -->\n
<!--\n
<script src="rsvp.js" type="text/javascript"></script>\n
<script src="renderjs.js" type="text/javascript"></script>\n
-->\n
<!-- custom script -->\n
<script src="numberfield.js" type="text/javascript"></script>\n
\n
</head>\n
<body>\n
<input type=\'number\' step="any" data-mini="true" />\n
</body>\n
</html>\n
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>555</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570624.83</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>numberfield.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string>/*global window, rJS */\n
(function(window, rJS) {\n
"use strict";\n
rJS(window).ready(function(gadget) {\n
return gadget.getElement().push(function(element) {\n
gadget.element = element;\n
});\n
}).declareMethod("render", function(options) {\n
var input = this.element.querySelector("input");\n
input.setAttribute("value", options.value);\n
input.setAttribute("name", options.key);\n
input.setAttribute("title", options.property_definition.description);\n
}).declareMethod("getContent", function() {\n
var input = this.element.querySelector("input"), result = {};\n
if (input.value !== "") {\n
result[input.getAttribute("name")] = parseFloat(input.value);\n
} else {\n
result[input.getAttribute("name")] = null;\n
}\n
return result;\n
});\n
})(window, rJS);</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>860</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Folder" module="OFS.Folder"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>string_field</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts31677070.37</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>index.html</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>text/html</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string encoding="cdata"><![CDATA[
<!DOCTYPE html>\n
<html>\n
<head>\n
<meta http-equiv="Content-type" content="text/html; charset=utf-8" />\n
<meta name="viewport" content="width=device-width, user-scalable=no" />\n
<title>Stringfield</title>\n
\n
<!-- renderjs -->\n
<!--\n
<script src="rsvp.js" type="text/javascript"></script>\n
<script src="renderjs.js" type="text/javascript"></script>\n
-->\n
<!-- custom script -->\n
<script src="stringfield.js" type="text/javascript"></script>\n
\n
</head>\n
<body>\n
<input type=\'text\' data-mini="true" />\n
</body>\n
</html>\n
]]></string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>541</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="File" module="OFS.Image"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_EtagSupport__etag</string> </key>
<value> <string>ts25570625.27</string> </value>
</item>
<item>
<key> <string>__name__</string> </key>
<value> <string>stringfield.js</string> </value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>application/javascript</string> </value>
</item>
<item>
<key> <string>data</string> </key>
<value> <string>/*global window, rJS */\n
(function(window, rJS) {\n
"use strict";\n
rJS(window).ready(function(gadget) {\n
return gadget.getElement().push(function(element) {\n
gadget.element = element;\n
});\n
}).declareMethod("render", function(options) {\n
var input = this.element.querySelector("input");\n
input.setAttribute("value", options.value || "");\n
input.setAttribute("name", options.key);\n
input.setAttribute("title", options.property_definition.description);\n
}).declareMethod("getContent", function() {\n
var input = this.element.querySelector("input"), result = {};\n
result[input.getAttribute("name")] = input.value;\n
return result;\n
});\n
})(window, rJS);</string> </value>
</item>
<item>
<key> <string>precondition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>size</string> </key>
<value> <int>734</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="InteractionWorkflowDefinition" module="Products.ERP5.InteractionWorkflow"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>groups</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>business_process_graph_editor_interaction_workflow</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Interaction" module="Products.ERP5.Interaction"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_mapping</string> </key>
<value>
<dictionary/>
</value>
</item>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>interactions</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="InteractionDefinition" module="Products.ERP5.Interaction"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>actbox_category</string> </key>
<value> <string>workflow</string> </value>
</item>
<item>
<key> <string>actbox_name</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>actbox_url</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>activate_script_name</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>after_script_name</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>before_commit_script_name</string> </key>
<value>
<list>
<string>afterEdit</string>
</list>
</value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>guard</string> </key>
<value>
<none/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>edit</string> </value>
</item>
<item>
<key> <string>method_id</string> </key>
<value>
<list>
<string>edit</string>
</list>
</value>
</item>
<item>
<key> <string>once_per_transaction</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>portal_type_filter</string> </key>
<value>
<none/>
</value>
</item>
<item>
<key> <string>portal_type_group_filter</string> </key>
<value>
<none/>
</value>
</item>
<item>
<key> <string>script_name</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>temporary_document_disallowed</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>trigger_type</string> </key>
<value> <int>2</int> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Scripts" module="Products.DCWorkflow.Scripts"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_mapping</string> </key>
<value>
<dictionary/>
</value>
</item>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>scripts</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="PythonScript" module="Products.PythonScripts.PythonScript"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>Script_magic</string> </key>
<value> <int>3</int> </value>
</item>
<item>
<key> <string>_bind_names</string> </key>
<value>
<object>
<klass>
<global name="NameAssignments" module="Shared.DC.Scripts.Bindings"/>
</klass>
<tuple/>
<state>
<dictionary>
<item>
<key> <string>_asgns</string> </key>
<value>
<dictionary>
<item>
<key> <string>name_container</string> </key>
<value> <string>container</string> </value>
</item>
<item>
<key> <string>name_context</string> </key>
<value> <string>context</string> </value>
</item>
<item>
<key> <string>name_m_self</string> </key>
<value> <string>script</string> </value>
</item>
<item>
<key> <string>name_subpath</string> </key>
<value> <string>traverse_subpath</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</state>
</object>
</value>
</item>
<item>
<key> <string>_body</string> </key>
<value> <string>import json\n
business_process = sci[\'object\']\n
graph = business_process.getProperty(\'jsplumb_graph\')\n
\n
assert graph\n
\n
if graph:\n
portal = business_process.getPortalObject()\n
trade_state_dict = dict(start=None, end=None)\n
for trade_state in portal.portal_categories.trade_state.getCategoryChildValueList():\n
# XXX I hope no duplicates\n
trade_state_dict[trade_state.getReference() or trade_state.getId()] = trade_state\n
\n
graph = json.loads(graph)[\'graph\']\n
for edge_data in graph[\'edge\'].values():\n
# Create the business link if it does not exist yet.\n
if not edge_data.get(\'business_link_url\'):\n
business_link = business_process.newContent(\n
portal_type=\'Business Link\',\n
predecessor_value=trade_state_dict[edge_data[\'source\']],\n
successor_value=trade_state_dict[edge_data[\'destination\']],\n
)\n
else:\n
# XXX Zope does not like to traverse unicode ...\n
business_link = portal.restrictedTraverse(str(edge_data[\'business_link_url\']))\n
business_link.edit(\n
title=edge_data.get(\'name\'),\n
# XXX Zope does not like to traverse unicode ...\n
trade_phase=str(edge_data.get(\'trade_phase\', \'\')),\n
)\n
</string> </value>
</item>
<item>
<key> <string>_params</string> </key>
<value> <string>sci</string> </value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>afterEdit</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Variables" module="Products.DCWorkflow.Variables"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_mapping</string> </key>
<value>
<dictionary/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>variables</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Worklists" module="Products.DCWorkflow.Worklists"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_mapping</string> </key>
<value>
<dictionary/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>worklists</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
Business Process | view_graph_editor
\ No newline at end of file
Business Process | business_process_graph_editor_interaction_workflow
\ No newline at end of file
erp5_graph_editor
\ No newline at end of file
business_process_graph_editor_interaction_workflow
\ No newline at end of file
erp5_graph_editor
\ No newline at end of file
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment