{"version":3,"file":"kendo.dataviz.diagram.min.js","names":["global","factory","exports","module","require","define","amd","globalThis","self","kendodataviz","diagram","js","this","$","undefined$1","kendo","window","dataviz","deepExtend","isArray","Array","Utils","isNearZero","num","Math","abs","isDefined","obj","isUndefined","isObject","Object","has","key","hasOwnProperty","call","isString","prototype","toString","isBoolean","isType","type","isNumber","isNaN","parseFloat","isFinite","isEmpty","length","simpleExtend","destination","source","name","initArray","size","value","array","i","serializePoints","points","res","p","push","x","y","join","deserializePoints","s","v","split","Point","parseInt","randomInteger","lower","upper","floor","random","DFT","el","func","childNodes","item","getMatrixAngle","m","d","atan2","b","PI","getMatrixScaling","sqrt","a","c","sign","number","findAngle","center","end","start","sngXComp","sngYComp","atan","findRadian","forEach","arr","iterator","thisRef","any","predicate","remove","what","ax","indexOf","splice","contains","inArray","fold","list","acc","context","initial","arguments","find","result","index","first","constraint","insert","element","position","all","clear","bisort","sortfunc","sort","n","addRange","range","apply","Easing","pos","cos","Ticker","Class","extend","init","adapters","target","tick","interval","duration","lastTime","handlers","_this","transition","timerDelegate","onTimerEvent","addAdapter","onComplete","handler","removeHandler","grep","h","trigger","caller","onStep","seekTo","to","seekFromTo","from","max","min","Date","getTime","intervalId","setInterval","stop","clearInterval","play","origin","initState","reverse","propagate","update","now","timePassed","movement","ui","Range","step","Infinity","j","k","rangeIntegerScale","jQuery","Point2D","isFunction","map","fn","plus","minus","offset","times","normalize","lengthSquared","middleOf","q","toPolar","useDegrees","factor","halfpi","len","Polar","isOnLine","temp","o1","u1","r1","Rect","inflate","r2","union","height","width","parse","str","xy","slice","PathDefiner","left","right","point","dx","dy","r","x1","y1","x2","y2","top","bottom","topLeft","topRight","bottomLeft","bottomRight","clone","equals","rect","rotatedBounds","angle","rotatedPoints","tl","tr","br","bl","rotate","delimiter","scale","scaleX","scaleY","staicPoint","adornerCenter","thisCenter","delta","scaled","zoom","overlaps","rectBottomRight","Size","intersectLine","start1","end1","start2","end2","isSegment","tangensdiff","Empty","toRect","empty","fromPoints","Intersect","lines","segments","rectWithLine","rects","rect1","rect2","intersect","reverseAngle","RectAlign","container","align","content","alignment","alignValues","toLowerCase","_singleAlign","_align","_left","_center","_right","stretch","_stretch","_top","middle","_middle","_bottom","alignCalc","Matrix","e","f","applyRect","fromSVGMatrix","vm","fromMatrixVector","fromList","translation","unit","rotation","sin","scaling","parts","nums","trim","substr","MatrixVector","fromMatrix","randomId","chars","charAt","round","Geometry","_distanceToLineSquared","d2","pt1","pt2","vx","vy","dot","distanceToLine","distanceToPolyline","minimum","Number","MAX_VALUE","p1","p2","HashTable","_buckets","add","_createGetBucket","get","_bucketExists","set","containsKey","hashId","_hash","hashes","_hashes","hash","bucket","ht","_hashString","_objectHashId","charCodeAt","id","_hashId","Dictionary","Observable","dictionary","_hashTable","entry","Error","forEachValue","forEachKey","keys","Queue","_tail","_head","enqueue","next","dequeue","current","Set","resource","kv","toArray","Node","shape","links","outgoing","incoming","weight","associatedShape","bounds","data","shortForm","isVirtual","isIsolated","isLinkedTo","node","that","link","getComplement","getChildren","children","getParents","parents","copy","balance","owner","adjacentTo","removeLink","hasLinkTo","degree","incidentWith","getLinksWith","getNeighbors","neighbors","Link","connection","sourceFound","targetFound","associatedConnection","getCommonNode","isBridging","v1","v2","getNodes","changeSource","changeTarget","changesNodes","w","oldSource","oldTarget","directTo","createReverseEdge","reversed","Graph","idOrDiagram","nodes","_nodeMap","_root","_hasCachedRelationships","cacheRelationships","forceRebuild","assignLevels","startNode","visited","level","child","root","found","getConnectedComponents","componentIndex","setItemIndices","componentId","_collectConnectedNodes","components","addNodeAndOutgoings","setIds","nodeIndex","nextId","calcBounds","getSpanningTree","tree","remaining","_addNode","levelCount","pop","ni","cn","newLink","addLink","treeLevels","takeRandomNode","excludedNodes","incidenceLessThan","pool","isHealthy","hasNode","sourceOrLink","addExistingLink","foundSource","getNode","addNode","foundTarget","removeAllLinks","hasLink","t","linkOrId","nodeOrId","_removeNode","removeNode","areConnected","n1","n2","layoutRect","newNode","newLinks","saveMapping","save","nodeMap","linkMap","nOriginal","nCopy","linkOriginal","linkCopy","linearize","addIds","depthFirstTraversal","action","foundNode","_dftIterator","breadthFirstTraversal","queue","_stronglyConnectedComponents","excludeSingleItems","indices","lowLinks","connected","stack","component","findCycles","isAcyclic","isSubGraph","other","otherArray","thisArray","makeAcyclic","oneNode","rev","N","intensityCatalog","flowIntensity","catalogEqualIntensity","intensity","sourceStack","targetStack","targets","li","targetLink","unshift","sources","si","sourceLink","ri","ril","u","concat","vertexOrder","kk","reversedEdges","Predefined","EightGraph","Mindmap","ThreeGraph","BinaryTree","levels","createBalancedTree","Linear","Tree","siblingsCount","Forest","trees","createBalancedForest","Workflow","Grid","g","previous","graphString","previousLink","graph","part","lin","_addShape","kendoDiagram","shapeDefaults","radius","fill","undoable","addShape","_addConnection","options","connect","createDiagramFromGraph","doLayout","randomSize","clientWidth","clientHeight","opt","color","gli","sourceShape","targetShape","SpringLayout","layoutGraph","limitToView","shi","news","counter","lastAdded","parent","treeCount","createRandomConnectedGraph","nodeCount","maxIncidence","isTree","poolNode","randomAdditions","randomDiagram","shapeCount","normalVariable","mean","deviation","log","geometry","drawing","defined","util","TRANSPARENT","Markers","none","arrowStart","filledCircle","arrowEnd","START","END","WIDTH","HEIGHT","diffNumericOptions","fields","field","elementOptions","hasChanges","Scale","toMatrix","format","invert","Translation","toMatrixVector","Length","Rotation","ZERO","create","values","CompositeTransform","translate","transform","render","visual","_transform","_renderTransform","rotateMatrix","scaleMatrix","translatePoint","AutoSizeableMixin","_setScale","originWidth","_originWidth","originHeight","_originHeight","_setTranslate","_initSize","autoSize","_measure","_updateSize","_diffNumericOptions","Element","_originSize","visible","drawingContainer","redraw","drawingElement","matrix","_hover","force","_measured","box","_boundingBox","startPoint","rawBBox","VisualBase","normalizeDrawingOptions","stroke","opacity","_fill","getColor","_stroke","show","hover","strokeOptions","dashType","fillOptions","gradient","GradientClass","RadialGradient","LinearGradient","TextBlock","_textColor","_font","_initText","fontSize","fontFamily","Text","text","font","fontOptions","fontStyle","fontWeight","sizeChanged","textOptions","Rectangle","_initPath","_setPosition","_drawPath","Path","closed","sizeOptions","sizeOptionsOrDefault","elements","createSegment","MarkerBase","anchor","createElement","_transformToPath","path","transformCopy","CircleMarker","Circle","positionMarker","targetSegment","ArrowMarker","xDiff","yDiff","_linePoints","deg","endPoint","controlOut","nextSegment","controlIn","prevSegment","MarkerPathMixin","_getPath","MultiPath","paths","_normalizeMarkerOptions","startCap","endCap","_removeMarker","marker","_markers","_createMarkers","_createMarker","markerType","append","_positionMarker","_capMap","_redrawMarker","pathChange","pathOptions","cap","pathCapType","optionsCap","created","_redrawMarkers","Group","_createElements","_setData","multipath","Line","Polyline","_updatePath","_pointsDiffer","currentPoints","differ","Image","_initImage","src","_rect","_childrenChange","_remove","removeAt","toFront","visuals","toBack","_reorderChildren","toIndex","group","drawingChildren","fixedPosition","boundingBox","childBoundingBox","_includeInBBox","clippedBBox","Layout","toDrawingRect","drawingRect","reflow","_initCircle","circleOptions","move","_circle","setRadius","Canvas","surface","Surface","_translate","_viewBox","viewBox","setSize","draw","insertBefore","destroy","clearHtml","drawingOptions","Color","toHex","Segment","Movable","Cursors","arrow","grip","cross","select","south","east","west","north","rowresize","colresize","HIT_TEST_DISTANCE","AUTO","TOP","RIGHT","LEFT","BOTTOM","DRAG_START","DRAG","DRAG_END","ITEMBOUNDSCHANGE","ROTATED","TARGET","HANDLE_NAMES","PositionAdapter","layoutState","froms","tos","subjects","getShapeById","LayoutUndoUnit","initialState","finalState","animate","_initialState","_finalState","title","undo","setState","redo","state","conn","ticker","CompositeUnit","units","undoUnit","ConnectionEditUnit","redoSource","redoTarget","_redoSource","_redoTarget","_undoSource","_undoTarget","_updateConnector","updateModel","ConnectionEditUndoUnit","undoSource","undoTarget","DeleteConnectionUnit","targetConnector","DeleteShapeUnit","TransformUnit","shapes","undoStates","adorner","redoStates","layout","refreshBounds","refresh","AddConnectionUnit","AddShapeUnit","deselect","PanUndoUnit","initialPosition","finalPosition","finalPos","pan","RotateUnit","undoRotates","redoRotates","redoAngle","_angle","_innerBounds","_initialize","ToFrontUnit","items","initialIndices","_toIndex","ToBackUnit","UndoRedoService","bind","events","capacity","begin","composite","cancel","commit","execute","_restart","addCompositeItem","count","EmptyTool","toolService","tryActivate","getCursor","ScrollerTool","tool","friction","support","mobileOS","canvas","scroller","scrollable","kendoMobileScroller","velocityMultiplier","mousewheelScrolling","scroll","_move","movableCanvas","virtualScroll","dimension","makeVirtual","virtualSize","dimensions","disable","meta","pannable","enabled","ctrlKey","noMeta","hoveredItem","hoveredAdorner","_hoveredConnector","enable","args","scrollPos","scrollLeft","scrollTop","_storePan","moveTo","_pan","PointerTool","selectSingle","handle","_hitTest","_resizingAdorner","isDragHandle","connections","undoRedoService","_getCursor","SelectionTool","selectable","multiple","selector","isSelected","selectArea","ConnectionTool","connector","_createConnection","_c","canDrag","connectionHandle","_connectionManipulation","_removeHover","activeConnection","_cachedTouchTarget","cachedTouchTarget","sourceConnector","Shape","getConnector","_syncConnectionChanges","_connectorsAdorner","ConnectionEditTool","isActive","handleName","testKey","toUpperCase","ToolService","tools","activeTool","_updateHoveredItem","_activateTool","_updateCursor","focus","suspendTracking","updateHovered","resumeTracking","keyDown","metaKey","altKey","toRemove","_triggerRemove","_syncChanges","_destroyToolBar","_discardNewConnection","selectAll","cut","paste","wheel","z","zoomRate","zoomOptions","zoomMin","zoomMax","setTool","addToSelection","newConnection","cursor","css","disabledShape","isNew","hit","_visible","selectedConnections","_selectedItems","Connection","_hitTestItems","_hitTestElements","shapeHit","connectionHit","idx","connectors","hitTestShapeConnectors","mainLayer","ConnectionRouterBase","LinearConnectionRouter","hitTest","getBounds","allPoints","PolylineRouter","route","CascadingRouter","SAME_SIDE_DISTANCE_RATIO","routePoints","_connectorPoints","_floatingPoints","_resolvedSourceConnector","_resolvedTargetConnector","sourcePoint","targetPoint","_connectorSides","axis","boundsPoint","secondarySign","_connectorSide","sideDistance","minSide","side","shapeBounds","sides","MAX_NUM","_sameSideDistance","pointX","pointY","sourceConnectorSide","targetConnectorSide","deltaX","deltaY","sameSideDistance","shiftX","shiftY","cascadeStartHorizontal","_startHorizontal","sourceSide","AdornerBase","_adorners","ConnectionEditAdorner","_ts","sp","tp","spVisual","handles","epVisual","_initialSource","_initialTarget","ts","radiusX","radiusY","sourcePointDistance","distanceTo","targetPointDistance","sourceHandle","targetHandle","modelToLayer","ConnectorsAdorner","_refreshHandler","ctr","_clearVisual","ConnectorVisual","_keepCachedTouchTarget","visualChildren","childrenCount","unbind","each","ResizingAdorner","_manipulating","_initSelection","_createHandles","selected","_internalChange","_rotatedHandler","_resizable","editable","resize","_handleOptions","_bounds","handleBounds","handlesCount","_getHandleBounds","_rotationOffset","_startAngle","_rotates","_positions","initialRotates","initialStates","handleOptions","_sp","_cp","_lp","shapeStates","visibleHandles","currentAngle","dragging","newBounds","staticPoint","dtl","dbr","changed","_truncateAngle","_rotating","shouldSnap","thr","_truncateDistance","hitToOppositeSide","_displaceBounds","newCenter","minWidth","minHeight","oldBounds","states","_truncatePositionToGuides","ruler","truncatePositionToGuides","_truncateSizeToGuides","truncateSizeToGuides","snap","snapOptions","snapAngle","snapSize","drag","_diffStates","_syncShapeChanges","rotationThumb","thumb","_rotationThumbBounds","Selector","_ep","_adorn","visualBounds","modelToView","relative","_visualBounds","shiftKey","HyperTree","EPSILON","DEG_TO_RAD","LayoutBase","defaultOptions","subtype","roots","nodeDistance","iterations","horizontalSeparation","verticalSeparation","underneathVerticalTopOffset","underneathHorizontalOffset","underneathVerticalSeparation","grid","offsetX","offsetY","componentSpacingX","componentSpacingY","layerSeparation","layeredIterations","startRadialAngle","endRadialAngle","radialSeparation","radialFirstLevelSeparation","keepComponentsInOneRadialLayout","ignoreContainers","layoutContainerChildren","ignoreInvisible","animateTransitions","gridLayoutComponents","maxWidth","startX","resultLinkSet","resultNodeSet","moveToOffset","boundingRect","currentHeight","currentWidth","deltax","deltay","nodeBounds","newpoints","pt","currentHorizontalOffset","transferOptions","DiagramToHyperTreeAdapter","shapeMap","edges","edgeMap","finalNodes","finalLinks","ignoredConnections","ignoredShapes","hyperMap","hyperTree","finalGraph","convert","_renormalizeShapes","_renormalizeConnections","l","mapConnection","mapShape","getEdge","listToRoot","containerGraph","parentContainer","firstNonIgnorableContainer","isContainer","_isIgnorableItem","isContainerConnection","isDescendantOf","scope","containers","isIgnorableItem","isCollapsed","_isVisible","_isTop","isShapeMapped","leastCommonAncestor","al","xa","xb","_isCollapsed","sink","sourceNode","sinkNode","areConnectedAlready","newEdge","finalNodeSet","LayoutState","initialTemperature","temperature","guessBounds","_expectedBounds","refineStage","_repulsion","_attraction","_shake","rho","alpha","_InverseSquareForce","wn","hn","wm","hm","pow","_SquareForce","distance","squareSize","area","ceil","TreeLayoutProcessor","treeGraph","layoutSwitch","layoutLeft","setChildrenDirection","setChildrenLayout","TreeDirection","measure","Width","arrange","layoutRight","layoutUp","up","layoutDown","down","treeDirection","layoutRadialTree","previousRoot","startAngle","endAngle","maxDepth","calculateAngularWidth","radialLayout","Angle","tipOverTree","startFromLevel","aw","diameter","sectorAngle","sortChildren","basevalue","pl","nl","normalizeAngle","col","deltaTheta","deltaThetaHalf","parentSector","fraction","sorted","childNode","cp","childAngleFraction","setPolarLocation","BoundingRectangle","direction","includeStart","rootDirection","rootLayout","childrenLayout","givenSize","shapeWidth","shapeHeight","AngleToParent","SectorAngle","pp","childrenwidth","selfLocation","single","male","female","leftcount","tipOverTreeStartLevel","TreeLayout","adapter","layoutComponents","getTree","getTreeForRoot","LayeredLayout","_initRuntimeProperties","layer","downstreamLinkCount","upstreamLinkCount","uBaryCenter","dBaryCenter","upstreamPriority","downstreamPriority","gridPosition","_prepare","targetLayer","layerMap","layerCount","shift","sortedNodes","o2","o1layer","o2layer","minLayer","layers","linksTo","_dummify","_optimizeCrossings","_swapPairs","arrangeNodes","_moveThingsAround","_dedummify","setMinDist","minDist","layerIndex","minDistances","getMinDist","dist","i1","i2","placeLeftToRight","leftClasses","leftPos","classNodes","placeLeft","POSITIVE_INFINITY","rightSibling","nodeLeftClass","D","upNodes","downNodes","neighbor","intDiv","placeRightToLeft","rightClasses","rightPos","placeRight","NEGATIVE_INFINITY","leftSibling","nodeRightClass","_getLeftWing","leftWing","computeClasses","_getRightWing","rightWing","wingPair","currentWing","wing","ndsinl","_nodesInLink","vnode","wings","classIndex","_isVerticalLayout","_isHorizontalLayout","_isIncreasingLayout","_gridPositionComparer","dest","currentNode","currDown","downNode","order","placed","sequenceStart","virtualStartIndex","_firstVirtualNode","virtualStart","sequence","_sequencer","virtualEnd","nextVirtualNode","virtualEndIndex","adjustDirections","ctx","fromLayerIndex","layerIncrement","maximumHeight","MIN_VALUE","prevBridge","prevBridgeTarget","nextBridge","nextBridgeTarget","getNeighborOnLayer","clayer","j1","j2","dir","_sequenceSingle","combineSequences","pair","leftHeap","_positionDescendingComparer","rightHeap","_positionAscendingComparer","leftRes","rightRes","leftClass","_getComposite","rightClass","it","layoutLayer","gridPos","iconsidered","considered","n1Priority","n2Priority","nodeGridPos","nodeBaryCenter","calcBaryCenter","nodePriority","moveRight","moveLeft","calcDownData","calcUpData","priority","rightNode","rightNodePriority","leftNode","leftNodePriority","mapVirtualNode","nodeToLinkMap","linkToNodeMap","addLinkBetweenLayers","upLayer","downLayer","o","oLayer","dLayer","oPos","dPos","depthOfDumminess","dedum","prevLink","moves","iter","optimizeLayerCrossings","sum","total","presorted","n1BaryCenter","n2BaryCenter","compareByIndex","compareValue","inode","maxIterations","downwards","secondPass","hasSwapped","calcCrossings","memCrossings","crossBefore","countLinksCrossingBetweenTwoLayers","node1","node2","node1GridPos","node2GridPos","crossAfter","ulayer","dlayer","link1","link2","n11","n12","n21","n22","l1","l2","crossings","n11gp","n12gp","numerator","denominator","graphOrNodes","capture","diagramOrGraphOrNodes","GraphAdapter","geom","Widget","outerWidth","_outerWidth","outerHeight","_outerHeight","HierarchicalDataSource","isPlainObject","math","NS","CASCADING","CHANGE","CLICK","ERROR","MAXINT","SELECT","ITEMROTATE","PAN","ZOOM_START","ZOOM_END","NONE","TRANSFORMED","BUTTON_TEMPLATE","ref","className","icon","themeColor","html","renderButton","DefaultConnectors","getPosition","defaultButtons","imageClass","isAutoConnector","closestConnector","resCtr","minimumDistance","indicesOfItems","extra","defaults","DiagramElement","dataItem","_template","serializable","serialize","json","_content","contentOptions","_contentVisual","_updateContentVisual","_createContentVisual","template","elementTemplate","paramName","_canSelect","toJSON","Connector","shapeId","tempStr","updateOptionsFromModel","createShapeVisual","updateBounds","_createConnectors","_setOptionsFromModel","model","modelOptions","filterShapeDataItem","redrawVisual","_isEditable","_redrawVisual","syncChanges","_suspendModelRefresh","_resumeModelRefresh","_rotate","_alignContent","contentVisual","containerRect","aligner","contentBounds","bbox","contentRect","alignedBounds","connectorDefaults","_transformedBounds","_rotatedBounds","_setBounds","_triggerBoundsChange","_layouting","refreshConnections","cloneDataItem","deselected","_internalSelection","_selectionChanged","deltaAngle","newPosition","sc","con","cons","nameOrPoint","toLocaleLowerCase","fnName","_transformPoint","boundsChange","shapeOptions","shapeVisual","_visualOptions","_updateConnectors","_showConnectors","rotatedPoint","visualOptions","visualTemplate","_initRouter","_sourcePoint","_targetPoint","_setSource","_setTarget","definers","fromConnector","toConnector","dataMap","_dataMap","fromX","fromY","toX","toY","filterConnectionDataItem","connectionsDataSource","getByUid","uid","clearField","shapeSource","defaultConnector","_removeFromSourceConnector","_clearSourceConnector","_setFromOptions","fromPoint","sourceDefiner","_sourceDefiner","shapeTarget","_removeFromTargetConnector","_clearTargetConnector","_setToOptions","toPoint","targetDefiner","_targetDefiner","instance","connectorName","setNewTarget","inactiveItem","_inactiveShapeItems","_deferredConnectionUpdates","onActivate","endIdx","startIdx","alignToPath","midIdx","selection","_router","pts","definition","_resolveConnectors","_refreshPath","sourceConnectors","targetConnectors","_resolveAutoConnectors","minNonConflictSource","minNonConflictTarget","minSource","minTarget","sourceIdx","targetIdx","minNonConflict","_testRoutePoints","router","passRoute","exclude","_getRouteExclude","_shapesQuadTree","hitTestRect","_isPointInsideShape","boundsX","boundsY","Diagram","userOptions","_initTheme","_initElements","_extendLayoutOptions","_initDefaults","_interactionDefaults","_initCanvas","ShapesQuadTree","adornerLayer","_createHandlers","_clipboard","pauseMouseHandlers","_fetchFreshData","_createGlobalToolBar","_createOptionElements","theme","dataSource","draggable","autoBind","tooltip","connectionDefaults","toolBar","DiagramToolBar","click","_toolBarClick","modal","textAlign","prepend","_resize","createShape","editor","view","createModel","_createShape","edit","createConnection","_connectionsDataMap","addConnection","editModel","editorType","editors","cancelEdit","shapeEditors","shapeTemplate","connectionSelectorHandler","connectionSelector","connectionEditors","connectionTemplate","PopupEditor","_update","_cancel","_editArgs","_getEditDataSource","cancelChanges","_destroyEditor","saveEdit","sync","wrapper","close","attr","addClass","appendTo","userShapeDefaults","copyDefaultOptions","mobile","canvasContainer","viewPort","viewport","on","_wheel","_keydown","_userEvents","UserEvents","multiTouch","fastTap","tap","_tap","_dragStart","_drag","_dragEnd","gesturestart","_gestureStart","gesturechange","_gestureChange","gestureend","_gestureEnd","doubleTap","_doubleTap","supportDoubleTap","_mouseover","_mouseout","_mouseMove","_mouseDown","_mouseUp","_syncHandler","_resizeHandler","onResize","_pauseMouseHandlers","_eventPositions","event","_meta","preventDefault","_createToolBar","focused","ctrlPressed","keyCode","origEvent","originalEvent","wheelDelta","detail","mwDelta","touch","pageX","pageY","documentToModel","initialCenter","eventArgs","_gesture","_initialCenter","previousGesture","documentToView","scaleDelta","_zoom","updateZoom","_getValidZoom","zoomedPoint","_panTransform","_updateAdorners","pointPosition","_kendoNode","srcElement","themeOptions","themeName","themes","SASS_THEMES","autoTheme","shapesLength","_createShapes","_createConnections","_findConnectionTarget","unbindResize","off","destroyScroller","_destroyGlobalToolBar","is","_activeElement","scrollContainer","offsets","documentElement","document","parentNode","scrollHeight","load","setOptions","added","removed","_parseBounds","splitDiagramElements","_removeItem","_removeShapeDataItem","_removeConnectionDataItem","_getDiagramItems","_fixOrdering","bringIntoView","original","newPan","_zoomMainLayer","alignShapes","val","raw","hideTooltip","_getPan","animatedScrollTo","scrollTo","_copyOffset","copied","mapping","_updateCopiedConnection","sourceConnection","di","_containerOffset","containerOffset","viewToDocument","viewToModel","_transformWithMatrix","_matrixInvert","_matrix","_layerMatrix","layerToModel","_layerMatrixInvert","viewPoint","modelToDocument","setDataSource","_dataSource","fetch","setConnectionsDataSource","_connectionDataSource","_redrawConnections","getShapeByModelId","getShapeByModelUid","getConnectionByModelId","getConnectionByModelUid","_transformMainLayer","_finishPan","NaN","_storeViewMatrix","_storeLayerMatrix","canvasTransform","shapePos","conPos","removedConnections","_removeShape","_removeConnection","_removeDataItems","recursive","_removeShapeConnections","hasChildren","loaded","_addDataItem","_addDataItemByUid","_addDataItems","parentShape","_refreshSource","dataBound","_bindingRoots","_addItem","preventClosing","singleToolBar","popupZIndex","closest","popupWidth","_popup","popupHeight","connectionBounds","showAt","one","_normalizePointZoom","InactiveItemsCollection","undone","redone","_loadingShapes","_loadingConnections","dsOptions","ds","_shapesRefreshHandler","_shapesRequestStartHandler","_shapesErrorHandler","_refreshShapes","_shapesRequestStart","_error","DataSource","_treeDataSource","_connectionsRefreshHandler","_connectionsRequestStartHandler","_connectionsErrorHandler","_refreshConnections","_connectionsRequestStart","_connectionsError","_shouldRefresh","_removeShapes","_updateShapes","_syncShapes","_suspended","_rebindShapesAndConnections","_addShapes","_addConnections","inactiveItems","activate","dataItems","_removeConnections","_updateConnections","_addConnectionDataItem","_validateConnector","_unbindDataSource","_errorHandler","adorners","_refresh","hide","exportDOMVisual","scrollOffset","viewRect","clipPath","fromRect","wrap","clipWrap","clip","exportVisual","when","then","deferredConnectionUpdates","ExportMixin","PDFMixin","_tools","createToolBar","createTools","appendTools","createPopup","kendoPopup","getKendoPopup","buttons","_toolBar","kendoToolBar","resizable","getKendoToolBar","createTool","toolName","attributes","_setAttributes","open","newGroup","editTool","showText","deleteTool","rotateAnticlockwiseTool","_appendGroup","_rotateGroup","rotateClockwiseTool","createShapeTool","_createGroup","createConnectionTool","undoTool","_historyGroup","redoTool","prop","_getAttributes","eventData","selectedElements","delete","selectedElemens","rotateClockwise","rotateAnticlockwise","Editor","_getFields","_initContainer","createEditable","Editable","clearContainer","modelFields","columns","formContent","_renderTemplate","_renderFields","_renderButtons","Window","userTriggered","sender","_cancelClick","_attachButtonEvents","unescape","form","_createButton","_cancelClickHandler","_updateClickHandler","_updateClick","_editUpdateClickHandler","reader","textField","idField","kendoDropDownList","dataValueField","dataTextField","optionLabel","valuePrimitive","InactiveItem","callbacks","callback","deffered","Deferred","deferred","resolve","QuadRoot","_add","_quadNode","_testRect","QuadNode","inBounds","nodeRect","nodeBottomRight","overlapsBounds","inserted","_initChildren","childIdx","shapeIdx","halfWidth","halfHeight","ROOT_SIZE","boundsChangeHandler","_boundsChange","initRoots","rootMap","rootSize","sectors","getSectors","inRoot","bottomX","bottomY","xIdx","yIdx","Model","_defaultId","ObservableObject","mainOptions","plugin"],"sources":["kendo.dataviz.diagram.js"],"mappings":"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","sourcesContent":["(function (global, factory) {\n typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory(require('kendo.data.js'), require('kendo.draganddrop.js'), require('kendo.userevents.js'), require('kendo.mobile.scroller.js'), require('kendo.drawing.js'), require('kendo.core.js'), require('kendo.dataviz.core.js'), require('kendo.toolbar.js'), require('kendo.editable.js'), require('kendo.window.js'), require('kendo.dropdownlist.js'), require('kendo.dataviz.themes.js'), require('kendo.html.button.js')) :\n typeof define === 'function' && define.amd ? define(['kendo.data', 'kendo.draganddrop', 'kendo.userevents', 'kendo.mobile.scroller', 'kendo.drawing', 'kendo.core', 'kendo.dataviz.core', 'kendo.toolbar', 'kendo.editable', 'kendo.window', 'kendo.dropdownlist', 'kendo.dataviz.themes', 'kendo.html.button'], factory) :\n (global = typeof globalThis !== 'undefined' ? globalThis : global || self, (global.kendodataviz = global.kendodataviz || {}, global.kendodataviz.diagram = global.kendodataviz.diagram || {}, global.kendodataviz.diagram.js = factory()));\n})(this, (function () {\n (function($, undefined$1) {\n var kendo = window.kendo,\n diagram = kendo.dataviz.diagram = {},\n deepExtend = kendo.deepExtend,\n isArray = Array.isArray,\n EPSILON = 1e-06;\n\n /*-------------------Diverse utilities----------------------------*/\n var Utils = {\n };\n\n deepExtend(Utils, {\n isNearZero: function(num) {\n return Math.abs(num) < EPSILON;\n },\n isDefined: function(obj) {\n return typeof obj !== 'undefined';\n },\n\n isUndefined: function(obj) {\n return (typeof obj === 'undefined') || obj === null;\n },\n /**\n * Returns whether the given object is an object or a value.\n */\n isObject: function(obj) {\n return obj === Object(obj);\n },\n /**\n * Returns whether the object has a property with the given name.\n */\n has: function(obj, key) {\n return Object.hasOwnProperty.call(obj, key);\n },\n /**\n * Returns whether the given object is a string.\n */\n isString: function(obj) {\n return Object.prototype.toString.call(obj) == '[object String]';\n },\n isBoolean: function(obj) {\n return Object.prototype.toString.call(obj) == '[object Boolean]';\n },\n isType: function(obj, type) {\n return Object.prototype.toString.call(obj) == '[object ' + type + ']';\n },\n /**\n * Returns whether the given object is a number.\n */\n isNumber: function(obj) {\n return !isNaN(parseFloat(obj)) && isFinite(obj);\n },\n /**\n * Return whether the given object (array or dictionary).\n */\n isEmpty: function(obj) {\n if (obj === null) {\n return true;\n }\n if (isArray(obj) || Utils.isString(obj)) {\n return obj.length === 0;\n }\n for (var key in obj) {\n if (Utils.has(obj, key)) {\n return false;\n }\n }\n return true;\n },\n simpleExtend: function(destination, source) {\n if (!Utils.isObject(source)) {\n return;\n }\n\n for (var name in source) {\n destination[name] = source[name];\n }\n },\n /**\n * Returns an array of the specified size and with each entry set to the given value.\n * @param size\n * @param value\n * @returns {Array}\n */\n initArray: function createIdArray(size, value) {\n var array = [];\n for (var i = 0; i < size; ++i) {\n array[i] = value;\n }\n return array;\n },\n serializePoints: function(points) {\n var res = [];\n for (var i = 0; i < points.length; i++) {\n var p = points[i];\n res.push(p.x + \";\" + p.y);\n }\n return res.join(\";\");\n },\n deserializePoints: function(s) {\n var v = s.split(\";\"), points = [];\n if (v.length % 2 !== 0) {\n throw \"Not an array of points.\";\n }\n for (var i = 0; i < v.length; i += 2) {\n points.push(new diagram.Point(\n parseInt(v[i], 10),\n parseInt(v[i + 1], 10)\n ));\n }\n return points;\n },\n /**\n * Returns an integer within the given bounds.\n * @param lower The inclusive lower bound.\n * @param upper The exclusive upper bound.\n * @returns {number}\n */\n randomInteger: function(lower, upper) {\n return parseInt(Math.floor(Math.random() * upper) + lower, 10);\n } ,\n /*\n Depth-first traversal of the given node.\n */\n DFT: function(el, func) {\n func(el);\n if (el.childNodes) {\n for (var i = 0; i < el.childNodes.length; i++) {\n var item = el.childNodes[i];\n this.DFT(item, func);\n }\n }\n },\n /*\n Returns the angle in degrees for the given matrix\n */\n getMatrixAngle: function(m) {\n if (m === null || m.d === 0) {\n return 0;\n }\n return Math.atan2(m.b, m.d) * 180 / Math.PI;\n },\n\n /*\n Returns the scaling factors for the given matrix.\n */\n getMatrixScaling: function(m) {\n var sX = Math.sqrt(m.a * m.a + m.c * m.c);\n var sY = Math.sqrt(m.b * m.b + m.d * m.d);\n return [sX, sY];\n }\n\n });\n\n /**\n * The Range defines an array of equally separated numbers.\n * @param start The start-value of the Range.\n * @param stop The end-value of the Range.\n * @param step The separation between the values (default:1).\n * @returns {Array}\n */\n function Range(start, stop, step) {\n if (typeof start == 'undefined' || typeof stop == 'undefined') {\n return [];\n }\n if (step && Utils.sign(stop - start) != Utils.sign(step)) {\n throw \"The sign of the increment should allow to reach the stop-value.\";\n }\n step = step || 1;\n start = start || 0;\n stop = stop || start;\n if ((stop - start) / step === Infinity) {\n throw \"Infinite range defined.\";\n }\n var range = [], i = -1, j;\n\n function rangeIntegerScale(x) {\n var k = 1;\n while (x * k % 1) {\n k *= 10;\n }\n return k;\n }\n\n var k = rangeIntegerScale(Math.abs(step));\n start *= k;\n stop *= k;\n step *= k;\n if (start > stop && step > 0) {\n step = -step;\n }\n if (step < 0) {\n while ((j = start + step * ++i) >= stop) {\n range.push(j / k);\n }\n }\n else {\n while ((j = start + step * ++i) <= stop) {\n range.push(j / k);\n }\n }\n return range;\n }\n\n /*-------------------Diverse math functions----------------------------*/\n\n function findRadian(start, end) {\n if (start == end) {\n return 0;\n }\n var sngXComp = end.x - start.x,\n sngYComp = start.y - end.y,\n atan = Math.atan(sngXComp / sngYComp);\n if (sngYComp >= 0) {\n return sngXComp < 0 ? atan + (2 * Math.PI) : atan;\n }\n return atan + Math.PI;\n }\n\n Utils.sign = function(number) {\n return number ? number < 0 ? -1 : 1 : 0;\n };\n\n Utils.findAngle = function(center, end) {\n return findRadian(center, end) * 180 / Math.PI;\n };\n\n /*-------------------Array Helpers ----------------------------*/\n\n Utils.forEach = function(arr, iterator, thisRef) {\n for (var i = 0; i < arr.length; i++) {\n iterator.call(thisRef, arr[i], i, arr);\n }\n };\n\n Utils.any = function(arr, predicate) {\n for (var i = 0; i < arr.length; ++i) {\n if (predicate(arr[i])) {\n return arr[i];\n }\n }\n return null;\n };\n\n Utils.remove = function(arr, what) {\n var ax;\n while ((ax = Utils.indexOf(arr, what)) !== -1) {\n arr.splice(ax, 1);\n }\n return arr;\n };\n\n Utils.contains = function(arr, obj) {\n return Utils.indexOf(arr, obj) !== -1;\n };\n\n Utils.indexOf = function(arr, what) {\n return $.inArray(what, arr);\n };\n\n Utils.fold = function(list, iterator, acc, context) {\n var initial = arguments.length > 2;\n\n for (var i = 0; i < list.length; i++) {\n var value = list[i];\n if (!initial) {\n acc = value;\n initial = true;\n }\n else {\n acc = iterator.call(context, acc, value, i, list);\n }\n }\n\n if (!initial) {\n throw 'Reduce of empty array with no initial value';\n }\n\n return acc;\n };\n\n Utils.find = function(arr, iterator, context) {\n var result;\n Utils.any(arr, function(value, index, list) {\n if (iterator.call(context, value, index, list)) {\n result = value;\n return true;\n }\n return false;\n });\n return result;\n };\n\n Utils.first = function(arr, constraint, context) {\n if (arr.length === 0) {\n return null;\n }\n if (Utils.isUndefined(constraint)) {\n return arr[0];\n }\n\n return Utils.find(arr, constraint, context);\n };\n\n /**\n * Inserts the given element at the specified position and returns the result.\n */\n Utils.insert = function(arr, element, position) {\n arr.splice(position, 0, element);\n return arr;\n };\n\n Utils.all = function(arr, iterator, context) {\n var result = true;\n var value;\n\n for (var i = 0; i < arr.length; i++) {\n value = arr[i];\n result = result && iterator.call(context, value, i, arr);\n\n if (!result) {\n break;\n }\n }\n\n return result;\n };\n\n Utils.clear = function(arr) {\n arr.splice(0, arr.length);\n };\n\n /**\n * Sort the arrays on the basis of the first one (considered as keys and the other array as values).\n * @param a\n * @param b\n * @param sortfunc (optiona) sorting function for the values in the first array\n */\n Utils.bisort = function(a, b, sortfunc) {\n if (Utils.isUndefined(a)) {\n throw \"First array is not specified.\";\n }\n if (Utils.isUndefined(b)) {\n throw \"Second array is not specified.\";\n }\n if (a.length != b.length) {\n throw \"The two arrays should have equal length\";\n }\n\n var all = [], i;\n\n for (i = 0; i < a.length; i++) {\n all.push({ 'x': a[i], 'y': b[i] });\n }\n if (Utils.isUndefined(sortfunc)) {\n all.sort(function(m, n) {\n return m.x - n.x;\n });\n }\n else {\n all.sort(function(m, n) {\n return sortfunc(m.x, n.x);\n });\n }\n\n Utils.clear(a);\n Utils.clear(b);\n\n for (i = 0; i < all.length; i++) {\n a.push(all[i].x);\n b.push(all[i].y);\n }\n };\n\n Utils.addRange = function(arr, range) {\n arr.push.apply(arr, range);\n };\n\n var Easing = {\n easeInOut: function(pos) {\n return ((-Math.cos(pos * Math.PI) / 2) + 0.5);\n }\n };\n\n /**\n * An animation ticker driving an adapter which sets a particular\n * property in function of the tick.\n * @type {*}\n */\n var Ticker = kendo.Class.extend({\n init: function() {\n this.adapters = [];\n this.target = 0;\n this.tick = 0;\n this.interval = 20;\n this.duration = 800;\n this.lastTime = null;\n this.handlers = [];\n var _this = this;\n this.transition = Easing.easeInOut;\n this.timerDelegate = function() {\n _this.onTimerEvent();\n };\n },\n addAdapter: function(a) {\n this.adapters.push(a);\n },\n onComplete: function(handler) {\n this.handlers.push(handler);\n },\n removeHandler: function(handler) {\n this.handlers = $.grep(this.handlers, function(h) {\n return h !== handler;\n });\n },\n trigger: function() {\n var _this = this;\n if (this.handlers) {\n Utils.forEach(this.handlers, function(h) {\n return h.call(_this.caller !== null ? _this.caller : _this);\n });\n }\n },\n onStep: function() {\n },\n seekTo: function(to) {\n this.seekFromTo(this.tick, to);\n },\n seekFromTo: function(from, to) {\n this.target = Math.max(0, Math.min(1, to));\n this.tick = Math.max(0, Math.min(1, from));\n this.lastTime = new Date().getTime();\n if (!this.intervalId) {\n this.intervalId = window.setInterval(this.timerDelegate, this.interval);\n }\n },\n stop: function() {\n if (this.intervalId) {\n window.clearInterval(this.intervalId);\n this.intervalId = null;\n\n //this.trigger.call(this);\n this.trigger();\n // this.next();\n }\n },\n play: function(origin) {\n if (this.adapters.length === 0) {\n return;\n }\n if (origin !== null) {\n this.caller = origin;\n }\n this.initState();\n this.seekFromTo(0, 1);\n },\n reverse: function() {\n this.seekFromTo(1, 0);\n },\n initState: function() {\n if (this.adapters.length === 0) {\n return;\n }\n for (var i = 0; i < this.adapters.length; i++) {\n this.adapters[i].initState();\n }\n },\n propagate: function() {\n var value = this.transition(this.tick);\n\n for (var i = 0; i < this.adapters.length; i++) {\n this.adapters[i].update(value);\n }\n },\n onTimerEvent: function() {\n var now = new Date().getTime();\n var timePassed = now - this.lastTime;\n this.lastTime = now;\n var movement = (timePassed / this.duration) * (this.tick < this.target ? 1 : -1);\n if (Math.abs(movement) >= Math.abs(this.tick - this.target)) {\n this.tick = this.target;\n } else {\n this.tick += movement;\n }\n\n try {\n this.propagate();\n } finally {\n this.onStep.call(this);\n if (this.target == this.tick) {\n this.stop();\n }\n }\n }\n });\n\n kendo.deepExtend(diagram, {\n init: function(element) {\n kendo.init(element, diagram.ui);\n },\n\n Utils: Utils,\n Range: Range,\n Ticker: Ticker\n });\n })(window.kendo.jQuery);\n\n (function($, undefined$1) {\n // Imports ================================================================\n var kendo = window.kendo,\n diagram = kendo.dataviz.diagram,\n Class = kendo.Class,\n deepExtend = kendo.deepExtend,\n dataviz = kendo.dataviz,\n Utils = diagram.Utils,\n Point = dataviz.Point2D,\n isFunction = kendo.isFunction,\n contains = Utils.contains,\n map = $.map;\n\n // Constants ==============================================================\n var HITTESTAREA = 3,\n EPSILON = 1e-06;\n\n deepExtend(Point.fn, {\n plus: function(p) {\n return new Point(this.x + p.x, this.y + p.y);\n },\n minus: function(p) {\n return new Point(this.x - p.x, this.y - p.y);\n },\n offset: function(value) {\n return new Point(this.x - value, this.y - value);\n },\n times: function(s) {\n return new Point(this.x * s, this.y * s);\n },\n normalize: function() {\n if (this.length() === 0) {\n return new Point();\n }\n return this.times(1 / this.length());\n },\n length: function() {\n return Math.sqrt(this.x * this.x + this.y * this.y);\n },\n toString: function() {\n return \"(\" + this.x + \",\" + this.y + \")\";\n },\n lengthSquared: function() {\n return (this.x * this.x + this.y * this.y);\n },\n middleOf: function MiddleOf(p, q) {\n return new Point(q.x - p.x, q.y - p.y).times(0.5).plus(p);\n },\n toPolar: function(useDegrees) {\n var factor = 1;\n if (useDegrees) {\n factor = 180 / Math.PI;\n }\n var a = Math.atan2(Math.abs(this.y), Math.abs(this.x));\n var halfpi = Math.PI / 2;\n var len = this.length();\n if (this.x === 0) {\n // note that the angle goes down and not the usual mathematical convention\n\n if (this.y === 0) {\n return new Polar(0, 0);\n }\n if (this.y > 0) {\n return new Polar(len, factor * halfpi);\n }\n if (this.y < 0) {\n return new Polar(len, factor * 3 * halfpi);\n }\n }\n else if (this.x > 0) {\n if (this.y === 0) {\n return new Polar(len, 0);\n }\n if (this.y > 0) {\n return new Polar(len, factor * a);\n }\n if (this.y < 0) {\n return new Polar(len, factor * (4 * halfpi - a));\n }\n }\n else {\n if (this.y === 0) {\n return new Polar(len, 2 * halfpi);\n }\n if (this.y > 0) {\n return new Polar(len, factor * (2 * halfpi - a));\n }\n if (this.y < 0) {\n return new Polar(len, factor * (2 * halfpi + a));\n }\n }\n },\n isOnLine: function(from, to) {\n if (from.x > to.x) { // from must be the leftmost point\n var temp = to;\n to = from;\n from = temp;\n }\n var r1 = new Rect(from.x, from.y).inflate(HITTESTAREA, HITTESTAREA),\n r2 = new Rect(to.x, to.y).inflate(HITTESTAREA, HITTESTAREA), o1, u1;\n if (r1.union(r2).contains(this)) {\n if (from.x === to.x || from.y === to.y) {\n return true;\n }\n else if (from.y < to.y) {\n o1 = r1.x + (((r2.x - r1.x) * (this.y - (r1.y + r1.height))) / ((r2.y + r2.height) - (r1.y + r1.height)));\n u1 = (r1.x + r1.width) + ((((r2.x + r2.width) - (r1.x + r1.width)) * (this.y - r1.y)) / (r2.y - r1.y));\n }\n else {\n o1 = r1.x + (((r2.x - r1.x) * (this.y - r1.y)) / (r2.y - r1.y));\n u1 = (r1.x + r1.width) + ((((r2.x + r2.width) - (r1.x + r1.width)) * (this.y - (r1.y + r1.height))) / ((r2.y + r2.height) - (r1.y + r1.height)));\n }\n return (this.x > o1 && this.x < u1);\n }\n return false;\n }\n });\n\n deepExtend(Point, {\n parse: function(str) {\n var tempStr = str.slice(1, str.length - 1),\n xy = tempStr.split(\",\"),\n x = parseInt(xy[0], 10),\n y = parseInt(xy[1], 10);\n if (!isNaN(x) && !isNaN(y)) {\n return new Point(x, y);\n }\n }\n });\n\n /**\n * Structure combining a Point with two additional points representing the handles or tangents attached to the first point.\n * If the additional points are null or equal to the first point the path will be sharp.\n * Left and right correspond to the direction of the underlying path.\n */\n var PathDefiner = Class.extend(\n {\n init: function(p, left, right) {\n this.point = p;\n this.left = left;\n this.right = right;\n }\n }\n );\n\n /**\n * Defines a rectangular region.\n */\n var Rect = Class.extend({\n init: function(x, y, width, height) {\n this.x = x || 0;\n this.y = y || 0;\n this.width = width || 0;\n this.height = height || 0;\n },\n contains: function(point) {\n return ((point.x >= this.x) && (point.x <= (this.x + this.width)) && (point.y >= this.y) && (point.y <= (this.y + this.height)));\n },\n inflate: function(dx, dy) {\n if (dy === undefined$1) {\n dy = dx;\n }\n\n this.x -= dx;\n this.y -= dy;\n this.width += 2 * dx + 1;\n this.height += 2 * dy + 1;\n return this;\n },\n offset: function(dx, dy) {\n var x = dx, y = dy;\n if (dx instanceof Point) {\n x = dx.x;\n y = dx.y;\n }\n this.x += x;\n this.y += y;\n return this;\n },\n union: function(r) {\n var x1 = Math.min(this.x, r.x);\n var y1 = Math.min(this.y, r.y);\n var x2 = Math.max((this.x + this.width), (r.x + r.width));\n var y2 = Math.max((this.y + this.height), (r.y + r.height));\n return new Rect(x1, y1, x2 - x1, y2 - y1);\n },\n center: function() {\n return new Point(this.x + this.width / 2, this.y + this.height / 2);\n },\n top: function() {\n return new Point(this.x + this.width / 2, this.y);\n },\n right: function() {\n return new Point(this.x + this.width, this.y + this.height / 2);\n },\n bottom: function() {\n return new Point(this.x + this.width / 2, this.y + this.height);\n },\n left: function() {\n return new Point(this.x, this.y + this.height / 2);\n },\n topLeft: function() {\n return new Point(this.x, this.y);\n },\n topRight: function() {\n return new Point(this.x + this.width, this.y);\n },\n bottomLeft: function() {\n return new Point(this.x, this.y + this.height);\n },\n bottomRight: function() {\n return new Point(this.x + this.width, this.y + this.height);\n },\n clone: function() {\n return new Rect(this.x, this.y, this.width, this.height);\n },\n isEmpty: function() {\n return !this.width && !this.height;\n },\n equals: function(rect) {\n return this.x === rect.x && this.y === rect.y && this.width === rect.width && this.height === rect.height;\n },\n rotatedBounds: function(angle) {\n var rect = this.clone(),\n points = this.rotatedPoints(angle),\n tl = points[0],\n tr = points[1],\n br = points[2],\n bl = points[3];\n\n rect.x = Math.min(br.x, tl.x, tr.x, bl.x);\n rect.y = Math.min(br.y, tl.y, tr.y, bl.y);\n rect.width = Math.max(br.x, tl.x, tr.x, bl.x) - rect.x;\n rect.height = Math.max(br.y, tl.y, tr.y, bl.y) - rect.y;\n\n return rect;\n },\n rotatedPoints: function(angle) {\n var rect = this,\n c = rect.center(),\n br = rect.bottomRight().rotate(c, 360 - angle),\n tl = rect.topLeft().rotate(c, 360 - angle),\n tr = rect.topRight().rotate(c, 360 - angle),\n bl = rect.bottomLeft().rotate(c, 360 - angle);\n\n return [tl, tr, br, bl];\n },\n toString: function(delimiter) {\n delimiter = delimiter || \" \";\n\n return this.x + delimiter + this.y + delimiter + this.width + delimiter + this.height;\n },\n scale: function(scaleX, scaleY, staicPoint, adornerCenter, angle) {\n var tl = this.topLeft();\n var thisCenter = this.center();\n tl.rotate(thisCenter, 360 - angle).rotate(adornerCenter, angle);\n\n var delta = staicPoint.minus(tl);\n var scaled = new Point(delta.x * scaleX, delta.y * scaleY);\n var position = delta.minus(scaled);\n tl = tl.plus(position);\n tl.rotate(adornerCenter, 360 - angle).rotate(thisCenter, angle);\n\n this.x = tl.x;\n this.y = tl.y;\n\n this.width *= scaleX;\n this.height *= scaleY;\n },\n\n zoom: function(zoom) {\n this.x *= zoom;\n this.y *= zoom;\n this.width *= zoom;\n this.height *= zoom;\n return this;\n },\n\n overlaps: function(rect) {\n var bottomRight = this.bottomRight();\n var rectBottomRight = rect.bottomRight();\n var overlaps = !(bottomRight.x < rect.x || bottomRight.y < rect.y ||\n rectBottomRight.x < this.x || rectBottomRight.y < this.y);\n return overlaps;\n }\n });\n\n var Size = Class.extend({\n init: function(width, height) {\n this.width = width;\n this.height = height;\n }\n });\n\n Size.prototype.Empty = new Size(0, 0);\n\n Rect.toRect = function(rect) {\n if (!(rect instanceof Rect)) {\n rect = new Rect(rect.x, rect.y, rect.width, rect.height);\n }\n\n return rect;\n };\n\n Rect.empty = function() {\n return new Rect(0, 0, 0, 0);\n };\n\n Rect.fromPoints = function(p, q) {\n if (isNaN(p.x) || isNaN(p.y) || isNaN(q.x) || isNaN(q.y)) {\n throw \"Some values are NaN.\";\n }\n return new Rect(Math.min(p.x, q.x), Math.min(p.y, q.y), Math.abs(p.x - q.x), Math.abs(p.y - q.y));\n };\n\n function isNearZero(num) {\n return Math.abs(num) < EPSILON;\n }\n\n function intersectLine(start1, end1, start2, end2, isSegment) {\n var tangensdiff = ((end1.x - start1.x) * (end2.y - start2.y)) - ((end1.y - start1.y) * (end2.x - start2.x));\n if (isNearZero(tangensdiff)) {\n //parallel lines\n return;\n }\n\n var num1 = ((start1.y - start2.y) * (end2.x - start2.x)) - ((start1.x - start2.x) * (end2.y - start2.y));\n var num2 = ((start1.y - start2.y) * (end1.x - start1.x)) - ((start1.x - start2.x) * (end1.y - start1.y));\n var r = num1 / tangensdiff;\n var s = num2 / tangensdiff;\n\n if (isSegment && (r < 0 || r > 1 || s < 0 || s > 1)) {\n //r < 0 => line 1 is below line 2\n //r > 1 => line 1 is above line 2\n //s < 0 => line 2 is below line 1\n //s > 1 => line 2 is above line 1\n return;\n }\n\n return new Point(start1.x + (r * (end1.x - start1.x)), start1.y + (r * (end1.y - start1.y)));\n }\n\n var Intersect = {\n lines: function(start1, end1, start2, end2) {\n return intersectLine(start1, end1, start2, end2);\n },\n segments: function(start1, end1, start2, end2) {\n return intersectLine(start1, end1, start2, end2, true);\n },\n rectWithLine: function(rect, start, end) {\n return Intersect.segments(start, end, rect.topLeft(), rect.topRight()) ||\n Intersect.segments(start, end, rect.topRight(), rect.bottomRight()) ||\n Intersect.segments(start, end, rect.bottomLeft(), rect.bottomRight()) ||\n Intersect.segments(start, end, rect.topLeft(), rect.bottomLeft());\n },\n rects: function(rect1, rect2, angle) {\n var tl = rect2.topLeft(),\n tr = rect2.topRight(),\n bl = rect2.bottomLeft(),\n br = rect2.bottomRight();\n var center = rect2.center();\n if (angle) {\n tl = tl.rotate(center, angle);\n tr = tr.rotate(center, angle);\n bl = bl.rotate(center, angle);\n br = br.rotate(center, angle);\n }\n\n var intersect = rect1.contains(tl) ||\n rect1.contains(tr) ||\n rect1.contains(bl) ||\n rect1.contains(br) ||\n Intersect.rectWithLine(rect1, tl, tr) ||\n Intersect.rectWithLine(rect1, tl, bl) ||\n Intersect.rectWithLine(rect1, tr, br) ||\n Intersect.rectWithLine(rect1, bl, br);\n\n if (!intersect) {//last possible case is rect1 to be completely within rect2\n tl = rect1.topLeft();\n tr = rect1.topRight();\n bl = rect1.bottomLeft();\n br = rect1.bottomRight();\n\n if (angle) {\n var reverseAngle = 360 - angle;\n tl = tl.rotate(center, reverseAngle);\n tr = tr.rotate(center, reverseAngle);\n bl = bl.rotate(center, reverseAngle);\n br = br.rotate(center, reverseAngle);\n }\n\n intersect = rect2.contains(tl) ||\n rect2.contains(tr) ||\n rect2.contains(bl) ||\n rect2.contains(br);\n }\n\n return intersect;\n }\n };\n\n /**\n * Aligns two rectangles, where one is the container and the other is content.\n */\n var RectAlign = Class.extend({\n init: function(container) {\n this.container = Rect.toRect(container);\n },\n\n align: function(content, alignment) {\n var alignValues = alignment.toLowerCase().split(\" \");\n\n for (var i = 0; i < alignValues.length; i++) {\n content = this._singleAlign(content, alignValues[i]);\n }\n\n return content;\n },\n _singleAlign: function(content, alignment) {\n if (isFunction(this[alignment])) {\n return this[alignment](content);\n }\n else {\n return content;\n }\n },\n\n left: function(content) {\n return this._align(content, this._left);\n },\n center: function(content) {\n return this._align(content, this._center);\n },\n right: function(content) {\n return this._align(content, this._right);\n },\n stretch: function(content) {\n return this._align(content, this._stretch);\n },\n top: function(content) {\n return this._align(content, this._top);\n },\n middle: function(content) {\n return this._align(content, this._middle);\n },\n bottom: function(content) {\n return this._align(content, this._bottom);\n },\n\n _left: function(container, content) {\n content.x = container.x;\n },\n _center: function(container, content) {\n content.x = ((container.width - content.width) / 2) || 0;\n },\n _right: function(container, content) {\n content.x = container.width - content.width;\n },\n _top: function(container, content) {\n content.y = container.y;\n },\n _middle: function(container, content) {\n content.y = ((container.height - content.height) / 2) || 0;\n },\n _bottom: function(container, content) {\n content.y = container.height - content.height;\n },\n _stretch: function(container, content) {\n content.x = 0;\n content.y = 0;\n content.height = container.height;\n content.width = container.width;\n },\n _align: function(content, alignCalc) {\n content = Rect.toRect(content);\n alignCalc(this.container, content);\n\n return content;\n }\n });\n\n var Polar = Class.extend({\n init: function(r, a) {\n this.r = r;\n this.angle = a;\n }\n });\n\n /**\n * SVG transformation matrix.\n */\n var Matrix = Class.extend({\n init: function(a, b, c, d, e, f) {\n this.a = a || 0;\n this.b = b || 0;\n this.c = c || 0;\n this.d = d || 0;\n this.e = e || 0;\n this.f = f || 0;\n },\n plus: function(m) {\n this.a += m.a;\n this.b += m.b;\n this.c += m.c;\n this.d += m.d;\n this.e += m.e;\n this.f += m.f;\n },\n minus: function(m) {\n this.a -= m.a;\n this.b -= m.b;\n this.c -= m.c;\n this.d -= m.d;\n this.e -= m.e;\n this.f -= m.f;\n },\n times: function(m) {\n return new Matrix(\n this.a * m.a + this.c * m.b,\n this.b * m.a + this.d * m.b,\n this.a * m.c + this.c * m.d,\n this.b * m.c + this.d * m.d,\n this.a * m.e + this.c * m.f + this.e,\n this.b * m.e + this.d * m.f + this.f\n );\n },\n apply: function(p) {\n return new Point(this.a * p.x + this.c * p.y + this.e, this.b * p.x + this.d * p.y + this.f);\n },\n applyRect: function(r) {\n return Rect.fromPoints(this.apply(r.topLeft()), this.apply(r.bottomRight()));\n },\n toString: function() {\n return \"matrix(\" + this.a + \" \" + this.b + \" \" + this.c + \" \" + this.d + \" \" + this.e + \" \" + this.f + \")\";\n }\n });\n\n deepExtend(Matrix, {\n fromSVGMatrix: function(vm) {\n var m = new Matrix();\n m.a = vm.a;\n m.b = vm.b;\n m.c = vm.c;\n m.d = vm.d;\n m.e = vm.e;\n m.f = vm.f;\n return m;\n },\n fromMatrixVector: function(v) {\n var m = new Matrix();\n m.a = v.a;\n m.b = v.b;\n m.c = v.c;\n m.d = v.d;\n m.e = v.e;\n m.f = v.f;\n return m;\n },\n fromList: function(v) {\n if (v.length !== 6) {\n throw \"The given list should consist of six elements.\";\n }\n var m = new Matrix();\n m.a = v[0];\n m.b = v[1];\n m.c = v[2];\n m.d = v[3];\n m.e = v[4];\n m.f = v[5];\n return m;\n },\n translation: function(x, y) {\n var m = new Matrix();\n m.a = 1;\n m.b = 0;\n m.c = 0;\n m.d = 1;\n m.e = x;\n m.f = y;\n return m;\n },\n unit: function() {\n return new Matrix(1, 0, 0, 1, 0, 0);\n },\n rotation: function(angle, x, y) {\n var m = new Matrix();\n m.a = Math.cos(angle * Math.PI / 180);\n m.b = Math.sin(angle * Math.PI / 180);\n m.c = -m.b;\n m.d = m.a;\n m.e = (x - x * m.a + y * m.b) || 0;\n m.f = (y - y * m.a - x * m.b) || 0;\n return m;\n },\n scaling: function(scaleX, scaleY) {\n var m = new Matrix();\n m.a = scaleX;\n m.b = 0;\n m.c = 0;\n m.d = scaleY;\n m.e = 0;\n m.f = 0;\n return m;\n },\n parse: function(v) {\n var parts, nums;\n if (v) {\n v = v.trim();\n // of the form \"matrix(...)\"\n if (v.slice(0, 6).toLowerCase() === \"matrix\") {\n nums = v.slice(7, v.length - 1).trim();\n parts = nums.split(\",\");\n if (parts.length === 6) {\n return Matrix.fromList(map(parts, function(p) {\n return parseFloat(p);\n }));\n }\n parts = nums.split(\" \");\n if (parts.length === 6) {\n return Matrix.fromList(map(parts, function(p) {\n return parseFloat(p);\n }));\n }\n }\n // of the form \"(...)\"\n if (v.slice(0, 1) === \"(\" && v.slice(v.length - 1) === \")\") {\n v = v.substr(1, v.length - 1);\n }\n if (v.indexOf(\",\") > 0) {\n parts = v.split(\",\");\n if (parts.length === 6) {\n return Matrix.fromList(map(parts, function(p) {\n return parseFloat(p);\n }));\n }\n }\n if (v.indexOf(\" \") > 0) {\n parts = v.split(\" \");\n if (parts.length === 6) {\n return Matrix.fromList(map(parts, function(p) {\n return parseFloat(p);\n }));\n }\n }\n }\n return parts;\n }\n });\n\n /**\n * SVG transformation represented as a vector.\n */\n var MatrixVector = Class.extend({\n init: function(a, b, c, d, e, f) {\n this.a = a || 0;\n this.b = b || 0;\n this.c = c || 0;\n this.d = d || 0;\n this.e = e || 0;\n this.f = f || 0;\n },\n fromMatrix: function FromMatrix(m) {\n var v = new MatrixVector();\n v.a = m.a;\n v.b = m.b;\n v.c = m.c;\n v.d = m.d;\n v.e = m.e;\n v.f = m.f;\n return v;\n }\n });\n\n /**\n * Returns a value with Gaussian (normal) distribution.\n * @param mean The mean value of the distribution.\n * @param deviation The deviation (spreading at half-height) of the distribution.\n * @returns {number}\n */\n function normalVariable(mean, deviation) {\n var x, y, r;\n do {\n x = Math.random() * 2 - 1;\n y = Math.random() * 2 - 1;\n r = x * x + y * y;\n }\n while (!r || r > 1);\n return mean + deviation * x * Math.sqrt(-2 * Math.log(r) / r);\n }\n\n /**\n * Returns a random identifier which can be used as an ID of objects, eventually augmented with a prefix.\n * @returns {string}\n */\n function randomId(length) {\n if (Utils.isUndefined(length)) {\n length = 10;\n }\n // old version return Math.floor((1 + Math.random()) * 0x1000000).toString(16).substring(1);\n var result = '';\n var chars = '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ';\n for (var i = length; i > 0; --i) {\n result += chars.charAt(Math.round(Math.random() * (chars.length - 1)));\n }\n return result;\n }\n\n var Geometry = {\n\n /**\n * Returns the squared distance to the line defined by the two given Points.\n * @param p An arbitrary Point.\n * @param a An endpoint of the line or segment.\n * @param b The complementary endpoint of the line or segment.\n */\n _distanceToLineSquared: function(p, a, b) {\n function d2(pt1, pt2) {\n return (pt1.x - pt2.x) * (pt1.x - pt2.x) + (pt1.y - pt2.y) * (pt1.y - pt2.y);\n }\n\n if (a === b) { // returns the distance of p to a\n return d2(p, a);\n }\n\n var vx = b.x - a.x,\n vy = b.y - a.y,\n dot = (p.x - a.x) * vx + (p.y - a.y) * vy;\n if (dot < 0) {\n return d2(a, p); // sits on side of a\n }\n\n dot = (b.x - p.x) * vx + (b.y - p.y) * vy;\n if (dot < 0) {\n return d2(b, p); // sits on side of b\n }\n // regular case, use crossproduct to get the sine out\n dot = (b.x - p.x) * vy - (b.y - p.y) * vx;\n return dot * dot / (vx * vx + vy * vy);\n },\n\n /**\n * Returns the distance to the line defined by the two given Points.\n * @param p An arbitrary Point.\n * @param a An endpoint of the line or segment.\n * @param b The complementary endpoint of the line or segment.\n */\n distanceToLine: function(p, a, b) {\n return Math.sqrt(this._distanceToLineSquared(p, a, b));\n },\n\n /**\n * Returns the distance of the given points to the polyline defined by the points.\n * @param p An arbitrary point.\n * @param points The points defining the polyline.\n * @returns {Number}\n */\n distanceToPolyline: function(p, points) {\n var minimum = Number.MAX_VALUE;\n if (Utils.isUndefined(points) || points.length === 0) {\n return Number.MAX_VALUE;\n }\n for (var s = 0; s < points.length - 1; s++) {\n var p1 = points[s];\n var p2 = points[s + 1];\n\n var d = this._distanceToLineSquared(p, p1, p2);\n if (d < minimum) {\n minimum = d;\n }\n }\n return Math.sqrt(minimum);\n }\n };\n\n /*---------------The HashTable structure--------------------------------*/\n\n /**\n * Represents a collection of key-value pairs that are organized based on the hash code of the key.\n * _buckets[hashId] = {key: key, value:...}\n * Important: do not use the standard Array access method, use the get/set methods instead.\n * See http://en.wikipedia.org/wiki/Hash_table\n */\n var HashTable = kendo.Class.extend({\n init: function() {\n this._buckets = [];\n this.length = 0;\n },\n\n /**\n * Adds the literal object with the given key (of the form {key: key,....}).\n */\n add: function(key, value) {\n\n var obj = this._createGetBucket(key);\n if (Utils.isDefined(value)) {\n obj.value = value;\n }\n return obj;\n },\n\n /**\n * Gets the literal object with the given key.\n */\n get: function(key) {\n if (this._bucketExists(key)) {\n return this._createGetBucket(key);\n }\n return null;\n },\n\n /**\n * Set the key-value pair.\n * @param key The key of the entry.\n * @param value The value to set. If the key already exists the value will be overwritten.\n */\n set: function(key, value) {\n this.add(key, value);\n },\n\n /**\n * Determines whether the HashTable contains a specific key.\n */\n containsKey: function(key) {\n return this._bucketExists(key);\n },\n\n /**\n * Removes the element with the specified key from the hashtable.\n * Returns the removed bucket.\n */\n remove: function(key) {\n if (this._bucketExists(key)) {\n var hashId = this._hash(key);\n delete this._buckets[hashId];\n this.length--;\n return key;\n }\n },\n\n /**\n * Foreach with an iterator working on the key-value pairs.\n * @param func\n */\n forEach: function(func) {\n var hashes = this._hashes();\n for (var i = 0, len = hashes.length; i < len; i++) {\n var hash = hashes[i];\n var bucket = this._buckets[hash];\n if (Utils.isUndefined(bucket)) {\n continue;\n }\n func(bucket);\n }\n },\n\n /**\n * Returns a (shallow) clone of the current HashTable.\n * @returns {HashTable}\n */\n clone: function() {\n var ht = new HashTable();\n var hashes = this._hashes();\n for (var i = 0, len = hashes.length; i < len; i++) {\n var hash = hashes[i];\n var bucket = this._buckets[hash];\n if (Utils.isUndefined(bucket)) {\n continue;\n }\n ht.add(bucket.key, bucket.value);\n }\n return ht;\n },\n\n /**\n * Returns the hashes of the buckets.\n * @returns {Array}\n * @private\n */\n _hashes: function() {\n var hashes = [];\n for (var hash in this._buckets) {\n if (this._buckets.hasOwnProperty(hash)) {\n hashes.push(hash);\n }\n }\n return hashes;\n },\n\n _bucketExists: function(key) {\n var hashId = this._hash(key);\n return Utils.isDefined(this._buckets[hashId]);\n },\n\n /**\n * Returns-adds the createGetBucket with the given key. If not present it will\n * be created and returned.\n * A createGetBucket is a literal object of the form {key: key, ...}.\n */\n _createGetBucket: function(key) {\n var hashId = this._hash(key);\n var bucket = this._buckets[hashId];\n if (Utils.isUndefined(bucket)) {\n bucket = { key: key };\n this._buckets[hashId] = bucket;\n this.length++;\n }\n return bucket;\n },\n\n /**\n * Hashing of the given key.\n */\n _hash: function(key) {\n if (Utils.isNumber(key)) {\n return key;\n }\n if (Utils.isString(key)) {\n return this._hashString(key);\n }\n if (Utils.isObject(key)) {\n return this._objectHashId(key);\n }\n throw \"Unsupported key type.\";\n },\n\n /**\n * Hashing of a string.\n */\n _hashString: function(s) {\n // see for example http://stackoverflow.com/questions/7616461/generate-a-hash-from-string-in-javascript-jquery\n var result = 0;\n if (s.length === 0) {\n return result;\n }\n for (var i = 0; i < s.length; i++) {\n var ch = s.charCodeAt(i);\n result = ((result * 32) - result) + ch;\n }\n return result;\n },\n\n /**\n * Returns the unique identifier for an object. This is automatically assigned and add on the object.\n */\n _objectHashId: function(key) {\n var id = key._hashId;\n if (Utils.isUndefined(id)) {\n id = randomId();\n key._hashId = id;\n }\n return id;\n }\n });\n\n /*---------------The Dictionary structure--------------------------------*/\n\n /**\n * Represents a collection of key-value pairs.\n * Important: do not use the standard Array access method, use the get/Set methods instead.\n */\n var Dictionary = kendo.Observable.extend({\n /**\n * Initializes a new instance of the Dictionary class.\n * @param dictionary Loads the content of the given dictionary into this new one.\n */\n init: function(dictionary) {\n var that = this;\n kendo.Observable.fn.init.call(that);\n this._hashTable = new HashTable();\n this.length = 0;\n if (Utils.isDefined(dictionary)) {\n if (Array.isArray(dictionary)) {\n for (var i = 0; i < dictionary.length; i++) {\n this.add(dictionary[i]);\n }\n } else {\n dictionary.forEach(function(k, v) {\n this.add(k, v);\n }, this);\n }\n }\n },\n\n /**\n * Adds a key-value to the dictionary.\n * If the key already exists this will assign the given value to the existing entry.\n */\n add: function(key, value) {\n var entry = this._hashTable.get(key);\n if (!entry) {\n entry = this._hashTable.add(key);\n this.length++;\n this.trigger('changed');\n }\n entry.value = value;\n },\n\n /**\n * Set the key-value pair.\n * @param key The key of the entry.\n * @param value The value to set. If the key already exists the value will be overwritten.\n */\n set: function(key, value) {\n this.add(key, value);\n },\n\n /**\n * Gets the value associated with the given key in the dictionary.\n */\n get: function(key) {\n var entry = this._hashTable.get(key);\n if (entry) {\n return entry.value;\n }\n throw new Error(\"Cannot find key \" + key);\n },\n\n /**\n * Returns whether the dictionary contains the given key.\n */\n containsKey: function(key) {\n return this._hashTable.containsKey(key);\n },\n\n /**\n * Removes the element with the specified key from the dictionary.\n */\n remove: function(key) {\n if (this.containsKey(key)) {\n this.trigger(\"changed\");\n this.length--;\n return this._hashTable.remove(key);\n }\n },\n\n /**\n * The functional gets the key and value as parameters.\n */\n forEach: function(func, thisRef) {\n this._hashTable.forEach(function(entry) {\n func.call(thisRef, entry.key, entry.value);\n });\n },\n\n /**\n * Same as forEach except that only the value is passed to the functional.\n */\n forEachValue: function(func, thisRef) {\n this._hashTable.forEach(function(entry) {\n func.call(thisRef, entry.value);\n });\n },\n\n /**\n * Calls a defined callback function for each key in the dictionary.\n */\n forEachKey: function(func, thisRef) {\n this._hashTable.forEach(function(entry) {\n func.call(thisRef, entry.key);\n });\n },\n\n /**\n * Gets an array with all keys in the dictionary.\n */\n keys: function() {\n var keys = [];\n this.forEachKey(function(key) {\n keys.push(key);\n });\n return keys;\n }\n });\n\n /*---------------Queue structure--------------------------------*/\n\n var Queue = kendo.Class.extend({\n\n init: function() {\n this._tail = null;\n this._head = null;\n this.length = 0;\n },\n\n /**\n * Enqueues an object to the end of the queue.\n */\n enqueue: function(value) {\n var entry = { value: value, next: null };\n if (!this._head) {\n this._head = entry;\n this._tail = this._head;\n }\n else {\n this._tail.next = entry;\n this._tail = this._tail.next;\n }\n this.length++;\n },\n\n /**\n * Removes and returns the object at top of the queue.\n */\n dequeue: function() {\n if (this.length < 1) {\n throw new Error(\"The queue is empty.\");\n }\n var value = this._head.value;\n this._head = this._head.next;\n this.length--;\n return value;\n },\n\n contains: function(item) {\n var current = this._head;\n while (current) {\n if (current.value === item) {\n return true;\n }\n current = current.next;\n }\n return false;\n }\n });\n\n\n /**\n * While other data structures can have multiple times the same item a Set owns only\n * once a particular item.\n * @type {*}\n */\n var Set = kendo.Observable.extend({\n init: function(resource) {\n var that = this;\n kendo.Observable.fn.init.call(that);\n this._hashTable = new HashTable();\n this.length = 0;\n if (Utils.isDefined(resource)) {\n if (resource instanceof HashTable) {\n resource.forEach(function(d) {\n this.add(d);\n });\n }\n else if (resource instanceof Dictionary) {\n resource.forEach(function(k, v) {\n this.add({ key: k, value: v });\n }, this);\n }\n }\n },\n\n contains: function(item) {\n return this._hashTable.containsKey(item);\n },\n\n add: function(item) {\n var entry = this._hashTable.get(item);\n if (!entry) {\n this._hashTable.add(item, item);\n this.length++;\n this.trigger('changed');\n }\n },\n\n get: function(item) {\n if (this.contains(item)) {\n return this._hashTable.get(item).value;\n }\n else {\n return null;\n }\n },\n\n /**\n * Returns the hash of the item.\n * @param item\n * @returns {*}\n */\n hash: function(item) {\n return this._hashTable._hash(item);\n },\n\n /**\n * Removes the given item from the set. No exception is thrown if the item is not in the Set.\n * @param item\n */\n remove: function(item) {\n if (this.contains(item)) {\n this._hashTable.remove(item);\n this.length--;\n this.trigger('changed');\n }\n },\n /**\n * Foreach with an iterator working on the key-value pairs.\n * @param func\n */\n forEach: function(func, context) {\n this._hashTable.forEach(function(kv) {\n func(kv.value);\n }, context);\n },\n toArray: function() {\n var r = [];\n this.forEach(function(d) {\n r.push(d);\n });\n return r;\n }\n });\n\n /*----------------Node-------------------------------*/\n\n /**\n * Defines the node (vertex) of a Graph.\n */\n var Node = kendo.Class.extend({\n\n init: function(id, shape) {\n\n /**\n * Holds all the links incident with the current node.\n * Do not use this property to manage the incoming links, use the appropriate add/remove methods instead.\n */\n this.links = [];\n\n /**\n * Holds the links from the current one to another Node .\n * Do not use this property to manage the incoming links, use the appropriate add/remove methods instead.\n */\n this.outgoing = [];\n\n /**\n * Holds the links from another Node to the current one.\n * Do not use this property to manage the incoming links, use the appropriate add/remove methods instead.\n */\n this.incoming = [];\n\n /**\n * Holds the weight of this Node.\n */\n this.weight = 1;\n\n if (Utils.isDefined(id)) {\n this.id = id;\n }\n else {\n this.id = randomId();\n }\n if (Utils.isDefined(shape)) {\n this.associatedShape = shape;\n // transfer the shape's bounds to the runtime props\n var b = shape.bounds();\n this.width = b.width;\n this.height = b.height;\n this.x = b.x;\n this.y = b.y;\n }\n else {\n this.associatedShape = null;\n }\n /**\n * The payload of the node.\n * @type {null}\n */\n this.data = null;\n this.type = \"Node\";\n this.shortForm = \"Node '\" + this.id + \"'\";\n /**\n * Whether this is an injected node during the analysis or layout process.\n * @type {boolean}\n */\n this.isVirtual = false;\n },\n\n /**\n * Returns whether this node has no links attached.\n */\n isIsolated: function() {\n return Utils.isEmpty(this.links);\n },\n\n /**\n * Gets or sets the bounding rectangle of this node.\n * This should be considered as runtime data, the property is not hotlinked to a SVG item.\n */\n bounds: function(r) {\n if (!Utils.isDefined(r)) {\n return new diagram.Rect(this.x, this.y, this.width, this.height);\n }\n\n this.x = r.x;\n this.y = r.y;\n this.width = r.width;\n this.height = r.height;\n },\n\n /**\n * Returns whether there is at least one link with the given (complementary) node. This can be either an\n * incoming or outgoing link.\n */\n isLinkedTo: function(node) {\n var that = this;\n return Utils.any(that.links, function(link) {\n return link.getComplement(that) === node;\n });\n },\n\n /**\n * Gets the children of this node, defined as the adjacent nodes with a link from this node to the adjacent one.\n * @returns {Array}\n */\n getChildren: function() {\n if (this.outgoing.length === 0) {\n return [];\n }\n var children = [];\n for (var i = 0, len = this.outgoing.length; i < len; i++) {\n var link = this.outgoing[i];\n children.push(link.getComplement(this));\n }\n return children;\n },\n\n /**\n * Gets the parents of this node, defined as the adjacent nodes with a link from the adjacent node to this one.\n * @returns {Array}\n */\n getParents: function() {\n if (this.incoming.length === 0) {\n return [];\n }\n var parents = [];\n for (var i = 0, len = this.incoming.length; i < len; i++) {\n var link = this.incoming[i];\n parents.push(link.getComplement(this));\n }\n return parents;\n },\n\n /**\n * Returns a clone of the Node. Note that the identifier is not cloned since it's a different Node instance.\n * @returns {Node}\n */\n clone: function() {\n var copy = new Node();\n if (Utils.isDefined(this.weight)) {\n copy.weight = this.weight;\n }\n if (Utils.isDefined(this.balance)) {\n copy.balance = this.balance;\n }\n if (Utils.isDefined(this.owner)) {\n copy.owner = this.owner;\n }\n copy.associatedShape = this.associatedShape;\n copy.x = this.x;\n copy.y = this.y;\n copy.width = this.width;\n copy.height = this.height;\n return copy;\n },\n\n /**\n * Returns whether there is a link from the current node to the given node.\n */\n adjacentTo: function(node) {\n return this.isLinkedTo(node) !== null;\n },\n\n /**\n * Removes the given link from the link collection this node owns.\n * @param link\n */\n removeLink: function(link) {\n if (link.source === this) {\n Utils.remove(this.links, link);\n Utils.remove(this.outgoing, link);\n link.source = null;\n }\n\n if (link.target === this) {\n Utils.remove(this.links, link);\n Utils.remove(this.incoming, link);\n link.target = null;\n }\n },\n\n /**\n * Returns whether there is a (outgoing) link from the current node to the given one.\n */\n hasLinkTo: function(node) {\n return Utils.any(this.outgoing, function(link) {\n return link.target === node;\n });\n },\n\n /**\n * Returns the degree of this node, i.e. the sum of incoming and outgoing links.\n */\n degree: function() {\n return this.links.length;\n },\n\n /**\n * Returns whether this node is either the source or the target of the given link.\n */\n incidentWith: function(link) {\n return contains(this.links, link);\n },\n\n /**\n * Returns the links between this node and the given one.\n */\n getLinksWith: function(node) {\n return Utils.all(this.links, function(link) {\n return link.getComplement(this) === node;\n }, this);\n },\n\n /**\n * Returns the nodes (either parent or child) which are linked to the current one.\n */\n getNeighbors: function() {\n var neighbors = [];\n Utils.forEach(this.incoming, function(e) {\n neighbors.push(e.getComplement(this));\n }, this);\n Utils.forEach(this.outgoing, function(e) {\n neighbors.push(e.getComplement(this));\n }, this);\n return neighbors;\n }\n });\n\n /**\n * Defines a directed link (edge, connection) of a Graph.\n */\n var Link = kendo.Class.extend({\n\n init: function(source, target, id, connection) {\n if (Utils.isUndefined(source)) {\n throw \"The source of the new link is not set.\";\n }\n if (Utils.isUndefined(target)) {\n throw \"The target of the new link is not set.\";\n }\n var sourceFound, targetFound;\n if (Utils.isString(source)) {\n sourceFound = new Node(source);\n }\n else {\n sourceFound = source;\n }\n if (Utils.isString(target)) {\n targetFound = new Node(target);\n }\n else {\n targetFound = target;\n }\n\n this.source = sourceFound;\n this.target = targetFound;\n this.source.links.push(this);\n this.target.links.push(this);\n this.source.outgoing.push(this);\n this.target.incoming.push(this);\n if (Utils.isDefined(id)) {\n this.id = id;\n }\n else {\n this.id = randomId();\n }\n if (Utils.isDefined(connection)) {\n this.associatedConnection = connection;\n }\n else {\n this.associatedConnection = null;\n }\n this.type = \"Link\";\n this.shortForm = \"Link '\" + this.source.id + \"->\" + this.target.id + \"'\";\n },\n\n /**\n * Returns the complementary node of the given one, if any.\n */\n getComplement: function(node) {\n if (this.source !== node && this.target !== node) {\n throw \"The given node is not incident with this link.\";\n }\n return this.source === node ? this.target : this.source;\n },\n\n /**\n * Returns the overlap of the current link with the given one, if any.\n */\n getCommonNode: function(link) {\n if (this.source === link.source || this.source === link.target) {\n return this.source;\n }\n if (this.target === link.source || this.target === link.target) {\n return this.target;\n }\n return null;\n },\n\n /**\n * Returns whether the current link is bridging the given nodes.\n */\n isBridging: function(v1, v2) {\n return this.source === v1 && this.target === v2 || this.source === v2 && this.target === v1;\n },\n\n /**\n * Returns the source and target of this link as a tuple.\n */\n getNodes: function() {\n return [this.source, this.target];\n },\n\n /**\n * Returns whether the given node is either the source or the target of the current link.\n */\n incidentWith: function(node) {\n return this.source === node || this.target === node;\n },\n\n /**\n * Returns whether the given link is a continuation of the current one. This can be both\n * via an incoming or outgoing link.\n */\n adjacentTo: function(link) {\n return contains(this.source.links, link) || contains(this.target.links, link);\n },\n\n /**\n * Changes the source-node of this link.\n */\n changeSource: function(node) {\n Utils.remove(this.source.links, this);\n Utils.remove(this.source.outgoing, this);\n\n node.links.push(this);\n node.outgoing.push(this);\n\n this.source = node;\n },\n\n /**\n * Changes the target-node of this link.\n * @param node\n */\n changeTarget: function(node) {\n Utils.remove(this.target.links, this);\n Utils.remove(this.target.incoming, this);\n\n node.links.push(this);\n node.incoming.push(this);\n\n this.target = node;\n },\n\n /**\n * Changes both the source and the target nodes of this link.\n */\n changesNodes: function(v, w) {\n if (this.source === v) {\n this.changeSource(w);\n }\n else if (this.target === v) {\n this.changeTarget(w);\n }\n },\n\n /**\n * Reverses the direction of this link.\n */\n reverse: function() {\n var oldSource = this.source;\n var oldTarget = this.target;\n\n this.source = oldTarget;\n Utils.remove(oldSource.outgoing, this);\n this.source.outgoing.push(this);\n\n this.target = oldSource;\n Utils.remove(oldTarget.incoming, this);\n this.target.incoming.push(this);\n return this;\n },\n\n /**\n * Ensures that the given target defines the endpoint of this link.\n */\n directTo: function(target) {\n if (this.source !== target && this.target !== target) {\n throw \"The given node is not incident with this link.\";\n }\n if (this.target !== target) {\n this.reverse();\n }\n },\n\n /**\n * Returns a reversed clone of this link.\n */\n createReverseEdge: function() {\n var r = this.clone();\n r.reverse();\n r.reversed = true;\n return r;\n },\n\n /**\n * Returns a clone of this link.\n */\n clone: function() {\n var clone = new Link(this.source, this.target);\n return clone;\n }\n });\n\n /*--------------Graph structure---------------------------------*/\n /**\n * Defines a directed graph structure.\n * Note that the incidence structure resides in the nodes through the incoming and outgoing links collection, rahter than\n * inside the Graph.\n */\n var Graph = kendo.Class.extend({\n init: function(idOrDiagram) {\n /**\n * The links or edge collection of this Graph.\n * @type {Array}\n */\n this.links = [];\n /**\n * The node or vertex collection of this Graph.\n * @type {Array}\n */\n this.nodes = [];\n\n this._nodeMap = new Dictionary();\n /**\n * The optional reference to the Diagram on which this Graph is based.\n * @type {null}\n */\n this.diagram = null;\n\n /**\n * The root of this Graph. If not set explicitly the first Node with zero incoming links will be taken.\n * @type {null}\n * @private\n */\n this._root = null;\n if (Utils.isDefined(idOrDiagram)) {\n if (Utils.isString(idOrDiagram)) {\n this.id = idOrDiagram;\n }\n else {\n this.diagram = idOrDiagram;\n this.id = idOrDiagram.id;\n }\n }\n else {\n this.id = randomId();\n }\n\n /**\n * The bounds of this graph if the nodes have spatial extension defined.\n * @type {Rect}\n */\n this.bounds = new Rect();\n // keeps track whether the children & parents have been created\n this._hasCachedRelationships = false;\n this.type = \"Graph\";\n },\n /**\n * Caches the relational information of parents and children in the 'parents' and 'children'\n * properties.\n * @param forceRebuild If set to true the relational info will be rebuild even if already present.\n */\n cacheRelationships: function(forceRebuild) {\n if (Utils.isUndefined(forceRebuild)) {\n forceRebuild = false;\n }\n if (this._hasCachedRelationships && !forceRebuild) {\n return;\n }\n for (var i = 0, len = this.nodes.length; i < len; i++) {\n var node = this.nodes[i];\n node.children = this.getChildren(node);\n node.parents = this.getParents(node);\n }\n this._hasCachedRelationships = true;\n },\n\n /**\n * Assigns tree-levels to the nodes assuming this is a tree graph.\n * If not connected or not a tree the process will succeed but\n * will have little meaning.\n * @param startNode The node from where the level numbering starts, usually the root of the tree.\n * @param visited The collection of visited nodes.\n * @param offset The offset or starting counter of the level info.\n */\n assignLevels: function(startNode, offset, visited) {\n if (!startNode) {\n throw \"Start node not specified.\";\n }\n if (Utils.isUndefined(offset)) {\n offset = 0;\n }\n // if not done before, cache the parents and children\n this.cacheRelationships();\n if (Utils.isUndefined(visited)) {\n visited = new Dictionary();\n Utils.forEach(this.nodes, function(n) {\n visited.add(n, false);\n });\n }\n visited.set(startNode, true);\n startNode.level = offset;\n var children = startNode.children;\n for (var i = 0, len = children.length; i < len; i++) {\n var child = children[i];\n if (!child || visited.get(child)) {\n continue;\n }\n this.assignLevels(child, offset + 1, visited);\n }\n },\n\n /**\n * Gets or set the root of this graph.\n * If not set explicitly the first Node with zero incoming links will be taken.\n * @param value\n * @returns {*}\n */\n root: function(value) {\n if (Utils.isUndefined(value)) {\n if (!this._root) {\n // TODO: better to use the longest path for the most probable root?\n var found = Utils.first(this.nodes, function(n) {\n return n.incoming.length === 0;\n });\n if (found) {\n return found;\n }\n return Utils.first(this.nodes);\n }\n else {\n return this._root;\n }\n }\n else {\n this._root = value;\n }\n },\n\n /**\n * Returns the connected components of this graph.\n * Note that the returned graphs are made up of the nodes and links of this graph, i.e. a pointer to the items of this graph.\n * If you alter the items of the components you'll alter the original graph and vice versa.\n * @returns {Array}\n */\n getConnectedComponents: function() {\n this.componentIndex = 0;\n this.setItemIndices();\n var componentId = Utils.initArray(this.nodes.length, -1);\n\n for (var v = 0; v < this.nodes.length; v++) {\n if (componentId[v] === -1) {\n this._collectConnectedNodes(componentId, v);\n this.componentIndex++;\n }\n }\n\n var components = [], i;\n for (i = 0; i < this.componentIndex; ++i) {\n components[i] = new Graph();\n }\n for (i = 0; i < componentId.length; ++i) {\n var graph = components[componentId[i]];\n graph.addNodeAndOutgoings(this.nodes[i]);\n }\n // sorting the components in decreasing order of node count\n components.sort(function(a, b) {\n return b.nodes.length - a.nodes.length;\n });\n return components;\n },\n\n _collectConnectedNodes: function(setIds, nodeIndex) {\n setIds[nodeIndex] = this.componentIndex; // part of the current component\n var node = this.nodes[nodeIndex];\n Utils.forEach(node.links,\n function(link) {\n var next = link.getComplement(node);\n var nextId = next.index;\n if (setIds[nextId] === -1) {\n this._collectConnectedNodes(setIds, nextId);\n }\n }, this);\n },\n\n /**\n * Calculates the bounds of this Graph if the Nodes have spatial dimensions defined.\n * @returns {Rect}\n */\n calcBounds: function() {\n if (this.isEmpty()) {\n this.bounds = new Rect();\n return this.bounds;\n }\n var b = null;\n for (var i = 0, len = this.nodes.length; i < len; i++) {\n var node = this.nodes[i];\n if (!b) {\n b = node.bounds();\n }\n else {\n b = b.union(node.bounds());\n }\n }\n this.bounds = b;\n return this.bounds;\n },\n\n /**\n * Creates a spanning tree for the current graph.\n * Important: this will not return a spanning forest if the graph is disconnected.\n * Prim's algorithm finds a minimum-cost spanning tree of an edge-weighted, connected, undirected graph;\n * see http://en.wikipedia.org/wiki/Prim%27s_algorithm .\n * @param root The root of the spanning tree.\n * @returns {Graph}\n */\n getSpanningTree: function(root) {\n var tree = new Graph();\n var map = new Dictionary(), source, target;\n tree.root = root.clone();\n tree.root.level = 0;\n tree.root.id = root.id;\n map.add(root, tree.root);\n root.level = 0;\n\n var visited = [];\n var remaining = [];\n tree._addNode(tree.root);\n visited.push(root);\n remaining.push(root);\n\n var levelCount = 1;\n while (remaining.length > 0) {\n var next = remaining.pop();\n for (var ni = 0; ni < next.links.length; ni++) {\n var link = next.links[ni];\n var cn = link.getComplement(next);\n if (contains(visited, cn)) {\n continue;\n }\n\n cn.level = next.level + 1;\n if (levelCount < cn.level + 1) {\n levelCount = cn.level + 1;\n }\n if (!contains(remaining, cn)) {\n remaining.push(cn);\n }\n if (!contains(visited, cn)) {\n visited.push(cn);\n }\n if (map.containsKey(next)) {\n source = map.get(next);\n }\n else {\n source = next.clone();\n source.level = next.level;\n source.id = next.id;\n map.add(next, source);\n }\n if (map.containsKey(cn)) {\n target = map.get(cn);\n }\n else {\n target = cn.clone();\n target.level = cn.level;\n target.id = cn.id;\n map.add(cn, target);\n }\n var newLink = new Link(source, target);\n tree.addLink(newLink);\n }\n\n }\n\n var treeLevels = [];\n for (var i = 0; i < levelCount; i++) {\n treeLevels.push([]);\n }\n\n Utils.forEach(tree.nodes, function(node) {\n treeLevels[node.level].push(node);\n });\n\n tree.treeLevels = treeLevels;\n tree.cacheRelationships();\n return tree;\n },\n\n /**\n * Returns a random node in this graph.\n * @param excludedNodes The collection of nodes which should not be considered.\n * @param incidenceLessThan The maximum degree or incidence the random node should have.\n * @returns {*}\n */\n takeRandomNode: function(excludedNodes, incidenceLessThan) {\n if (Utils.isUndefined(excludedNodes)) {\n excludedNodes = [];\n }\n if (Utils.isUndefined(incidenceLessThan)) {\n incidenceLessThan = 4;\n }\n if (this.nodes.length === 0) {\n return null;\n }\n if (this.nodes.length === 1) {\n return contains(excludedNodes, this.nodes[0]) ? null : this.nodes[0];\n }\n var pool = $.grep(this.nodes, function(node) {\n return !contains(excludedNodes, node) && node.degree() <= incidenceLessThan;\n });\n if (Utils.isEmpty(pool)) {\n return null;\n }\n return pool[Utils.randomInteger(0, pool.length)];\n },\n\n /**\n * Returns whether this is an empty graph.\n */\n isEmpty: function() {\n return Utils.isEmpty(this.nodes);\n },\n\n /**\n * Checks whether the endpoints of the links are all in the nodes collection.\n */\n isHealthy: function() {\n return Utils.all(this.links, function(link) {\n return contains(this.nodes, link.source) && contains(this.nodes, link.target);\n }, this);\n },\n\n /**\n * Gets the parents of this node, defined as the adjacent nodes with a link from the adjacent node to this one.\n * @returns {Array}\n */\n getParents: function(n) {\n if (!this.hasNode(n)) {\n throw \"The given node is not part of this graph.\";\n }\n return n.getParents();\n },\n\n /**\n * Gets the children of this node, defined as the adjacent nodes with a link from this node to the adjacent one.\n * @returns {Array}\n */\n getChildren: function(n) {\n if (!this.hasNode(n)) {\n throw \"The given node is not part of this graph.\";\n }\n return n.getChildren();\n },\n\n /**\n * Adds a new link to the graph between the given nodes.\n */\n addLink: function(sourceOrLink, target, owner) {\n\n if (Utils.isUndefined(sourceOrLink)) {\n throw \"The source of the link is not defined.\";\n }\n if (Utils.isUndefined(target)) {\n // can only be undefined if the first one is a Link\n if (Utils.isDefined(sourceOrLink.type) && sourceOrLink.type === \"Link\") {\n this.addExistingLink(sourceOrLink);\n return;\n }\n else {\n throw \"The target of the link is not defined.\";\n }\n }\n\n var foundSource = this.getNode(sourceOrLink);\n if (Utils.isUndefined(foundSource)) {\n foundSource = this.addNode(sourceOrLink);\n }\n var foundTarget = this.getNode(target);\n if (Utils.isUndefined(foundTarget)) {\n foundTarget = this.addNode(target);\n }\n\n var newLink = new Link(foundSource, foundTarget);\n\n if (Utils.isDefined(owner)) {\n newLink.owner = owner;\n }\n\n /*newLink.source.outgoing.push(newLink);\n newLink.source.links.push(newLink);\n newLink.target.incoming.push(newLink);\n newLink.target.links.push(newLink);*/\n\n this.links.push(newLink);\n\n return newLink;\n },\n\n /**\n * Removes all the links in this graph.\n */\n removeAllLinks: function() {\n while (this.links.length > 0) {\n var link = this.links[0];\n this.removeLink(link);\n }\n },\n\n /**\n * Adds the given link to the current graph.\n */\n addExistingLink: function(link) {\n\n if (this.hasLink(link)) {\n return;\n }\n this.links.push(link);\n if (this.hasNode(link.source.id)) {\n // priority to the existing node with the id even if other props are different\n var s = this.getNode(link.source.id);\n link.changeSource(s);\n }\n else {\n this.addNode(link.source);\n }\n\n if (this.hasNode(link.target.id)) {\n var t = this.getNode(link.target.id);\n link.changeTarget(t);\n }\n else {\n this.addNode(link.target);\n }\n\n /* if (!link.source.outgoing.contains(link)) {\n link.source.outgoing.push(link);\n }\n if (!link.source.links.contains(link)) {\n link.source.links.push(link);\n }\n if (!link.target.incoming.contains(link)) {\n link.target.incoming.push(link);\n }\n if (!link.target.links.contains(link)) {\n link.target.links.push(link);\n }*/\n },\n\n /**\n * Returns whether the given identifier or Link is part of this graph.\n * @param linkOrId An identifier or a Link object.\n * @returns {*}\n */\n hasLink: function(linkOrId) {\n if (Utils.isString(linkOrId)) {\n return Utils.any(this.links, function(link) {\n return link.id === linkOrId;\n });\n }\n if (linkOrId.type === \"Link\") {\n return contains(this.links, linkOrId);\n }\n throw \"The given object is neither an identifier nor a Link.\";\n },\n /**\n * Gets the node with the specified Id or null if not part of this graph.\n */\n getNode: function(nodeOrId) {\n var id = nodeOrId.id || nodeOrId;\n if (this._nodeMap.containsKey(id)) {\n return this._nodeMap.get(id);\n }\n },\n\n /**\n * Returns whether the given node or node Id is part of this graph.\n */\n hasNode: function(nodeOrId) {\n var id = nodeOrId.id || nodeOrId;\n return this._nodeMap.containsKey(id);\n },\n\n _addNode: function(node) {\n this.nodes.push(node);\n this._nodeMap.add(node.id, node);\n },\n\n _removeNode: function(node) {\n Utils.remove(this.nodes, node);\n this._nodeMap.remove(node.id);\n },\n\n /**\n * Removes the given node from this graph.\n * The node can be specified as an object or as an identifier (string).\n */\n removeNode: function(nodeOrId) {\n var n = nodeOrId;\n if (Utils.isString(nodeOrId)) {\n n = this.getNode(nodeOrId);\n }\n\n if (Utils.isDefined(n)) {\n var links = n.links;\n n.links = [];\n for (var i = 0, len = links.length; i < len; i++) {\n var link = links[i];\n this.removeLink(link);\n }\n this._removeNode(n);\n }\n else {\n throw \"The identifier should be a Node or the Id (string) of a node.\";\n }\n },\n\n /**\n * Returns whether the given nodes are connected with a least one link independently of the direction.\n */\n areConnected: function(n1, n2) {\n return Utils.any(this.links, function(link) {\n return link.source == n1 && link.target == n2 || link.source == n2 && link.target == n1;\n });\n },\n\n /**\n * Removes the given link from this graph.\n */\n removeLink: function(link) {\n /* if (!this.links.contains(link)) {\n throw \"The given link is not part of the Graph.\";\n }\n */\n Utils.remove(this.links, link);\n\n Utils.remove(link.source.outgoing, link);\n Utils.remove(link.source.links, link);\n Utils.remove(link.target.incoming, link);\n Utils.remove(link.target.links, link);\n },\n\n /**\n * Adds a new node to this graph, if not already present.\n * The node can be an existing Node or the identifier of a new node.\n * No error is thrown if the node is already there and the existing one is returned.\n */\n addNode: function(nodeOrId, layoutRect, owner) {\n\n var newNode = null;\n\n if (!Utils.isDefined(nodeOrId)) {\n throw \"No Node or identifier for a new Node is given.\";\n }\n\n if (Utils.isString(nodeOrId)) {\n if (this.hasNode(nodeOrId)) {\n return this.getNode(nodeOrId);\n }\n newNode = new Node(nodeOrId);\n }\n else {\n if (this.hasNode(nodeOrId)) {\n return this.getNode(nodeOrId);\n }\n // todo: ensure that the param is a Node?\n newNode = nodeOrId;\n }\n\n if (Utils.isDefined(layoutRect)) {\n newNode.bounds(layoutRect);\n }\n\n if (Utils.isDefined(owner)) {\n newNode.owner = owner;\n }\n this._addNode(newNode);\n return newNode;\n },\n\n /**\n * Adds the given Node and its outgoing links.\n */\n addNodeAndOutgoings: function(node) {\n if (!this.hasNode(node)) {\n this._addNode(node);\n }\n\n var newLinks = node.outgoing;\n node.outgoing = [];\n Utils.forEach(newLinks, function(link) {\n this.addExistingLink(link);\n }, this);\n },\n\n /**\n * Sets the 'index' property on the links and nodes of this graph.\n */\n setItemIndices: function() {\n var i;\n for (i = 0; i < this.nodes.length; ++i) {\n this.nodes[i].index = i;\n }\n\n for (i = 0; i < this.links.length; ++i) {\n this.links[i].index = i;\n }\n },\n\n /**\n * Returns a clone of this graph.\n */\n clone: function(saveMapping) {\n var copy = new Graph();\n var save = Utils.isDefined(saveMapping) && saveMapping === true;\n if (save) {\n copy.nodeMap = new Dictionary();\n copy.linkMap = new Dictionary();\n }\n // we need a map even if the saveMapping is not set\n var map = new Dictionary();\n Utils.forEach(this.nodes, function(nOriginal) {\n var nCopy = nOriginal.clone();\n map.set(nOriginal, nCopy);\n copy._addNode(nCopy);\n\n if (save) {\n copy.nodeMap.set(nCopy, nOriginal);\n }\n });\n\n Utils.forEach(this.links, function(linkOriginal) {\n if (map.containsKey(linkOriginal.source) && map.containsKey(linkOriginal.target)) {\n var linkCopy = copy.addLink(map.get(linkOriginal.source), map.get(linkOriginal.target));\n if (save) {\n copy.linkMap.set(linkCopy, linkOriginal);\n }\n }\n });\n\n return copy;\n },\n\n /**\n * The parsing allows a quick way to create graphs.\n * - [\"n1->n2\", \"n2->n3\"]: creates the three nodes and adds the links\n * - [\"n1->n2\", {id: \"QSDF\"}, \"n2->n3\"]: same as previous but also performs a deep extend of the link between n1 and n2 with the given object.\n */\n linearize: function(addIds) {\n return Graph.Utils.linearize(this, addIds);\n },\n\n /**\n * Performs a depth-first traversal starting at the given node.\n * @param startNode a node or id of a node in this graph\n * @param action\n */\n depthFirstTraversal: function(startNode, action) {\n if (Utils.isUndefined(startNode)) {\n throw \"You need to supply a starting node.\";\n }\n if (Utils.isUndefined(action)) {\n throw \"You need to supply an action.\";\n }\n if (!this.hasNode(startNode)) {\n throw \"The given start-node is not part of this graph\";\n }\n var foundNode = this.getNode(startNode);// case the given one is an Id\n var visited = [];\n this._dftIterator(foundNode, action, visited);\n },\n\n _dftIterator: function(node, action, visited) {\n\n action(node);\n visited.push(node);\n var children = node.getChildren();\n for (var i = 0, len = children.length; i < len; i++) {\n var child = children[i];\n if (contains(visited, child)) {\n continue;\n }\n this._dftIterator(child, action, visited);\n }\n },\n\n /**\n * Performs a breadth-first traversal starting at the given node.\n * @param startNode a node or id of a node in this graph\n * @param action\n */\n breadthFirstTraversal: function(startNode, action) {\n\n if (Utils.isUndefined(startNode)) {\n throw \"You need to supply a starting node.\";\n }\n if (Utils.isUndefined(action)) {\n throw \"You need to supply an action.\";\n }\n\n if (!this.hasNode(startNode)) {\n throw \"The given start-node is not part of this graph\";\n }\n var foundNode = this.getNode(startNode);// case the given one is an Id\n var queue = new Queue();\n var visited = [];\n queue.enqueue(foundNode);\n\n while (queue.length > 0) {\n var node = queue.dequeue();\n action(node);\n visited.push(node);\n var children = node.getChildren();\n for (var i = 0, len = children.length; i < len; i++) {\n var child = children[i];\n if (contains(visited, child) || contains(queue, child)) {\n continue;\n }\n queue.enqueue(child);\n }\n }\n },\n\n /**\n * This is the classic Tarjan algorithm for strongly connected components.\n * See e.g. http://en.wikipedia.org/wiki/Tarjan's_strongly_connected_components_algorithm\n * @param excludeSingleItems Whether isolated nodes should be excluded from the analysis.\n * @param node The start node from which the analysis starts.\n * @param indices Numbers the nodes consecutively in the order in which they are discovered.\n * @param lowLinks The smallest index of any node known to be reachable from the node, including the node itself\n * @param connected The current component.\n * @param stack The bookkeeping stack of things to visit.\n * @param index The counter of visited nodes used to assign the indices.\n * @private\n */\n _stronglyConnectedComponents: function(excludeSingleItems, node, indices, lowLinks, connected, stack, index) {\n indices.add(node, index);\n lowLinks.add(node, index);\n index++;\n\n stack.push(node);\n\n var children = node.getChildren(), next;\n for (var i = 0, len = children.length; i < len; i++) {\n next = children[i];\n if (!indices.containsKey(next)) {\n this._stronglyConnectedComponents(excludeSingleItems, next, indices, lowLinks, connected, stack, index);\n lowLinks.add(node, Math.min(lowLinks.get(node), lowLinks.get(next)));\n }\n else if (contains(stack, next)) {\n lowLinks.add(node, Math.min(lowLinks.get(node), indices.get(next)));\n }\n }\n // If v is a root node, pop the stack and generate a strong component\n if (lowLinks.get(node) === indices.get(node)) {\n var component = [];\n do {\n next = stack.pop();\n component.push(next);\n }\n while (next !== node);\n if (!excludeSingleItems || (component.length > 1)) {\n connected.push(component);\n }\n }\n },\n\n /**\n * Returns the cycles found in this graph.\n * The returned arrays consist of the nodes which are strongly coupled.\n * @param excludeSingleItems Whether isolated nodes should be excluded.\n * @returns {Array} The array of cycles found.\n */\n findCycles: function(excludeSingleItems) {\n if (Utils.isUndefined(excludeSingleItems)) {\n excludeSingleItems = true;\n }\n var indices = new Dictionary();\n var lowLinks = new Dictionary();\n var connected = [];\n var stack = [];\n for (var i = 0, len = this.nodes.length; i < len; i++) {\n var node = this.nodes[i];\n if (indices.containsKey(node)) {\n continue;\n }\n this._stronglyConnectedComponents(excludeSingleItems, node, indices, lowLinks, connected, stack, 0);\n }\n return connected;\n },\n\n /**\n * Returns whether this graph is acyclic.\n * @returns {*}\n */\n isAcyclic: function() {\n return Utils.isEmpty(this.findCycles());\n },\n\n /**\n * Returns whether the given graph is a subgraph of this one.\n * @param other Another graph instance.\n */\n isSubGraph: function(other) {\n var otherArray = other.linearize();\n var thisArray = this.linearize();\n return Utils.all(otherArray, function(s) {\n return contains(thisArray, s);\n });\n },\n\n /**\n * Makes an acyclic graph from the current (connected) one.\n * * @returns {Array} The reversed links.\n */\n makeAcyclic: function() {\n // if empty or almost empty\n if (this.isEmpty() || this.nodes.length <= 1 || this.links.length <= 1) {\n return [];\n }\n // singular case of just two nodes\n if (this.nodes.length == 2) {\n var result = [];\n if (this.links.length > 1) {\n var oneLink = this.links[0];\n var oneNode = oneLink.source;\n for (var i = 0, len = this.links.length; i < len; i++) {\n var link = this.links[i];\n if (link.source == oneNode) {\n continue;\n }\n var rev = link.reverse();\n result.push(rev);\n }\n }\n return result;\n }\n\n var copy = this.clone(true); // copy.nodeMap tells you the mapping\n var N = this.nodes.length;\n\n var intensityCatalog = new Dictionary();\n\n /**\n * If there are both incoming and outgoing links this will return the flow intensity (out-in).\n * Otherwise the node acts as a flow source with N specifying the (equal) intensity.\n * @param node\n * @returns {number}\n */\n var flowIntensity = function(node) {\n if (node.outgoing.length === 0) {\n return (2 - N);\n }\n else if (node.incoming.length === 0) {\n return (N - 2);\n }\n else {\n return node.outgoing.length - node.incoming.length;\n }\n };\n\n /**\n * Collects the nodes with the same intensity.\n * @param node\n * @param intensityCatalog\n */\n var catalogEqualIntensity = function(node, intensityCatalog) {\n var intensity = flowIntensity(node, N);\n if (!intensityCatalog.containsKey(intensity)) {\n intensityCatalog.set(intensity, []);\n }\n intensityCatalog.get(intensity).push(node);\n };\n\n Utils.forEach(copy.nodes, function(v) {\n catalogEqualIntensity(v, intensityCatalog);\n });\n\n var sourceStack = [];\n var targetStack = [];\n\n while (copy.nodes.length > 0) {\n var source, target, intensity;\n if (intensityCatalog.containsKey(2 - N)) {\n var targets = intensityCatalog.get(2 - N); // nodes without outgoings\n while (targets.length > 0) {\n target = targets.pop();\n for (var li = 0; li < target.links.length; li++) {\n var targetLink = target.links[li];\n source = targetLink.getComplement(target);\n intensity = flowIntensity(source, N);\n Utils.remove(intensityCatalog.get(intensity), source);\n source.removeLink(targetLink);\n catalogEqualIntensity(source, intensityCatalog);\n }\n copy._removeNode(target);\n targetStack.unshift(target);\n }\n }\n\n // move sources to sourceStack\n if (intensityCatalog.containsKey(N - 2)) {\n var sources = intensityCatalog.get(N - 2); // nodes without incomings\n while (sources.length > 0) {\n source = sources.pop();\n for (var si = 0; si < source.links.length; si++) {\n var sourceLink = source.links[si];\n target = sourceLink.getComplement(source);\n intensity = flowIntensity(target, N);\n Utils.remove(intensityCatalog.get(intensity), target);\n target.removeLink(sourceLink);\n catalogEqualIntensity(target, intensityCatalog);\n }\n sourceStack.push(source);\n copy._removeNode(source);\n }\n }\n\n if (copy.nodes.length > 0) {\n for (var k = N - 3; k > 2 - N; k--) {\n if (intensityCatalog.containsKey(k) &&\n intensityCatalog.get(k).length > 0) {\n var maxdiff = intensityCatalog.get(k);\n var v = maxdiff.pop();\n for (var ri = 0; ri < v.links.length; ri++) {\n var ril = v.links[ri];\n var u = ril.getComplement(v);\n intensity = flowIntensity(u, N);\n Utils.remove(intensityCatalog.get(intensity), u);\n u.removeLink(ril);\n catalogEqualIntensity(u, intensityCatalog);\n }\n sourceStack.push(v);\n copy._removeNode(v);\n break;\n }\n }\n }\n }\n\n sourceStack = sourceStack.concat(targetStack);\n\n var vertexOrder = new Dictionary();\n for (var kk = 0; kk < this.nodes.length; kk++) {\n vertexOrder.set(copy.nodeMap.get(sourceStack[kk]), kk);\n }\n\n var reversedEdges = [];\n Utils.forEach(this.links, function(link) {\n if (vertexOrder.get(link.source) > vertexOrder.get(link.target)) {\n link.reverse();\n reversedEdges.push(link);\n }\n });\n return reversedEdges;\n }\n });\n\n /**\n * A collection of predefined graphs for demo and testing purposes.\n */\n Graph.Predefined = {\n /**\n * Eight-shapes graph all connected in a cycle.\n * @returns {*}\n * @constructor\n */\n EightGraph: function() {\n return Graph.Utils.parse([ \"1->2\", \"2->3\", \"3->4\", \"4->1\", \"3->5\", \"5->6\", \"6->7\", \"7->3\"]);\n },\n\n /**\n * Creates a typical mindmap diagram.\n * @returns {*}\n * @constructor\n */\n Mindmap: function() {\n return Graph.Utils.parse([\"0->1\", \"0->2\", \"0->3\", \"0->4\", \"0->5\", \"1->6\", \"1->7\", \"7->8\", \"2->9\", \"9->10\", \"9->11\", \"3->12\",\n \"12->13\", \"13->14\", \"4->15\", \"4->16\", \"15->17\", \"15->18\", \"18->19\", \"18->20\", \"14->21\", \"14->22\", \"5->23\", \"23->24\", \"23->25\", \"6->26\"]);\n },\n\n /**\n * Three nodes connected in a cycle.\n * @returns {*}\n * @constructor\n */\n ThreeGraph: function() {\n return Graph.Utils.parse([ \"1->2\", \"2->3\", \"3->1\"]);\n },\n\n /**\n * A tree with each node having two children.\n * @param levels How many levels the binary tree should have.\n * @returns {diagram.Graph}\n * @constructor\n */\n BinaryTree: function(levels) {\n if (Utils.isUndefined(levels)) {\n levels = 5;\n }\n return Graph.Utils.createBalancedTree(levels, 2);\n },\n\n /**\n * A linear graph (discrete line segment).\n * @param length How many segments (the node count is hence (length+1)).\n * @returns {diagram.Graph}\n * @constructor\n */\n Linear: function(length) {\n if (Utils.isUndefined(length)) {\n length = 10;\n }\n return Graph.Utils.createBalancedTree(length, 1);\n },\n\n /**\n * A standard tree-graph with the specified levels and children (siblings) count.\n * Note that for a balanced tree of level N and sibling count s, counting the root as level zero:\n * - NodeCount = (1-s^(N+1))/(1-s)]\n * - LinkCount = s.(1-s^N)/(1-s)\n * @param levels How many levels the tree should have.\n * @param siblingsCount How many siblings each level should have.\n * @returns {diagram.Graph}\n * @constructor\n */\n Tree: function(levels, siblingsCount) {\n return Graph.Utils.createBalancedTree(levels, siblingsCount);\n },\n\n /**\n * Creates a forest.\n * Note that for a balanced forest of level N, sibling count s and tree count t, counting the root as level zero:\n * - NodeCount = t.(1-s^(N+1))/(1-s)]\n * - LinkCount = t.s.(1-s^N)/(1-s)\n * @param levels How many levels the tree should have.\n * @param siblingsCount How many siblings each level should have.\n * @param trees The amount of trees the forest should have.\n * @returns {diagram.Graph}\n * @constructor\n */\n Forest: function(levels, siblingsCount, trees) {\n return Graph.Utils.createBalancedForest(levels, siblingsCount, trees);\n },\n\n /**\n * A workflow-like graph with cycles.\n * @returns {*}\n * @constructor\n */\n Workflow: function() {\n return Graph.Utils.parse(\n [\"0->1\", \"1->2\", \"2->3\", \"1->4\", \"4->3\", \"3->5\", \"5->6\", \"6->3\", \"6->7\", \"5->4\"]\n );\n },\n\n /**\n * A grid graph with the direction of the links avoiding cycles.\n * Node count: (n+1).(m+1)\n * Link count: n.(m+1) + m.(n+1)\n * @param n Horizontal count of grid cells. If zero this will result in a linear graph.\n * @param m Vertical count of grid cells. If zero this will result in a linear graph.\n * @constructor\n */\n Grid: function(n, m) {\n var g = new diagram.Graph();\n if (n <= 0 && m <= 0) {\n return g;\n }\n\n for (var i = 0; i < n + 1; i++) {\n var previous = null;\n for (var j = 0; j < m + 1; j++) {\n // using x-y coordinates to name the nodes\n var node = new Node(i.toString() + \".\" + j.toString());\n g.addNode(node);\n if (previous) {\n g.addLink(previous, node);\n }\n if (i > 0) {\n var left = g.getNode((i - 1).toString() + \".\" + j.toString());\n g.addLink(left, node);\n }\n previous = node;\n }\n }\n return g;\n }\n\n };\n\n /**\n * Graph generation and other utilities.\n */\n Graph.Utils = {\n /**\n * The parsing allows a quick way to create graphs.\n * - [\"n1->n2\", \"n2->n3\"]: creates the three nodes and adds the links\n * - [\"n1->n2\", {id: \"id177\"}, \"n2->n3\"]: same as previous but also performs a deep extend of the link between n1 and n2 with the given object.\n */\n parse: function(graphString) {\n\n var previousLink, graph = new diagram.Graph(), parts = graphString.slice();\n for (var i = 0, len = parts.length; i < len; i++) {\n var part = parts[i];\n if (Utils.isString(part)) // link spec\n {\n if (part.indexOf(\"->\") < 0) {\n throw \"The link should be specified as 'a->b'.\";\n }\n var p = part.split(\"->\");\n if (p.length != 2) {\n throw \"The link should be specified as 'a->b'.\";\n }\n previousLink = new Link(p[0], p[1]);\n graph.addLink(previousLink);\n }\n if (Utils.isObject(part)) {\n if (!previousLink) {\n throw \"Specification found before Link definition.\";\n }\n kendo.deepExtend(previousLink, part);\n }\n }\n return graph;\n },\n\n /**\n * Returns a linearized representation of the given Graph.\n * See also the Graph.Utils.parse method for the inverse operation.\n */\n linearize: function(graph, addIds) {\n if (Utils.isUndefined(graph)) {\n throw \"Expected an instance of a Graph object in slot one.\";\n }\n if (Utils.isUndefined(addIds)) {\n addIds = false;\n }\n var lin = [];\n for (var i = 0, len = graph.links.length; i < len; i++) {\n var link = graph.links[i];\n lin.push(link.source.id + \"->\" + link.target.id);\n if (addIds) {\n lin.push({ id: link.id });\n }\n }\n return lin;\n },\n\n /**\n * The method used by the diagram creation to instantiate a shape.\n * @param kendoDiagram The Kendo diagram where the diagram will be created.\n * @param p The position at which to place the shape.\n * @param shapeDefaults Optional Shape options.\n * @param id Optional identifier of the shape.\n * @returns {*}\n * @private\n */\n _addShape: function(kendoDiagram, p, id, shapeDefaults) {\n if (Utils.isUndefined(p)) {\n p = new diagram.Point(0, 0);\n }\n\n if (Utils.isUndefined(id)) {\n id = randomId();\n }\n\n shapeDefaults = kendo.deepExtend({\n width: 20,\n height: 20,\n id: id,\n radius: 10,\n fill: \"#778899\",\n data: \"circle\",\n undoable: false,\n x: p.x,\n y: p.y\n }, shapeDefaults);\n\n return kendoDiagram.addShape(shapeDefaults);\n },\n /**\n * The method used by the diagram creation to instantiate a connection.\n * @param diagram he Kendo diagram where the diagram will be created.\n * @param from The source shape.\n * @param to The target shape.\n * @param options Optional Connection options.\n * @returns {*}\n * @private\n */\n _addConnection: function(diagram, from, to, options) {\n return diagram.connect(from, to, options);\n },\n\n /**\n * Creates a diagram from the given Graph.\n * @param diagram The Kendo diagram where the diagram will be created.\n * @param graph The graph structure defining the diagram.\n */\n createDiagramFromGraph: function(diagram, graph, doLayout, randomSize) {\n\n if (Utils.isUndefined(diagram)) {\n throw \"The diagram surface is undefined.\";\n }\n if (Utils.isUndefined(graph)) {\n throw \"No graph specification defined.\";\n }\n if (Utils.isUndefined(doLayout)) {\n doLayout = true;\n }\n if (Utils.isUndefined(randomSize)) {\n randomSize = false;\n }\n\n var width = diagram.element.clientWidth || 200;\n var height = diagram.element.clientHeight || 200;\n var map = [], node, shape;\n for (var i = 0, len = graph.nodes.length; i < len; i++) {\n node = graph.nodes[i];\n var p = node.position;\n if (Utils.isUndefined(p)) {\n if (Utils.isDefined(node.x) && Utils.isDefined(node.y)) {\n p = new Point(node.x, node.y);\n }\n else {\n p = new Point(Utils.randomInteger(10, width - 20), Utils.randomInteger(10, height - 20));\n }\n }\n var opt = {};\n\n if (node.id === \"0\") {\n /* kendo.deepExtend(opt,\n {\n fill: \"Orange\",\n data: 'circle',\n width: 100,\n height: 100,\n center: new Point(50, 50)\n });*/\n }\n else if (randomSize) {\n kendo.deepExtend(opt, {\n width: Math.random() * 150 + 20,\n height: Math.random() * 80 + 50,\n data: 'rectangle',\n fill: {\n color: \"#778899\"\n }\n });\n }\n\n shape = this._addShape(diagram, p, node.id, opt);\n //shape.content(node.id);\n\n var bounds = shape.bounds();\n if (Utils.isDefined(bounds)) {\n node.x = bounds.x;\n node.y = bounds.y;\n node.width = bounds.width;\n node.height = bounds.height;\n }\n map[node.id] = shape;\n }\n for (var gli = 0; gli < graph.links.length; gli++) {\n var link = graph.links[gli];\n var sourceShape = map[link.source.id];\n if (Utils.isUndefined(sourceShape)) {\n continue;\n }\n var targetShape = map[link.target.id];\n if (Utils.isUndefined(targetShape)) {\n continue;\n }\n this._addConnection(diagram, sourceShape, targetShape, { id: link.id });\n\n }\n if (doLayout) {\n var l = new diagram.SpringLayout(diagram);\n l.layoutGraph(graph, { limitToView: false });\n for (var shi = 0; shi < graph.nodes.length; shi++) {\n node = graph.nodes[shi];\n shape = map[node.id];\n shape.bounds(new Rect(node.x, node.y, node.width, node.height));\n }\n }\n },\n\n /**\n * Creates a balanced tree with the specified number of levels and siblings count.\n * Note that for a balanced tree of level N and sibling count s, counting the root as level zero:\n * - NodeCount = (1-s^(N+1))/(1-s)]\n * - LinkCount = s.(1-s^N)/(1-s)\n * @param levels How many levels the tree should have.\n * @param siblingsCount How many siblings each level should have.\n * @returns {diagram.Graph}\n */\n createBalancedTree: function(levels, siblingsCount) {\n if (Utils.isUndefined(levels)) {\n levels = 3;\n }\n if (Utils.isUndefined(siblingsCount)) {\n siblingsCount = 3;\n }\n\n var g = new diagram.Graph(), counter = -1, lastAdded = [], news;\n if (levels <= 0 || siblingsCount <= 0) {\n return g;\n }\n var root = new Node((++counter).toString());\n g.addNode(root);\n g.root = root;\n lastAdded.push(root);\n for (var i = 0; i < levels; i++) {\n news = [];\n for (var j = 0; j < lastAdded.length; j++) {\n var parent = lastAdded[j];\n for (var k = 0; k < siblingsCount; k++) {\n var item = new Node((++counter).toString());\n g.addLink(parent, item);\n news.push(item);\n }\n }\n lastAdded = news;\n }\n return g;\n },\n\n /**\n * Creates a balanced tree with the specified number of levels and siblings count.\n * Note that for a balanced forest of level N, sibling count s and tree count t, counting the root as level zero:\n * - NodeCount = t.(1-s^(N+1))/(1-s)]\n * - LinkCount = t.s.(1-s^N)/(1-s)\n * @param levels How many levels the tree should have.\n * @param siblingsCount How many siblings each level should have.\n * @returns {diagram.Graph}\n * @param treeCount The number of trees the forest should have.\n */\n createBalancedForest: function(levels, siblingsCount, treeCount) {\n if (Utils.isUndefined(levels)) {\n levels = 3;\n }\n if (Utils.isUndefined(siblingsCount)) {\n siblingsCount = 3;\n }\n if (Utils.isUndefined(treeCount)) {\n treeCount = 5;\n }\n var g = new diagram.Graph(), counter = -1, lastAdded = [], news;\n if (levels <= 0 || siblingsCount <= 0 || treeCount <= 0) {\n return g;\n }\n\n for (var t = 0; t < treeCount; t++) {\n var root = new Node((++counter).toString());\n g.addNode(root);\n lastAdded = [root];\n for (var i = 0; i < levels; i++) {\n news = [];\n for (var j = 0; j < lastAdded.length; j++) {\n var parent = lastAdded[j];\n for (var k = 0; k < siblingsCount; k++) {\n var item = new Node((++counter).toString());\n g.addLink(parent, item);\n news.push(item);\n }\n }\n lastAdded = news;\n }\n }\n return g;\n },\n\n /**\n * Creates a random graph (uniform distribution) with the specified amount of nodes.\n * @param nodeCount The amount of nodes the random graph should have.\n * @param maxIncidence The maximum allowed degree of the nodes.\n * @param isTree Whether the return graph should be a tree (default: false).\n * @returns {diagram.Graph}\n */\n createRandomConnectedGraph: function(nodeCount, maxIncidence, isTree) {\n\n /* Swa's Mathematica export of random Bernoulli graphs\n gr[n_,p_]:=Module[{g=RandomGraph[BernoulliGraphDistribution[n,p],VertexLabels->\"Name\",DirectedEdges->True]},\n While[Not[ConnectedGraphQ[g]],g=RandomGraph[BernoulliGraphDistribution[n,p],VertexLabels->\"Name\",DirectedEdges->True]];g];\n project[a_]:=(\"\\\"\"<>ToString[Part[#,1]]<>\"->\"<>ToString[Part[#,2]]<>\"\\\"\")& @ a;\n export[g_]:=project/@ EdgeList[g]\n g = gr[12,.1]\n export [g]\n */\n\n if (Utils.isUndefined(nodeCount)) {\n nodeCount = 40;\n }\n if (Utils.isUndefined(maxIncidence)) {\n maxIncidence = 4;\n }\n if (Utils.isUndefined(isTree)) {\n isTree = false;\n }\n\n var g = new diagram.Graph(), counter = -1;\n if (nodeCount <= 0) {\n return g;\n }\n\n var root = new Node((++counter).toString());\n g.addNode(root);\n if (nodeCount === 1) {\n return g;\n }\n if (nodeCount > 1) {\n // random tree\n for (var i = 1; i < nodeCount; i++) {\n var poolNode = g.takeRandomNode([], maxIncidence);\n if (!poolNode) {\n //failed to find one so the graph will have less nodes than specified\n break;\n }\n var newNode = g.addNode(i.toString());\n g.addLink(poolNode, newNode);\n }\n if (!isTree && nodeCount > 1) {\n var randomAdditions = Utils.randomInteger(1, nodeCount);\n for (var ri = 0; ri < randomAdditions; ri++) {\n var n1 = g.takeRandomNode([], maxIncidence);\n var n2 = g.takeRandomNode([], maxIncidence);\n if (n1 && n2 && !g.areConnected(n1, n2)) {\n g.addLink(n1, n2);\n }\n }\n }\n return g;\n }\n },\n\n /**\n * Generates a random diagram.\n * @param diagram The host diagram.\n * @param shapeCount The number of shapes the random diagram should contain.\n * @param maxIncidence The maximum degree the shapes can have.\n * @param isTree Whether the generated diagram should be a tree\n * @param layoutType The optional layout type to apply after the diagram is generated.\n */\n randomDiagram: function(diagram, shapeCount, maxIncidence, isTree, randomSize) {\n var g = kendo.dataviz.diagram.Graph.Utils.createRandomConnectedGraph(shapeCount, maxIncidence, isTree);\n Graph.Utils.createDiagramFromGraph(diagram, g, false, randomSize);\n }\n };\n\n kendo.deepExtend(diagram, {\n init: function(element) {\n kendo.init(element, diagram.ui);\n },\n\n Point: Point,\n Intersect: Intersect,\n Geometry: Geometry,\n Rect: Rect,\n Size: Size,\n RectAlign: RectAlign,\n Matrix: Matrix,\n MatrixVector: MatrixVector,\n normalVariable: normalVariable,\n randomId: randomId,\n Dictionary: Dictionary,\n HashTable: HashTable,\n Queue: Queue,\n Set: Set,\n Node: Node,\n Link: Link,\n Graph: Graph,\n PathDefiner: PathDefiner\n });\n })(window.kendo.jQuery);\n\n (function($, undefined$1) {\n // Imports ================================================================\n var kendo = window.kendo,\n diagram = kendo.dataviz.diagram,\n Class = kendo.Class,\n deepExtend = kendo.deepExtend,\n Point = diagram.Point,\n Rect = diagram.Rect,\n Matrix = diagram.Matrix,\n Utils = diagram.Utils,\n isNumber = Utils.isNumber,\n isString = Utils.isString,\n MatrixVector = diagram.MatrixVector,\n\n g = kendo.geometry,\n d = kendo.drawing,\n\n defined = d.util.defined,\n\n inArray = $.inArray;\n\n // Constants ==============================================================\n var TRANSPARENT = \"transparent\",\n Markers = {\n none: \"none\",\n arrowStart: \"ArrowStart\",\n filledCircle: \"FilledCircle\",\n arrowEnd: \"ArrowEnd\"\n },\n FULL_CIRCLE_ANGLE = 360,\n START = \"start\",\n END = \"end\",\n WIDTH = \"width\",\n HEIGHT = \"height\",\n X = \"x\",\n Y = \"y\";\n\n diagram.Markers = Markers;\n\n function diffNumericOptions(options, fields) {\n var elementOptions = this.options;\n var hasChanges = false;\n var value, field;\n for (var i = 0; i < fields.length; i++) {\n field = fields[i];\n value = options[field];\n if (isNumber(value) && elementOptions[field] !== value) {\n elementOptions[field] = value;\n hasChanges = true;\n }\n }\n\n return hasChanges;\n }\n\n var Scale = Class.extend({\n init: function(x, y) {\n this.x = x;\n this.y = y;\n },\n toMatrix: function() {\n return Matrix.scaling(this.x, this.y);\n },\n toString: function() {\n return kendo.format(\"scale({0},{1})\", this.x, this.y);\n },\n invert: function() {\n return new Scale(1 / this.x, 1 / this.y);\n }\n });\n\n var Translation = Class.extend({\n init: function(x, y) {\n this.x = x;\n this.y = y;\n },\n toMatrixVector: function() {\n return new MatrixVector(0, 0, 0, 0, this.x, this.y);\n },\n toMatrix: function() {\n return Matrix.translation(this.x, this.y);\n },\n toString: function() {\n return kendo.format(\"translate({0},{1})\", this.x, this.y);\n },\n plus: function(delta) {\n this.x += delta.x;\n this.y += delta.y;\n },\n times: function(factor) {\n this.x *= factor;\n this.y *= factor;\n },\n length: function() {\n return Math.sqrt(this.x * this.x + this.y * this.y);\n },\n normalize: function() {\n if (this.Length === 0) {\n return;\n }\n this.times(1 / this.length());\n },\n invert: function() {\n return new Translation(-this.x, -this.y);\n }\n });\n\n var Rotation = Class.extend({\n init: function(angle, x, y) {\n this.x = x || 0;\n this.y = y || 0;\n this.angle = angle;\n },\n toString: function() {\n if (this.x && this.y) {\n return kendo.format(\"rotate({0},{1},{2})\", this.angle, this.x, this.y);\n } else {\n return kendo.format(\"rotate({0})\", this.angle);\n }\n },\n toMatrix: function() {\n return Matrix.rotation(this.angle, this.x, this.y); // T*R*T^-1\n },\n center: function() {\n return new Point(this.x, this.y);\n },\n invert: function() {\n return new Rotation(FULL_CIRCLE_ANGLE - this.angle, this.x, this.y);\n }\n });\n\n Rotation.ZERO = new Rotation(0);\n\n Rotation.create = function(rotation) {\n return new Rotation(rotation.angle, rotation.x, rotation.y);\n };\n\n Rotation.parse = function(str) {\n var values = str.slice(1, str.length - 1).split(\",\"),\n angle = values[0],\n x = values[1],\n y = values[2];\n var rotation = new Rotation(angle, x, y);\n return rotation;\n };\n\n var CompositeTransform = Class.extend({\n init: function(x, y, scaleX, scaleY, angle, center) {\n this.translate = new Translation(x, y);\n if (scaleX !== undefined$1 && scaleY !== undefined$1) {\n this.scale = new Scale(scaleX, scaleY);\n }\n if (angle !== undefined$1) {\n this.rotate = center ? new Rotation(angle, center.x, center.y) : new Rotation(angle);\n }\n },\n toString: function() {\n var toString = function(transform) {\n return transform ? transform.toString() : \"\";\n };\n\n return toString(this.translate) +\n toString(this.rotate) +\n toString(this.scale);\n },\n\n render: function(visual) {\n visual._transform = this;\n visual._renderTransform();\n },\n\n toMatrix: function() {\n var m = Matrix.unit();\n\n if (this.translate) {\n m = m.times(this.translate.toMatrix());\n }\n if (this.rotate) {\n m = m.times(this.rotate.toMatrix());\n }\n if (this.scale) {\n m = m.times(this.scale.toMatrix());\n }\n return m;\n },\n invert: function() {\n var rotate = this.rotate ? this.rotate.invert() : undefined$1,\n rotateMatrix = rotate ? rotate.toMatrix() : Matrix.unit(),\n scale = this.scale ? this.scale.invert() : undefined$1,\n scaleMatrix = scale ? scale.toMatrix() : Matrix.unit();\n\n var translatePoint = new Point(-this.translate.x, -this.translate.y);\n translatePoint = rotateMatrix.times(scaleMatrix).apply(translatePoint);\n var translate = new Translation(translatePoint.x, translatePoint.y);\n\n var transform = new CompositeTransform();\n transform.translate = translate;\n transform.rotate = rotate;\n transform.scale = scale;\n\n return transform;\n }\n });\n\n var AutoSizeableMixin = {\n _setScale: function() {\n var options = this.options;\n var originWidth = this._originWidth;\n var originHeight = this._originHeight;\n var scaleX = options.width / originWidth;\n var scaleY = options.height / originHeight;\n\n if (!isNumber(scaleX)) {\n scaleX = 1;\n }\n if (!isNumber(scaleY)) {\n scaleY = 1;\n }\n\n this._transform.scale = new Scale(scaleX, scaleY);\n },\n\n _setTranslate: function() {\n var options = this.options;\n var x = options.x || 0;\n var y = options.y || 0;\n this._transform.translate = new Translation(x, y);\n },\n\n _initSize: function() {\n var options = this.options;\n var transform = false;\n if (options.autoSize !== false && (defined(options.width) || defined(options.height))) {\n this._measure(true);\n this._setScale();\n transform = true;\n }\n\n if (defined(options.x) || defined(options.y)) {\n this._setTranslate();\n transform = true;\n }\n\n if (transform) {\n this._renderTransform();\n }\n },\n\n _updateSize: function(options) {\n var update = false;\n\n if (this.options.autoSize !== false && this._diffNumericOptions(options, [WIDTH, HEIGHT])) {\n update = true;\n this._measure(true);\n this._setScale();\n }\n\n if (this._diffNumericOptions(options, [X, Y])) {\n update = true;\n this._setTranslate();\n }\n\n if (update) {\n this._renderTransform();\n }\n\n return update;\n }\n };\n\n var Element = Class.extend({\n init: function(options) {\n var element = this;\n element.options = deepExtend({}, element.options, options);\n element.id = element.options.id;\n element._originSize = Rect.empty();\n element._transform = new CompositeTransform();\n },\n\n visible: function(value) {\n return this.drawingContainer().visible(value);\n },\n\n redraw: function(options) {\n if (options && options.id) {\n this.id = options.id;\n }\n },\n\n position: function(x, y) {\n var options = this.options;\n if (!defined(x)) {\n return new Point(options.x, options.y);\n }\n\n if (defined(y)) {\n options.x = x;\n options.y = y;\n } else if (x instanceof Point) {\n options.x = x.x;\n options.y = x.y;\n }\n\n this._transform.translate = new Translation(options.x, options.y);\n this._renderTransform();\n },\n\n rotate: function(angle, center) {\n if (defined(angle)) {\n this._transform.rotate = new Rotation(angle, center.x, center.y);\n this._renderTransform();\n }\n return this._transform.rotate || Rotation.ZERO;\n },\n\n drawingContainer: function() {\n return this.drawingElement;\n },\n\n _renderTransform: function() {\n var matrix = this._transform.toMatrix();\n this.drawingContainer().transform(new g.Matrix(matrix.a, matrix.b, matrix.c, matrix.d, matrix.e, matrix.f));\n },\n\n _hover: function() {},\n\n _diffNumericOptions: diffNumericOptions,\n\n _measure: function(force) {\n var rect;\n if (!this._measured || force) {\n var box = this._boundingBox() || new g.Rect();\n var startPoint = box.topLeft();\n rect = new Rect(startPoint.x, startPoint.y, box.width(), box.height());\n this._originSize = rect;\n this._originWidth = rect.width;\n this._originHeight = rect.height;\n this._measured = true;\n } else {\n rect = this._originSize;\n }\n return rect;\n },\n\n _boundingBox: function() {\n return this.drawingElement.rawBBox();\n }\n });\n\n var VisualBase = Element.extend({\n init: function(options) {\n Element.fn.init.call(this, options);\n\n options = this.options;\n options.fill = normalizeDrawingOptions(options.fill);\n options.stroke = normalizeDrawingOptions(options.stroke);\n },\n\n options: {\n stroke: {\n color: \"gray\",\n width: 1\n },\n fill: {\n color: TRANSPARENT\n }\n },\n\n fill: function(color, opacity) {\n this._fill({\n color: getColor(color),\n opacity: opacity\n });\n },\n\n stroke: function(color, width, opacity) {\n this._stroke({\n color: getColor(color),\n width: width,\n opacity: opacity\n });\n },\n\n redraw: function(options) {\n if (options) {\n var stroke = options.stroke;\n var fill = options.fill;\n if (stroke) {\n this._stroke(normalizeDrawingOptions(stroke));\n }\n if (fill) {\n this._fill(normalizeDrawingOptions(fill));\n }\n\n Element.fn.redraw.call(this, options);\n }\n },\n\n _hover: function(show) {\n var drawingElement = this.drawingElement;\n var options = this.options;\n var hover = options.hover;\n\n if (hover && hover.fill) {\n var fill = show ? normalizeDrawingOptions(hover.fill) : options.fill;\n drawingElement.fill(fill.color, fill.opacity);\n }\n },\n\n _stroke: function(strokeOptions) {\n var options = this.options;\n deepExtend(options, {\n stroke: strokeOptions\n });\n\n strokeOptions = options.stroke;\n\n var stroke = null;\n if (strokeOptions.width > 0) {\n stroke = {\n color: strokeOptions.color,\n width: strokeOptions.width,\n opacity: strokeOptions.opacity,\n dashType: strokeOptions.dashType\n };\n }\n\n this.drawingElement.options.set(\"stroke\", stroke);\n },\n\n _fill: function(fillOptions) {\n var options = this.options;\n deepExtend(options, {\n fill: fillOptions || {}\n });\n var fill = options.fill;\n\n if (fill.gradient) {\n var gradient = fill.gradient;\n var GradientClass = (gradient.type === \"radial\" ? d.RadialGradient : d.LinearGradient);\n this.drawingElement.fill(new GradientClass(gradient));\n } else {\n this.drawingElement.fill(fill.color, fill.opacity);\n }\n }\n });\n\n var TextBlock = VisualBase.extend({\n init: function(options) {\n options = this._textColor(options);\n VisualBase.fn.init.call(this, options);\n\n this._font();\n this._initText();\n this._initSize();\n },\n\n options: {\n fontSize: 15,\n fontFamily: \"sans-serif\",\n stroke: {\n width: 0\n },\n fill: {\n color: \"black\"\n },\n autoSize: true\n },\n\n _initText: function() {\n var options = this.options;\n\n this.drawingElement = new d.Text(defined(options.text) ? options.text : \"\", new g.Point(), {\n font: options.font\n });\n\n this._fill();\n this._stroke();\n },\n\n _textColor: function(options) {\n if (options && options.color) {\n options = deepExtend({}, options, {\n fill: {\n color: options.color\n }\n });\n }\n return options;\n },\n\n _font: function() {\n var options = this.options;\n if (options.fontFamily && defined(options.fontSize)) {\n var fontOptions = [];\n\n if (options.fontStyle) {\n fontOptions.push(options.fontStyle);\n }\n\n if (options.fontWeight) {\n fontOptions.push(options.fontWeight);\n }\n\n fontOptions.push(options.fontSize + (isNumber(options.fontSize) ? \"px\" : \"\"));\n fontOptions.push(options.fontFamily);\n\n options.font = fontOptions.join(\" \");\n } else {\n delete options.font;\n }\n },\n\n content: function(text) {\n return this.drawingElement.content(text);\n },\n\n redraw: function(options) {\n if (options) {\n var sizeChanged = false;\n var textOptions = this.options;\n\n options = this._textColor(options);\n\n VisualBase.fn.redraw.call(this, options);\n\n if (options.fontFamily || defined(options.fontSize) || options.fontStyle || options.fontWeight) {\n deepExtend(textOptions, {\n fontFamily: options.fontFamily,\n fontSize: options.fontSize,\n fontStyle: options.fontStyle,\n fontWeight: options.fontWeight\n });\n this._font();\n this.drawingElement.options.set(\"font\", textOptions.font);\n sizeChanged = true;\n }\n\n if (options.text) {\n this.content(options.text);\n sizeChanged = true;\n }\n\n if (!this._updateSize(options) && sizeChanged) {\n this._initSize();\n }\n }\n }\n });\n\n deepExtend(TextBlock.fn, AutoSizeableMixin);\n\n var Rectangle = VisualBase.extend({\n init: function(options) {\n VisualBase.fn.init.call(this, options);\n this._initPath();\n this._setPosition();\n },\n\n _setPosition: function() {\n var options = this.options;\n var x = options.x;\n var y = options.y;\n if (defined(x) || defined(y)) {\n this.position(x || 0, y || 0);\n }\n },\n\n redraw: function(options) {\n if (options) {\n VisualBase.fn.redraw.call(this, options);\n if (this._diffNumericOptions(options, [WIDTH, HEIGHT])) {\n this._drawPath();\n }\n if (this._diffNumericOptions(options, [X, Y])) {\n this._setPosition();\n }\n }\n },\n\n _initPath: function() {\n var options = this.options;\n this.drawingElement = new d.Path({\n stroke: options.stroke,\n closed: true\n });\n\n this._fill();\n this._drawPath();\n },\n\n _drawPath: function() {\n var drawingElement = this.drawingElement;\n var sizeOptions = sizeOptionsOrDefault(this.options);\n var width = sizeOptions.width;\n var height = sizeOptions.height;\n\n drawingElement.segments.elements([\n createSegment(0, 0),\n createSegment(width, 0),\n createSegment(width, height),\n createSegment(0, height)\n ]);\n }\n });\n\n var MarkerBase = VisualBase.extend({\n init: function(options) {\n VisualBase.fn.init.call(this, options);\n var anchor = this.options.anchor;\n this.anchor = new g.Point(anchor.x, anchor.y);\n this.createElement();\n },\n\n options: {\n stroke: {\n color: TRANSPARENT,\n width: 0\n },\n fill: {\n color: \"black\"\n }\n },\n\n _transformToPath: function(point, path) {\n var transform = path.transform();\n if (point && transform) {\n point = point.transformCopy(transform);\n }\n return point;\n },\n\n redraw: function(options) {\n if (options) {\n if (options.position) {\n this.options.position = options.position;\n }\n\n VisualBase.fn.redraw.call(this, options);\n }\n }\n });\n\n var CircleMarker = MarkerBase.extend({\n options: {\n radius: 4,\n anchor: {\n x: 0,\n y: 0\n }\n },\n\n createElement: function() {\n var options = this.options;\n this.drawingElement = new d.Circle(new g.Circle(this.anchor, options.radius), {\n fill: options.fill,\n stroke: options.stroke\n });\n },\n\n positionMarker: function(path) {\n var options = this.options;\n var position = options.position;\n var segments = path.segments;\n var targetSegment;\n var point;\n\n if (position == START) {\n targetSegment = segments[0];\n } else {\n targetSegment = segments[segments.length - 1];\n }\n if (targetSegment) {\n point = this._transformToPath(targetSegment.anchor(), path);\n this.drawingElement.transform(g.transform().translate(point.x, point.y));\n }\n }\n });\n\n var ArrowMarker = MarkerBase.extend({\n options: {\n path: \"M 0 0 L 10 5 L 0 10 L 3 5 z\" ,\n anchor: {\n x: 10,\n y: 5\n }\n },\n\n createElement: function() {\n var options = this.options;\n this.drawingElement = d.Path.parse(options.path, {\n fill: options.fill,\n stroke: options.stroke\n });\n },\n\n positionMarker: function(path) {\n var points = this._linePoints(path);\n var start = points.start;\n var end = points.end;\n var transform = g.transform();\n if (start) {\n transform.rotate(lineAngle(start, end), end);\n }\n\n if (end) {\n var anchor = this.anchor;\n var translate = end.clone().translate(-anchor.x, -anchor.y);\n transform.translate(translate.x, translate.y);\n }\n this.drawingElement.transform(transform);\n },\n\n _linePoints: function(path) {\n var options = this.options;\n var segments = path.segments;\n var startPoint, endPoint, targetSegment;\n if (options.position == START) {\n targetSegment = segments[0];\n if (targetSegment) {\n endPoint = targetSegment.anchor();\n startPoint = targetSegment.controlOut();\n var nextSegment = segments[1];\n if (!startPoint && nextSegment) {\n startPoint = nextSegment.anchor();\n }\n }\n } else {\n targetSegment = segments[segments.length - 1];\n if (targetSegment) {\n endPoint = targetSegment.anchor();\n startPoint = targetSegment.controlIn();\n var prevSegment = segments[segments.length - 2];\n if (!startPoint && prevSegment) {\n startPoint = prevSegment.anchor();\n }\n }\n }\n if (endPoint) {\n return {\n start: this._transformToPath(startPoint, path),\n end: this._transformToPath(endPoint, path)\n };\n }\n }\n });\n\n var MarkerPathMixin = {\n _getPath: function(position) {\n var path = this.drawingElement;\n if (path instanceof d.MultiPath) {\n if (position == START) {\n path = path.paths[0];\n } else {\n path = path.paths[path.paths.length - 1];\n }\n }\n if (path && path.segments.length) {\n return path;\n }\n },\n\n _normalizeMarkerOptions: function(options) {\n var startCap = options.startCap;\n var endCap = options.endCap;\n\n if (isString(startCap)) {\n options.startCap = {\n type: startCap\n };\n }\n\n if (isString(endCap)) {\n options.endCap = {\n type: endCap\n };\n }\n },\n\n _removeMarker: function(position) {\n var marker = this._markers[position];\n if (marker) {\n this.drawingContainer().remove(marker.drawingElement);\n delete this._markers[position];\n }\n },\n\n _createMarkers: function() {\n var options = this.options;\n this._normalizeMarkerOptions(options);\n\n this._markers = {};\n this._markers[START] = this._createMarker(options.startCap, START);\n this._markers[END] = this._createMarker(options.endCap, END);\n },\n\n _createMarker: function(options, position) {\n var type = (options || {}).type;\n var path = this._getPath(position);\n var markerType, marker;\n if (!path) {\n this._removeMarker(position);\n return;\n }\n\n if (type == Markers.filledCircle) {\n markerType = CircleMarker;\n } else if (type == Markers.arrowStart || type == Markers.arrowEnd) {\n markerType = ArrowMarker;\n } else {\n this._removeMarker(position);\n }\n if (markerType) {\n marker = new markerType(deepExtend({}, options, {\n position: position\n }));\n marker.positionMarker(path);\n this.drawingContainer().append(marker.drawingElement);\n\n return marker;\n }\n },\n\n _positionMarker: function(position) {\n var marker = this._markers[position];\n\n if (marker) {\n var path = this._getPath(position);\n if (path) {\n marker.positionMarker(path);\n } else {\n this._removeMarker(position);\n }\n }\n },\n\n _capMap: {\n start: \"startCap\",\n end: \"endCap\"\n },\n\n _redrawMarker: function(pathChange, position, options) {\n this._normalizeMarkerOptions(options);\n\n var pathOptions = this.options;\n var cap = this._capMap[position];\n var pathCapType = (pathOptions[cap] || {}).type;\n var optionsCap = options[cap];\n var created = false;\n if (optionsCap) {\n pathOptions[cap] = deepExtend({}, pathOptions[cap], optionsCap);\n if (optionsCap.type && pathCapType != optionsCap.type) {\n this._removeMarker(position);\n this._markers[position] = this._createMarker(pathOptions[cap], position);\n created = true;\n } else if (this._markers[position]) {\n this._markers[position].redraw(optionsCap);\n }\n } else if (pathChange && !this._markers[position] && pathOptions[cap]) {\n this._markers[position] = this._createMarker(pathOptions[cap], position);\n created = true;\n }\n return created;\n },\n\n _redrawMarkers: function(pathChange, options) {\n if (!this._redrawMarker(pathChange, START, options) && pathChange) {\n this._positionMarker(START);\n }\n if (!this._redrawMarker(pathChange, END, options) && pathChange) {\n this._positionMarker(END);\n }\n }\n };\n\n var Path = VisualBase.extend({\n init: function(options) {\n VisualBase.fn.init.call(this, options);\n this.container = new d.Group();\n this._createElements();\n this._initSize();\n },\n\n options: {\n autoSize: true\n },\n\n drawingContainer: function() {\n return this.container;\n },\n\n data: function(value) {\n var options = this.options;\n if (value) {\n if (options.data != value) {\n options.data = value;\n this._setData(value);\n this._initSize();\n this._redrawMarkers(true, {});\n }\n } else {\n return options.data;\n }\n },\n\n redraw: function(options) {\n if (options) {\n VisualBase.fn.redraw.call(this, options);\n\n var pathOptions = this.options;\n var data = options.data;\n\n if (defined(data) && pathOptions.data != data) {\n pathOptions.data = data;\n this._setData(data);\n if (!this._updateSize(options)) {\n this._initSize();\n }\n this._redrawMarkers(true, options);\n } else {\n this._updateSize(options);\n this._redrawMarkers(false, options);\n }\n }\n },\n\n _createElements: function() {\n var options = this.options;\n\n this.drawingElement = d.Path.parse(options.data || \"\", {\n stroke: options.stroke\n });\n\n this._fill();\n this.container.append(this.drawingElement);\n this._createMarkers();\n },\n\n _setData: function(data) {\n var drawingElement = this.drawingElement;\n var multipath = d.Path.parse(data || \"\");\n var paths = multipath.paths.slice(0);\n multipath.paths.elements([]);\n drawingElement.paths.elements(paths);\n }\n });\n\n deepExtend(Path.fn, AutoSizeableMixin);\n deepExtend(Path.fn, MarkerPathMixin);\n\n var Line = VisualBase.extend({\n init: function(options) {\n VisualBase.fn.init.call(this, options);\n this.container = new d.Group();\n this._initPath();\n this._createMarkers();\n },\n\n drawingContainer: function() {\n return this.container;\n },\n\n redraw: function(options) {\n if (options) {\n options = options || {};\n var from = options.from;\n var to = options.to;\n if (from) {\n this.options.from = from;\n }\n\n if (to) {\n this.options.to = to;\n }\n\n if (from || to) {\n this._drawPath();\n this._redrawMarkers(true, options);\n } else {\n this._redrawMarkers(false, options);\n }\n\n VisualBase.fn.redraw.call(this, options);\n }\n },\n\n _initPath: function() {\n var options = this.options;\n var drawingElement = this.drawingElement = new d.Path({\n stroke: options.stroke\n });\n\n this._fill();\n this._drawPath();\n this.container.append(drawingElement);\n },\n\n _drawPath: function() {\n var options = this.options;\n var drawingElement = this.drawingElement;\n var from = options.from || new Point();\n var to = options.to || new Point();\n\n drawingElement.segments.elements([\n createSegment(from.x, from.y),\n createSegment(to.x, to.y)\n ]);\n }\n });\n\n deepExtend(Line.fn, MarkerPathMixin);\n\n var Polyline = VisualBase.extend({\n init: function(options) {\n VisualBase.fn.init.call(this, options);\n this.container = new d.Group();\n this._initPath();\n this._createMarkers();\n },\n\n drawingContainer: function() {\n return this.container;\n },\n\n points: function(points) {\n var options = this.options;\n if (points) {\n options.points = points;\n this._updatePath();\n } else {\n return options.points;\n }\n },\n\n redraw: function(options) {\n if (options) {\n var points = options.points;\n VisualBase.fn.redraw.call(this, options);\n\n if (points && this._pointsDiffer(points)) {\n this.points(points);\n this._redrawMarkers(true, options);\n } else {\n this._redrawMarkers(false, options);\n }\n }\n },\n\n _initPath: function() {\n var options = this.options;\n this.drawingElement = new d.Path({\n stroke: options.stroke\n });\n\n this._fill();\n this.container.append(this.drawingElement);\n\n if (options.points) {\n this._updatePath();\n }\n },\n\n _pointsDiffer: function(points) {\n var currentPoints = this.options.points;\n var differ = currentPoints.length !== points.length;\n if (!differ) {\n for (var i = 0; i < points.length; i++) {\n if (currentPoints[i].x !== points[i].x || currentPoints[i].y !== points[i].y) {\n differ = true;\n break;\n }\n }\n }\n\n return differ;\n },\n\n _updatePath: function() {\n var drawingElement = this.drawingElement;\n var options = this.options;\n var points = options.points;\n var segments = [];\n var point;\n for (var i = 0; i < points.length; i++) {\n point = points[i];\n segments.push(createSegment(point.x, point.y));\n }\n\n drawingElement.segments.elements(segments);\n },\n\n options: {\n points: []\n }\n });\n\n deepExtend(Polyline.fn, MarkerPathMixin);\n\n var Image = Element.extend({\n init: function(options) {\n Element.fn.init.call(this, options);\n\n this._initImage();\n },\n\n redraw: function(options) {\n if (options) {\n if (options.source) {\n this.drawingElement.src(options.source);\n }\n\n if (this._diffNumericOptions(options, [WIDTH, HEIGHT, X, Y])) {\n this.drawingElement.rect(this._rect());\n }\n\n Element.fn.redraw.call(this, options);\n }\n },\n\n _initImage: function() {\n var options = this.options;\n var rect = this._rect();\n\n this.drawingElement = new d.Image(options.source, rect, {});\n },\n\n _rect: function() {\n var sizeOptions = sizeOptionsOrDefault(this.options);\n var origin = new g.Point(sizeOptions.x, sizeOptions.y);\n var size = new g.Size(sizeOptions.width, sizeOptions.height);\n\n return new g.Rect(origin, size);\n }\n });\n\n var Group = Element.extend({\n init: function(options) {\n this.children = [];\n Element.fn.init.call(this, options);\n this.drawingElement = new d.Group();\n this._initSize();\n },\n\n options: {\n autoSize: false\n },\n\n append: function(visual) {\n this.drawingElement.append(visual.drawingContainer());\n this.children.push(visual);\n this._childrenChange = true;\n },\n\n remove: function(visual) {\n if (this._remove(visual)) {\n this._childrenChange = true;\n }\n },\n\n _remove: function(visual) {\n var index = inArray(visual, this.children);\n if (index >= 0) {\n this.drawingElement.removeAt(index);\n this.children.splice(index, 1);\n return true;\n }\n },\n\n clear: function() {\n this.drawingElement.clear();\n this.children = [];\n this._childrenChange = true;\n },\n\n toFront: function(visuals) {\n var visual;\n\n for (var i = 0; i < visuals.length; i++) {\n visual = visuals[i];\n if (this._remove(visual)) {\n this.append(visual);\n }\n }\n },\n //TO DO: add drawing group support for moving and inserting children\n toBack: function(visuals) {\n this._reorderChildren(visuals, 0);\n },\n\n toIndex: function(visuals, indices) {\n this._reorderChildren(visuals, indices);\n },\n\n _reorderChildren: function(visuals, indices) {\n var group = this.drawingElement;\n var drawingChildren = group.children.slice(0);\n var children = this.children;\n var fixedPosition = isNumber(indices);\n var i, index, toIndex, drawingElement, visual;\n\n for (i = 0; i < visuals.length; i++) {\n visual = visuals[i];\n drawingElement = visual.drawingContainer();\n\n index = inArray(visual, children);\n if (index >= 0) {\n drawingChildren.splice(index, 1);\n children.splice(index, 1);\n\n toIndex = fixedPosition ? indices : indices[i];\n\n drawingChildren.splice(toIndex, 0, drawingElement);\n children.splice(toIndex, 0, visual);\n }\n }\n group.clear();\n group.append.apply(group, drawingChildren);\n },\n\n redraw: function(options) {\n if (options) {\n if (this._childrenChange) {\n this._childrenChange = false;\n if (!this._updateSize(options)) {\n this._initSize();\n }\n } else {\n this._updateSize(options);\n }\n\n Element.fn.redraw.call(this, options);\n }\n },\n\n _boundingBox: function() {\n var children = this.children;\n var boundingBox;\n var visual, childBoundingBox;\n for (var i = 0; i < children.length; i++) {\n visual = children[i];\n if (visual.visible() && visual._includeInBBox !== false) {\n childBoundingBox = visual.drawingContainer().clippedBBox(null);\n if (childBoundingBox) {\n if (boundingBox) {\n boundingBox = g.Rect.union(boundingBox, childBoundingBox);\n } else {\n boundingBox = childBoundingBox;\n }\n }\n }\n }\n\n return boundingBox;\n }\n });\n\n deepExtend(Group.fn, AutoSizeableMixin);\n\n var Layout = Group.extend({\n init: function(rect, options) {\n this.children = [];\n Element.fn.init.call(this, options);\n this.drawingElement = new d.Layout(toDrawingRect(rect), options);\n this._initSize();\n },\n\n rect: function(rect) {\n if (rect) {\n this.drawingElement.rect(toDrawingRect(rect));\n } else {\n var drawingRect = this.drawingElement.rect();\n if (drawingRect) {\n return new Rect(drawingRect.origin.x, drawingRect.origin.y, drawingRect.size.width, drawingRect.size.height);\n }\n }\n },\n\n reflow: function() {\n this.drawingElement.reflow();\n },\n\n redraw: function(options) {\n kendo.deepExtend(this.drawingElement.options, options);\n Group.fn.redraw.call(this, options);\n }\n });\n\n var Circle = VisualBase.extend({\n init: function(options) {\n VisualBase.fn.init.call(this, options);\n this._initCircle();\n this._initSize();\n },\n\n redraw: function(options) {\n if (options) {\n var circleOptions = this.options;\n\n if (options.center) {\n deepExtend(circleOptions, {\n center: options.center\n });\n this._center.move(circleOptions.center.x, circleOptions.center.y);\n }\n\n if (this._diffNumericOptions(options, [\"radius\"])) {\n this._circle.setRadius(circleOptions.radius);\n }\n\n this._updateSize(options);\n\n VisualBase.fn.redraw.call(this, options);\n }\n },\n\n _initCircle: function() {\n var options = this.options;\n var width = options.width;\n var height = options.height;\n var radius = options.radius;\n if (!defined(radius)) {\n if (!defined(width)) {\n width = height;\n }\n if (!defined(height)) {\n height = width;\n }\n options.radius = radius = Math.min(width, height) / 2;\n }\n\n var center = options.center || { x: radius, y: radius };\n this._center = new g.Point(center.x, center.y);\n this._circle = new g.Circle(this._center, radius);\n this.drawingElement = new d.Circle(this._circle, {\n stroke: options.stroke\n });\n\n this._fill();\n }\n });\n deepExtend(Circle.fn, AutoSizeableMixin);\n\n var Canvas = Class.extend({\n init: function(element, options) {\n options = options || {};\n this.element = element;\n this.surface = d.Surface.create(element, options);\n if (kendo.isFunction(this.surface.translate)) {\n this.translate = this._translate;\n }\n\n this.drawingElement = new d.Group();\n this._viewBox = new Rect(0, 0, options.width, options.height);\n this.size(this._viewBox);\n },\n\n bounds: function() {\n var box = this.drawingElement.clippedBBox();\n return new Rect(0, 0, box.width(), box.height());\n },\n\n size: function(size) {\n var viewBox = this._viewBox;\n if (defined(size)) {\n viewBox.width = size.width;\n viewBox.height = size.height;\n this.surface.setSize(size);\n }\n return {\n width: viewBox.width,\n height: viewBox.height\n };\n },\n\n _translate: function(x, y) {\n var viewBox = this._viewBox;\n if (defined(x) && defined(y)) {\n viewBox.x = x;\n viewBox.y = y;\n this.surface.translate({ x: x, y: y });\n }\n return {\n x: viewBox.x,\n y: viewBox.y\n };\n },\n\n draw: function() {\n this.surface.draw(this.drawingElement);\n },\n\n append: function(visual) {\n this.drawingElement.append(visual.drawingContainer());\n return this;\n },\n\n remove: function(visual) {\n this.drawingElement.remove(visual.drawingContainer());\n },\n\n insertBefore: function() {\n\n },\n\n clear: function() {\n this.drawingElement.clear();\n },\n\n destroy: function(clearHtml) {\n this.surface.destroy();\n if (clearHtml) {\n $(this.element).remove();\n }\n }\n });\n\n // Helper functions ===========================================\n\n function sizeOptionsOrDefault(options) {\n return {\n x: options.x || 0,\n y: options.y || 0,\n width: options.width || 0,\n height: options.height || 0\n };\n }\n\n function normalizeDrawingOptions(options) {\n if (options) {\n var drawingOptions = options;\n\n if (isString(drawingOptions)) {\n drawingOptions = {\n color: drawingOptions\n };\n }\n\n if (drawingOptions.color) {\n drawingOptions.color = getColor(drawingOptions.color);\n }\n return drawingOptions;\n }\n }\n\n function getColor(value) {\n var color;\n if (value != TRANSPARENT) {\n color = new d.Color(value).toHex();\n } else {\n color = value;\n }\n return color;\n }\n\n function lineAngle(p1, p2) {\n var xDiff = p2.x - p1.x;\n var yDiff = p2.y - p1.y;\n var angle = d.util.deg(Math.atan2(yDiff, xDiff));\n return angle;\n }\n\n function createSegment(x, y) {\n return new d.Segment(new g.Point(x, y));\n }\n\n function toDrawingRect(rect) {\n if (rect) {\n return new g.Rect([rect.x, rect.y], [rect.width, rect.height]);\n }\n }\n\n // Exports ================================================================\n kendo.deepExtend(diagram, {\n init: function(element) {\n kendo.init(element, diagram.ui);\n },\n diffNumericOptions: diffNumericOptions,\n Element: Element,\n Scale: Scale,\n Translation: Translation,\n Rotation: Rotation,\n Circle: Circle,\n Group: Group,\n Rectangle: Rectangle,\n Canvas: Canvas,\n Path: Path,\n Layout: Layout,\n Line: Line,\n MarkerBase: MarkerBase,\n ArrowMarker: ArrowMarker,\n CircleMarker: CircleMarker,\n Polyline: Polyline,\n CompositeTransform: CompositeTransform,\n TextBlock: TextBlock,\n Image: Image,\n VisualBase: VisualBase\n });\n })(window.kendo.jQuery);\n\n (function($, undefined$1) {\n // Imports ================================================================\n var kendo = window.kendo,\n dataviz = kendo.dataviz,\n diagram = dataviz.diagram,\n Class = kendo.Class,\n Group = diagram.Group,\n Rect = diagram.Rect,\n Rectangle = diagram.Rectangle,\n Utils = diagram.Utils,\n isUndefined = Utils.isUndefined,\n Point = diagram.Point,\n Circle = diagram.Circle,\n Ticker = diagram.Ticker,\n deepExtend = kendo.deepExtend,\n Movable = kendo.ui.Movable,\n util = kendo.drawing.util,\n defined = util.defined,\n inArray = $.inArray;\n\n // Constants ==============================================================\n var Cursors = {\n arrow: \"default\",\n grip: \"pointer\",\n cross: \"pointer\",\n add: \"pointer\",\n move: \"move\",\n select: \"pointer\",\n south: \"s-resize\",\n east: \"e-resize\",\n west: \"w-resize\",\n north: \"n-resize\",\n rowresize: \"row-resize\",\n colresize: \"col-resize\"\n },\n HIT_TEST_DISTANCE = 10,\n AUTO = \"Auto\",\n TOP = \"Top\",\n RIGHT = \"Right\",\n LEFT = \"Left\",\n BOTTOM = \"Bottom\",\n DEFAULT_SNAP_SIZE = 10,\n DEFAULT_SNAP_ANGLE = 10,\n DRAG_START = \"dragStart\",\n DRAG = \"drag\",\n DRAG_END = \"dragEnd\",\n ITEMROTATE = \"itemRotate\",\n ITEMBOUNDSCHANGE = \"itemBoundsChange\",\n MIN_SNAP_SIZE = 5,\n MIN_SNAP_ANGLE = 5,\n MOUSE_ENTER = \"mouseEnter\",\n MOUSE_LEAVE = \"mouseLeave\",\n ZOOM_START = \"zoomStart\",\n ZOOM_END = \"zoomEnd\",\n SCROLL_MIN = -20000,\n SCROLL_MAX = 20000,\n FRICTION = 0.90,\n FRICTION_MOBILE = 0.93,\n VELOCITY_MULTIPLIER = 5,\n TRANSPARENT = \"transparent\",\n PAN = \"pan\",\n ROTATED = \"rotated\",\n SOURCE = \"source\",\n TARGET = \"target\",\n HANDLE_NAMES = {\n \"-1\": SOURCE,\n \"1\": TARGET\n };\n\n diagram.Cursors = Cursors;\n\n var PositionAdapter = kendo.Class.extend({\n init: function(layoutState) {\n this.layoutState = layoutState;\n this.diagram = layoutState.diagram;\n },\n initState: function() {\n this.froms = [];\n this.tos = [];\n this.subjects = [];\n function pusher(id, bounds) {\n var shape = this.diagram.getShapeById(id);\n if (shape) {\n this.subjects.push(shape);\n this.froms.push(shape.bounds().topLeft());\n this.tos.push(bounds.topLeft());\n }\n }\n\n this.layoutState.nodeMap.forEach(pusher, this);\n },\n update: function(tick) {\n if (this.subjects.length <= 0) {\n return;\n }\n for (var i = 0; i < this.subjects.length; i++) {\n //todo: define a Lerp function instead\n this.subjects[i].position(\n new Point(this.froms[i].x + (this.tos[i].x - this.froms[i].x) * tick, this.froms[i].y + (this.tos[i].y - this.froms[i].y) * tick)\n );\n }\n }\n });\n\n var LayoutUndoUnit = Class.extend({\n init: function(initialState, finalState, animate) {\n if (isUndefined(animate)) {\n this.animate = false;\n }\n else {\n this.animate = animate;\n }\n this._initialState = initialState;\n this._finalState = finalState;\n this.title = \"Diagram layout\";\n },\n undo: function() {\n this.setState(this._initialState);\n },\n redo: function() {\n this.setState(this._finalState);\n },\n setState: function(state) {\n var diagram = state.diagram;\n if (this.animate) {\n state.linkMap.forEach(\n function(id, points) {\n var conn = diagram.getShapeById(id);\n conn.visible(false);\n if (conn) {\n conn.points(points);\n }\n }\n );\n var ticker = new Ticker();\n ticker.addAdapter(new PositionAdapter(state));\n ticker.onComplete(function() {\n state.linkMap.forEach(\n function(id) {\n var conn = diagram.getShapeById(id);\n conn.visible(true);\n }\n );\n });\n ticker.play();\n }\n else {\n state.nodeMap.forEach(function(id, bounds) {\n var shape = diagram.getShapeById(id);\n if (shape) {\n shape.position(bounds.topLeft());\n }\n });\n state.linkMap.forEach(\n function(id, points) {\n var conn = diagram.getShapeById(id);\n if (conn) {\n conn.points(points);\n }\n }\n );\n }\n }\n });\n\n var CompositeUnit = Class.extend({\n init: function(unit) {\n this.units = [];\n this.title = \"Composite unit\";\n if (unit !== undefined$1) {\n this.units.push(unit);\n }\n },\n add: function(undoUnit) {\n this.units.push(undoUnit);\n },\n undo: function() {\n for (var i = 0; i < this.units.length; i++) {\n this.units[i].undo();\n }\n },\n redo: function() {\n for (var i = 0; i < this.units.length; i++) {\n this.units[i].redo();\n }\n }\n });\n\n var ConnectionEditUnit = Class.extend({\n init: function(item, redoSource, redoTarget) {\n this.item = item;\n this._redoSource = redoSource;\n this._redoTarget = redoTarget;\n if (defined(redoSource)) {\n this._undoSource = item.source();\n }\n\n if (defined(redoTarget)) {\n this._undoTarget = item.target();\n }\n this.title = \"Connection Editing\";\n },\n undo: function() {\n if (this._undoSource !== undefined$1) {\n this.item._updateConnector(this._undoSource, \"source\");\n }\n\n if (this._undoTarget !== undefined$1) {\n this.item._updateConnector(this._undoTarget, \"target\");\n }\n\n this.item.updateModel();\n },\n redo: function() {\n if (this._redoSource !== undefined$1) {\n this.item._updateConnector(this._redoSource, \"source\");\n }\n\n if (this._redoTarget !== undefined$1) {\n this.item._updateConnector(this._redoTarget, \"target\");\n }\n\n this.item.updateModel();\n }\n });\n\n var ConnectionEditUndoUnit = Class.extend({\n init: function(item, undoSource, undoTarget) {\n this.item = item;\n this._undoSource = undoSource;\n this._undoTarget = undoTarget;\n this._redoSource = item.source();\n this._redoTarget = item.target();\n this.title = \"Connection Editing\";\n },\n undo: function() {\n this.item._updateConnector(this._undoSource, \"source\");\n this.item._updateConnector(this._undoTarget, \"target\");\n this.item.updateModel();\n },\n redo: function() {\n this.item._updateConnector(this._redoSource, \"source\");\n this.item._updateConnector(this._redoTarget, \"target\");\n this.item.updateModel();\n }\n });\n\n var DeleteConnectionUnit = Class.extend({\n init: function(connection) {\n this.connection = connection;\n this.diagram = connection.diagram;\n this.targetConnector = connection.targetConnector;\n this.title = \"Delete connection\";\n },\n undo: function() {\n this.diagram._addConnection(this.connection, false);\n },\n redo: function() {\n this.diagram.remove(this.connection, false);\n }\n });\n\n var DeleteShapeUnit = Class.extend({\n init: function(shape) {\n this.shape = shape;\n this.diagram = shape.diagram;\n this.title = \"Deletion\";\n },\n undo: function() {\n this.diagram._addShape(this.shape, false);\n this.shape.select(false);\n },\n redo: function() {\n this.shape.select(false);\n this.diagram.remove(this.shape, false);\n }\n });\n /**\n * Holds the undoredo state when performing a rotation, translation or scaling. The adorner is optional.\n * @type {*}\n */\n var TransformUnit = Class.extend({\n init: function(shapes, undoStates, adorner) {\n this.shapes = shapes;\n this.undoStates = undoStates;\n this.title = \"Transformation\";\n this.redoStates = [];\n this.adorner = adorner;\n for (var i = 0; i < this.shapes.length; i++) {\n var shape = this.shapes[i];\n this.redoStates.push(shape.bounds());\n }\n },\n undo: function() {\n for (var i = 0; i < this.shapes.length; i++) {\n var shape = this.shapes[i];\n shape.bounds(this.undoStates[i]);\n if (shape.hasOwnProperty(\"layout\")) {\n shape.layout(shape, this.redoStates[i], this.undoStates[i]);\n }\n shape.updateModel();\n }\n if (this.adorner) {\n this.adorner.refreshBounds();\n this.adorner.refresh();\n }\n },\n redo: function() {\n for (var i = 0; i < this.shapes.length; i++) {\n var shape = this.shapes[i];\n shape.bounds(this.redoStates[i]);\n // the 'layout' property, if implemented, lets the shape itself work out what to do with the new bounds\n if (shape.hasOwnProperty(\"layout\")) {\n shape.layout(shape, this.undoStates[i], this.redoStates[i]);\n }\n shape.updateModel();\n }\n\n if (this.adorner) {\n this.adorner.refreshBounds();\n this.adorner.refresh();\n }\n }\n });\n\n var AddConnectionUnit = Class.extend({\n init: function(connection, diagram) {\n this.connection = connection;\n this.diagram = diagram;\n this.title = \"New connection\";\n },\n\n undo: function() {\n this.diagram.remove(this.connection, false);\n },\n\n redo: function() {\n this.diagram._addConnection(this.connection, false);\n }\n });\n\n var AddShapeUnit = Class.extend({\n init: function(shape, diagram) {\n this.shape = shape;\n this.diagram = diagram;\n this.title = \"New shape\";\n },\n\n undo: function() {\n this.diagram.deselect();\n this.diagram.remove(this.shape, false);\n },\n\n redo: function() {\n this.diagram._addShape(this.shape, false);\n }\n });\n\n var PanUndoUnit = Class.extend({\n init: function(initialPosition, finalPosition, diagram) {\n this.initial = initialPosition;\n this.finalPos = finalPosition;\n this.diagram = diagram;\n this.title = \"Pan Unit\";\n },\n undo: function() {\n this.diagram.pan(this.initial);\n },\n redo: function() {\n this.diagram.pan(this.finalPos);\n }\n });\n\n var RotateUnit = Class.extend({\n init: function(adorner, shapes, undoRotates) {\n this.shapes = shapes;\n this.undoRotates = undoRotates;\n this.title = \"Rotation\";\n this.redoRotates = [];\n this.redoAngle = adorner._angle;\n this.adorner = adorner;\n this.center = adorner._innerBounds.center();\n for (var i = 0; i < this.shapes.length; i++) {\n var shape = this.shapes[i];\n this.redoRotates.push(shape.rotate().angle);\n }\n },\n undo: function() {\n var i, shape;\n for (i = 0; i < this.shapes.length; i++) {\n shape = this.shapes[i];\n shape.rotate(this.undoRotates[i], this.center, false);\n if (shape.hasOwnProperty(\"layout\")) {\n shape.layout(shape);\n }\n shape.updateModel();\n }\n if (this.adorner) {\n this.adorner._initialize();\n this.adorner.refresh();\n }\n },\n redo: function() {\n var i, shape;\n for (i = 0; i < this.shapes.length; i++) {\n shape = this.shapes[i];\n shape.rotate(this.redoRotates[i], this.center, false);\n if (shape.hasOwnProperty(\"layout\")) {\n shape.layout(shape);\n }\n shape.updateModel();\n }\n if (this.adorner) {\n this.adorner._initialize();\n this.adorner.refresh();\n }\n }\n });\n\n var ToFrontUnit = Class.extend({\n init: function(diagram, items, initialIndices) {\n this.diagram = diagram;\n this.indices = initialIndices;\n this.items = items;\n this.title = \"Rotate Unit\";\n },\n undo: function() {\n this.diagram._toIndex(this.items, this.indices);\n },\n redo: function() {\n this.diagram.toFront(this.items, false);\n }\n });\n\n var ToBackUnit = Class.extend({\n init: function(diagram, items, initialIndices) {\n this.diagram = diagram;\n this.indices = initialIndices;\n this.items = items;\n this.title = \"Rotate Unit\";\n },\n undo: function() {\n this.diagram._toIndex(this.items, this.indices);\n },\n redo: function() {\n this.diagram.toBack(this.items, false);\n }\n });\n\n /**\n * Undo-redo service.\n */\n var UndoRedoService = kendo.Observable.extend({\n init: function(options) {\n kendo.Observable.fn.init.call(this, options);\n this.bind(this.events, options);\n this.stack = [];\n this.index = 0;\n this.capacity = 100;\n },\n\n events: [\"undone\", \"redone\"],\n\n /**\n * Starts the collection of units. Add those with\n * the addCompositeItem method and call commit. Or cancel to forget about it.\n */\n begin: function() {\n this.composite = new CompositeUnit();\n },\n\n /**\n * Cancels the collection process of unit started with 'begin'.\n */\n cancel: function() {\n this.composite = undefined$1;\n },\n\n /**\n * Commits a batch of units.\n */\n commit: function(execute) {\n if (this.composite.units.length > 0) {\n this._restart(this.composite, execute);\n }\n this.composite = undefined$1;\n },\n\n /**\n * Adds a unit as part of the begin-commit batch.\n * @param undoUnit\n */\n addCompositeItem: function(undoUnit) {\n if (this.composite) {\n this.composite.add(undoUnit);\n } else {\n this.add(undoUnit);\n }\n },\n\n /**\n * Standard addition of a unit. See also the batch version; begin-addCompositeUnit-commit methods.\n * @param undoUnit The unit to be added.\n * @param execute If false, the unit will be added but not executed.\n */\n add: function(undoUnit, execute) {\n this._restart(undoUnit, execute);\n },\n\n /**\n * Returns the number of undoable unit in the stack.\n * @returns {Number}\n */\n\n pop: function() {\n if (this.index > 0) {\n this.stack.pop();\n this.index--;\n }\n },\n\n count: function() {\n return this.stack.length;\n },\n\n /**\n * Rollback of the unit on top of the stack.\n */\n undo: function() {\n if (this.index > 0) {\n this.index--;\n this.stack[this.index].undo();\n this.trigger(\"undone\");\n }\n },\n\n /**\n * Redo of the last undone action.\n */\n redo: function() {\n if (this.stack.length > 0 && this.index < this.stack.length) {\n this.stack[this.index].redo();\n this.index++;\n this.trigger(\"redone\");\n }\n },\n\n _restart: function(composite, execute) {\n // throw away anything beyond this point if this is a new branch\n this.stack.splice(this.index, this.stack.length - this.index);\n this.stack.push(composite);\n if (execute !== false) {\n this.redo();\n } else {\n this.index++;\n }\n // check the capacity\n if (this.stack.length > this.capacity) {\n this.stack.splice(0, this.stack.length - this.capacity);\n this.index = this.capacity; //points to the end of the stack\n }\n },\n\n /**\n * Clears the stack.\n */\n clear: function() {\n this.stack = [];\n this.index = 0;\n }\n });\n\n // Tools =========================================\n\n var EmptyTool = Class.extend({\n init: function(toolService) {\n this.toolService = toolService;\n },\n start: function() {\n },\n move: function() {\n },\n end: function() {\n },\n tryActivate: function() {\n return false;\n },\n getCursor: function() {\n return Cursors.arrow;\n }\n });\n\n var ScrollerTool = EmptyTool.extend({\n init: function(toolService) {\n var tool = this;\n var friction = kendo.support.mobileOS ? FRICTION_MOBILE : FRICTION;\n EmptyTool.fn.init.call(tool, toolService);\n\n var diagram = tool.toolService.diagram,\n canvas = diagram.canvas;\n\n var scroller = diagram.scroller = tool.scroller = $(diagram.scrollable).kendoMobileScroller({\n friction: friction,\n velocityMultiplier: VELOCITY_MULTIPLIER,\n mousewheelScrolling: false,\n zoom: false,\n scroll: tool._move.bind(tool)\n }).data(\"kendoMobileScroller\");\n\n if (canvas.translate) {\n tool.movableCanvas = new Movable(canvas.element);\n }\n\n var virtualScroll = function(dimension, min, max) {\n dimension.makeVirtual();\n dimension.virtualSize(min || SCROLL_MIN, max || SCROLL_MAX);\n };\n\n virtualScroll(scroller.dimensions.x);\n virtualScroll(scroller.dimensions.y);\n scroller.disable();\n },\n\n tryActivate: function(p, meta) {\n var toolService = this.toolService;\n var options = toolService.diagram.options.pannable;\n var enabled = meta.ctrlKey;\n\n if (defined(options.key)) {\n if (!options.key || options.key == \"none\") {\n enabled = noMeta(meta) && !defined(toolService.hoveredItem);\n } else {\n enabled = meta[options.key + \"Key\"];\n }\n }\n\n return options !== false && enabled && !defined(toolService.hoveredAdorner) && !defined(toolService._hoveredConnector);\n },\n\n start: function() {\n this.scroller.enable();\n },\n move: function() {\n },//the tool itself should not handle the scrolling. Let kendo scroller take care of this part. Check _move\n _move: function(args) {\n var tool = this,\n diagram = tool.toolService.diagram,\n canvas = diagram.canvas,\n scrollPos = new Point(args.scrollLeft, args.scrollTop);\n\n if (canvas.translate) {\n diagram._storePan(scrollPos.times(-1));\n tool.movableCanvas.moveTo(scrollPos);\n canvas.translate(scrollPos.x, scrollPos.y);\n } else {\n scrollPos = scrollPos.plus(diagram._pan.times(-1));\n }\n\n diagram.trigger(PAN, { pan: scrollPos });\n },\n end: function() {\n this.scroller.disable();\n },\n getCursor: function() {\n return Cursors.move;\n }\n });\n\n /**\n * The tool handling the transformations via the adorner.\n * @type {*}\n */\n var PointerTool = Class.extend({\n init: function(toolService) {\n this.toolService = toolService;\n },\n tryActivate: function() {\n return true; // the pointer tool is last and handles all others requests.\n },\n start: function(p, meta) {\n var toolService = this.toolService,\n diagram = toolService.diagram,\n hoveredItem = toolService.hoveredItem;\n\n if (hoveredItem) {\n toolService.selectSingle(hoveredItem, meta);\n if (hoveredItem.adorner) { //connection\n this.adorner = hoveredItem.adorner;\n this.handle = this.adorner._hitTest(p);\n }\n }\n\n if (!this.handle) {\n this.handle = diagram._resizingAdorner._hitTest(p);\n if (this.handle) {\n this.adorner = diagram._resizingAdorner;\n }\n }\n\n if (this.adorner) {\n if (!this.adorner.isDragHandle(this.handle) || !diagram.trigger(DRAG_START, { shapes: this.adorner.shapes, connections: [] })) {\n this.adorner.start(p);\n } else {\n toolService.startPoint = p;\n toolService.end(p);\n }\n }\n },\n\n move: function(p) {\n if (this.adorner) {\n this.adorner.move(this.handle, p);\n if (this.adorner.isDragHandle(this.handle)) {\n this.toolService.diagram.trigger(DRAG, { shapes: this.adorner.shapes, connections: [] });\n }\n }\n },\n\n end: function() {\n var diagram = this.toolService.diagram,\n adorner = this.adorner,\n unit;\n\n if (adorner) {\n if (!adorner.isDragHandle(this.handle) || !diagram.trigger(DRAG_END, { shapes: adorner.shapes, connections: [] })) {\n unit = adorner.stop();\n if (unit) {\n diagram.undoRedoService.add(unit, false);\n }\n } else {\n adorner.cancel();\n }\n }\n\n this.adorner = undefined$1;\n this.handle = undefined$1;\n },\n getCursor: function(p) {\n return this.toolService.hoveredItem ? this.toolService.hoveredItem._getCursor(p) : Cursors.arrow;\n }\n });\n\n var SelectionTool = Class.extend({\n init: function(toolService) {\n this.toolService = toolService;\n },\n tryActivate: function(p, meta) {\n var toolService = this.toolService;\n var selectable = toolService.diagram.options.selectable;\n var enabled = selectable && selectable.multiple !== false;\n\n if (enabled) {\n if (selectable.key && selectable.key != \"none\") {\n enabled = meta[selectable.key + \"Key\"];\n } else {\n enabled = noMeta(meta);\n }\n }\n\n return enabled && !defined(toolService.hoveredItem) && !defined(toolService.hoveredAdorner);\n },\n start: function(p) {\n var diagram = this.toolService.diagram;\n diagram.deselect();\n diagram.selector.start(p);\n },\n move: function(p) {\n var diagram = this.toolService.diagram;\n diagram.selector.move(p);\n },\n end: function(p, meta) {\n var diagram = this.toolService.diagram, hoveredItem = this.toolService.hoveredItem;\n var rect = diagram.selector.bounds();\n if ((!hoveredItem || !hoveredItem.isSelected) && !meta.ctrlKey) {\n diagram.deselect();\n }\n if (!rect.isEmpty()) {\n diagram.selectArea(rect);\n }\n diagram.selector.end();\n },\n getCursor: function() {\n return Cursors.arrow;\n }\n });\n\n var ConnectionTool = Class.extend({\n init: function(toolService) {\n this.toolService = toolService;\n this.type = \"ConnectionTool\";\n },\n tryActivate: function() {\n return this.toolService._hoveredConnector;\n },\n start: function(p, meta) {\n var toolService = this.toolService,\n diagram = toolService.diagram,\n connector = toolService._hoveredConnector,\n connection = diagram._createConnection({}, connector._c, p);\n\n if (canDrag(connection) && !diagram.trigger(DRAG_START, { shapes: [], connections: [connection], connectionHandle: TARGET }) && diagram._addConnection(connection)) {\n toolService._connectionManipulation(connection, connector._c.shape, true);\n toolService._removeHover();\n toolService.selectSingle(toolService.activeConnection, meta);\n if (meta.type == \"touchmove\") {\n diagram._cachedTouchTarget = connector.visual;\n }\n } else {\n connection.source(null);\n toolService.end(p);\n }\n },\n\n move: function(p) {\n var toolService = this.toolService;\n var connection = toolService.activeConnection;\n\n connection.target(p);\n toolService.diagram.trigger(DRAG, { shapes: [], connections: [connection], connectionHandle: TARGET });\n return true;\n },\n\n end: function(p) {\n var toolService = this.toolService,\n d = toolService.diagram,\n connection = toolService.activeConnection,\n hoveredItem = toolService.hoveredItem,\n connector = toolService._hoveredConnector,\n target,\n cachedTouchTarget = d._cachedTouchTarget;\n\n if (!connection) {\n return;\n }\n\n if (connector && connector._c != connection.sourceConnector) {\n target = connector._c;\n } else if (hoveredItem && hoveredItem instanceof diagram.Shape) {\n target = hoveredItem.getConnector(AUTO) || hoveredItem.getConnector(p);\n } else {\n target = p;\n }\n\n connection.target(target);\n\n if (!d.trigger(DRAG_END, { shapes: [], connections: [connection], connectionHandle: TARGET })) {\n connection.updateModel();\n d._syncConnectionChanges();\n } else {\n d.remove(connection, false);\n d.undoRedoService.pop();\n }\n toolService._connectionManipulation();\n\n if (cachedTouchTarget) {\n d._connectorsAdorner.visual.remove(cachedTouchTarget);\n d._cachedTouchTarget = null;\n }\n },\n\n getCursor: function() {\n return Cursors.arrow;\n }\n });\n\n var ConnectionEditTool = Class.extend({\n init: function(toolService) {\n this.toolService = toolService;\n this.type = \"ConnectionTool\";\n },\n\n tryActivate: function(p, meta) {\n var toolService = this.toolService,\n diagram = toolService.diagram,\n selectable = diagram.options.selectable,\n item = toolService.hoveredItem,\n isActive = selectable !== false &&\n item && item.path && !(item.isSelected && meta.ctrlKey);\n\n if (isActive) {\n this._c = item;\n }\n\n return isActive;\n },\n\n start: function(p, meta) {\n var toolService = this.toolService;\n var connection = this._c;\n\n toolService.selectSingle(connection, meta);\n\n var adorner = connection.adorner;\n\n var handle, name;\n if (adorner) {\n handle = adorner._hitTest(p);\n name = HANDLE_NAMES[handle];\n }\n\n if (canDrag(connection) && adorner && !toolService.diagram.trigger(DRAG_START, { shapes: [], connections: [connection], connectionHandle: name })) {\n this.handle = handle;\n this.handleName = name;\n adorner.start(p);\n } else {\n toolService.startPoint = p;\n toolService.end(p);\n }\n },\n\n move: function(p) {\n var adorner = this._c.adorner;\n if (canDrag(this._c) && adorner) {\n adorner.move(this.handle, p);\n this.toolService.diagram.trigger(DRAG, { shapes: [], connections: [this._c], connectionHandle: this.handleName });\n\n return true;\n }\n },\n\n end: function(p) {\n var connection = this._c;\n var adorner = connection.adorner;\n var toolService = this.toolService;\n var diagram = toolService.diagram;\n\n if (adorner) {\n if (canDrag(connection)) {\n var unit = adorner.stop(p);\n if (!diagram.trigger(DRAG_END, { shapes: [], connections: [connection], connectionHandle: this.handleName })) {\n diagram.undoRedoService.add(unit, false);\n connection.updateModel();\n diagram._syncConnectionChanges();\n } else {\n unit.undo();\n }\n }\n }\n },\n\n getCursor: function() {\n return Cursors.move;\n }\n });\n\n function testKey(key, str) {\n return str.charCodeAt(0) == key || str.toUpperCase().charCodeAt(0) == key;\n }\n\n /**\n * The service managing the tools.\n * @type {*}\n */\n var ToolService = Class.extend({\n init: function(diagram) {\n this.diagram = diagram;\n this.tools = [\n new ScrollerTool(this),\n new ConnectionEditTool(this),\n new ConnectionTool(this),\n new SelectionTool(this),\n new PointerTool(this)\n ]; // the order matters.\n\n this.activeTool = undefined$1;\n },\n\n start: function(p, meta) {\n meta = deepExtend({}, meta);\n if (this.activeTool) {\n this.activeTool.end(p, meta);\n }\n this._updateHoveredItem(p);\n this._activateTool(p, meta);\n this.activeTool.start(p, meta);\n this._updateCursor(p);\n this.diagram.focus();\n this.diagram.canvas.surface.suspendTracking();\n this.startPoint = p;\n return true;\n },\n\n move: function(p, meta) {\n meta = deepExtend({}, meta);\n var updateHovered = true;\n if (this.activeTool) {\n updateHovered = this.activeTool.move(p, meta);\n }\n if (updateHovered) {\n this._updateHoveredItem(p);\n }\n this._updateCursor(p);\n return true;\n },\n\n end: function(p, meta) {\n meta = deepExtend({}, meta);\n if (this.activeTool) {\n this.activeTool.end(p, meta);\n }\n this.diagram.canvas.surface.resumeTracking();\n this.activeTool = undefined$1;\n this._updateCursor(p);\n return true;\n },\n\n keyDown: function(key, meta) {\n var diagram = this.diagram;\n meta = deepExtend({ ctrlKey: false, metaKey: false, altKey: false }, meta);\n if ((meta.ctrlKey || meta.metaKey) && !meta.altKey) {// ctrl or option\n if (testKey(key, \"a\")) {// A: select all\n diagram.selectAll();\n diagram._destroyToolBar();\n return true;\n } else if (testKey(key, \"z\")) {// Z: undo\n diagram.undo();\n diagram._destroyToolBar();\n return true;\n } else if (testKey(key, \"y\")) {// y: redo\n diagram.redo();\n diagram._destroyToolBar();\n return true;\n } else if (testKey(key, \"c\")) {\n diagram.copy();\n diagram._destroyToolBar();\n } else if (testKey(key, \"x\")) {\n diagram.cut();\n diagram._destroyToolBar();\n } else if (testKey(key, \"v\")) {\n diagram.paste();\n diagram._destroyToolBar();\n } else if (testKey(key, \"l\")) {\n diagram.layout();\n diagram._destroyToolBar();\n } else if (testKey(key, \"d\")) {\n diagram._destroyToolBar();\n diagram.copy();\n diagram.paste();\n }\n } else if (key === 46 || key === 8) {// del: deletion\n var toRemove = this.diagram._triggerRemove(diagram.select());\n if (toRemove.length) {\n this.diagram.remove(toRemove, true);\n this.diagram._syncChanges();\n this.diagram._destroyToolBar();\n }\n\n return true;\n } else if (key === 27) {// ESC: stop any action\n this._discardNewConnection();\n diagram.deselect();\n diagram._destroyToolBar();\n return true;\n }\n\n },\n wheel: function(p, meta) {\n var diagram = this.diagram,\n delta = meta.delta,\n z = diagram.zoom(),\n options = diagram.options,\n zoomRate = options.zoomRate,\n zoomOptions = { point: p, meta: meta, zoom: z };\n\n if (diagram.trigger(ZOOM_START, zoomOptions)) {\n return;\n }\n\n if (delta < 0) {\n z += zoomRate;\n } else {\n z -= zoomRate;\n }\n\n z = kendo.dataviz.round(Math.max(options.zoomMin, Math.min(options.zoomMax, z)), 2);\n zoomOptions.zoom = z;\n\n diagram.zoom(z, zoomOptions);\n diagram.trigger(ZOOM_END, zoomOptions);\n\n return true;\n },\n setTool: function(tool, index) {\n tool.toolService = this;\n this.tools[index] = tool;\n },\n\n selectSingle: function(item, meta) {\n var diagram = this.diagram;\n var selectable = diagram.options.selectable;\n if (selectable && !item.isSelected && item.options.selectable !== false) {\n var addToSelection = meta.ctrlKey && selectable.multiple !== false;\n diagram.select(item, { addToSelection: addToSelection });\n }\n },\n\n _discardNewConnection: function() {\n if (this.newConnection) {\n this.diagram.remove(this.newConnection);\n this.newConnection = undefined$1;\n }\n },\n _activateTool: function(p, meta) {\n for (var i = 0; i < this.tools.length; i++) {\n var tool = this.tools[i];\n if (tool.tryActivate(p, meta)) {\n this.activeTool = tool;\n break; // activating the first available tool in the loop.\n }\n }\n },\n _updateCursor: function(p) {\n var element = this.diagram.element;\n var cursor = this.activeTool ? this.activeTool.getCursor(p) : (this.hoveredAdorner ? this.hoveredAdorner._getCursor(p) : (this.hoveredItem ? this.hoveredItem._getCursor(p) : Cursors.arrow));\n\n element.css({ cursor: cursor });\n },\n _connectionManipulation: function(connection, disabledShape, isNew) {\n this.activeConnection = connection;\n this.disabledShape = disabledShape;\n if (isNew) {\n this.newConnection = this.activeConnection;\n } else {\n this.newConnection = undefined$1;\n }\n },\n _updateHoveredItem: function(p) {\n var hit = this._hitTest(p);\n var diagram = this.diagram;\n\n if (hit != this.hoveredItem && (!this.disabledShape || hit != this.disabledShape)) {\n if (this.hoveredItem) {\n diagram.trigger(MOUSE_LEAVE, { item: this.hoveredItem });\n this.hoveredItem._hover(false);\n }\n\n if (hit && hit.options.enable) {\n diagram.trigger(MOUSE_ENTER, { item: hit });\n\n this.hoveredItem = hit; // Shape, connection or connector\n this.hoveredItem._hover(true);\n } else {\n this.hoveredItem = undefined$1;\n }\n }\n },\n _removeHover: function() {\n if (this.hoveredItem) {\n this.hoveredItem._hover(false);\n this.hoveredItem = undefined$1;\n }\n },\n _hitTest: function(point) {\n var hit, d = this.diagram, item, i;\n\n // connectors\n if (this._hoveredConnector) {\n this._hoveredConnector._hover(false);\n this._hoveredConnector = undefined$1;\n }\n if (d._connectorsAdorner._visible) {\n hit = d._connectorsAdorner._hitTest(point);\n if (hit) {\n return hit;\n }\n }\n\n hit = this.diagram._resizingAdorner._hitTest(point);\n if (hit) {\n this.hoveredAdorner = d._resizingAdorner;\n if (hit.x !== 0 || hit.y !== 0) { // hit testing for resizers or rotator, otherwise if (0,0) than pass through.\n return;\n }\n hit = undefined$1;\n } else {\n this.hoveredAdorner = undefined$1;\n }\n\n if (!this.activeTool || this.activeTool.type !== \"ConnectionTool\") {\n var selectedConnections = []; // only the connections should have higher presence because the connection edit point is on top of connector.\n // TODO: This should be reworked. The connection adorner should be one for all selected connections and should be hit tested prior the connections and shapes itself.\n for (i = 0; i < d._selectedItems.length; i++) {\n item = d._selectedItems[i];\n if (item instanceof diagram.Connection) {\n selectedConnections.push(item);\n }\n }\n hit = this._hitTestItems(selectedConnections, point);\n }\n\n return hit || this._hitTestElements(point);\n },\n\n _hitTestElements: function(point) {\n var diagram = this.diagram;\n var shapeHit = this._hitTestItems(diagram.shapes, point);\n var connectionHit = this._hitTestItems(diagram.connections, point);\n var hit;\n\n if ((!this.activeTool || this.activeTool.type != \"ConnectionTool\") && shapeHit && connectionHit && !hitTestShapeConnectors(shapeHit, point)) {\n var mainLayer = diagram.mainLayer;\n var shapeIdx = inArray(shapeHit.visual, mainLayer.children);\n var connectionIdx = inArray(connectionHit.visual, mainLayer.children);\n hit = shapeIdx > connectionIdx ? shapeHit : connectionHit;\n }\n return hit || shapeHit || connectionHit;\n },\n\n _hitTestItems: function(array, point) {\n var i, item, hit;\n for (i = array.length - 1; i >= 0; i--) {\n item = array[i];\n hit = item._hitTest(point);\n if (hit) {\n return hit;\n }\n }\n }\n });\n\n // Routing =========================================\n\n /**\n * Base class for connection routers.\n */\n var ConnectionRouterBase = kendo.Class.extend({\n init: function() {\n }\n /*route: function (connection) {\n },\n hitTest: function (p) {\n\n },\n getBounds: function () {\n\n }*/\n });\n\n /**\n * Base class for polyline and cascading routing.\n */\n var LinearConnectionRouter = ConnectionRouterBase.extend({\n init: function(connection) {\n var that = this;\n ConnectionRouterBase.fn.init.call(that);\n this.connection = connection;\n },\n /**\n * Hit testing for polyline paths.\n */\n hitTest: function(p) {\n var rec = this.getBounds().inflate(HIT_TEST_DISTANCE);\n if (!rec.contains(p)) {\n return false;\n }\n return diagram.Geometry.distanceToPolyline(p, this.connection.allPoints()) < HIT_TEST_DISTANCE;\n },\n\n /**\n * Bounds of a polyline.\n * @returns {kendo.dataviz.diagram.Rect}\n */\n getBounds: function() {\n var points = this.connection.allPoints(),\n s = points[0],\n e = points[points.length - 1],\n right = Math.max(s.x, e.x),\n left = Math.min(s.x, e.x),\n top = Math.min(s.y, e.y),\n bottom = Math.max(s.y, e.y);\n\n for (var i = 1; i < points.length - 1; ++i) {\n right = Math.max(right, points[i].x);\n left = Math.min(left, points[i].x);\n top = Math.min(top, points[i].y);\n bottom = Math.max(bottom, points[i].y);\n }\n\n return new Rect(left, top, right - left, bottom - top);\n }\n });\n\n /**\n * A simple poly-linear routing which does not alter the intermediate points.\n * Does hold the underlying hit, bounds....logic.\n * @type {*|Object|void|extend|Zepto.extend|b.extend}\n */\n var PolylineRouter = LinearConnectionRouter.extend({\n init: function(connection) {\n var that = this;\n LinearConnectionRouter.fn.init.call(that);\n this.connection = connection;\n },\n route: function() {\n // just keep the points as is\n }\n });\n\n var CascadingRouter = LinearConnectionRouter.extend({\n SAME_SIDE_DISTANCE_RATIO: 5,\n\n init: function(connection) {\n var that = this;\n LinearConnectionRouter.fn.init.call(that);\n this.connection = connection;\n },\n\n routePoints: function(start, end, sourceConnector, targetConnector) {\n var result;\n\n if (sourceConnector && targetConnector) {\n result = this._connectorPoints(start, end, sourceConnector, targetConnector);\n } else {\n result = this._floatingPoints(start, end, sourceConnector);\n }\n return result;\n },\n\n route: function() {\n var sourceConnector = this.connection._resolvedSourceConnector;\n var targetConnector = this.connection._resolvedTargetConnector;\n var start = this.connection.sourcePoint();\n var end = this.connection.targetPoint();\n var points = this.routePoints(start, end, sourceConnector, targetConnector);\n this.connection.points(points);\n },\n\n _connectorSides: [{\n name: \"Top\",\n axis: \"y\",\n boundsPoint: \"topLeft\",\n secondarySign: 1\n }, {\n name: \"Left\",\n axis: \"x\",\n boundsPoint: \"topLeft\",\n secondarySign: 1\n }, {\n name: \"Bottom\",\n axis: \"y\",\n boundsPoint: \"bottomRight\",\n secondarySign: -1\n }, {\n name: \"Right\",\n axis: \"x\",\n boundsPoint: \"bottomRight\",\n secondarySign: -1\n }],\n\n _connectorSide: function(connector, targetPoint) {\n var position = connector.position();\n var shapeBounds = connector.shape.bounds(ROTATED);\n var bounds = {\n topLeft: shapeBounds.topLeft(),\n bottomRight: shapeBounds.bottomRight()\n };\n var sides = this._connectorSides;\n var min = util.MAX_NUM;\n var sideDistance;\n var minSide;\n var axis;\n var side;\n for (var idx = 0; idx < sides.length; idx++) {\n side = sides[idx];\n axis = side.axis;\n sideDistance = Math.round(Math.abs(position[axis] - bounds[side.boundsPoint][axis]));\n if (sideDistance < min) {\n min = sideDistance;\n minSide = side;\n } else if (sideDistance === min &&\n (position[axis] - targetPoint[axis]) * side.secondarySign > (position[minSide.axis] - targetPoint[minSide.axis]) * minSide.secondarySign) {\n minSide = side;\n }\n }\n return minSide.name;\n },\n\n _sameSideDistance: function(connector) {\n var bounds = connector.shape.bounds(ROTATED);\n return Math.min(bounds.width, bounds.height) / this.SAME_SIDE_DISTANCE_RATIO;\n },\n\n _connectorPoints: function(start, end, sourceConnector, targetConnector) {\n var sourceConnectorSide = this._connectorSide(sourceConnector, end);\n var targetConnectorSide = this._connectorSide(targetConnector, start);\n var deltaX = end.x - start.x;\n var deltaY = end.y - start.y;\n var sameSideDistance = this._sameSideDistance(sourceConnector);\n var result = [];\n var pointX, pointY;\n\n if (sourceConnectorSide === TOP || sourceConnectorSide == BOTTOM) {\n if (targetConnectorSide == TOP || targetConnectorSide == BOTTOM) {\n if (sourceConnectorSide == targetConnectorSide) {\n if (sourceConnectorSide == TOP) {\n pointY = Math.min(start.y, end.y) - sameSideDistance;\n } else {\n pointY = Math.max(start.y, end.y) + sameSideDistance;\n }\n result = [new Point(start.x, pointY), new Point(end.x, pointY)];\n } else {\n result = [new Point(start.x, start.y + deltaY / 2), new Point(end.x, start.y + deltaY / 2)];\n }\n } else {\n result = [new Point(start.x, end.y)];\n }\n } else {\n if (targetConnectorSide == LEFT || targetConnectorSide == RIGHT) {\n if (sourceConnectorSide == targetConnectorSide) {\n if (sourceConnectorSide == LEFT) {\n pointX = Math.min(start.x, end.x) - sameSideDistance;\n } else {\n pointX = Math.max(start.x, end.x) + sameSideDistance;\n }\n result = [new Point(pointX, start.y), new Point(pointX, end.y)];\n } else {\n result = [new Point(start.x + deltaX / 2, start.y), new Point(start.x + deltaX / 2, start.y + deltaY)];\n }\n } else {\n result = [new Point(end.x, start.y)];\n }\n }\n return result;\n },\n\n _floatingPoints: function(start, end, sourceConnector) {\n var sourceConnectorSide = sourceConnector ? this._connectorSide(sourceConnector, end) : null;\n var cascadeStartHorizontal = this._startHorizontal(start, end, sourceConnectorSide);\n var points = [start, start, end, end];\n var deltaX = end.x - start.x;\n var deltaY = end.y - start.y;\n var length = points.length;\n var shiftX;\n var shiftY;\n\n // note that this is more generic than needed for only two intermediate points.\n for (var idx = 1; idx < length - 1; ++idx) {\n if (cascadeStartHorizontal) {\n if (idx % 2 !== 0) {\n shiftX = deltaX / (length / 2);\n shiftY = 0;\n }\n else {\n shiftX = 0;\n shiftY = deltaY / ((length - 1) / 2);\n }\n }\n else {\n if (idx % 2 !== 0) {\n shiftX = 0;\n shiftY = deltaY / (length / 2);\n }\n else {\n shiftX = deltaX / ((length - 1) / 2);\n shiftY = 0;\n }\n }\n points[idx] = new Point(points[idx - 1].x + shiftX, points[idx - 1].y + shiftY);\n }\n // need to fix the wrong 1.5 factor of the last intermediate point\n idx--;\n if ((cascadeStartHorizontal && (idx % 2 !== 0)) || (!cascadeStartHorizontal && (idx % 2 === 0))) {\n points[length - 2] = new Point(points[length - 1].x, points[length - 2].y);\n } else {\n points[length - 2] = new Point(points[length - 2].x, points[length - 1].y);\n }\n\n return [points[1], points[2]];\n },\n\n _startHorizontal: function(start, end, sourceSide) {\n var horizontal;\n if (sourceSide !== null && (sourceSide === RIGHT || sourceSide === LEFT)) {\n horizontal = true;\n } else {\n horizontal = Math.abs(start.x - end.x) > Math.abs(start.y - end.y);\n }\n\n return horizontal;\n }\n });\n\n // Adorners =========================================\n\n var AdornerBase = Class.extend({\n init: function(diagram, options) {\n var that = this;\n that.diagram = diagram;\n that.options = deepExtend({}, that.options, options);\n that.visual = new Group();\n that.diagram._adorners.push(that);\n },\n refresh: function() {\n\n }\n });\n\n var ConnectionEditAdorner = AdornerBase.extend({\n init: function(connection, options) {\n var that = this, diagram;\n that.connection = connection;\n diagram = that.connection.diagram;\n that._ts = diagram.toolService;\n AdornerBase.fn.init.call(that, diagram, options);\n var sp = that.connection.sourcePoint();\n var tp = that.connection.targetPoint();\n that.spVisual = new Circle(deepExtend(that.options.handles, { center: sp }));\n that.epVisual = new Circle(deepExtend(that.options.handles, { center: tp }));\n that.visual.append(that.spVisual);\n that.visual.append(that.epVisual);\n },\n\n options: {\n handles: {}\n },\n\n _getCursor: function() {\n return Cursors.move;\n },\n\n start: function(p) {\n this.handle = this._hitTest(p);\n this.startPoint = p;\n this._initialSource = this.connection.source();\n this._initialTarget = this.connection.target();\n switch (this.handle) {\n case -1:\n if (this.connection.targetConnector) {\n this._ts._connectionManipulation(this.connection, this.connection.targetConnector.shape);\n }\n break;\n case 1:\n if (this.connection.sourceConnector) {\n this._ts._connectionManipulation(this.connection, this.connection.sourceConnector.shape);\n }\n break;\n }\n },\n\n move: function(handle, p) {\n switch (handle) {\n case -1:\n this.connection.source(p);\n break;\n case 1:\n this.connection.target(p);\n break;\n default:\n var delta = p.minus(this.startPoint);\n this.startPoint = p;\n if (!this.connection.sourceConnector) {\n this.connection.source(this.connection.sourcePoint().plus(delta));\n }\n if (!this.connection.targetConnector) {\n this.connection.target(this.connection.targetPoint().plus(delta));\n }\n break;\n }\n this.refresh();\n return true;\n },\n\n stop: function(p) {\n var ts = this.diagram.toolService, item = ts.hoveredItem, target;\n if (ts._hoveredConnector) {\n target = ts._hoveredConnector._c;\n } else if (item && item instanceof diagram.Shape) {\n target = item.getConnector(AUTO) || item.getConnector(p);\n } else {\n target = p;\n }\n\n if (this.handle === -1) {\n this.connection.source(target);\n } else if (this.handle === 1) {\n this.connection.target(target);\n }\n\n this.handle = undefined$1;\n this._ts._connectionManipulation();\n return new ConnectionEditUndoUnit(this.connection, this._initialSource, this._initialTarget);\n },\n\n _hitTest: function(point) {\n var sourcePoint = this.connection.sourcePoint();\n var targetPoint = this.connection.targetPoint();\n var radiusX = this.options.handles.width / 2 + HIT_TEST_DISTANCE;\n var radiusY = this.options.handles.height / 2 + HIT_TEST_DISTANCE;\n var sourcePointDistance = sourcePoint.distanceTo(point);\n var targetPointDistance = targetPoint.distanceTo(point);\n var sourceHandle = new Rect(sourcePoint.x, sourcePoint.y).inflate(radiusX, radiusY).contains(point);\n var targetHandle = new Rect(targetPoint.x, targetPoint.y).inflate(radiusX, radiusY).contains(point);\n var handle = 0;\n\n if (sourceHandle && (!targetHandle || sourcePointDistance < targetPointDistance)) {\n handle = -1;\n } else if (targetHandle && (!sourceHandle || targetPointDistance < sourcePointDistance)) {\n handle = 1;\n }\n\n return handle;\n },\n\n refresh: function() {\n this.spVisual.redraw({ center: this.diagram.modelToLayer(this.connection.sourcePoint()) });\n this.epVisual.redraw({ center: this.diagram.modelToLayer(this.connection.targetPoint()) });\n }\n });\n\n var ConnectorsAdorner = AdornerBase.extend({\n init: function(diagram, options) {\n var that = this;\n AdornerBase.fn.init.call(that, diagram, options);\n that._refreshHandler = function(e) {\n if (e.item == that.shape) {\n that.refresh();\n }\n };\n },\n\n show: function(shape) {\n var that = this, len, i, ctr;\n that._visible = true;\n that.shape = shape;\n that.diagram.bind(ITEMBOUNDSCHANGE, that._refreshHandler);\n len = shape.connectors.length;\n that.connectors = [];\n that._clearVisual();\n for (i = 0; i < len; i++) {\n ctr = new ConnectorVisual(shape.connectors[i]);\n that.connectors.push(ctr);\n that.visual.append(ctr.visual);\n }\n that.visual.visible(true);\n that.refresh();\n },\n\n _clearVisual: function() {\n var that = this;\n if (that.diagram._cachedTouchTarget) {\n that._keepCachedTouchTarget();\n } else {\n that.visual.clear();\n }\n },\n\n _keepCachedTouchTarget: function() {\n var that = this,\n visualChildren = that.visual.children;\n var childrenCount = visualChildren.length;\n var index = inArray(that.diagram._cachedTouchTarget, visualChildren);\n for (var i = childrenCount - 1; i >= 0; i--) {\n if (i == index) {\n continue;\n }\n that.visual.remove(visualChildren[i]);\n }\n },\n\n destroy: function() {\n var that = this;\n that.diagram.unbind(ITEMBOUNDSCHANGE, that._refreshHandler);\n that.shape = undefined$1;\n that._visible = undefined$1;\n that.visual.visible(false);\n },\n\n _hitTest: function(p) {\n var ctr, i;\n for (i = 0; i < this.connectors.length; i++) {\n ctr = this.connectors[i];\n if (ctr._hitTest(p)) {\n ctr._hover(true);\n this.diagram.toolService._hoveredConnector = ctr;\n break;\n }\n }\n },\n\n refresh: function() {\n if (this.shape) {\n var bounds = this.shape.bounds();\n bounds = this.diagram.modelToLayer(bounds);\n this.visual.position(bounds.topLeft());\n $.each(this.connectors, function() {\n this.refresh();\n });\n }\n }\n });\n\n function hitToOppositeSide(hit, bounds) {\n var result;\n\n if (hit.x == -1 && hit.y == -1) {\n result = bounds.bottomRight();\n } else if (hit.x == 1 && hit.y == 1) {\n result = bounds.topLeft();\n } else if (hit.x == -1 && hit.y == 1) {\n result = bounds.topRight();\n } else if (hit.x == 1 && hit.y == -1) {\n result = bounds.bottomLeft();\n } else if (hit.x === 0 && hit.y == -1) {\n result = bounds.bottom();\n } else if (hit.x === 0 && hit.y == 1) {\n result = bounds.top();\n } else if (hit.x == 1 && hit.y === 0) {\n result = bounds.left();\n } else if (hit.x == -1 && hit.y === 0) {\n result = bounds.right();\n }\n\n return result;\n }\n\n var ResizingAdorner = AdornerBase.extend({\n init: function(diagram, options) {\n var that = this;\n AdornerBase.fn.init.call(that, diagram, options);\n that._manipulating = false;\n that.map = [];\n that.shapes = [];\n\n that._initSelection();\n that._createHandles();\n that.redraw();\n that.diagram.bind(\"select\", function(e) {\n that._initialize(e.selected);\n });\n\n that._refreshHandler = function() {\n if (!that._internalChange) {\n that.refreshBounds();\n that.refresh();\n }\n };\n\n that._rotatedHandler = function() {\n if (that.shapes.length == 1) {\n that._angle = that.shapes[0].rotate().angle;\n }\n that._refreshHandler();\n };\n\n that.diagram.bind(ITEMBOUNDSCHANGE, that._refreshHandler).bind(ITEMROTATE, that._rotatedHandler);\n that.refreshBounds();\n that.refresh();\n },\n\n options: {\n handles: {\n fill: {\n color: \"#fff\"\n },\n stroke: {\n color: \"#282828\"\n },\n height: 7,\n width: 7,\n hover: {\n fill: {\n color: \"#282828\"\n },\n stroke: {\n color: \"#282828\"\n }\n }\n },\n selectable: {\n stroke: {\n color: \"#778899\",\n width: 1,\n dashType: \"dash\"\n },\n fill: {\n color: TRANSPARENT\n }\n },\n offset: 10\n },\n\n _initSelection: function() {\n var that = this;\n var diagram = that.diagram;\n var selectable = diagram.options.selectable;\n var options = deepExtend({}, that.options.selectable, selectable);\n that.rect = new Rectangle(options);\n that.visual.append(that.rect);\n },\n\n _resizable: function() {\n return this.options.editable && this.options.editable.resize !== false;\n },\n\n _handleOptions: function() {\n return (this.options.editable.resize || {}).handles || this.options.handles;\n },\n\n _createHandles: function() {\n var handles, item, y, x;\n\n if (this._resizable()) {\n handles = this._handleOptions();\n for (x = -1; x <= 1; x++) {\n for (y = -1; y <= 1; y++) {\n if ((x !== 0) || (y !== 0)) { // (0, 0) element, (-1, -1) top-left, (+1, +1) bottom-right\n item = new Rectangle(handles);\n item.drawingElement._hover = this._hover.bind(this);\n this.map.push({ x: x, y: y, visual: item });\n this.visual.append(item);\n }\n }\n }\n }\n },\n\n bounds: function(value) {\n if (value) {\n this._innerBounds = value.clone();\n this._bounds = this.diagram.modelToLayer(value).inflate(this.options.offset, this.options.offset);\n } else {\n return this._bounds;\n }\n },\n\n _hitTest: function(p) {\n var tp = this.diagram.modelToLayer(p),\n i, hit, handleBounds, handlesCount = this.map.length, handle;\n\n if (this._angle) {\n tp = tp.clone().rotate(this._bounds.center(), this._angle);\n }\n\n if (this._resizable()) {\n for (i = 0; i < handlesCount; i++) {\n handle = this.map[i];\n hit = new Point(handle.x, handle.y);\n handleBounds = this._getHandleBounds(hit); //local coordinates\n handleBounds.offset(this._bounds.x, this._bounds.y);\n if (handleBounds.contains(tp)) {\n return hit;\n }\n }\n }\n\n if (this._bounds.contains(tp)) {\n return new Point(0, 0);\n }\n },\n\n _getHandleBounds: function(p) {\n if (this._resizable()) {\n var handles = this._handleOptions(),\n w = handles.width,\n h = handles.height,\n r = new Rect(0, 0, w, h);\n\n if (p.x < 0) {\n r.x = - w / 2;\n } else if (p.x === 0) {\n r.x = Math.floor(this._bounds.width / 2) - w / 2;\n } else if (p.x > 0) {\n r.x = this._bounds.width + 1.0 - w / 2;\n } if (p.y < 0) {\n r.y = - h / 2;\n } else if (p.y === 0) {\n r.y = Math.floor(this._bounds.height / 2) - h / 2;\n } else if (p.y > 0) {\n r.y = this._bounds.height + 1.0 - h / 2;\n }\n\n return r;\n }\n },\n\n _getCursor: function(point) {\n var hit = this._hitTest(point);\n if (hit && (hit.x >= -1) && (hit.x <= 1) && (hit.y >= -1) && (hit.y <= 1) && this._resizable()) {\n var angle = this._angle;\n if (angle) {\n angle = 360 - angle;\n hit.rotate(new Point(0, 0), angle);\n hit = new Point(Math.round(hit.x), Math.round(hit.y));\n }\n\n if (hit.x == -1 && hit.y == -1) {\n return \"nw-resize\";\n }\n if (hit.x == 1 && hit.y == 1) {\n return \"se-resize\";\n }\n if (hit.x == -1 && hit.y == 1) {\n return \"sw-resize\";\n }\n if (hit.x == 1 && hit.y == -1) {\n return \"ne-resize\";\n }\n if (hit.x === 0 && hit.y == -1) {\n return \"n-resize\";\n }\n if (hit.x === 0 && hit.y == 1) {\n return \"s-resize\";\n }\n if (hit.x == 1 && hit.y === 0) {\n return \"e-resize\";\n }\n if (hit.x == -1 && hit.y === 0) {\n return \"w-resize\";\n }\n }\n return this._manipulating ? Cursors.move : Cursors.select;\n },\n\n _initialize: function() {\n var that = this, i, item,\n items = that.diagram.select();\n\n that.shapes = [];\n for (i = 0; i < items.length; i++) {\n item = items[i];\n if (item instanceof diagram.Shape) {\n that.shapes.push(item);\n item._rotationOffset = new Point();\n }\n }\n\n that._angle = that.shapes.length == 1 ? that.shapes[0].rotate().angle : 0;\n that._startAngle = that._angle;\n that._rotates();\n that._positions();\n that.refreshBounds();\n that.refresh();\n that.redraw();\n },\n\n _rotates: function() {\n var that = this, i, shape;\n that.initialRotates = [];\n for (i = 0; i < that.shapes.length; i++) {\n shape = that.shapes[i];\n that.initialRotates.push(shape.rotate().angle);\n }\n },\n\n _positions: function() {\n var that = this, i, shape;\n that.initialStates = [];\n for (i = 0; i < that.shapes.length; i++) {\n shape = that.shapes[i];\n that.initialStates.push(shape.bounds());\n }\n },\n\n _hover: function(value, element) {\n if (this._resizable()) {\n var handleOptions = this._handleOptions(),\n hover = handleOptions.hover,\n stroke = handleOptions.stroke,\n fill = handleOptions.fill;\n\n if (value && Utils.isDefined(hover.stroke)) {\n stroke = deepExtend({}, stroke, hover.stroke);\n }\n\n if (value && Utils.isDefined(hover.fill)) {\n fill = hover.fill;\n }\n element.stroke(stroke.color, stroke.width, stroke.opacity);\n element.fill(fill.color, fill.opacity);\n }\n },\n\n start: function(p) {\n this._sp = p;\n this._cp = p;\n this._lp = p;\n this._manipulating = true;\n this._internalChange = true;\n this.shapeStates = [];\n for (var i = 0; i < this.shapes.length; i++) {\n var shape = this.shapes[i];\n this.shapeStates.push(shape.bounds());\n }\n },\n\n redraw: function() {\n var i, handle,\n visibleHandles = this._resizable();\n\n for (i = 0; i < this.map.length; i++) {\n handle = this.map[i];\n handle.visual.visible(visibleHandles);\n }\n },\n\n angle: function(value) {\n if (defined(value)) {\n this._angle = value;\n }\n\n return this._angle;\n },\n\n rotate: function() {\n var center = this._innerBounds.center();\n var currentAngle = this.angle();\n this._internalChange = true;\n for (var i = 0; i < this.shapes.length; i++) {\n var shape = this.shapes[i];\n currentAngle = (currentAngle + this.initialRotates[i] - this._startAngle) % 360;\n shape.rotate(currentAngle, center);\n }\n this.refresh();\n },\n\n move: function(handle, p) {\n var delta, dragging,\n dtl = new Point(),\n dbr = new Point(),\n bounds, center, shape,\n i, angle, newBounds,\n changed = 0, staticPoint,\n scaleX, scaleY;\n\n if (handle.y === -2 && handle.x === -1) {\n center = this._innerBounds.center();\n this._angle = this._truncateAngle(Utils.findAngle(center, p));\n for (i = 0; i < this.shapes.length; i++) {\n shape = this.shapes[i];\n angle = (this._angle + this.initialRotates[i] - this._startAngle) % 360;\n shape.rotate(angle, center);\n if (shape.hasOwnProperty(\"layout\")) {\n shape.layout(shape);\n }\n this._rotating = true;\n }\n this.refresh();\n } else {\n if (this.shouldSnap()) {\n var thr = this._truncateDistance(p.minus(this._lp));\n // threshold\n if (thr.x === 0 && thr.y === 0) {\n this._cp = p;\n return;\n }\n delta = thr;\n this._lp = new Point(this._lp.x + thr.x, this._lp.y + thr.y);\n } else {\n delta = p.minus(this._cp);\n }\n\n if (this.isDragHandle(handle)) {\n dbr = dtl = delta; // dragging\n dragging = true;\n } else {\n if (this._angle) { // adjust the delta so that resizers resize in the correct direction after rotation.\n delta.rotate(new Point(0, 0), this._angle);\n }\n if (handle.x == -1) {\n dtl.x = delta.x;\n } else if (handle.x == 1) {\n dbr.x = delta.x;\n }\n if (handle.y == -1) {\n dtl.y = delta.y;\n } else if (handle.y == 1) {\n dbr.y = delta.y;\n }\n }\n\n if (!dragging) {\n staticPoint = hitToOppositeSide(handle, this._innerBounds);\n scaleX = (this._innerBounds.width + delta.x * handle.x) / this._innerBounds.width;\n scaleY = (this._innerBounds.height + delta.y * handle.y) / this._innerBounds.height;\n }\n\n for (i = 0; i < this.shapes.length; i++) {\n shape = this.shapes[i];\n bounds = shape.bounds();\n if (dragging) {\n if (!canDrag(shape)) {\n continue;\n }\n newBounds = this._displaceBounds(bounds, dtl, dbr, dragging);\n } else {\n newBounds = bounds.clone();\n newBounds.scale(scaleX, scaleY, staticPoint, this._innerBounds.center(), shape.rotate().angle);\n var newCenter = newBounds.center(); // fixes the new rotation center.\n newCenter.rotate(bounds.center(), -this._angle);\n newBounds = new Rect(newCenter.x - newBounds.width / 2, newCenter.y - newBounds.height / 2, newBounds.width, newBounds.height);\n }\n if (newBounds.width >= shape.options.minWidth && newBounds.height >= shape.options.minHeight) { // if we up-size very small shape\n var oldBounds = bounds;\n shape.bounds(newBounds);\n if (shape.hasOwnProperty(\"layout\")) {\n shape.layout(shape, oldBounds, newBounds);\n }\n if (oldBounds.width !== newBounds.width || oldBounds.height !== newBounds.height) {\n shape.rotate(shape.rotate().angle); // forces the rotation to update it's rotation center\n }\n changed += 1;\n }\n }\n\n if (changed) {\n if (changed == i) {\n newBounds = this._displaceBounds(this._innerBounds, dtl, dbr, dragging);\n this.bounds(newBounds);\n } else {\n this.refreshBounds();\n }\n this.refresh();\n }\n\n this._positions();\n }\n\n this._cp = p;\n },\n\n isDragHandle: function(handle) {\n return handle.x === 0 && handle.y === 0;\n },\n\n cancel: function() {\n var shapes = this.shapes;\n var states = this.shapeStates;\n for (var idx = 0; idx < shapes.length; idx++) {\n shapes[idx].bounds(states[idx]);\n }\n this.refreshBounds();\n this.refresh();\n this._manipulating = undefined$1;\n this._internalChange = undefined$1;\n this._rotating = undefined$1;\n },\n\n _truncatePositionToGuides: function(bounds) {\n if (this.diagram.ruler) {\n return this.diagram.ruler.truncatePositionToGuides(bounds);\n }\n return bounds;\n },\n\n _truncateSizeToGuides: function(bounds) {\n if (this.diagram.ruler) {\n return this.diagram.ruler.truncateSizeToGuides(bounds);\n }\n return bounds;\n },\n\n _truncateAngle: function(a) {\n var snap = this.snapOptions();\n var snapAngle = Math.max(snap.angle || DEFAULT_SNAP_ANGLE, MIN_SNAP_ANGLE);\n return snap ? Math.floor((a % 360) / snapAngle) * snapAngle : (a % 360);\n },\n\n _truncateDistance: function(d) {\n if (d instanceof diagram.Point) {\n return new diagram.Point(this._truncateDistance(d.x), this._truncateDistance(d.y));\n } else {\n var snap = this.snapOptions() || {};\n var snapSize = Math.max(snap.size || DEFAULT_SNAP_SIZE, MIN_SNAP_SIZE);\n return snap ? Math.floor(d / snapSize) * snapSize : d;\n }\n },\n\n snapOptions: function() {\n var editable = this.diagram.options.editable;\n var snap = ((editable || {}).drag || {}).snap || {};\n return snap;\n },\n\n shouldSnap: function() {\n var editable = this.diagram.options.editable;\n var drag = (editable || {}).drag;\n var snap = (drag || {}).snap;\n return editable !== false && drag !== false && snap !== false;\n },\n\n _displaceBounds: function(bounds, dtl, dbr, dragging) {\n var tl = bounds.topLeft().plus(dtl),\n br = bounds.bottomRight().plus(dbr),\n newBounds = Rect.fromPoints(tl, br),\n newCenter;\n if (!dragging) {\n newCenter = newBounds.center();\n newCenter.rotate(bounds.center(), -this._angle);\n newBounds = new Rect(newCenter.x - newBounds.width / 2, newCenter.y - newBounds.height / 2, newBounds.width, newBounds.height);\n }\n return newBounds;\n },\n\n stop: function() {\n var unit, i, shape;\n if (this._cp != this._sp) {\n if (this._rotating) {\n unit = new RotateUnit(this, this.shapes, this.initialRotates);\n this._rotating = false;\n } else if (this._diffStates()) {\n if (this.diagram.ruler) {\n for (i = 0; i < this.shapes.length; i++) {\n shape = this.shapes[i];\n var bounds = shape.bounds();\n bounds = this._truncateSizeToGuides(this._truncatePositionToGuides(bounds));\n shape.bounds(bounds);\n this.refreshBounds();\n this.refresh();\n }\n }\n for (i = 0; i < this.shapes.length; i++) {\n shape = this.shapes[i];\n shape.updateModel();\n }\n unit = new TransformUnit(this.shapes, this.shapeStates, this);\n this.diagram._syncShapeChanges();\n }\n }\n\n this._manipulating = undefined$1;\n this._internalChange = undefined$1;\n this._rotating = undefined$1;\n return unit;\n },\n\n _diffStates: function() {\n var shapes = this.shapes;\n var states = this.shapeStates;\n for (var idx = 0; idx < shapes.length; idx++) {\n if (!shapes[idx].bounds().equals(states[idx])) {\n return true;\n }\n }\n return false;\n },\n\n refreshBounds: function() {\n var bounds = this.shapes.length == 1 ?\n this.shapes[0].bounds().clone() :\n this.diagram.boundingBox(this.shapes, true);\n\n this.bounds(bounds);\n },\n\n refresh: function() {\n var that = this, b, bounds;\n if (this.shapes.length > 0) {\n bounds = this.bounds();\n this.visual.visible(true);\n this.visual.position(bounds.topLeft());\n $.each(this.map, function() {\n b = that._getHandleBounds(new Point(this.x, this.y));\n this.visual.position(b.topLeft());\n });\n this.visual.position(bounds.topLeft());\n\n var center = new Point(bounds.width / 2, bounds.height / 2);\n this.visual.rotate(this._angle, center);\n this.rect.redraw({ width: bounds.width, height: bounds.height });\n if (this.rotationThumb) {\n var thumb = this.options.editable.rotate.thumb;\n this._rotationThumbBounds = new Rect(bounds.center().x, bounds.y + thumb.y, 0, 0).inflate(thumb.width);\n this.rotationThumb.redraw({ x: bounds.width / 2 - thumb.width / 2 });\n }\n } else {\n this.visual.visible(false);\n }\n }\n });\n\n var Selector = Class.extend({\n init: function(diagram) {\n var selectable = diagram.options.selectable;\n this.options = deepExtend({}, this.options, selectable);\n\n this.visual = new Rectangle(this.options);\n this.diagram = diagram;\n },\n options: {\n stroke: {\n color: \"#778899\",\n width: 1,\n dashType: \"dash\"\n },\n fill: {\n color: TRANSPARENT\n }\n },\n start: function(p) {\n this._sp = this._ep = p;\n this.refresh();\n this.diagram._adorn(this, true);\n },\n end: function() {\n this._sp = this._ep = undefined$1;\n this.diagram._adorn(this, false);\n },\n bounds: function(value) {\n if (value) {\n this._bounds = value;\n }\n return this._bounds;\n },\n move: function(p) {\n this._ep = p;\n this.refresh();\n },\n refresh: function() {\n if (this._sp) {\n var visualBounds = Rect.fromPoints(this.diagram.modelToLayer(this._sp), this.diagram.modelToLayer(this._ep));\n this.bounds(Rect.fromPoints(this._sp, this._ep));\n this.visual.position(visualBounds.topLeft());\n this.visual.redraw({ height: visualBounds.height + 1, width: visualBounds.width + 1 });\n }\n }\n });\n\n var ConnectorVisual = Class.extend({\n init: function(connector) {\n this.options = deepExtend({}, connector.options);\n this._c = connector;\n this.visual = new Circle(this.options);\n this.refresh();\n },\n _hover: function(value) {\n var options = this.options,\n hover = options.hover,\n stroke = options.stroke,\n fill = options.fill;\n\n if (value && Utils.isDefined(hover.stroke)) {\n stroke = deepExtend({}, stroke, hover.stroke);\n }\n\n if (value && Utils.isDefined(hover.fill)) {\n fill = hover.fill;\n }\n\n this.visual.redraw({\n stroke: stroke,\n fill: fill\n });\n },\n refresh: function() {\n var p = this._c.shape.diagram.modelToView(this._c.position()),\n relative = p.minus(this._c.shape.bounds(\"transformed\").topLeft()),\n value = new Rect(p.x, p.y, 0, 0);\n value.inflate(this.options.width / 2, this.options.height / 2);\n this._visualBounds = value;\n this.visual.redraw({ center: new Point(relative.x, relative.y) });\n },\n _hitTest: function(p) {\n var tp = this._c.shape.diagram.modelToView(p);\n return this._visualBounds.contains(tp);\n }\n });\n\n function canDrag(element) {\n var editable = element.options.editable;\n return editable && editable.drag !== false;\n }\n\n function hitTestShapeConnectors(shape, point) {\n var connector, position, rect;\n for (var idx = 0; idx < shape.connectors.length; idx++) {\n connector = shape.connectors[idx];\n position = connector.position();\n rect = new Rect(position.x, position.y);\n rect.inflate(HIT_TEST_DISTANCE, HIT_TEST_DISTANCE);\n if (rect.contains(point)) {\n return connector;\n }\n }\n }\n\n function noMeta(meta) {\n return meta.ctrlKey === false && meta.altKey === false && meta.shiftKey === false;\n }\n\n deepExtend(diagram, {\n CompositeUnit: CompositeUnit,\n TransformUnit: TransformUnit,\n PanUndoUnit: PanUndoUnit,\n AddShapeUnit: AddShapeUnit,\n AddConnectionUnit: AddConnectionUnit,\n DeleteShapeUnit: DeleteShapeUnit,\n DeleteConnectionUnit: DeleteConnectionUnit,\n ConnectionEditAdorner: ConnectionEditAdorner,\n ConnectionTool: ConnectionTool,\n ConnectorVisual: ConnectorVisual,\n UndoRedoService: UndoRedoService,\n ResizingAdorner: ResizingAdorner,\n Selector: Selector,\n ToolService: ToolService,\n ConnectorsAdorner: ConnectorsAdorner,\n LayoutUndoUnit: LayoutUndoUnit,\n ConnectionEditUnit: ConnectionEditUnit,\n ToFrontUnit: ToFrontUnit,\n ToBackUnit: ToBackUnit,\n ConnectionRouterBase: ConnectionRouterBase,\n PolylineRouter: PolylineRouter,\n CascadingRouter: CascadingRouter,\n SelectionTool: SelectionTool,\n ScrollerTool: ScrollerTool,\n PointerTool: PointerTool,\n ConnectionEditTool: ConnectionEditTool,\n RotateUnit: RotateUnit\n });\n })(window.kendo.jQuery);\n\n (function($, undefined$1) {\n var kendo = window.kendo,\n diagram = kendo.dataviz.diagram,\n Graph = diagram.Graph,\n Node = diagram.Node,\n Link = diagram.Link,\n deepExtend = kendo.deepExtend,\n Size = diagram.Size,\n Rect = diagram.Rect,\n Dictionary = diagram.Dictionary,\n Set = diagram.Set,\n HyperTree = diagram.Graph,\n Utils = diagram.Utils,\n Point = diagram.Point,\n EPSILON = 1e-06,\n DEG_TO_RAD = Math.PI / 180,\n contains = Utils.contains,\n grep = $.grep;\n\n /**\n * Base class for layout algorithms.\n * @type {*}\n */\n var LayoutBase = kendo.Class.extend({\n defaultOptions: {\n type: \"Tree\",\n subtype: \"Down\",\n roots: null,\n animate: false,\n //-------------------------------------------------------------------\n /**\n * Force-directed option: whether the motion of the nodes should be limited by the boundaries of the diagram surface.\n */\n limitToView: false,\n /**\n * Force-directed option: the amount of friction applied to the motion of the nodes.\n */\n friction: 0.9,\n /**\n * Force-directed option: the optimal distance between nodes (minimum energy).\n */\n nodeDistance: 50,\n /**\n * Force-directed option: the number of time things are being calculated.\n */\n iterations: 300,\n //-------------------------------------------------------------------\n /**\n * Tree option: the separation in one direction (depends on the subtype what direction this is).\n */\n horizontalSeparation: 90,\n /**\n * Tree option: the separation in the complementary direction (depends on the subtype what direction this is).\n */\n verticalSeparation: 50,\n\n //-------------------------------------------------------------------\n /**\n * Tip-over tree option: children-to-parent vertical distance.\n */\n underneathVerticalTopOffset: 15,\n /**\n * Tip-over tree option: children-to-parent horizontal distance.\n */\n underneathHorizontalOffset: 15,\n /**\n * Tip-over tree option: leaf-to-next-branch vertical distance.\n */\n underneathVerticalSeparation: 15,\n //-------------------------------------------------------------------\n /**\n * Settings object to organize the different components of the diagram in a grid layout structure\n */\n grid: {\n /**\n * The width of the grid in which components are arranged. Beyond this width a component will be on the next row.\n */\n width: 1500,\n /**\n * The left offset of the grid.\n */\n offsetX: 50,\n /**\n * The top offset of the grid.\n */\n offsetY: 50,\n /**\n * The horizontal padding within a cell of the grid where a single component resides.\n */\n componentSpacingX: 20,\n /**\n * The vertical padding within a cell of the grid where a single component resides.\n */\n componentSpacingY: 20\n },\n\n //-------------------------------------------------------------------\n /**\n * Layered option: the separation height/width between the layers.\n */\n layerSeparation: 50,\n /**\n * Layered option: how many rounds of shifting and fine-tuning.\n */\n layeredIterations: 2,\n /**\n * Tree-radial option: the angle at which the layout starts.\n */\n startRadialAngle: 0,\n /**\n * Tree-radial option: the angle at which the layout starts.\n */\n endRadialAngle: 360,\n /**\n * Tree-radial option: the separation between levels.\n */\n radialSeparation: 150,\n /**\n * Tree-radial option: the separation between the root and the first level.\n */\n radialFirstLevelSeparation: 200,\n /**\n * Tree-radial option: whether a virtual roots bing the components in one radial layout.\n */\n keepComponentsInOneRadialLayout: false,\n //-------------------------------------------------------------------\n\n // TODO: ensure to change this to false when containers are around\n ignoreContainers: true,\n layoutContainerChildren: false,\n ignoreInvisible: true,\n animateTransitions: false\n },\n init: function() {\n },\n\n /**\n * Organizes the components in a grid.\n * Returns the final set of nodes (not the Graph).\n * @param components\n */\n gridLayoutComponents: function(components) {\n if (!components) {\n throw \"No components supplied.\";\n }\n\n // calculate and cache the bounds of the components\n Utils.forEach(components, function(c) {\n c.calcBounds();\n });\n\n // order by decreasing width\n components.sort(function(a, b) {\n return b.bounds.width - a.bounds.width;\n });\n\n var maxWidth = this.options.grid.width,\n offsetX = this.options.grid.componentSpacingX,\n offsetY = this.options.grid.componentSpacingY,\n height = 0,\n startX = this.options.grid.offsetX,\n startY = this.options.grid.offsetY,\n x = startX,\n y = startY,\n i,\n resultLinkSet = [],\n resultNodeSet = [];\n\n while (components.length > 0) {\n if (x >= maxWidth) {\n // start a new row\n x = startX;\n y += height + offsetY;\n // reset the row height\n height = 0;\n }\n var component = components.pop();\n this.moveToOffset(component, new Point(x, y));\n for (i = 0; i < component.nodes.length; i++) {\n resultNodeSet.push(component.nodes[i]); // to be returned in the end\n }\n for (i = 0; i < component.links.length; i++) {\n resultLinkSet.push(component.links[i]);\n }\n var boundingRect = component.bounds;\n var currentHeight = boundingRect.height;\n if (currentHeight <= 0 || isNaN(currentHeight)) {\n currentHeight = 0;\n }\n var currentWidth = boundingRect.width;\n if (currentWidth <= 0 || isNaN(currentWidth)) {\n currentWidth = 0;\n }\n\n if (currentHeight >= height) {\n height = currentHeight;\n }\n x += currentWidth + offsetX;\n }\n\n return {\n nodes: resultNodeSet,\n links: resultLinkSet\n };\n },\n\n moveToOffset: function(component, p) {\n var i, j,\n bounds = component.bounds,\n deltax = p.x - bounds.x,\n deltay = p.y - bounds.y;\n\n for (i = 0; i < component.nodes.length; i++) {\n var node = component.nodes[i];\n var nodeBounds = node.bounds();\n if (nodeBounds.width === 0 && nodeBounds.height === 0 && nodeBounds.x === 0 && nodeBounds.y === 0) {\n nodeBounds = new Rect(0, 0, 0, 0);\n }\n nodeBounds.x += deltax;\n nodeBounds.y += deltay;\n node.bounds(nodeBounds);\n }\n for (i = 0; i < component.links.length; i++) {\n var link = component.links[i];\n if (link.points) {\n var newpoints = [];\n var points = link.points;\n for (j = 0; j < points.length; j++) {\n var pt = points[j];\n pt.x += deltax;\n pt.y += deltay;\n newpoints.push(pt);\n }\n link.points = newpoints;\n }\n }\n this.currentHorizontalOffset += bounds.width + this.options.grid.offsetX;\n return new Point(deltax, deltay);\n },\n\n transferOptions: function(options) {\n\n // Size options lead to stackoverflow and need special handling\n\n this.options = kendo.deepExtend({}, this.defaultOptions);\n if (Utils.isUndefined(options)) {\n return;\n }\n\n this.options = kendo.deepExtend(this.options, options || {});\n }\n });\n\n /**\n * The data bucket a hypertree holds in its nodes. *\n * @type {*}\n */\n /* var ContainerGraph = kendo.Class.extend({\n init: function (diagram) {\n this.diagram = diagram;\n this.graph = new Graph(diagram);\n this.container = null;\n this.containerNode = null;\n }\n\n });*/\n\n /**\n * Adapter between the diagram control and the graph representation. It converts shape and connections to nodes and edges taking into the containers and their collapsef state,\n * the visibility of items and more. If the layoutContainerChildren is true a hypertree is constructed which holds the hierarchy of containers and many conditions are analyzed\n * to investigate how the effective graph structure looks like and how the layout has to be performed.\n * @type {*}\n */\n var DiagramToHyperTreeAdapter = kendo.Class.extend({\n init: function(diagram) {\n\n /**\n * The mapping to/from the original nodes.\n * @type {Dictionary}\n */\n this.nodeMap = new Dictionary();\n\n /**\n * Gets the mapping of a shape to a container in case the shape sits in a collapsed container.\n * @type {Dictionary}\n */\n this.shapeMap = new Dictionary();\n\n /**\n * The nodes being mapped.\n * @type {Dictionary}\n */\n this.nodes = [];\n\n /**\n * The connections being mapped.\n * @type {Dictionary}\n */\n this.edges = [];\n\n // the mapping from an edge to all the connections it represents, this can be both because of multiple connections between\n // two shapes or because a container holds multiple connections to another shape or container.\n this.edgeMap = new Dictionary();\n\n /**\n * The resulting set of Nodes when the analysis has finished.\n * @type {Array}\n */\n this.finalNodes = [];\n\n /**\n * The resulting set of Links when the analysis has finished.\n * @type {Array}\n */\n this.finalLinks = [];\n\n /**\n * The items being omitted because of multigraph edges.\n * @type {Array}\n */\n this.ignoredConnections = [];\n\n /**\n * The items being omitted because of containers, visibility and other factors.\n * @type {Array}\n */\n this.ignoredShapes = [];\n\n /**\n * The map from a node to the partition/hypernode in which it sits. This hyperMap is null if 'options.layoutContainerChildren' is false.\n * @type {Dictionary}\n */\n this.hyperMap = new Dictionary();\n\n /**\n * The hypertree contains the hierarchy defined by the containers.\n * It's in essence a Graph of Graphs with a tree structure defined by the hierarchy of containers.\n * @type {HyperTree}\n */\n this.hyperTree = new Graph();\n\n /**\n * The resulting graph after conversion. Note that this does not supply the information contained in the\n * ignored connection and shape collections.\n * @type {null}\n */\n this.finalGraph = null;\n\n this.diagram = diagram;\n },\n\n /**\n * The hyperTree is used when the 'options.layoutContainerChildren' is true. It contains the hierarchy of containers whereby each node is a ContainerGraph.\n * This type of node has a Container reference to the container which holds the Graph items. There are three possible situations during the conversion process:\n * - Ignore the containers: the container are non-existent and only normal shapes are mapped. If a shape has a connection to a container it will be ignored as well\n * since there is no node mapped for the container.\n * - Do not ignore the containers and leave the content of the containers untouched: the top-level elements are being mapped and the children within a container are not altered.\n * - Do not ignore the containers and organize the content of the containers as well: the hypertree is constructed and there is a partitioning of all nodes and connections into the hypertree.\n * The only reason a connection or node is not being mapped might be due to the visibility, which includes the visibility change through a collapsed parent container.\n * @param options\n */\n convert: function(options) {\n\n if (Utils.isUndefined(this.diagram)) {\n throw \"No diagram to convert.\";\n }\n\n this.options = kendo.deepExtend({\n ignoreInvisible: true,\n ignoreContainers: true,\n layoutContainerChildren: false\n },\n options || {}\n );\n\n this.clear();\n // create the nodes which participate effectively in the graph analysis\n this._renormalizeShapes();\n\n // recreate the incoming and outgoing collections of each and every node\n this._renormalizeConnections();\n\n // export the resulting graph\n this.finalNodes = new Dictionary(this.nodes);\n this.finalLinks = new Dictionary(this.edges);\n\n this.finalGraph = new Graph();\n this.finalNodes.forEach(function(n) {\n this.finalGraph.addNode(n);\n }, this);\n this.finalLinks.forEach(function(l) {\n this.finalGraph.addExistingLink(l);\n }, this);\n return this.finalGraph;\n },\n\n /**\n * Maps the specified connection to an edge of the graph deduced from the given diagram.\n * @param connection\n * @returns {*}\n */\n mapConnection: function(connection) {\n return this.edgeMap.get(connection.id);\n },\n\n /**\n * Maps the specified shape to a node of the graph deduced from the given diagram.\n * @param shape\n * @returns {*}\n */\n mapShape: function(shape) {\n return this.nodeMap.get(shape.id);\n },\n\n /**\n * Gets the edge, if any, between the given nodes.\n * @param a\n * @param b\n */\n getEdge: function(a, b) {\n return Utils.first(a.links, function(link) {\n return link.getComplement(a) === b;\n });\n },\n\n /**\n * Clears all the collections used by the conversion process.\n */\n clear: function() {\n this.finalGraph = null;\n this.hyperTree = (!this.options.ignoreContainers && this.options.layoutContainerChildren) ? new HyperTree() : null;\n this.hyperMap = (!this.options.ignoreContainers && this.options.layoutContainerChildren) ? new Dictionary() : null;\n this.nodeMap = new Dictionary();\n this.shapeMap = new Dictionary();\n this.nodes = [];\n this.edges = [];\n this.edgeMap = new Dictionary();\n this.ignoredConnections = [];\n this.ignoredShapes = [];\n this.finalNodes = [];\n this.finalLinks = [];\n },\n\n /**\n * The path from a given ContainerGraph to the root (container).\n * @param containerGraph\n * @returns {Array}\n */\n listToRoot: function(containerGraph) {\n var list = [];\n var s = containerGraph.container;\n if (!s) {\n return list;\n }\n list.push(s);\n while (s.parentContainer) {\n s = s.parentContainer;\n list.push(s);\n }\n list.reverse();\n return list;\n },\n\n firstNonIgnorableContainer: function(shape) {\n\n if (shape.isContainer && !this._isIgnorableItem(shape)) {\n return shape;\n }\n return !shape.parentContainer ? null : this.firstNonIgnorableContainer(shape.parentContainer);\n },\n isContainerConnection: function(a, b) {\n if (a.isContainer && this.isDescendantOf(a, b)) {\n return true;\n }\n return b.isContainer && this.isDescendantOf(b, a);\n },\n\n /**\n * Returns true if the given shape is a direct child or a nested container child of the given container.\n * If the given container and shape are the same this will return false since a shape cannot be its own child.\n * @param scope\n * @param a\n * @returns {boolean}\n */\n isDescendantOf: function(scope, a) {\n if (!scope.isContainer) {\n throw \"Expecting a container.\";\n }\n if (scope === a) {\n return false;\n }\n if (contains(scope.children, a)) {\n return true;\n }\n var containers = [];\n for (var i = 0, len = scope.children.length; i < len; i++) {\n var c = scope.children[i];\n if (c.isContainer && this.isDescendantOf(c, a)) {\n containers.push(c);\n }\n }\n\n return containers.length > 0;\n },\n isIgnorableItem: function(shape) {\n if (this.options.ignoreInvisible) {\n if (shape.isCollapsed && this._isVisible(shape)) {\n return false;\n }\n if (!shape.isCollapsed && this._isVisible(shape)) {\n return false;\n }\n return true;\n }\n else {\n return shape.isCollapsed && !this._isTop(shape);\n }\n },\n\n /**\n * Determines whether the shape is or needs to be mapped to another shape. This occurs essentially when the shape sits in\n * a collapsed container hierarchy and an external connection needs a node endpoint. This node then corresponds to the mapped shape and is\n * necessarily a container in the parent hierarchy of the shape.\n * @param shape\n */\n isShapeMapped: function(shape) {\n return shape.isCollapsed && !this._isVisible(shape) && !this._isTop(shape);\n },\n\n leastCommonAncestor: function(a, b) {\n if (!a) {\n throw \"Parameter should not be null.\";\n }\n if (!b) {\n throw \"Parameter should not be null.\";\n }\n\n if (!this.hyperTree) {\n throw \"No hypertree available.\";\n }\n var al = this.listToRoot(a);\n var bl = this.listToRoot(b);\n var found = null;\n if (Utils.isEmpty(al) || Utils.isEmpty(bl)) {\n return this.hyperTree.root.data;\n }\n var xa = al[0];\n var xb = bl[0];\n var i = 0;\n while (xa === xb) {\n found = al[i];\n i++;\n if (i >= al.length || i >= bl.length) {\n break;\n }\n xa = al[i];\n xb = bl[i];\n }\n if (!found) {\n return this.hyperTree.root.data;\n }\n else {\n return grep(this.hyperTree.nodes, function(n) {\n return n.data.container === found;\n });\n }\n },\n /**\n * Determines whether the specified item is a top-level shape or container.\n * @param item\n * @returns {boolean}\n * @private\n */\n _isTop: function(item) {\n return !item.parentContainer;\n },\n\n /**\n * Determines iteratively (by walking up the container stack) whether the specified shape is visible.\n * This does NOT tell whether the item is not visible due to an explicit Visibility change or due to a collapse state.\n * @param shape\n * @returns {*}\n * @private\n */\n _isVisible: function(shape) {\n\n if (!shape.visible()) {\n return false;\n }\n return !shape.parentContainer ? shape.visible() : this._isVisible(shape.parentContainer);\n },\n\n _isCollapsed: function(shape) {\n\n if (shape.isContainer && shape.isCollapsed) {\n return true;\n }\n return shape.parentContainer && this._isCollapsed(shape.parentContainer);\n },\n\n /**\n * First part of the graph creation; analyzing the shapes and containers and deciding whether they should be mapped to a Node.\n * @private\n */\n _renormalizeShapes: function() {\n // add the nodes, the adjacency structure will be reconstructed later on\n if (this.options.ignoreContainers) {\n for (var i = 0, len = this.diagram.shapes.length; i < len; i++) {\n var shape = this.diagram.shapes[i];\n\n // if not visible (and ignoring the invisible ones) or a container we skip\n if ((this.options.ignoreInvisible && !this._isVisible(shape)) || shape.isContainer) {\n this.ignoredShapes.push(shape);\n continue;\n }\n var node = new Node(shape.id, shape);\n node.isVirtual = false;\n\n // the mapping will always contain singletons and the hyperTree will be null\n this.nodeMap.add(shape.id, node);\n this.nodes.push(node);\n }\n }\n else {\n throw \"Containers are not supported yet, but stay tuned.\";\n }\n },\n\n /**\n * Second part of the graph creation; analyzing the connections and deciding whether they should be mapped to an edge.\n * @private\n */\n _renormalizeConnections: function() {\n if (this.diagram.connections.length === 0) {\n return;\n }\n for (var i = 0, len = this.diagram.connections.length; i < len; i++) {\n var conn = this.diagram.connections[i];\n\n if (this.isIgnorableItem(conn)) {\n this.ignoredConnections.push(conn);\n continue;\n }\n\n var source = !conn.sourceConnector ? null : conn.sourceConnector.shape;\n var sink = !conn.targetConnector ? null : conn.targetConnector.shape;\n\n // no layout for floating connections\n if (!source || !sink) {\n this.ignoredConnections.push(conn);\n continue;\n }\n\n if (contains(this.ignoredShapes, source) && !this.shapeMap.containsKey(source)) {\n this.ignoredConnections.push(conn);\n continue;\n }\n if (contains(this.ignoredShapes, sink) && !this.shapeMap.containsKey(sink)) {\n this.ignoredConnections.push(conn);\n continue;\n }\n\n // if the endpoint sits in a collapsed container we need the container rather than the shape itself\n if (this.shapeMap.containsKey(source)) {\n source = this.shapeMap[source];\n }\n if (this.shapeMap.containsKey(sink)) {\n sink = this.shapeMap[sink];\n }\n\n var sourceNode = this.mapShape(source);\n var sinkNode = this.mapShape(sink);\n if ((sourceNode === sinkNode) || this.areConnectedAlready(sourceNode, sinkNode)) {\n this.ignoredConnections.push(conn);\n continue;\n }\n\n if (sourceNode === null || sinkNode === null) {\n throw \"A shape was not mapped to a node.\";\n }\n if (this.options.ignoreContainers) {\n // much like a floating connection here since at least one end is attached to a container\n if (sourceNode.isVirtual || sinkNode.isVirtual) {\n this.ignoredConnections.push(conn);\n continue;\n }\n var newEdge = new Link(sourceNode, sinkNode, conn.id, conn);\n\n this.edgeMap.add(conn.id, newEdge);\n this.edges.push(newEdge);\n }\n else {\n throw \"Containers are not supported yet, but stay tuned.\";\n }\n }\n },\n\n areConnectedAlready: function(n, m) {\n return Utils.any(this.edges, function(l) {\n return l.source === n && l.target === m || l.source === m && l.target === n;\n });\n }\n\n /**\n * Depth-first traversal of the given container.\n * @param container\n * @param action\n * @param includeStart\n * @private\n */\n /* _visitContainer: function (container, action, includeStart) {\n\n *//*if (container == null) throw new ArgumentNullException(\"container\");\n if (action == null) throw new ArgumentNullException(\"action\");\n if (includeStart) action(container);\n if (container.children.isEmpty()) return;\n foreach(\n var item\n in\n container.children.OfType < IShape > ()\n )\n {\n var childContainer = item\n as\n IContainerShape;\n if (childContainer != null) this.VisitContainer(childContainer, action);\n else action(item);\n }*//*\n }*/\n\n\n });\n\n /**\n * The classic spring-embedder (aka force-directed, Fruchterman-Rheingold, barycentric) algorithm.\n * http://en.wikipedia.org/wiki/Force-directed_graph_drawing\n * - Chapter 12 of Tamassia et al. \"Handbook of graph drawing and visualization\".\n * - Kobourov on preprint arXiv; http://arxiv.org/pdf/1201.3011.pdf\n * - Fruchterman and Rheingold in SOFTWARE-PRACTICE AND EXPERIENCE, VOL. 21(1 1), 1129-1164 (NOVEMBER 1991)\n * @type {*}\n */\n var SpringLayout = LayoutBase.extend({\n init: function(diagram) {\n var that = this;\n LayoutBase.fn.init.call(that);\n if (Utils.isUndefined(diagram)) {\n throw \"Diagram is not specified.\";\n }\n this.diagram = diagram;\n },\n\n layout: function(options) {\n\n this.transferOptions(options);\n\n var adapter = new DiagramToHyperTreeAdapter(this.diagram);\n var graph = adapter.convert(options);\n if (graph.isEmpty()) {\n return;\n }\n // split into connected components\n var components = graph.getConnectedComponents();\n if (Utils.isEmpty(components)) {\n return;\n }\n for (var i = 0; i < components.length; i++) {\n var component = components[i];\n this.layoutGraph(component, options);\n }\n var finalNodeSet = this.gridLayoutComponents(components);\n return new diagram.LayoutState(this.diagram, finalNodeSet);\n },\n\n layoutGraph: function(graph, options) {\n\n if (Utils.isDefined(options)) {\n this.transferOptions(options);\n }\n this.graph = graph;\n\n var initialTemperature = this.options.nodeDistance * 9;\n this.temperature = initialTemperature;\n\n var guessBounds = this._expectedBounds();\n this.width = guessBounds.width;\n this.height = guessBounds.height;\n\n for (var step = 0; step < this.options.iterations; step++) {\n this.refineStage = step >= this.options.iterations * 5 / 6;\n this.tick();\n // exponential cooldown\n this.temperature = this.refineStage ?\n initialTemperature / 30 :\n initialTemperature * (1 - step / (2 * this.options.iterations ));\n }\n },\n\n /**\n * Single iteration of the simulation.\n */\n tick: function() {\n var i;\n // collect the repulsive forces on each node\n for (i = 0; i < this.graph.nodes.length; i++) {\n this._repulsion(this.graph.nodes[i]);\n }\n\n // collect the attractive forces on each node\n for (i = 0; i < this.graph.links.length; i++) {\n this._attraction(this.graph.links[i]);\n }\n // update the positions\n for (i = 0; i < this.graph.nodes.length; i++) {\n var node = this.graph.nodes[i];\n var offset = Math.sqrt(node.dx * node.dx + node.dy * node.dy);\n if (offset === 0) {\n return;\n }\n node.x += Math.min(offset, this.temperature) * node.dx / offset;\n node.y += Math.min(offset, this.temperature) * node.dy / offset;\n if (this.options.limitToView) {\n node.x = Math.min(this.width, Math.max(node.width / 2, node.x));\n node.y = Math.min(this.height, Math.max(node.height / 2, node.y));\n }\n }\n },\n\n /**\n * Shakes the node away from its current position to escape the deadlock.\n * @param node A Node.\n * @private\n */\n _shake: function(node) {\n // just a simple polar neighborhood\n var rho = Math.random() * this.options.nodeDistance / 4;\n var alpha = Math.random() * 2 * Math.PI;\n node.x += rho * Math.cos(alpha);\n node.y -= rho * Math.sin(alpha);\n },\n\n /**\n * The typical Coulomb-Newton force law F=k/r^2\n * @remark This only works in dimensions less than three.\n * @param d\n * @param n A Node.\n * @param m Another Node.\n * @returns {number}\n * @private\n */\n _InverseSquareForce: function(d, n, m) {\n var force;\n if (!this.refineStage) {\n force = Math.pow(d, 2) / Math.pow(this.options.nodeDistance, 2);\n }\n else {\n var deltax = n.x - m.x;\n var deltay = n.y - m.y;\n\n var wn = n.width / 2;\n var hn = n.height / 2;\n var wm = m.width / 2;\n var hm = m.height / 2;\n\n force = (Math.pow(deltax, 2) / Math.pow(wn + wm + this.options.nodeDistance, 2)) + (Math.pow(deltay, 2) / Math.pow(hn + hm + this.options.nodeDistance, 2));\n }\n return force * 4 / 3;\n },\n\n /**\n * The typical Hooke force law F=kr^2\n * @param d\n * @param n\n * @param m\n * @returns {number}\n * @private\n */\n _SquareForce: function(d, n, m) {\n return 1 / this._InverseSquareForce(d, n, m);\n },\n\n _repulsion: function(n) {\n n.dx = 0;\n n.dy = 0;\n Utils.forEach(this.graph.nodes, function(m) {\n if (m === n) {\n return;\n }\n while (n.x === m.x && n.y === m.y) {\n this._shake(m);\n }\n var vx = n.x - m.x;\n var vy = n.y - m.y;\n var distance = Math.sqrt(vx * vx + vy * vy);\n var r = this._SquareForce(distance, n, m) * 2;\n n.dx += (vx / distance) * r;\n n.dy += (vy / distance) * r;\n }, this);\n },\n _attraction: function(link) {\n var t = link.target;\n var s = link.source;\n if (s === t) {\n // loops induce endless shakes\n return;\n }\n while (s.x === t.x && s.y === t.y) {\n this._shake(t);\n }\n\n var vx = s.x - t.x;\n var vy = s.y - t.y;\n var distance = Math.sqrt(vx * vx + vy * vy);\n\n var a = this._InverseSquareForce(distance, s, t) * 5;\n var dx = (vx / distance) * a;\n var dy = (vy / distance) * a;\n t.dx += dx;\n t.dy += dy;\n s.dx -= dx;\n s.dy -= dy;\n },\n\n /**\n * Calculates the expected bounds after layout.\n * @returns {*}\n * @private\n */\n _expectedBounds: function() {\n\n var size, N = this.graph.nodes.length, /*golden ration optimal?*/ ratio = 1.5, multiplier = 4;\n if (N === 0) {\n return size;\n }\n size = Utils.fold(this.graph.nodes, function(s, node) {\n var area = node.width * node.height;\n if (area > 0) {\n s += Math.sqrt(area);\n return s;\n }\n return 0;\n }, 0, this);\n var av = size / N;\n var squareSize = av * Math.ceil(Math.sqrt(N));\n var width = squareSize * Math.sqrt(ratio);\n var height = squareSize / Math.sqrt(ratio);\n return { width: width * multiplier, height: height * multiplier };\n }\n\n });\n\n var TreeLayoutProcessor = kendo.Class.extend({\n\n init: function(options) {\n this.center = null;\n this.options = options;\n },\n layout: function(treeGraph, root) {\n this.graph = treeGraph;\n if (!this.graph.nodes || this.graph.nodes.length === 0) {\n return;\n }\n\n if (!contains(this.graph.nodes, root)) {\n throw \"The given root is not in the graph.\";\n }\n\n this.center = root;\n this.graph.cacheRelationships();\n /* var nonull = this.graph.nodes.where(function (n) {\n return n.associatedShape != null;\n });*/\n\n // transfer the rects\n /*nonull.forEach(function (n) {\n n.Location = n.associatedShape.Position;\n n.NodeSize = n.associatedShape.ActualBounds.ToSize();\n }\n\n );*/\n\n // caching the children\n /* nonull.forEach(function (n) {\n n.children = n.getChildren();\n });*/\n\n this.layoutSwitch();\n\n // apply the layout to the actual visuals\n // nonull.ForEach(n => n.associatedShape.Position = n.Location);\n },\n\n layoutLeft: function(left) {\n this.setChildrenDirection(this.center, \"Left\", false);\n this.setChildrenLayout(this.center, \"Default\", false);\n var h = 0, w = 0, y, i, node;\n for (i = 0; i < left.length; i++) {\n node = left[i];\n node.TreeDirection = \"Left\";\n var s = this.measure(node, Size.Empty);\n w = Math.max(w, s.Width);\n h += s.height + this.options.verticalSeparation;\n }\n\n h -= this.options.verticalSeparation;\n var x = this.center.x - this.options.horizontalSeparation;\n y = this.center.y + ((this.center.height - h) / 2);\n for (i = 0; i < left.length; i++) {\n node = left[i];\n var p = new Point(x - node.Size.width, y);\n\n this.arrange(node, p);\n y += node.Size.height + this.options.verticalSeparation;\n }\n },\n\n layoutRight: function(right) {\n this.setChildrenDirection(this.center, \"Right\", false);\n this.setChildrenLayout(this.center, \"Default\", false);\n var h = 0, w = 0, y, i, node;\n for (i = 0; i < right.length; i++) {\n node = right[i];\n node.TreeDirection = \"Right\";\n var s = this.measure(node, Size.Empty);\n w = Math.max(w, s.Width);\n h += s.height + this.options.verticalSeparation;\n }\n\n h -= this.options.verticalSeparation;\n var x = this.center.x + this.options.horizontalSeparation + this.center.width;\n y = this.center.y + ((this.center.height - h) / 2);\n for (i = 0; i < right.length; i++) {\n node = right[i];\n var p = new Point(x, y);\n this.arrange(node, p);\n y += node.Size.height + this.options.verticalSeparation;\n }\n },\n\n layoutUp: function(up) {\n this.setChildrenDirection(this.center, \"Up\", false);\n this.setChildrenLayout(this.center, \"Default\", false);\n var w = 0, y, node, i;\n for (i = 0; i < up.length; i++) {\n node = up[i];\n node.TreeDirection = \"Up\";\n var s = this.measure(node, Size.Empty);\n w += s.width + this.options.horizontalSeparation;\n }\n\n w -= this.options.horizontalSeparation;\n var x = this.center.x + (this.center.width / 2) - (w / 2);\n\n // y = this.center.y -verticalSeparation -this.center.height/2 - h;\n for (i = 0; i < up.length; i++) {\n node = up[i];\n y = this.center.y - this.options.verticalSeparation - node.Size.height;\n var p = new Point(x, y);\n this.arrange(node, p);\n x += node.Size.width + this.options.horizontalSeparation;\n }\n },\n\n layoutDown: function(down) {\n var node, i;\n this.setChildrenDirection(this.center, \"Down\", false);\n this.setChildrenLayout(this.center, \"Default\", false);\n var w = 0, y;\n for (i = 0; i < down.length; i++) {\n node = down[i];\n node.treeDirection = \"Down\";\n var s = this.measure(node, Size.Empty);\n w += s.width + this.options.horizontalSeparation;\n }\n\n w -= this.options.horizontalSeparation;\n var x = this.center.x + (this.center.width / 2) - (w / 2);\n y = this.center.y + this.options.verticalSeparation + this.center.height;\n for (i = 0; i < down.length; i++) {\n node = down[i];\n var p = new Point(x, y);\n this.arrange(node, p);\n x += node.Size.width + this.options.horizontalSeparation;\n }\n },\n\n layoutRadialTree: function() {\n // var rmax = children.Aggregate(0D, (current, node) => Math.max(node.SectorAngle, current));\n this.setChildrenDirection(this.center, \"Radial\", false);\n this.setChildrenLayout(this.center, \"Default\", false);\n this.previousRoot = null;\n var startAngle = this.options.startRadialAngle * DEG_TO_RAD;\n var endAngle = this.options.endRadialAngle * DEG_TO_RAD;\n if (endAngle <= startAngle) {\n throw \"Final angle should not be less than the start angle.\";\n }\n\n this.maxDepth = 0;\n this.origin = new Point(this.center.x, this.center.y);\n this.calculateAngularWidth(this.center, 0);\n\n // perform the layout\n if (this.maxDepth > 0) {\n this.radialLayout(this.center, this.options.radialFirstLevelSeparation, startAngle, endAngle);\n }\n\n // update properties of the root node\n this.center.Angle = endAngle - startAngle;\n },\n\n tipOverTree: function(down, startFromLevel) {\n if (Utils.isUndefined(startFromLevel)) {\n startFromLevel = 0;\n }\n\n this.setChildrenDirection(this.center, \"Down\", false);\n this.setChildrenLayout(this.center, \"Default\", false);\n this.setChildrenLayout(this.center, \"Underneath\", false, startFromLevel);\n var w = 0, y, node, i;\n for (i = 0; i < down.length; i++) {\n node = down[i];\n\n // if (node.IsSpecial) continue;\n node.TreeDirection = \"Down\";\n var s = this.measure(node, Size.Empty);\n w += s.width + this.options.horizontalSeparation;\n }\n\n w -= this.options.horizontalSeparation;\n\n // putting the root in the center with respect to the whole diagram is not a nice result, let's put it with respect to the first level only\n w -= down[down.length - 1].width;\n w += down[down.length - 1].associatedShape.bounds().width;\n\n var x = this.center.x + (this.center.width / 2) - (w / 2);\n y = this.center.y + this.options.verticalSeparation + this.center.height;\n for (i = 0; i < down.length; i++) {\n node = down[i];\n // if (node.IsSpecial) continue;\n var p = new Point(x, y);\n this.arrange(node, p);\n x += node.Size.width + this.options.horizontalSeparation;\n }\n\n /*//let's place the special node, assuming there is only one\n if (down.Count(n => n.IsSpecial) > 0)\n {\n var special = (from n in down where n.IsSpecial select n).First();\n if (special.Children.Count > 0)\n throw new DiagramException(\"The 'special' element should not have children.\");\n special.Data.Location = new Point(Center.Data.Location.X + Center.AssociatedShape.BoundingRectangle.Width + this.options.HorizontalSeparation, Center.Data.Location.Y);\n }*/\n },\n calculateAngularWidth: function(n, d) {\n if (d > this.maxDepth) {\n this.maxDepth = d;\n }\n\n var aw = 0, w = 1000, h = 1000, diameter = d === 0 ? 0 : Math.sqrt((w * w) + (h * h)) / d;\n\n if (n.children.length > 0) {\n // eventually with n.IsExpanded\n for (var i = 0, len = n.children.length; i < len; i++) {\n var child = n.children[i];\n aw += this.calculateAngularWidth(child, d + 1);\n }\n aw = Math.max(diameter, aw);\n }\n else {\n aw = diameter;\n }\n\n n.sectorAngle = aw;\n return aw;\n },\n sortChildren: function(n) {\n var basevalue = 0, i;\n\n // update basevalue angle for node ordering\n if (n.parents.length > 1) {\n throw \"Node is not part of a tree.\";\n }\n var p = n.parents[0];\n if (p) {\n var pl = new Point(p.x, p.y);\n var nl = new Point(n.x, n.y);\n basevalue = this.normalizeAngle(Math.atan2(pl.y - nl.y, pl.x - nl.x));\n }\n\n var count = n.children.length;\n if (count === 0) {\n return null;\n }\n\n var angle = [];\n var idx = [];\n\n for (i = 0; i < count; ++i) {\n var c = n.children[i];\n var l = new Point(c.x, c.y);\n idx[i] = i;\n angle[i] = this.normalizeAngle(-basevalue + Math.atan2(l.y - l.y, l.x - l.x));\n }\n\n Utils.bisort(angle, idx);\n var col = []; // list of nodes\n var children = n.children;\n for (i = 0; i < count; ++i) {\n col.push(children[idx[i]]);\n }\n\n return col;\n },\n\n normalizeAngle: function(angle) {\n while (angle > Math.PI * 2) {\n angle -= 2 * Math.PI;\n }\n while (angle < 0) {\n angle += Math.PI * 2;\n }\n return angle;\n },\n radialLayout: function(node, radius, startAngle, endAngle) {\n var deltaTheta = endAngle - startAngle;\n var deltaThetaHalf = deltaTheta / 2.0;\n var parentSector = node.sectorAngle;\n var fraction = 0;\n var sorted = this.sortChildren(node);\n for (var i = 0, len = sorted.length; i < len; i++) {\n var childNode = sorted[i];\n var cp = childNode;\n var childAngleFraction = cp.sectorAngle / parentSector;\n if (childNode.children.length > 0) {\n this.radialLayout(childNode,\n radius + this.options.radialSeparation,\n startAngle + (fraction * deltaTheta),\n startAngle + ((fraction + childAngleFraction) * deltaTheta));\n }\n\n this.setPolarLocation(childNode, radius, startAngle + (fraction * deltaTheta) + (childAngleFraction * deltaThetaHalf));\n cp.angle = childAngleFraction * deltaTheta;\n fraction += childAngleFraction;\n }\n },\n setPolarLocation: function(node, radius, angle) {\n node.x = this.origin.x + (radius * Math.cos(angle));\n node.y = this.origin.y + (radius * Math.sin(angle));\n node.BoundingRectangle = new Rect(node.x, node.y, node.width, node.height);\n },\n\n /**\n * Sets the children direction recursively.\n * @param node\n * @param direction\n * @param includeStart\n */\n setChildrenDirection: function(node, direction, includeStart) {\n var rootDirection = node.treeDirection;\n this.graph.depthFirstTraversal(node, function(n) {\n n.treeDirection = direction;\n });\n if (!includeStart) {\n node.treeDirection = rootDirection;\n }\n },\n\n /**\n * Sets the children layout recursively.\n * @param node\n * @param layout\n * @param includeStart\n * @param startFromLevel\n */\n setChildrenLayout: function(node, layout, includeStart, startFromLevel) {\n if (Utils.isUndefined(startFromLevel)) {\n startFromLevel = 0;\n }\n var rootLayout = node.childrenLayout;\n if (startFromLevel > 0) {\n // assign levels to the Node.Level property\n this.graph.assignLevels(node);\n\n // assign the layout on the condition that the level is at least the 'startFromLevel'\n this.graph.depthFirstTraversal(\n node, function(s) {\n if (s.level >= startFromLevel + 1) {\n s.childrenLayout = layout;\n }\n }\n );\n }\n else {\n this.graph.depthFirstTraversal(node, function(s) {\n s.childrenLayout = layout;\n });\n\n // if the start should not be affected we put the state back\n if (!includeStart) {\n node.childrenLayout = rootLayout;\n }\n }\n },\n\n /**\n * Returns the actual size of the node. The given size is the allowed space wherein the node can lay out itself.\n * @param node\n * @param givenSize\n * @returns {Size}\n */\n measure: function(node, givenSize) {\n var w = 0, h = 0, s;\n var result = new Size(0, 0);\n if (!node) {\n throw \"\";\n }\n var b = node.associatedShape.bounds();\n var shapeWidth = b.width;\n var shapeHeight = b.height;\n if (node.parents.length !== 1) {\n throw \"Node not in a spanning tree.\";\n }\n\n var parent = node.parents[0];\n if (node.treeDirection === \"Undefined\") {\n node.treeDirection = parent.treeDirection;\n }\n\n if (Utils.isEmpty(node.children)) {\n result = new Size(\n Math.abs(shapeWidth) < EPSILON ? 50 : shapeWidth,\n Math.abs(shapeHeight) < EPSILON ? 25 : shapeHeight);\n }\n else if (node.children.length === 1) {\n switch (node.treeDirection) {\n case \"Radial\":\n s = this.measure(node.children[0], givenSize); // child size\n w = shapeWidth + (this.options.radialSeparation * Math.cos(node.AngleToParent)) + s.width;\n h = shapeHeight + Math.abs(this.options.radialSeparation * Math.sin(node.AngleToParent)) + s.height;\n break;\n case \"Left\":\n case \"Right\":\n switch (node.childrenLayout) {\n\n case \"TopAlignedWithParent\":\n break;\n\n case \"BottomAlignedWithParent\":\n break;\n\n case \"Underneath\":\n s = this.measure(node.children[0], givenSize);\n w = shapeWidth + s.width + this.options.underneathHorizontalOffset;\n h = shapeHeight + this.options.underneathVerticalTopOffset + s.height;\n break;\n\n case \"Default\":\n s = this.measure(node.children[0], givenSize);\n w = shapeWidth + this.options.horizontalSeparation + s.width;\n h = Math.max(shapeHeight, s.height);\n break;\n\n default:\n throw \"Unhandled TreeDirection in the Radial layout measuring.\";\n }\n break;\n case \"Up\":\n case \"Down\":\n switch (node.childrenLayout) {\n\n case \"TopAlignedWithParent\":\n case \"BottomAlignedWithParent\":\n break;\n\n case \"Underneath\":\n s = this.measure(node.children[0], givenSize);\n w = Math.max(shapeWidth, s.width + this.options.underneathHorizontalOffset);\n h = shapeHeight + this.options.underneathVerticalTopOffset + s.height;\n break;\n\n case \"Default\":\n s = this.measure(node.children[0], givenSize);\n h = shapeHeight + this.options.verticalSeparation + s.height;\n w = Math.max(shapeWidth, s.width);\n break;\n\n default:\n throw \"Unhandled TreeDirection in the Down layout measuring.\";\n }\n break;\n default:\n throw \"Unhandled TreeDirection in the layout measuring.\";\n }\n\n result = new Size(w, h);\n }\n else {\n var i, childNode;\n switch (node.treeDirection) {\n case \"Left\":\n case \"Right\":\n switch (node.childrenLayout) {\n\n case \"TopAlignedWithParent\":\n case \"BottomAlignedWithParent\":\n break;\n\n case \"Underneath\":\n w = shapeWidth;\n h = shapeHeight + this.options.underneathVerticalTopOffset;\n for (i = 0; i < node.children.length; i++) {\n childNode = node.children[i];\n s = this.measure(childNode, givenSize);\n w = Math.max(w, s.width + this.options.underneathHorizontalOffset);\n h += s.height + this.options.underneathVerticalSeparation;\n }\n\n h -= this.options.underneathVerticalSeparation;\n break;\n\n case \"Default\":\n w = shapeWidth;\n h = 0;\n for (i = 0; i < node.children.length; i++) {\n childNode = node.children[i];\n s = this.measure(childNode, givenSize);\n w = Math.max(w, shapeWidth + this.options.horizontalSeparation + s.width);\n h += s.height + this.options.verticalSeparation;\n }\n h -= this.options.verticalSeparation;\n break;\n\n default:\n throw \"Unhandled TreeDirection in the Right layout measuring.\";\n }\n\n break;\n case \"Up\":\n case \"Down\":\n\n switch (node.childrenLayout) {\n\n case \"TopAlignedWithParent\":\n case \"BottomAlignedWithParent\":\n break;\n\n case \"Underneath\":\n w = shapeWidth;\n h = shapeHeight + this.options.underneathVerticalTopOffset;\n for (i = 0; i < node.children.length; i++) {\n childNode = node.children[i];\n s = this.measure(childNode, givenSize);\n w = Math.max(w, s.width + this.options.underneathHorizontalOffset);\n h += s.height + this.options.underneathVerticalSeparation;\n }\n\n h -= this.options.underneathVerticalSeparation;\n break;\n\n case \"Default\":\n w = 0;\n h = 0;\n for (i = 0; i < node.children.length; i++) {\n childNode = node.children[i];\n s = this.measure(childNode, givenSize);\n w += s.width + this.options.horizontalSeparation;\n h = Math.max(h, s.height + this.options.verticalSeparation + shapeHeight);\n }\n\n w -= this.options.horizontalSeparation;\n break;\n\n default:\n throw \"Unhandled TreeDirection in the Down layout measuring.\";\n }\n\n break;\n default:\n throw \"Unhandled TreeDirection in the layout measuring.\";\n }\n\n result = new Size(w, h);\n }\n\n node.SectorAngle = Math.sqrt((w * w / 4) + (h * h / 4));\n node.Size = result;\n return result;\n },\n arrange: function(n, p) {\n var i, pp, child, node, childrenwidth, b = n.associatedShape.bounds();\n var shapeWidth = b.width;\n var shapeHeight = b.height;\n if (Utils.isEmpty(n.children)) {\n n.x = p.x;\n n.y = p.y;\n n.BoundingRectangle = new Rect(p.x, p.y, shapeWidth, shapeHeight);\n }\n else {\n var x, y;\n var selfLocation;\n switch (n.treeDirection) {\n case \"Left\":\n switch (n.childrenLayout) {\n case \"TopAlignedWithParent\":\n case \"BottomAlignedWithParent\":\n break;\n\n case \"Underneath\":\n selfLocation = p;\n n.x = selfLocation.x;\n n.y = selfLocation.y;\n n.BoundingRectangle = new Rect(n.x, n.y, n.width, n.height);\n y = p.y + shapeHeight + this.options.underneathVerticalTopOffset;\n for (i = 0; i < node.children.length; i++) {\n node = node.children[i];\n x = selfLocation.x - node.associatedShape.width - this.options.underneathHorizontalOffset;\n pp = new Point(x, y);\n this.arrange(node, pp);\n y += node.Size.height + this.options.underneathVerticalSeparation;\n }\n break;\n\n case \"Default\":\n selfLocation = new Point(p.x + n.Size.width - shapeWidth, p.y + ((n.Size.height - shapeHeight) / 2));\n n.x = selfLocation.x;\n n.y = selfLocation.y;\n n.BoundingRectangle = new Rect(n.x, n.y, n.width, n.height);\n x = selfLocation.x - this.options.horizontalSeparation; // alignment of children\n y = p.y;\n for (i = 0; i < n.children.length; i++) {\n node = n.children[i];\n pp = new Point(x - node.Size.width, y);\n this.arrange(node, pp);\n y += node.Size.height + this.options.verticalSeparation;\n }\n break;\n\n default:\n throw \"Unsupported TreeDirection\";\n }\n\n break;\n case \"Right\":\n switch (n.childrenLayout) {\n case \"TopAlignedWithParent\":\n case \"BottomAlignedWithParent\":\n break;\n\n case \"Underneath\":\n selfLocation = p;\n n.x = selfLocation.x;\n n.y = selfLocation.y;\n n.BoundingRectangle = new Rect(n.x, n.y, n.width, n.height);\n x = p.x + shapeWidth + this.options.underneathHorizontalOffset;\n\n // alignment of children left-underneath the parent\n y = p.y + shapeHeight + this.options.underneathVerticalTopOffset;\n for (i = 0; i < n.children.length; i++) {\n node = n.children[i];\n pp = new Point(x, y);\n this.arrange(node, pp);\n y += node.Size.height + this.options.underneathVerticalSeparation;\n }\n\n break;\n\n case \"Default\":\n selfLocation = new Point(p.x, p.y + ((n.Size.height - shapeHeight) / 2));\n n.x = selfLocation.x;\n n.y = selfLocation.y;\n n.BoundingRectangle = new Rect(n.x, n.y, n.width, n.height);\n x = p.x + shapeWidth + this.options.horizontalSeparation; // alignment of children\n y = p.y;\n for (i = 0; i < n.children.length; i++) {\n node = n.children[i];\n pp = new Point(x, y);\n this.arrange(node, pp);\n y += node.Size.height + this.options.verticalSeparation;\n }\n break;\n\n default:\n throw \"Unsupported TreeDirection\";\n }\n\n break;\n case \"Up\":\n selfLocation = new Point(p.x + ((n.Size.width - shapeWidth) / 2), p.y + n.Size.height - shapeHeight);\n n.x = selfLocation.x;\n n.y = selfLocation.y;\n n.BoundingRectangle = new Rect(n.x, n.y, n.width, n.height);\n if (Math.abs(selfLocation.x - p.x) < EPSILON) {\n childrenwidth = 0;\n // means there is an aberration due to the oversized Element with respect to the children\n for (i = 0; i < n.children.length; i++) {\n child = n.children[i];\n childrenwidth += child.Size.width + this.options.horizontalSeparation;\n }\n childrenwidth -= this.options.horizontalSeparation;\n x = p.x + ((shapeWidth - childrenwidth) / 2);\n }\n else {\n x = p.x;\n }\n\n for (i = 0; i < n.children.length; i++) {\n node = n.children[i];\n y = selfLocation.y - this.options.verticalSeparation - node.Size.height;\n pp = new Point(x, y);\n this.arrange(node, pp);\n x += node.Size.width + this.options.horizontalSeparation;\n }\n break;\n\n case \"Down\":\n\n switch (n.childrenLayout) {\n case \"TopAlignedWithParent\":\n case \"BottomAlignedWithParent\":\n break;\n case \"Underneath\":\n selfLocation = p;\n n.x = selfLocation.x;\n n.y = selfLocation.y;\n n.BoundingRectangle = new Rect(n.x, n.y, n.width, n.height);\n x = p.x + this.options.underneathHorizontalOffset; // alignment of children left-underneath the parent\n y = p.y + shapeHeight + this.options.underneathVerticalTopOffset;\n for (i = 0; i < n.children.length; i++) {\n node = n.children[i];\n pp = new Point(x, y);\n this.arrange(node, pp);\n y += node.Size.height + this.options.underneathVerticalSeparation;\n }\n break;\n\n case \"Default\":\n selfLocation = new Point(p.x + ((n.Size.width - shapeWidth) / 2), p.y);\n n.x = selfLocation.x;\n n.y = selfLocation.y;\n n.BoundingRectangle = new Rect(n.x, n.y, n.width, n.height);\n if (Math.abs(selfLocation.x - p.x) < EPSILON) {\n childrenwidth = 0;\n // means there is an aberration due to the oversized Element with respect to the children\n for (i = 0; i < n.children.length; i++) {\n child = n.children[i];\n childrenwidth += child.Size.width + this.options.horizontalSeparation;\n }\n\n childrenwidth -= this.options.horizontalSeparation;\n x = p.x + ((shapeWidth - childrenwidth) / 2);\n }\n else {\n x = p.x;\n }\n\n for (i = 0; i < n.children.length; i++) {\n node = n.children[i];\n y = selfLocation.y + this.options.verticalSeparation + shapeHeight;\n pp = new Point(x, y);\n this.arrange(node, pp);\n x += node.Size.width + this.options.horizontalSeparation;\n }\n break;\n\n default:\n throw \"Unsupported TreeDirection\";\n }\n break;\n\n case \"None\":\n break;\n\n default:\n throw \"Unsupported TreeDirection\";\n }\n }\n },\n layoutSwitch: function() {\n if (!this.center) {\n return;\n }\n\n if (Utils.isEmpty(this.center.children)) {\n return;\n }\n\n var type = this.options.subtype;\n if (Utils.isUndefined(type)) {\n type = \"Down\";\n }\n var single, male, female, leftcount;\n var children = this.center.children;\n switch (type.toLowerCase()) {\n case \"radial\":\n case \"radialtree\":\n this.layoutRadialTree();\n break;\n\n case \"mindmaphorizontal\":\n case \"mindmap\":\n single = this.center.children;\n\n if (this.center.children.length === 1) {\n this.layoutRight(single);\n }\n else {\n // odd number will give one more at the right\n leftcount = children.length / 2;\n male = grep(this.center.children, function(n) {\n return Utils.indexOf(children, n) < leftcount;\n });\n female = grep(this.center.children, function(n) {\n return Utils.indexOf(children, n) >= leftcount;\n });\n\n this.layoutLeft(male);\n this.layoutRight(female);\n }\n break;\n\n case \"mindmapvertical\":\n single = this.center.children;\n\n if (this.center.children.length === 1) {\n this.layoutDown(single);\n }\n else {\n // odd number will give one more at the right\n leftcount = children.length / 2;\n male = grep(this.center.children, function(n) {\n return Utils.indexOf(children, n) < leftcount;\n });\n female = grep(this.center.children, function(n) {\n return Utils.indexOf(children, n) >= leftcount;\n });\n this.layoutUp(male);\n this.layoutDown(female);\n }\n break;\n\n case \"right\":\n this.layoutRight(this.center.children);\n break;\n\n case \"left\":\n this.layoutLeft(this.center.children);\n break;\n\n case \"up\":\n case \"bottom\":\n this.layoutUp(this.center.children);\n break;\n\n case \"down\":\n case \"top\":\n this.layoutDown(this.center.children);\n break;\n\n case \"tipover\":\n case \"tipovertree\":\n if (this.options.tipOverTreeStartLevel < 0) {\n throw \"The tip-over level should be a positive integer.\";\n }\n this.tipOverTree(this.center.children, this.options.tipOverTreeStartLevel);\n break;\n\n case \"undefined\":\n case \"none\":\n break;\n }\n }\n });\n\n /**\n * The various tree layout algorithms.\n * @type {*}\n */\n var TreeLayout = LayoutBase.extend({\n init: function(diagram) {\n var that = this;\n LayoutBase.fn.init.call(that);\n if (Utils.isUndefined(diagram)) {\n throw \"No diagram specified.\";\n }\n this.diagram = diagram;\n },\n\n /**\n * Arranges the diagram in a tree-layout with the specified options and tree subtype.\n */\n layout: function(options) {\n\n this.transferOptions(options);\n\n // transform the diagram into a Graph\n var adapter = new DiagramToHyperTreeAdapter(this.diagram);\n\n /**\n * The Graph reduction from the given diagram.\n * @type {*}\n */\n this.graph = adapter.convert();\n\n var finalNodeSet = this.layoutComponents();\n\n // note that the graph contains the original data and\n // the components are another instance of nodes referring to the same set of shapes\n return new diagram.LayoutState(this.diagram, finalNodeSet);\n },\n\n layoutComponents: function() {\n if (this.graph.isEmpty()) {\n return;\n }\n\n // split into connected components\n var components = this.graph.getConnectedComponents();\n if (Utils.isEmpty(components)) {\n return;\n }\n\n var layout = new TreeLayoutProcessor(this.options);\n var trees = [];\n // find a spanning tree for each component\n for (var i = 0; i < components.length; i++) {\n var component = components[i];\n\n var treeGraph = this.getTree(component);\n if (!treeGraph) {\n throw \"Failed to find a spanning tree for the component.\";\n }\n var root = treeGraph.root;\n var tree = treeGraph.tree;\n layout.layout(tree, root);\n\n trees.push(tree);\n }\n\n return this.gridLayoutComponents(trees);\n\n },\n\n /**\n * Gets a spanning tree (and root) for the given graph.\n * Ensure that the given graph is connected!\n * @param graph\n * @returns {*} A literal object consisting of the found root and the spanning tree.\n */\n getTree: function(graph) {\n var root = null;\n if (this.options.roots && this.options.roots.length > 0) {\n for (var i = 0, len = graph.nodes.length; i < len; i++) {\n var node = graph.nodes[i];\n for (var j = 0; j < this.options.roots.length; j++) {\n var givenRootShape = this.options.roots[j];\n if (givenRootShape === node.associatedShape) {\n root = node;\n break;\n }\n }\n }\n }\n if (!root) {\n // finds the most probable root on the basis of the longest path in the component\n root = graph.root();\n // should not happen really\n if (!root) {\n throw \"Unable to find a root for the tree.\";\n }\n }\n return this.getTreeForRoot(graph, root);\n },\n\n getTreeForRoot: function(graph, root) {\n\n var tree = graph.getSpanningTree(root);\n if (Utils.isUndefined(tree) || tree.isEmpty()) {\n return null;\n }\n return {\n tree: tree,\n root: tree.root\n };\n }\n\n });\n\n /**\n * The Sugiyama aka layered layout algorithm.\n * @type {*}\n */\n var LayeredLayout = LayoutBase.extend({\n init: function(diagram) {\n var that = this;\n LayoutBase.fn.init.call(that);\n if (Utils.isUndefined(diagram)) {\n throw \"Diagram is not specified.\";\n }\n this.diagram = diagram;\n },\n\n layout: function(options) {\n\n this.transferOptions(options);\n\n var adapter = new DiagramToHyperTreeAdapter(this.diagram);\n var graph = adapter.convert(options);\n if (graph.isEmpty()) {\n return;\n }\n // split into connected components\n var components = graph.getConnectedComponents();\n if (Utils.isEmpty(components)) {\n return;\n }\n for (var i = 0; i < components.length; i++) {\n var component = components[i];\n this.layoutGraph(component, options);\n }\n var finalNodeSet = this.gridLayoutComponents(components);\n return new diagram.LayoutState(this.diagram, finalNodeSet);\n\n },\n\n /**\n * Initializes the runtime data properties of the layout.\n * @private\n */\n _initRuntimeProperties: function() {\n for (var k = 0; k < this.graph.nodes.length; k++) {\n var node = this.graph.nodes[k];\n node.layer = -1;\n node.downstreamLinkCount = 0;\n node.upstreamLinkCount = 0;\n\n node.isVirtual = false;\n\n node.uBaryCenter = 0.0;\n node.dBaryCenter = 0.0;\n\n node.upstreamPriority = 0;\n node.downstreamPriority = 0;\n\n node.gridPosition = 0;\n }\n },\n _prepare: function(graph) {\n var current = [], i, l, link;\n\n // defines a mapping of a node to the layer index\n var layerMap = new Dictionary();\n var layerCount = 0;\n var targetLayer, next, target;\n\n Utils.forEach(graph.nodes, function(node) {\n if (node.incoming.length === 0) {\n layerMap.set(node, 0);\n current.push(node);\n }\n });\n\n while (current.length > 0) {\n next = current.shift();\n for (i = 0; i < next.outgoing.length; i++) {\n link = next.outgoing[i];\n target = link.target;\n\n if (layerMap.containsKey(target)) {\n targetLayer = Math.max(layerMap.get(next) + 1, layerMap.get(target));\n } else {\n targetLayer = layerMap.get(next) + 1;\n }\n layerMap.set(target, targetLayer);\n if (targetLayer > layerCount) {\n layerCount = targetLayer;\n }\n\n if (!contains(current, target)) {\n current.push(target);\n }\n }\n }\n\n var sortedNodes = layerMap.keys();\n\n sortedNodes.sort(function(o1, o2) {\n var o1layer = layerMap.get(o1);\n var o2layer = layerMap.get(o2);\n return Utils.sign(o2layer - o1layer);\n });\n\n for (var n = 0; n < sortedNodes.length; ++n) {\n var node = sortedNodes[n];\n var minLayer = Number.MAX_VALUE;\n\n if (node.outgoing.length === 0) {\n continue;\n }\n\n for (l = 0; l < node.outgoing.length; ++l) {\n link = node.outgoing[l];\n minLayer = Math.min(minLayer, layerMap.get(link.target));\n }\n\n if (minLayer > 1) {\n layerMap.set(node, minLayer - 1);\n }\n }\n\n this.layers = [];\n var layer;\n for (i = 0; i < layerCount + 1; i++) {\n layer = [];\n layer.linksTo = {};\n this.layers.push(layer);\n }\n\n layerMap.forEach(function(node, layer) {\n node.layer = layer;\n this.layers[layer].push(node);\n }, this);\n\n // set initial grid positions\n for (l = 0; l < this.layers.length; l++) {\n layer = this.layers[l];\n for (i = 0; i < layer.length; i++) {\n layer[i].gridPosition = i;\n }\n }\n },\n /**\n * Performs the layout of a single component.\n */\n layoutGraph: function(graph, options) {\n if (Utils.isUndefined(graph)) {\n throw \"No graph given or graph analysis of the diagram failed.\";\n }\n if (Utils.isDefined(options)) {\n this.transferOptions(options);\n }\n this.graph = graph;\n\n // sets unique indices on the nodes\n graph.setItemIndices();\n\n // ensures no cycles present for this layout\n var reversedEdges = graph.makeAcyclic();\n\n // define the runtime props being used by the layout algorithm\n this._initRuntimeProperties();\n\n this._prepare(graph, options);\n\n this._dummify();\n\n this._optimizeCrossings();\n\n this._swapPairs();\n\n this.arrangeNodes();\n\n this._moveThingsAround();\n\n this._dedummify();\n\n // re-reverse the links which were switched earlier\n Utils.forEach(reversedEdges, function(e) {\n if (e.points) {\n e.points.reverse();\n }\n });\n },\n\n setMinDist: function(m, n, minDist) {\n var l = m.layer;\n var i = m.layerIndex;\n this.minDistances[l][i] = minDist;\n },\n\n getMinDist: function(m, n) {\n var dist = 0,\n i1 = m.layerIndex,\n i2 = n.layerIndex,\n l = m.layer,\n min = Math.min(i1, i2),\n max = Math.max(i1, i2);\n // use Sum()?\n for (var k = min; k < max; ++k) {\n dist += this.minDistances[l][k];\n }\n return dist;\n },\n\n placeLeftToRight: function(leftClasses) {\n var leftPos = new Dictionary(), n, node;\n for (var c = 0; c < this.layers.length; ++c) {\n var classNodes = leftClasses[c];\n if (!classNodes) {\n continue;\n }\n\n for (n = 0; n < classNodes.length; n++) {\n node = classNodes[n];\n if (!leftPos.containsKey(node)) {\n this.placeLeft(node, leftPos, c);\n }\n }\n\n // adjust class\n var d = Number.POSITIVE_INFINITY;\n for (n = 0; n < classNodes.length; n++) {\n node = classNodes[n];\n var rightSibling = this.rightSibling(node);\n if (rightSibling && this.nodeLeftClass.get(rightSibling) !== c) {\n d = Math.min(d, leftPos.get(rightSibling) - leftPos.get(node) - this.getMinDist(node, rightSibling));\n }\n }\n if (d === Number.POSITIVE_INFINITY) {\n var D = [];\n for (n = 0; n < classNodes.length; n++) {\n node = classNodes[n];\n var neighbors = [];\n Utils.addRange(neighbors, this.upNodes.get(node));\n Utils.addRange(neighbors, this.downNodes.get(node));\n\n for (var e = 0; e < neighbors.length; e++) {\n var neighbor = neighbors[e];\n if (this.nodeLeftClass.get(neighbor) < c) {\n D.push(leftPos.get(neighbor) - leftPos.get(node));\n }\n }\n }\n D.sort();\n if (D.length === 0) {\n d = 0;\n }\n else if (D.length % 2 === 1) {\n d = D[this.intDiv(D.length, 2)];\n }\n else {\n d = (D[this.intDiv(D.length, 2) - 1] + D[this.intDiv(D.length, 2)]) / 2;\n }\n }\n for (n = 0; n < classNodes.length; n++) {\n node = classNodes[n];\n leftPos.set(node, leftPos.get(node) + d);\n }\n }\n return leftPos;\n },\n\n placeRightToLeft: function(rightClasses) {\n var rightPos = new Dictionary(), n, node;\n for (var c = 0; c < this.layers.length; ++c) {\n var classNodes = rightClasses[c];\n if (!classNodes) {\n continue;\n }\n\n for (n = 0; n < classNodes.length; n++) {\n node = classNodes[n];\n if (!rightPos.containsKey(node)) {\n this.placeRight(node, rightPos, c);\n }\n }\n\n // adjust class\n var d = Number.NEGATIVE_INFINITY;\n for (n = 0; n < classNodes.length; n++) {\n node = classNodes[n];\n var leftSibling = this.leftSibling(node);\n if (leftSibling && this.nodeRightClass.get(leftSibling) !== c) {\n d = Math.max(d, rightPos.get(leftSibling) - rightPos.get(node) + this.getMinDist(leftSibling, node));\n }\n }\n if (d === Number.NEGATIVE_INFINITY) {\n var D = [];\n for (n = 0; n < classNodes.length; n++) {\n node = classNodes[n];\n var neighbors = [];\n Utils.addRange(neighbors, this.upNodes.get(node));\n Utils.addRange(neighbors, this.downNodes.get(node));\n\n for (var e = 0; e < neighbors.length; e++) {\n var neighbor = neighbors[e];\n if (this.nodeRightClass.get(neighbor) < c) {\n D.push(rightPos.get(node) - rightPos.get(neighbor));\n }\n }\n }\n D.sort();\n if (D.length === 0) {\n d = 0;\n }\n else if (D.length % 2 === 1) {\n d = D[this.intDiv(D.length, 2)];\n }\n else {\n d = (D[this.intDiv(D.length, 2) - 1] + D[this.intDiv(D.length, 2)]) / 2;\n }\n }\n for (n = 0; n < classNodes.length; n++) {\n node = classNodes[n];\n rightPos.set(node, rightPos.get(node) + d);\n }\n }\n return rightPos;\n },\n\n _getLeftWing: function() {\n var leftWing = { value: null };\n var result = this.computeClasses(leftWing, 1);\n this.nodeLeftClass = leftWing.value;\n return result;\n },\n\n _getRightWing: function() {\n var rightWing = { value: null };\n var result = this.computeClasses(rightWing, -1);\n this.nodeRightClass = rightWing.value;\n return result;\n },\n\n computeClasses: function(wingPair, d) {\n var currentWing = 0,\n wing = wingPair.value = new Dictionary();\n\n for (var l = 0; l < this.layers.length; ++l) {\n currentWing = l;\n\n var layer = this.layers[l];\n for (var n = d === 1 ? 0 : layer.length - 1; n >= 0 && n < layer.length; n += d) {\n var node = layer[n];\n if (!wing.containsKey(node)) {\n wing.set(node, currentWing);\n if (node.isVirtual) {\n var ndsinl = this._nodesInLink(node);\n for (var kk = 0; kk < ndsinl.length; kk++) {\n var vnode = ndsinl[kk];\n wing.set(vnode, currentWing);\n }\n }\n }\n else {\n currentWing = wing.get(node);\n }\n }\n }\n\n var wings = [];\n for (var i = 0; i < this.layers.length; i++) {\n wings.push(null);\n }\n wing.forEach(function(node, classIndex) {\n if (wings[classIndex] === null) {\n wings[classIndex] = [];\n }\n wings[classIndex].push(node);\n });\n\n return wings;\n },\n _isVerticalLayout: function() {\n return this.options.subtype.toLowerCase() === \"up\" || this.options.subtype.toLowerCase() === \"down\" || this.options.subtype.toLowerCase() === \"vertical\";\n },\n\n _isHorizontalLayout: function() {\n return this.options.subtype.toLowerCase() === \"right\" || this.options.subtype.toLowerCase() === \"left\" || this.options.subtype.toLowerCase() === \"horizontal\";\n },\n _isIncreasingLayout: function() {\n // meaning that the visiting of the layers goes in the natural order of increasing layer index\n return this.options.subtype.toLowerCase() === \"right\" || this.options.subtype.toLowerCase() === \"down\";\n },\n _moveThingsAround: function() {\n var i, l, node, layer, n, w;\n // sort the layers by their grid position\n for (l = 0; l < this.layers.length; ++l) {\n layer = this.layers[l];\n layer.sort(this._gridPositionComparer);\n }\n\n this.minDistances = [];\n for (l = 0; l < this.layers.length; ++l) {\n layer = this.layers[l];\n this.minDistances[l] = [];\n for (n = 0; n < layer.length; ++n) {\n node = layer[n];\n node.layerIndex = n;\n this.minDistances[l][n] = this.options.nodeDistance;\n if (n < layer.length - 1) {\n if (this._isVerticalLayout()) {\n this.minDistances[l][n] += (node.width + layer[n + 1].width) / 2;\n }\n else {\n this.minDistances[l][n] += (node.height + layer[n + 1].height) / 2;\n }\n }\n }\n }\n\n this.downNodes = new Dictionary();\n this.upNodes = new Dictionary();\n Utils.forEach(this.graph.nodes, function(node) {\n this.downNodes.set(node, []);\n this.upNodes.set(node, []);\n }, this);\n Utils.forEach(this.graph.links, function(link) {\n var origin = link.source;\n var dest = link.target;\n var down = null, up = null;\n if (origin.layer > dest.layer) {\n down = link.source;\n up = link.target;\n }\n else {\n up = link.source;\n down = link.target;\n }\n this.downNodes.get(up).push(down);\n this.upNodes.get(down).push(up);\n }, this);\n this.downNodes.forEachValue(function(list) {\n list.sort(this._gridPositionComparer);\n }, this);\n this.upNodes.forEachValue(function(list) {\n list.sort(this._gridPositionComparer);\n }, this);\n\n for (l = 0; l < this.layers.length - 1; ++l) {\n layer = this.layers[l];\n for (w = 0; w < layer.length - 1; w++) {\n var currentNode = layer[w];\n if (!currentNode.isVirtual) {\n continue;\n }\n\n var currDown = this.downNodes.get(currentNode)[0];\n if (!currDown.isVirtual) {\n continue;\n }\n\n for (n = w + 1; n < layer.length; ++n) {\n node = layer[n];\n if (!node.isVirtual) {\n continue;\n }\n\n var downNode = this.downNodes.get(node)[0];\n if (!downNode.isVirtual) {\n continue;\n }\n\n if (currDown.gridPosition > downNode.gridPosition) {\n var pos = currDown.gridPosition;\n currDown.gridPosition = downNode.gridPosition;\n downNode.gridPosition = pos;\n var i1 = currDown.layerIndex;\n var i2 = downNode.layerIndex;\n this.layers[l + 1][i1] = downNode;\n this.layers[l + 1][i2] = currDown;\n currDown.layerIndex = i2;\n downNode.layerIndex = i1;\n }\n }\n }\n }\n\n\n var leftClasses = this._getLeftWing();\n var rightClasses = this._getRightWing();\n\n\n var leftPos = this.placeLeftToRight(leftClasses);\n var rightPos = this.placeRightToLeft(rightClasses);\n var x = new Dictionary();\n Utils.forEach(this.graph.nodes, function(node) {\n x.set(node, (leftPos.get(node) + rightPos.get(node)) / 2);\n });\n\n\n var order = new Dictionary();\n var placed = new Dictionary();\n for (l = 0; l < this.layers.length; ++l) {\n layer = this.layers[l];\n var sequenceStart = -1, sequenceEnd = -1;\n for (n = 0; n < layer.length; ++n) {\n node = layer[n];\n order.set(node, 0);\n placed.set(node, false);\n if (node.isVirtual) {\n if (sequenceStart === -1) {\n sequenceStart = n;\n }\n else if (sequenceStart === n - 1) {\n sequenceStart = n;\n }\n else {\n sequenceEnd = n;\n order.set(layer[sequenceStart], 0);\n if (x.get(node) - x.get(layer[sequenceStart]) === this.getMinDist(layer[sequenceStart], node)) {\n placed.set(layer[sequenceStart], true);\n }\n else {\n placed.set(layer[sequenceStart], false);\n }\n sequenceStart = n;\n }\n }\n }\n }\n var directions = [1, -1];\n Utils.forEach(directions, function(d) {\n var start = d === 1 ? 0 : this.layers.length - 1;\n for (var l = start; l >= 0 && l < this.layers.length; l += d) {\n var layer = this.layers[l];\n var virtualStartIndex = this._firstVirtualNode(layer);\n var virtualStart = null;\n var sequence = null;\n if (virtualStartIndex !== -1) {\n virtualStart = layer[virtualStartIndex];\n sequence = [];\n for (i = 0; i < virtualStartIndex; i++) {\n sequence.push(layer[i]);\n }\n }\n else {\n virtualStart = null;\n sequence = layer;\n }\n if (sequence.length > 0) {\n this._sequencer(x, null, virtualStart, d, sequence);\n for (i = 0; i < sequence.length - 1; ++i) {\n this.setMinDist(sequence[i], sequence[i + 1], x.get(sequence[i + 1]) - x.get(sequence[i]));\n }\n if (virtualStart) {\n this.setMinDist(sequence[sequence.length - 1], virtualStart, x.get(virtualStart) - x.get(sequence[sequence.length - 1]));\n }\n }\n\n while (virtualStart) {\n var virtualEnd = this.nextVirtualNode(layer, virtualStart);\n if (!virtualEnd) {\n virtualStartIndex = virtualStart.layerIndex;\n sequence = [];\n for (i = virtualStartIndex + 1; i < layer.length; i++) {\n sequence.push(layer[i]);\n }\n if (sequence.length > 0) {\n this._sequencer(x, virtualStart, null, d, sequence);\n for (i = 0; i < sequence.length - 1; ++i) {\n this.setMinDist(sequence[i], sequence[i + 1], x.get(sequence[i + 1]) - x.get(sequence[i]));\n }\n this.setMinDist(virtualStart, sequence[0], x.get(sequence[0]) - x.get(virtualStart));\n }\n }\n else if (order.get(virtualStart) === d) {\n virtualStartIndex = virtualStart.layerIndex;\n var virtualEndIndex = virtualEnd.layerIndex;\n sequence = [];\n for (i = virtualStartIndex + 1; i < virtualEndIndex; i++) {\n sequence.push(layer[i]);\n }\n if (sequence.length > 0) {\n this._sequencer(x, virtualStart, virtualEnd, d, sequence);\n }\n placed.set(virtualStart, true);\n }\n virtualStart = virtualEnd;\n }\n this.adjustDirections(l, d, order, placed);\n }\n }, this);\n\n\n var fromLayerIndex = this._isIncreasingLayout() ? 0 : this.layers.length - 1;\n var reachedFinalLayerIndex = function(k, ctx) {\n if (ctx._isIncreasingLayout()) {\n return k < ctx.layers.length;\n }\n else {\n return k >= 0;\n }\n };\n var layerIncrement = this._isIncreasingLayout() ? +1 : -1, offset = 0;\n\n /**\n * Calcs the max height of the given layer.\n */\n function maximumHeight(layer, ctx) {\n var height = Number.MIN_VALUE;\n for (var n = 0; n < layer.length; ++n) {\n var node = layer[n];\n if (ctx._isVerticalLayout()) {\n height = Math.max(height, node.height);\n }\n else {\n height = Math.max(height, node.width);\n }\n }\n return height;\n }\n\n for (i = fromLayerIndex; reachedFinalLayerIndex(i, this); i += layerIncrement) {\n layer = this.layers[i];\n var height = maximumHeight(layer, this);\n\n for (n = 0; n < layer.length; ++n) {\n node = layer[n];\n if (this._isVerticalLayout()) {\n node.x = x.get(node);\n node.y = offset + height / 2;\n }\n else {\n node.x = offset + height / 2;\n node.y = x.get(node);\n }\n }\n\n offset += this.options.layerSeparation + height;\n }\n },\n\n adjustDirections: function(l, d, order, placed) {\n if (l + d < 0 || l + d >= this.layers.length) {\n return;\n }\n\n var prevBridge = null, prevBridgeTarget = null;\n var layer = this.layers[l + d];\n for (var n = 0; n < layer.length; ++n) {\n var nextBridge = layer[n];\n if (nextBridge.isVirtual) {\n var nextBridgeTarget = this.getNeighborOnLayer(nextBridge, l);\n if (nextBridgeTarget.isVirtual) {\n if (prevBridge) {\n var p = placed.get(prevBridgeTarget);\n var clayer = this.layers[l];\n var i1 = prevBridgeTarget.layerIndex;\n var i2 = nextBridgeTarget.layerIndex;\n for (var i = i1 + 1; i < i2; ++i) {\n if (clayer[i].isVirtual) {\n p = p && placed.get(clayer[i]);\n }\n }\n if (p) {\n order.set(prevBridge, d);\n var j1 = prevBridge.layerIndex;\n var j2 = nextBridge.layerIndex;\n for (var j = j1 + 1; j < j2; ++j) {\n if (layer[j].isVirtual) {\n order.set(layer[j], d);\n }\n }\n }\n }\n prevBridge = nextBridge;\n prevBridgeTarget = nextBridgeTarget;\n }\n }\n }\n },\n\n getNeighborOnLayer: function(node, l) {\n var neighbor = this.upNodes.get(node)[0];\n if (neighbor.layer === l) {\n return neighbor;\n }\n neighbor = this.downNodes.get(node)[0];\n if (neighbor.layer === l) {\n return neighbor;\n }\n return null;\n },\n\n _sequencer: function(x, virtualStart, virtualEnd, dir, sequence) {\n if (sequence.length === 1) {\n this._sequenceSingle(x, virtualStart, virtualEnd, dir, sequence[0]);\n }\n\n if (sequence.length > 1) {\n var r = sequence.length, t = this.intDiv(r, 2);\n this._sequencer(x, virtualStart, virtualEnd, dir, sequence.slice(0, t));\n this._sequencer(x, virtualStart, virtualEnd, dir, sequence.slice(t));\n this.combineSequences(x, virtualStart, virtualEnd, dir, sequence);\n }\n },\n\n _sequenceSingle: function(x, virtualStart, virtualEnd, dir, node) {\n var neighbors = dir === -1 ? this.downNodes.get(node) : this.upNodes.get(node);\n\n var n = neighbors.length;\n if (n !== 0) {\n if (n % 2 === 1) {\n x.set(node, x.get(neighbors[this.intDiv(n, 2)]));\n }\n else {\n x.set(node, (x.get(neighbors[this.intDiv(n, 2) - 1]) + x.get(neighbors[this.intDiv(n, 2)])) / 2);\n }\n\n if (virtualStart) {\n x.set(node, Math.max(x.get(node), x.get(virtualStart) + this.getMinDist(virtualStart, node)));\n }\n if (virtualEnd) {\n x.set(node, Math.min(x.get(node), x.get(virtualEnd) - this.getMinDist(node, virtualEnd)));\n }\n }\n },\n\n combineSequences: function(x, virtualStart, virtualEnd, dir, sequence) {\n var r = sequence.length, t = this.intDiv(r, 2);\n\n // collect left changes\n var leftHeap = [], i, c, n, neighbors, neighbor, pair;\n for (i = 0; i < t; ++i) {\n c = 0;\n neighbors = dir === -1 ? this.downNodes.get(sequence[i]) : this.upNodes.get(sequence[i]);\n for (n = 0; n < neighbors.length; ++n) {\n neighbor = neighbors[n];\n if (x.get(neighbor) >= x.get(sequence[i])) {\n c++;\n }\n else {\n c--;\n leftHeap.push({ k: x.get(neighbor) + this.getMinDist(sequence[i], sequence[t - 1]), v: 2 });\n }\n }\n leftHeap.push({ k: x.get(sequence[i]) + this.getMinDist(sequence[i], sequence[t - 1]), v: c });\n }\n if (virtualStart) {\n leftHeap.push({ k: x.get(virtualStart) + this.getMinDist(virtualStart, sequence[t - 1]), v: Number.MAX_VALUE });\n }\n leftHeap.sort(this._positionDescendingComparer);\n\n // collect right changes\n var rightHeap = [];\n for (i = t; i < r; ++i) {\n c = 0;\n neighbors = dir === -1 ? this.downNodes.get(sequence[i]) : this.upNodes.get(sequence[i]);\n for (n = 0; n < neighbors.length; ++n) {\n neighbor = neighbors[n];\n if (x.get(neighbor) <= x.get(sequence[i])) {\n c++;\n }\n else {\n c--;\n rightHeap.push({ k: x.get(neighbor) - this.getMinDist(sequence[i], sequence[t]), v: 2 });\n }\n }\n rightHeap.push({ k: x.get(sequence[i]) - this.getMinDist(sequence[i], sequence[t]), v: c });\n }\n if (virtualEnd) {\n rightHeap.push({ k: x.get(virtualEnd) - this.getMinDist(virtualEnd, sequence[t]), v: Number.MAX_VALUE });\n }\n rightHeap.sort(this._positionAscendingComparer);\n\n var leftRes = 0, rightRes = 0;\n var m = this.getMinDist(sequence[t - 1], sequence[t]);\n while (x.get(sequence[t]) - x.get(sequence[t - 1]) < m) {\n if (leftRes < rightRes) {\n if (leftHeap.length === 0) {\n x.set(sequence[t - 1], x.get(sequence[t]) - m);\n break;\n }\n else {\n pair = leftHeap.shift();\n leftRes = leftRes + pair.v;\n x.set(sequence[t - 1], pair.k);\n x.set(sequence[t - 1], Math.max(x.get(sequence[t - 1]), x.get(sequence[t]) - m));\n }\n }\n else {\n if (rightHeap.length === 0) {\n x.set(sequence[t], x.get(sequence[t - 1]) + m);\n break;\n }\n else {\n pair = rightHeap.shift();\n rightRes = rightRes + pair.v;\n x.set(sequence[t], pair.k);\n x.set(sequence[t], Math.min(x.get(sequence[t]), x.get(sequence[t - 1]) + m));\n }\n }\n }\n for (i = t - 2; i >= 0; i--) {\n x.set(sequence[i], Math.min(x.get(sequence[i]), x.get(sequence[t - 1]) - this.getMinDist(sequence[i], sequence[t - 1])));\n }\n for (i = t + 1; i < r; i++) {\n x.set(sequence[i], Math.max(x.get(sequence[i]), x.get(sequence[t]) + this.getMinDist(sequence[i], sequence[t])));\n }\n },\n\n placeLeft: function(node, leftPos, leftClass) {\n var pos = Number.NEGATIVE_INFINITY;\n Utils.forEach(this._getComposite(node), function(v) {\n var leftSibling = this.leftSibling(v);\n if (leftSibling && this.nodeLeftClass.get(leftSibling) === this.nodeLeftClass.get(v)) {\n if (!leftPos.containsKey(leftSibling)) {\n this.placeLeft(leftSibling, leftPos, leftClass);\n }\n pos = Math.max(pos, leftPos.get(leftSibling) + this.getMinDist(leftSibling, v));\n }\n }, this);\n if (pos === Number.NEGATIVE_INFINITY) {\n pos = 0;\n }\n Utils.forEach(this._getComposite(node), function(v) {\n leftPos.set(v, pos);\n });\n },\n\n placeRight: function(node, rightPos, rightClass) {\n var pos = Number.POSITIVE_INFINITY;\n Utils.forEach(this._getComposite(node), function(v) {\n var rightSibling = this.rightSibling(v);\n if (rightSibling && this.nodeRightClass.get(rightSibling) === this.nodeRightClass.get(v)) {\n if (!rightPos.containsKey(rightSibling)) {\n this.placeRight(rightSibling, rightPos, rightClass);\n }\n pos = Math.min(pos, rightPos.get(rightSibling) - this.getMinDist(v, rightSibling));\n }\n }, this);\n if (pos === Number.POSITIVE_INFINITY) {\n pos = 0;\n }\n Utils.forEach(this._getComposite(node), function(v) {\n rightPos.set(v, pos);\n });\n },\n\n leftSibling: function(node) {\n var layer = this.layers[node.layer],\n layerIndex = node.layerIndex;\n return layerIndex === 0 ? null : layer[layerIndex - 1];\n },\n\n rightSibling: function(node) {\n var layer = this.layers[node.layer];\n var layerIndex = node.layerIndex;\n return layerIndex === layer.length - 1 ? null : layer[layerIndex + 1];\n\n },\n\n _getComposite: function(node) {\n return node.isVirtual ? this._nodesInLink(node) : [node];\n },\n\n arrangeNodes: function() {\n var i, l, ni, layer, node;\n // Initialize node's base priority\n for (l = 0; l < this.layers.length; l++) {\n layer = this.layers[l];\n\n for (ni = 0; ni < layer.length; ni++) {\n node = layer[ni];\n node.upstreamPriority = node.upstreamLinkCount;\n node.downstreamPriority = node.downstreamLinkCount;\n }\n }\n\n // Layout is invoked after MinimizeCrossings\n // so we may assume node's barycenters are initially correct\n\n var maxLayoutIterations = 2;\n for (var it = 0; it < maxLayoutIterations; it++) {\n for (i = this.layers.length - 1; i >= 1; i--) {\n this.layoutLayer(false, i);\n }\n\n for (i = 0; i < this.layers.length - 1; i++) {\n this.layoutLayer(true, i);\n }\n }\n\n // Offset the whole structure so that there are no gridPositions < 0\n var gridPos = Number.MAX_VALUE;\n for (l = 0; l < this.layers.length; l++) {\n layer = this.layers[l];\n\n for (ni = 0; ni < layer.length; ni++) {\n node = layer[ni];\n gridPos = Math.min(gridPos, node.gridPosition);\n }\n }\n\n if (gridPos < 0) {\n for (l = 0; l < this.layers.length; l++) {\n layer = this.layers[l];\n\n for (ni = 0; ni < layer.length; ni++) {\n node = layer[ni];\n node.gridPosition = node.gridPosition - gridPos;\n }\n }\n }\n },\n\n /// \n /// Layout of a single layer.\n /// \n /// The layer to organize.\n /// If set to true we move down in the layer stack.\n /// \n layoutLayer: function(down, layer) {\n var iconsidered;\n var considered;\n\n if (down) {\n considered = this.layers[iconsidered = layer + 1];\n }\n else {\n considered = this.layers[iconsidered = layer - 1];\n }\n\n // list containing the nodes in the considered layer sorted by priority\n var sorted = [];\n for (var n = 0; n < considered.length; n++) {\n sorted.push(considered[n]);\n }\n sorted.sort(function(n1, n2) {\n var n1Priority = (n1.upstreamPriority + n1.downstreamPriority) / 2;\n var n2Priority = (n2.upstreamPriority + n2.downstreamPriority) / 2;\n\n if (Math.abs(n1Priority - n2Priority) < 0.0001) {\n return 0;\n }\n if (n1Priority < n2Priority) {\n return 1;\n }\n return -1;\n });\n\n // each node strives for its barycenter; high priority nodes start first\n Utils.forEach(sorted, function(node) {\n var nodeGridPos = node.gridPosition;\n var nodeBaryCenter = this.calcBaryCenter(node);\n var nodePriority = (node.upstreamPriority + node.downstreamPriority) / 2;\n\n if (Math.abs(nodeGridPos - nodeBaryCenter) < 0.0001) {\n // This node is exactly at its barycenter -> perfect\n return;\n }\n\n if (Math.abs(nodeGridPos - nodeBaryCenter) < 0.25 + 0.0001) {\n // This node is close enough to the barycenter -> should work\n return;\n }\n\n if (nodeGridPos < nodeBaryCenter) {\n // Try to move the node to the right in an\n // attempt to reach its barycenter\n while (nodeGridPos < nodeBaryCenter) {\n if (!this.moveRight(node, considered, nodePriority)) {\n break;\n }\n\n nodeGridPos = node.gridPosition;\n }\n }\n else {\n // Try to move the node to the left in an\n // attempt to reach its barycenter\n while (nodeGridPos > nodeBaryCenter) {\n if (!this.moveLeft(node, considered, nodePriority)) {\n break;\n }\n\n nodeGridPos = node.gridPosition;\n }\n }\n }, this);\n\n // after the layer has been rearranged we need to recalculate the barycenters\n // of the nodes in the surrounding layers\n if (iconsidered > 0) {\n this.calcDownData(iconsidered - 1);\n }\n if (iconsidered < this.layers.length - 1) {\n this.calcUpData(iconsidered + 1);\n }\n },\n\n /// \n /// Moves the node to the right and returns true if this was possible.\n /// \n /// The node.\n /// The layer.\n /// Returns true if the shift was possible, otherwise false.\n moveRight: function(node, layer, priority) {\n var index = Utils.indexOf(layer, node);\n if (index === layer.length - 1) {\n // this is the last node in the layer, so we can move to the right without troubles\n node.gridPosition = node.gridPosition + 0.5;\n return true;\n }\n\n var rightNode = layer[index + 1];\n var rightNodePriority = (rightNode.upstreamPriority + rightNode.downstreamPriority) / 2;\n\n // check if there is space between the right and the current node\n if (rightNode.gridPosition > node.gridPosition + 1) {\n node.gridPosition = node.gridPosition + 0.5;\n return true;\n }\n\n // we have reached a node with higher priority; no movement is allowed\n if (rightNodePriority > priority ||\n Math.abs(rightNodePriority - priority) < 0.0001) {\n return false;\n }\n\n // the right node has lower priority - try to move it\n if (this.moveRight(rightNode, layer, priority)) {\n node.gridPosition = node.gridPosition + 0.5;\n return true;\n }\n\n return false;\n },\n\n /// \n /// Moves the node to the left and returns true if this was possible.\n /// \n /// The node.\n /// The layer.\n /// Returns true if the shift was possible, otherwise false.\n moveLeft: function(node, layer, priority) {\n var index = Utils.indexOf(layer, node);\n if (index === 0) {\n // this is the last node in the layer, so we can move to the left without troubles\n node.gridPosition = node.gridPosition - 0.5;\n return true;\n }\n\n var leftNode = layer[index - 1];\n var leftNodePriority = (leftNode.upstreamPriority + leftNode.downstreamPriority) / 2;\n\n // check if there is space between the left and the current node\n if (leftNode.gridPosition < node.gridPosition - 1) {\n node.gridPosition = node.gridPosition - 0.5;\n return true;\n }\n\n // we have reached a node with higher priority; no movement is allowed\n if (leftNodePriority > priority ||\n Math.abs(leftNodePriority - priority) < 0.0001) {\n return false;\n }\n\n // The left node has lower priority - try to move it\n if (this.moveLeft(leftNode, layer, priority)) {\n node.gridPosition = node.gridPosition - 0.5;\n return true;\n }\n\n return false;\n },\n\n mapVirtualNode: function(node, link) {\n this.nodeToLinkMap.set(node, link);\n if (!this.linkToNodeMap.containsKey(link)) {\n this.linkToNodeMap.set(link, []);\n }\n this.linkToNodeMap.get(link).push(node);\n },\n\n _nodesInLink: function(node) {\n return this.linkToNodeMap.get(this.nodeToLinkMap.get(node));\n },\n\n /// \n /// Inserts dummy nodes to break long links.\n /// \n _dummify: function() {\n this.linkToNodeMap = new Dictionary();\n this.nodeToLinkMap = new Dictionary();\n\n var layer, pos, newNode, node, r, newLink, i, l, links = this.graph.links.slice(0);\n var layers = this.layers;\n\n var addLinkBetweenLayers = function(upLayer, downLayer, link) {\n layers[upLayer].linksTo[downLayer] = layers[upLayer].linksTo[downLayer] || [];\n layers[upLayer].linksTo[downLayer].push(link);\n };\n\n for (l = 0; l < links.length; l++) {\n var link = links[l];\n var o = link.source;\n var d = link.target;\n\n var oLayer = o.layer;\n var dLayer = d.layer;\n var oPos = o.gridPosition;\n var dPos = d.gridPosition;\n\n var step = (dPos - oPos) / Math.abs(dLayer - oLayer);\n\n var p = o;\n if (oLayer - dLayer > 1) {\n for (i = oLayer - 1; i > dLayer; i--) {\n newNode = new Node();\n newNode.x = o.x;\n newNode.y = o.y;\n newNode.width = o.width / 100;\n newNode.height = o.height / 100;\n\n layer = layers[i];\n pos = (i - dLayer) * step + oPos;\n if (pos > layer.length) {\n pos = layer.length;\n }\n\n // check if origin and dest are both last\n if (oPos >= layers[oLayer].length - 1 &&\n dPos >= layers[dLayer].length - 1) {\n pos = layer.length;\n }\n\n // check if origin and destination are both first\n else if (oPos === 0 && dPos === 0) {\n pos = 0;\n }\n\n newNode.layer = i;\n newNode.uBaryCenter = 0.0;\n newNode.dBaryCenter = 0.0;\n newNode.upstreamLinkCount = 0;\n newNode.downstreamLinkCount = 0;\n newNode.gridPosition = pos;\n newNode.isVirtual = true;\n\n Utils.insert(layer, newNode, pos);\n\n // translate rightwards nodes' positions\n for (r = pos + 1; r < layer.length; r++) {\n node = layer[r];\n node.gridPosition = node.gridPosition + 1;\n }\n\n newLink = new Link(p, newNode);\n newLink.depthOfDumminess = 0;\n\n addLinkBetweenLayers(i - 1, i, newLink);\n\n p = newNode;\n\n // add the new node and the new link to the graph\n this.graph._addNode(newNode);\n this.graph.addLink(newLink);\n\n newNode.index = this.graph.nodes.length - 1;\n this.mapVirtualNode(newNode, link);\n }\n\n // set the origin of the real arrow to the last dummy\n addLinkBetweenLayers(dLayer - 1, dLayer, newLink);\n link.changeSource(p);\n link.depthOfDumminess = oLayer - dLayer - 1;\n } else if (oLayer - dLayer < -1) {\n for (i = oLayer + 1; i < dLayer; i++) {\n newNode = new Node();\n newNode.x = o.x;\n newNode.y = o.y;\n newNode.width = o.width / 100;\n newNode.height = o.height / 100;\n\n layer = layers[i];\n pos = (i - oLayer) * step + oPos;\n if (pos > layer.length) {\n pos = layer.length;\n }\n\n // check if origin and dest are both last\n if (oPos >= layers[oLayer].length - 1 &&\n dPos >= layers[dLayer].length - 1) {\n pos = layer.length;\n }\n\n // check if origin and destination are both first\n else if (oPos === 0 && dPos === 0) {\n pos = 0;\n }\n\n newNode.layer = i;\n newNode.uBaryCenter = 0.0;\n newNode.dBaryCenter = 0.0;\n newNode.upstreamLinkCount = 0;\n newNode.downstreamLinkCount = 0;\n newNode.gridPosition = pos;\n newNode.isVirtual = true;\n\n pos &= pos; // truncates to int\n Utils.insert(layer, newNode, pos);\n\n // translate rightwards nodes' positions\n for (r = pos + 1; r < layer.length; r++) {\n node = layer[r];\n node.gridPosition = node.gridPosition + 1;\n }\n\n newLink = new Link(p, newNode);\n newLink.depthOfDumminess = 0;\n addLinkBetweenLayers(i - 1, i, newLink);\n\n p = newNode;\n\n // add the new node and the new link to the graph\n this.graph._addNode(newNode);\n this.graph.addLink(newLink);\n\n newNode.index = this.graph.nodes.length - 1;\n this.mapVirtualNode(newNode, link);\n }\n addLinkBetweenLayers(dLayer - 1, dLayer, link);\n\n // Set the origin of the real arrow to the last dummy\n link.changeSource(p);\n link.depthOfDumminess = dLayer - oLayer - 1;\n } else {\n addLinkBetweenLayers(oLayer, dLayer, link);\n }\n }\n },\n\n /// \n /// Removes the dummy nodes inserted earlier to break long links.\n /// \n /// The virtual nodes are effectively turned into intermediate connection points.\n _dedummify: function() {\n var dedum = true;\n while (dedum) {\n dedum = false;\n\n for (var l = 0; l < this.graph.links.length; l++) {\n var link = this.graph.links[l];\n if (!link.depthOfDumminess) {\n continue;\n }\n\n var points = [];\n\n // add points in reverse order\n points.unshift({ x: link.target.x, y: link.target.y });\n points.unshift({ x: link.source.x, y: link.source.y });\n\n // _dedummify the link\n var temp = link;\n var depthOfDumminess = link.depthOfDumminess;\n for (var d = 0; d < depthOfDumminess; d++) {\n var node = temp.source;\n var prevLink = node.incoming[0];\n\n points.unshift({ x: prevLink.source.x, y: prevLink.source.y });\n\n temp = prevLink;\n }\n\n // restore the original link origin\n link.changeSource(temp.source);\n\n // reset dummification flag\n link.depthOfDumminess = 0;\n\n // note that we only need the intermediate points, floating links have been dropped in the analysis\n if (points.length > 2) {\n // first and last are the endpoints\n points.splice(0, 1);\n points.splice(points.length - 1);\n link.points = points;\n }\n else {\n link.points = [];\n }\n\n // we are not going to delete the dummy elements;\n // they won't be needed anymore anyway.\n\n dedum = true;\n break;\n }\n }\n },\n\n /// \n /// Optimizes/reduces the crossings between the layers by turning the crossing problem into a (combinatorial) number ordering problem.\n /// \n _optimizeCrossings: function() {\n var moves = -1, i;\n var maxIterations = 3;\n var iter = 0;\n\n while (moves !== 0) {\n if (iter++ > maxIterations) {\n break;\n }\n\n moves = 0;\n\n for (i = this.layers.length - 1; i >= 1; i--) {\n moves += this.optimizeLayerCrossings(false, i);\n }\n\n for (i = 0; i < this.layers.length - 1; i++) {\n moves += this.optimizeLayerCrossings(true, i);\n }\n }\n },\n\n calcUpData: function(layer) {\n if (layer === 0) {\n return;\n }\n\n var considered = this.layers[layer], i, l, link;\n var upLayer = new Set();\n var temp = this.layers[layer - 1];\n for (i = 0; i < temp.length; i++) {\n upLayer.add(temp[i]);\n }\n\n for (i = 0; i < considered.length; i++) {\n var node = considered[i];\n\n // calculate barycenter\n var sum = 0;\n var total = 0;\n\n for (l = 0; l < node.incoming.length; l++) {\n link = node.incoming[l];\n if (upLayer.contains(link.source)) {\n total++;\n sum += link.source.gridPosition;\n }\n }\n\n for (l = 0; l < node.outgoing.length; l++) {\n link = node.outgoing[l];\n if (upLayer.contains(link.target)) {\n total++;\n sum += link.target.gridPosition;\n }\n }\n\n if (total > 0) {\n node.uBaryCenter = sum / total;\n node.upstreamLinkCount = total;\n }\n else {\n node.uBaryCenter = i;\n node.upstreamLinkCount = 0;\n }\n }\n },\n\n calcDownData: function(layer) {\n if (layer === this.layers.length - 1) {\n return;\n }\n\n var considered = this.layers[layer], i , l, link;\n var downLayer = new Set();\n var temp = this.layers[layer + 1];\n for (i = 0; i < temp.length; i++) {\n downLayer.add(temp[i]);\n }\n\n for (i = 0; i < considered.length; i++) {\n var node = considered[i];\n\n // calculate barycenter\n var sum = 0;\n var total = 0;\n\n for (l = 0; l < node.incoming.length; l++) {\n link = node.incoming[l];\n if (downLayer.contains(link.source)) {\n total++;\n sum += link.source.gridPosition;\n }\n }\n\n for (l = 0; l < node.outgoing.length; l++) {\n link = node.outgoing[l];\n if (downLayer.contains(link.target)) {\n total++;\n sum += link.target.gridPosition;\n }\n }\n\n if (total > 0) {\n node.dBaryCenter = sum / total;\n node.downstreamLinkCount = total;\n }\n else {\n node.dBaryCenter = i;\n node.downstreamLinkCount = 0;\n }\n }\n },\n\n /// \n /// Optimizes the crossings.\n /// \n /// The big trick here is the usage of weights or values attached to connected nodes which turn a problem of crossing links\n /// to an a problem of ordering numbers.\n /// The layer index.\n /// If set to true we move down in the layer stack.\n /// The number of nodes having moved, i.e. the number of crossings reduced.\n optimizeLayerCrossings: function(down, layer) {\n var iconsidered;\n var considered;\n\n if (down) {\n considered = this.layers[iconsidered = layer + 1];\n }\n else {\n considered = this.layers[iconsidered = layer - 1];\n }\n\n // remember what it was\n var presorted = considered.slice(0);\n\n // calculate barycenters for all nodes in the considered layer\n if (down) {\n this.calcUpData(iconsidered);\n }\n else {\n this.calcDownData(iconsidered);\n }\n\n var that = this;\n // sort nodes within this layer according to the barycenters\n considered.sort(function(n1, n2) {\n var n1BaryCenter = that.calcBaryCenter(n1),\n n2BaryCenter = that.calcBaryCenter(n2);\n if (Math.abs(n1BaryCenter - n2BaryCenter) < 0.0001) {\n // in case of coinciding barycenters compare by the count of in/out links\n if (n1.degree() === n2.degree()) {\n return that.compareByIndex(n1, n2);\n }\n else if (n1.degree() < n2.degree()) {\n return 1;\n }\n return -1;\n }\n var compareValue = (n2BaryCenter - n1BaryCenter) * 1000;\n if (compareValue > 0) {\n return -1;\n }\n else if (compareValue < 0) {\n return 1;\n }\n return that.compareByIndex(n1, n2);\n });\n\n // count relocations\n var i, moves = 0;\n for (i = 0; i < considered.length; i++) {\n if (considered[i] !== presorted[i]) {\n moves++;\n }\n }\n\n if (moves > 0) {\n // now that the boxes have been arranged, update their grid positions\n var inode = 0;\n for (i = 0; i < considered.length; i++) {\n var node = considered[i];\n node.gridPosition = inode++;\n }\n }\n\n return moves;\n },\n\n /// \n /// Swaps a pair of nodes in a layer.\n /// \n /// Index of the layer.\n /// The Nth node in the layer.\n _swapPairs: function() {\n var maxIterations = this.options.layeredIterations;\n var iter = 0;\n\n while (true) {\n if (iter++ > maxIterations) {\n break;\n }\n\n var downwards = (iter % 4 <= 1);\n var secondPass = (iter % 4 === 1);\n\n for (var l = (downwards ? 0 : this.layers.length - 1);\n downwards ? l <= this.layers.length - 1 : l >= 0; l += (downwards ? 1 : -1)) {\n var layer = this.layers[l];\n var hasSwapped = false;\n\n // there is no need to recalculate crossings if they were calculated\n // on the previous step and nothing has changed\n var calcCrossings = true;\n var memCrossings = 0;\n\n for (var n = 0; n < layer.length - 1; n++) {\n // count crossings\n var up = 0;\n var down = 0;\n var crossBefore = 0;\n\n if (calcCrossings) {\n if (l !== 0) {\n up = this.countLinksCrossingBetweenTwoLayers(l - 1, l);\n }\n if (l !== this.layers.length - 1) {\n down = this.countLinksCrossingBetweenTwoLayers(l, l + 1);\n }\n if (downwards) {\n up *= 2;\n }\n else {\n down *= 2;\n }\n\n crossBefore = up + down;\n }\n else {\n crossBefore = memCrossings;\n }\n\n if (crossBefore === 0) {\n continue;\n }\n\n // Swap nodes\n var node1 = layer[n];\n var node2 = layer[n + 1];\n\n var node1GridPos = node1.gridPosition;\n var node2GridPos = node2.gridPosition;\n layer[n] = node2;\n layer[n + 1] = node1;\n node1.gridPosition = node2GridPos;\n node2.gridPosition = node1GridPos;\n\n // count crossings again and if worse than before, restore swapping\n up = 0;\n if (l !== 0) {\n up = this.countLinksCrossingBetweenTwoLayers(l - 1, l);\n }\n down = 0;\n if (l !== this.layers.length - 1) {\n down = this.countLinksCrossingBetweenTwoLayers(l, l + 1);\n }\n if (downwards) {\n up *= 2;\n }\n else {\n down *= 2;\n }\n var crossAfter = up + down;\n\n var revert = false;\n if (secondPass) {\n revert = crossAfter >= crossBefore;\n }\n else {\n revert = crossAfter > crossBefore;\n }\n\n if (revert) {\n node1 = layer[n];\n node2 = layer[n + 1];\n\n node1GridPos = node1.gridPosition;\n node2GridPos = node2.gridPosition;\n layer[n] = node2;\n layer[n + 1] = node1;\n node1.gridPosition = node2GridPos;\n node2.gridPosition = node1GridPos;\n\n // nothing has changed, remember the crossings so that\n // they are not calculated again on the next step\n memCrossings = crossBefore;\n calcCrossings = false;\n }\n else {\n hasSwapped = true;\n calcCrossings = true;\n }\n }\n\n if (hasSwapped) {\n if (l !== this.layers.length - 1) {\n this.calcUpData(l + 1);\n }\n if (l !== 0) {\n this.calcDownData(l - 1);\n }\n }\n }\n }\n },\n\n /// \n /// Counts the number of links crossing between two layers.\n /// \n /// The layer index.\n /// Another layer index.\n /// \n countLinksCrossingBetweenTwoLayers: function(ulayer, dlayer) {\n var links = this.layers[ulayer].linksTo[dlayer];\n var link1, link2, n11, n12, n21, n22, l1, l2;\n var crossings = 0;\n var length = links.length;\n\n for (l1 = 0; l1 < length; l1++) {\n link1 = links[l1];\n for (l2 = l1 + 1; l2 < length; l2++) {\n\n link2 = links[l2];\n\n if (link1.target.layer === dlayer) {\n n11 = link1.source;\n n12 = link1.target;\n }\n else {\n n11 = link1.target;\n n12 = link1.source;\n }\n\n if (link2.target.layer === dlayer) {\n n21 = link2.source;\n n22 = link2.target;\n }\n else {\n n21 = link2.target;\n n22 = link2.source;\n }\n\n var n11gp = n11.gridPosition;\n var n12gp = n12.gridPosition;\n var n21gp = n21.gridPosition;\n var n22gp = n22.gridPosition;\n\n if ((n11gp - n21gp) * (n12gp - n22gp) < 0) {\n crossings++;\n }\n }\n }\n\n return crossings;\n },\n\n calcBaryCenter: function(node) {\n var upstreamLinkCount = node.upstreamLinkCount;\n var downstreamLinkCount = node.downstreamLinkCount;\n var uBaryCenter = node.uBaryCenter;\n var dBaryCenter = node.dBaryCenter;\n\n if (upstreamLinkCount > 0 && downstreamLinkCount > 0) {\n return (uBaryCenter + dBaryCenter) / 2;\n }\n if (upstreamLinkCount > 0) {\n return uBaryCenter;\n }\n if (downstreamLinkCount > 0) {\n return dBaryCenter;\n }\n\n return 0;\n },\n\n _gridPositionComparer: function(x, y) {\n if (x.gridPosition < y.gridPosition) {\n return -1;\n }\n if (x.gridPosition > y.gridPosition) {\n return 1;\n }\n return 0;\n },\n\n _positionAscendingComparer: function(x, y) {\n return x.k < y.k ? -1 : x.k > y.k ? 1 : 0;\n },\n\n _positionDescendingComparer: function(x, y) {\n return x.k < y.k ? 1 : x.k > y.k ? -1 : 0;\n },\n\n _firstVirtualNode: function(layer) {\n for (var c = 0; c < layer.length; c++) {\n if (layer[c].isVirtual) {\n return c;\n }\n }\n return -1;\n },\n\n compareByIndex: function(o1, o2) {\n var i1 = o1.index;\n var i2 = o2.index;\n\n if (i1 < i2) {\n return 1;\n }\n\n if (i1 > i2) {\n return -1;\n }\n\n return 0;\n },\n\n intDiv: function(numerator, denominator) {\n return (numerator - numerator % denominator) / denominator;\n },\n\n nextVirtualNode: function(layer, node) {\n var nodeIndex = node.layerIndex;\n for (var i = nodeIndex + 1; i < layer.length; ++i) {\n if (layer[i].isVirtual) {\n return layer[i];\n }\n }\n return null;\n }\n\n });\n\n /**\n * Captures the state of a diagram; node positions, link points and so on.\n * @type {*}\n */\n var LayoutState = kendo.Class.extend({\n init: function(diagram, graphOrNodes) {\n if (Utils.isUndefined(diagram)) {\n throw \"No diagram given\";\n }\n this.diagram = diagram;\n this.nodeMap = new Dictionary();\n this.linkMap = new Dictionary();\n this.capture(graphOrNodes ? graphOrNodes : diagram);\n },\n\n /**\n * Will capture either\n * - the state of the shapes and the intermediate points of the connections in the diagram\n * - the bounds of the nodes contained in the Graph together with the intermediate points of the links in the Graph\n * - the bounds of the nodes in the Array\n * - the links points and node bounds in the literal object\n * @param diagramOrGraphOrNodes\n */\n capture: function(diagramOrGraphOrNodes) {\n var node,\n nodes,\n shape,\n i,\n conn,\n link,\n links;\n\n if (diagramOrGraphOrNodes instanceof diagram.Graph) {\n\n for (i = 0; i < diagramOrGraphOrNodes.nodes.length; i++) {\n node = diagramOrGraphOrNodes.nodes[i];\n shape = node.associatedShape;\n //shape.bounds(new Rect(node.x, node.y, node.width, node.height));\n this.nodeMap.set(shape.visual.id, new Rect(node.x, node.y, node.width, node.height));\n }\n for (i = 0; i < diagramOrGraphOrNodes.links.length; i++) {\n link = diagramOrGraphOrNodes.links[i];\n conn = link.associatedConnection;\n this.linkMap.set(conn.visual.id, link.points());\n }\n }\n else if (diagramOrGraphOrNodes instanceof Array) {\n nodes = diagramOrGraphOrNodes;\n for (i = 0; i < nodes.length; i++) {\n node = nodes[i];\n shape = node.associatedShape;\n if (shape) {\n this.nodeMap.set(shape.visual.id, new Rect(node.x, node.y, node.width, node.height));\n }\n }\n }\n else if (diagramOrGraphOrNodes.hasOwnProperty(\"links\") && diagramOrGraphOrNodes.hasOwnProperty(\"nodes\")) {\n nodes = diagramOrGraphOrNodes.nodes;\n links = diagramOrGraphOrNodes.links;\n for (i = 0; i < nodes.length; i++) {\n node = nodes[i];\n shape = node.associatedShape;\n if (shape) {\n this.nodeMap.set(shape.visual.id, new Rect(node.x, node.y, node.width, node.height));\n }\n }\n for (i = 0; i < links.length; i++) {\n link = links[i];\n conn = link.associatedConnection;\n if (conn) {\n this.linkMap.set(conn.visual.id, link.points);\n }\n }\n }\n else { // capture the diagram\n var shapes = this.diagram.shapes;\n var connections = this.diagram.connections;\n for (i = 0; i < shapes.length; i++) {\n shape = shapes[i];\n this.nodeMap.set(shape.visual.id, shape.bounds());\n }\n for (i = 0; i < connections.length; i++) {\n conn = connections[i];\n this.linkMap.set(conn.visual.id, conn.points());\n }\n }\n }\n });\n\n deepExtend(diagram, {\n init: function(element) {\n kendo.init(element, diagram.ui);\n },\n SpringLayout: SpringLayout,\n TreeLayout: TreeLayout,\n GraphAdapter: DiagramToHyperTreeAdapter,\n LayeredLayout: LayeredLayout,\n LayoutBase: LayoutBase,\n LayoutState: LayoutState\n });\n })(window.kendo.jQuery);\n\n (function($, undefined$1) {\n // Imports ================================================================\n var dataviz = kendo.dataviz,\n draw = kendo.drawing,\n geom = kendo.geometry,\n diagram = dataviz.diagram,\n Widget = kendo.ui.Widget,\n Class = kendo.Class,\n deepExtend = kendo.deepExtend,\n outerWidth = kendo._outerWidth,\n outerHeight = kendo._outerHeight,\n extend = $.extend,\n HierarchicalDataSource = kendo.data.HierarchicalDataSource,\n Canvas = diagram.Canvas,\n Group = diagram.Group,\n Rectangle = diagram.Rectangle,\n Circle = diagram.Circle,\n CompositeTransform = diagram.CompositeTransform,\n Rect = diagram.Rect,\n Path = diagram.Path,\n DeleteShapeUnit = diagram.DeleteShapeUnit,\n DeleteConnectionUnit = diagram.DeleteConnectionUnit,\n TextBlock = diagram.TextBlock,\n Image = diagram.Image,\n Point = diagram.Point,\n Intersect = diagram.Intersect,\n ConnectionEditAdorner = diagram.ConnectionEditAdorner,\n UndoRedoService = diagram.UndoRedoService,\n ToolService = diagram.ToolService,\n Selector = diagram.Selector,\n ResizingAdorner = diagram.ResizingAdorner,\n ConnectorsAdorner = diagram.ConnectorsAdorner,\n Cursors = diagram.Cursors,\n Utils = diagram.Utils,\n Observable = kendo.Observable,\n ToBackUnit = diagram.ToBackUnit,\n ToFrontUnit = diagram.ToFrontUnit,\n PolylineRouter = diagram.PolylineRouter,\n CascadingRouter = diagram.CascadingRouter,\n isUndefined = Utils.isUndefined,\n isDefined = Utils.isDefined,\n defined = draw.util.defined,\n isArray = Array.isArray,\n isFunction = kendo.isFunction,\n isString = Utils.isString,\n isPlainObject = $.isPlainObject,\n\n math = Math;\n\n // Constants ==============================================================\n var NS = \".kendoDiagram\",\n CASCADING = \"cascading\",\n ITEMBOUNDSCHANGE = \"itemBoundsChange\",\n CHANGE = \"change\",\n CLICK = \"click\",\n DRAG = \"drag\",\n DRAG_END = \"dragEnd\",\n DRAG_START = \"dragStart\",\n MOUSE_ENTER = \"mouseEnter\",\n MOUSE_LEAVE = \"mouseLeave\",\n ERROR = \"error\",\n AUTO = \"Auto\",\n TOP = \"Top\",\n RIGHT = \"Right\",\n LEFT = \"Left\",\n BOTTOM = \"Bottom\",\n MAXINT = 9007199254740992,\n SELECT = \"select\",\n ITEMROTATE = \"itemRotate\",\n PAN = \"pan\",\n ZOOM_START = \"zoomStart\",\n ZOOM_END = \"zoomEnd\",\n NONE = \"none\",\n DEFAULT_CANVAS_WIDTH = 600,\n DEFAULT_CANVAS_HEIGHT = 600,\n DEFAULT_SHAPE_TYPE = \"rectangle\",\n DEFAULT_SHAPE_WIDTH = 100,\n DEFAULT_SHAPE_HEIGHT = 100,\n DEFAULT_SHAPE_MINWIDTH = 20,\n DEFAULT_SHAPE_MINHEIGHT = 20,\n DEFAULT_SHAPE_POSITION = 0,\n DEFAULT_CONNECTION_BACKGROUND = \"Yellow\",\n MAX_VALUE = Number.MAX_VALUE,\n MIN_VALUE = -Number.MAX_VALUE,\n ABSOLUTE = \"absolute\",\n TRANSFORMED = \"transformed\",\n ROTATED = \"rotated\",\n TRANSPARENT = \"transparent\",\n WIDTH = \"width\",\n HEIGHT = \"height\",\n X = \"x\",\n Y = \"y\",\n MOUSEWHEEL_NS = \"DOMMouseScroll\" + NS + \" mousewheel\" + NS,\n MOBILE_ZOOM_RATE = 0.05,\n MOBILE_PAN_DISTANCE = 5,\n BUTTON_TEMPLATE = function (ref) {\n var className = ref.className;\n var icon = ref.icon;\n var themeColor = ref.themeColor;\n var text = ref.text;\n\n return kendo.html.renderButton((\"\"), {\n icon: icon,\n themeColor: themeColor\n });\n },\n CONNECTION_CONTENT_OFFSET = 5;\n\n diagram.DefaultConnectors = [{\n name: TOP\n }, {\n name: BOTTOM\n }, {\n name: LEFT\n }, {\n name: RIGHT\n }, {\n name: AUTO,\n position: function(shape) {\n return shape.getPosition(\"center\");\n }\n }];\n\n var defaultButtons = {\n cancel: {\n text: \"Cancel\",\n icon: \"cancel-outline\",\n className: \"k-diagram-cancel\",\n },\n update: {\n text: \"Save\",\n imageClass: \"save\",\n className: \"k-diagram-update\",\n icon: \"save\",\n themeColor: \"primary\"\n }\n };\n\n diagram.shapeDefaults = function(extra) {\n var defaults = {\n type: DEFAULT_SHAPE_TYPE,\n path: \"\",\n autoSize: true,\n visual: null,\n x: DEFAULT_SHAPE_POSITION,\n y: DEFAULT_SHAPE_POSITION,\n minWidth: DEFAULT_SHAPE_MINWIDTH,\n minHeight: DEFAULT_SHAPE_MINHEIGHT,\n width: DEFAULT_SHAPE_WIDTH,\n height: DEFAULT_SHAPE_HEIGHT,\n hover: {},\n editable: {\n connect: true,\n tools: []\n },\n connectors: diagram.DefaultConnectors,\n rotation: {\n angle: 0\n }\n };\n\n Utils.simpleExtend(defaults, extra);\n\n return defaults;\n };\n\n function mwDelta(e) {\n var origEvent = e.originalEvent,\n delta = 0;\n\n if (origEvent.wheelDelta) {\n delta = -origEvent.wheelDelta / 40;\n delta = delta > 0 ? math.ceil(delta) : math.floor(delta);\n } else if (origEvent.detail) {\n delta = origEvent.detail;\n }\n\n return delta;\n }\n\n function isAutoConnector(connector) {\n return connector.options.name.toLowerCase() === AUTO.toLowerCase();\n }\n\n function closestConnector(point, connectors) {\n var minimumDistance = MAXINT, resCtr, connector;\n for (var i = 0; i < connectors.length; i++) {\n connector = connectors[i];\n if (!isAutoConnector(connector)) {\n var dist = point.distanceTo(connector.position());\n if (dist < minimumDistance) {\n minimumDistance = dist;\n resCtr = connector;\n }\n }\n }\n return resCtr;\n }\n\n function indicesOfItems(group, visuals) {\n var i, indices = [], visual;\n var children = group.drawingContainer().children;\n var length = children.length;\n for (i = 0; i < visuals.length; i++) {\n visual = visuals[i];\n for (var j = 0; j < length; j++) {\n if (children[j] == visual.drawingContainer()) {\n indices.push(j);\n break;\n }\n }\n }\n return indices;\n }\n\n var DiagramElement = Observable.extend({\n init: function(options) {\n var that = this;\n that.dataItem = (options || {}).dataItem;\n Observable.fn.init.call(that);\n that.options = deepExtend({ id: diagram.randomId() }, that.options, options);\n that.isSelected = false;\n that.visual = new Group({\n id: that.options.id,\n autoSize: that.options.autoSize\n });\n that.id = that.options.id;\n that._template();\n },\n\n options: {\n hover: {},\n cursor: Cursors.grip,\n content: {\n align: \"center middle\"\n },\n selectable: true,\n serializable: true,\n enable: true\n },\n\n _getCursor: function(point) {\n if (this.adorner) {\n return this.adorner._getCursor(point);\n }\n return this.options.cursor;\n },\n\n visible: function(value) {\n if (isUndefined(value)) {\n return this.visual.visible();\n } else {\n this.visual.visible(value);\n }\n },\n\n bounds: function() {\n },\n\n refresh: function() {\n this.visual.redraw();\n },\n\n position: function(point) {\n this.options.x = point.x;\n this.options.y = point.y;\n this.visual.position(point);\n },\n\n toString: function() {\n return this.options.id;\n },\n\n serialize: function() {\n // the options json object describes the shape perfectly. So this object can serve as shape serialization.\n var json = deepExtend({}, { options: this.options });\n if (this.dataItem) {\n json.dataItem = this.dataItem.toString();\n }\n return json;\n },\n\n _content: function(content) {\n if (content !== undefined$1) {\n var options = this.options;\n\n if (diagram.Utils.isString(content)) {\n options.content.text = content;\n } else {\n deepExtend(options.content, content);\n }\n\n var contentOptions = options.content;\n var contentVisual = this._contentVisual;\n\n if (!contentVisual) {\n this._createContentVisual(contentOptions);\n } else {\n this._updateContentVisual(contentOptions);\n }\n }\n\n return this.options.content.text;\n },\n\n _createContentVisual: function(options) {\n if (options.text) {\n this._contentVisual = new TextBlock(options);\n this._contentVisual._includeInBBox = false;\n this.visual.append(this._contentVisual);\n }\n },\n\n _updateContentVisual: function(options) {\n this._contentVisual.redraw(options);\n },\n\n _hitTest: function(point) {\n var bounds = this.bounds();\n return this.visible() && bounds.contains(point) && this.options.enable;\n },\n\n _template: function() {\n var that = this;\n if (that.options.content.template) {\n var data = that.dataItem || {},\n elementTemplate = kendo.template(that.options.content.template, {\n paramName: \"dataItem\"\n });\n\n that.options.content.text = elementTemplate(data);\n }\n },\n\n _canSelect: function() {\n return this.options.selectable !== false;\n },\n\n toJSON: function() {\n return {\n id: this.options.id\n };\n }\n });\n\n var Connector = Class.extend({\n init: function(shape, options) {\n this.options = deepExtend({}, this.options, options);\n this.connections = [];\n this.shape = shape;\n },\n options: {\n width: 7,\n height: 7,\n fill: {\n color: DEFAULT_CONNECTION_BACKGROUND\n },\n hover: {}\n },\n position: function() {\n if (this.options.position) {\n return this.options.position(this.shape);\n } else {\n return this.shape.getPosition(this.options.name);\n }\n },\n toJSON: function() {\n return {\n shapeId: this.shape.toString(),\n connector: this.options.name\n };\n }\n });\n\n Connector.parse = function(diagram, str) {\n var tempStr = str.split(\":\"),\n id = tempStr[0],\n name = tempStr[1] || AUTO;\n\n for (var i = 0; i < diagram.shapes.length; i++) {\n var shape = diagram.shapes[i];\n if (shape.options.id == id) {\n return shape.getConnector(name.trim());\n }\n }\n };\n\n var Shape = DiagramElement.extend({\n init: function(options, diagram) {\n var that = this;\n DiagramElement.fn.init.call(that, options);\n this.diagram = diagram;\n this.updateOptionsFromModel();\n options = that.options;\n that.connectors = [];\n that.type = options.type;\n that.createShapeVisual();\n that.updateBounds();\n that.content(that.content());\n\n that._createConnectors();\n },\n\n options: diagram.shapeDefaults(),\n\n _setOptionsFromModel: function(model) {\n var modelOptions = filterShapeDataItem(model || this.dataItem);\n this.options = deepExtend({}, this.options, modelOptions);\n\n this.redrawVisual();\n },\n\n updateOptionsFromModel: function(model, field) {\n if (this.diagram && this.diagram._isEditable) {\n var modelOptions = filterShapeDataItem(model || this.dataItem);\n\n if (model && field) {\n if (!dataviz.inArray(field, [\"x\", \"y\", \"width\", \"height\"])) {\n if (this.options.visual) {\n this._redrawVisual();\n } else if (modelOptions.type) {\n this.options = deepExtend({}, this.options, modelOptions);\n this._redrawVisual();\n }\n\n if (this.options.content) {\n this._template();\n this.content(this.options.content);\n }\n } else {\n var bounds = this.bounds();\n bounds[field] = model[field];\n this.bounds(bounds);\n }\n } else {\n this.options = deepExtend({}, this.options, modelOptions);\n }\n }\n },\n\n _redrawVisual: function() {\n this.visual.clear();\n this._contentVisual = null;\n this.options.dataItem = this.dataItem;\n this.createShapeVisual();\n this.updateBounds();\n },\n\n redrawVisual: function() {\n this._redrawVisual();\n if (this.options.content) {\n this._template();\n this.content(this.options.content);\n }\n },\n\n updateModel: function(syncChanges) {\n var diagram = this.diagram;\n if (diagram && diagram._isEditable) {\n var bounds = this._bounds;\n var model = this.dataItem;\n\n if (model) {\n diagram._suspendModelRefresh();\n if (defined(model.x) && bounds.x !== model.x) {\n model.set(\"x\", bounds.x);\n }\n\n if (defined(model.y) && bounds.y !== model.y) {\n model.set(\"y\", bounds.y);\n }\n\n if (defined(model.width) && bounds.width !== model.width) {\n model.set(\"width\", bounds.width);\n }\n\n if (defined(model.height) && bounds.height !== model.height) {\n model.set(\"height\", bounds.height);\n }\n\n this.dataItem = model;\n diagram._resumeModelRefresh();\n\n if (syncChanges) {\n diagram._syncShapeChanges();\n }\n }\n }\n },\n\n updateBounds: function() {\n var bounds = this.visual._measure(true);\n var options = this.options;\n this.bounds(new Rect(options.x, options.y, bounds.width, bounds.height));\n this._rotate();\n this._alignContent();\n },\n\n content: function(content) {\n var result = this._content(content);\n\n this._alignContent();\n\n return result;\n },\n\n _alignContent: function() {\n var contentOptions = this.options.content || {};\n var contentVisual = this._contentVisual;\n if (contentVisual && contentOptions.align) {\n var containerRect = this.visual._measure();\n var aligner = new diagram.RectAlign(containerRect);\n var contentBounds = contentVisual.drawingElement.bbox(null);\n\n var contentRect = new Rect(0, 0, contentBounds.width(), contentBounds.height());\n var alignedBounds = aligner.align(contentRect, contentOptions.align);\n\n contentVisual.position(alignedBounds.topLeft());\n }\n },\n\n _createConnectors: function() {\n var options = this.options,\n length = options.connectors.length,\n connectorDefaults = options.connectorDefaults,\n connector, i;\n\n for (i = 0; i < length; i++) {\n connector = new Connector(\n this, deepExtend({},\n connectorDefaults,\n options.connectors[i]\n )\n );\n this.connectors.push(connector);\n }\n },\n\n bounds: function(value) {\n var bounds;\n\n if (value) {\n if (isString(value)) {\n switch (value) {\n case TRANSFORMED :\n bounds = this._transformedBounds();\n break;\n case ABSOLUTE :\n bounds = this._transformedBounds();\n var pan = this.diagram._pan;\n bounds.x += pan.x;\n bounds.y += pan.y;\n break;\n case ROTATED :\n bounds = this._rotatedBounds();\n break;\n default:\n bounds = this._bounds;\n }\n } else {\n this._setBounds(value);\n this._triggerBoundsChange();\n if (!(this.diagram && this.diagram._layouting)) {\n this.refreshConnections();\n }\n }\n } else {\n bounds = this._bounds;\n }\n\n return bounds;\n },\n\n _setBounds: function(rect) {\n var options = this.options;\n var topLeft = rect.topLeft();\n var x = options.x = topLeft.x;\n var y = options.y = topLeft.y;\n var width = options.width = math.max(rect.width, options.minWidth);\n var height = options.height = math.max(rect.height, options.minHeight);\n\n this._bounds = new Rect(x, y, width, height);\n\n this.visual.redraw({\n x: x,\n y: y,\n width: width,\n height: height\n });\n },\n\n position: function(point) {\n if (point) {\n this.bounds(new Rect(point.x, point.y, this._bounds.width, this._bounds.height));\n } else {\n return this._bounds.topLeft();\n }\n },\n /**\n * Returns a clone of this shape.\n * @returns {Shape}\n */\n clone: function() {\n var json = this.serialize();\n\n json.options.id = diagram.randomId();\n\n if (this.diagram && this.diagram._isEditable && defined(this.dataItem)) {\n json.options.dataItem = cloneDataItem(this.dataItem);\n }\n\n return new Shape(json.options);\n },\n\n select: function(value) {\n var diagram = this.diagram, selected, deselected;\n if (isUndefined(value)) {\n value = true;\n }\n\n if (this._canSelect()) {\n if (this.isSelected != value) {\n selected = [];\n deselected = [];\n this.isSelected = value;\n if (this.isSelected) {\n diagram._selectedItems.push(this);\n selected.push(this);\n } else {\n Utils.remove(diagram._selectedItems, this);\n deselected.push(this);\n }\n\n if (!diagram._internalSelection) {\n diagram._selectionChanged(selected, deselected);\n }\n\n return true;\n }\n }\n },\n\n rotate: function(angle, center, undoable) { // we assume the center is always the center of the shape.\n var rotate = this.visual.rotate();\n if (angle !== undefined$1) {\n if (undoable !== false && this.diagram && this.diagram.undoRedoService && angle !== rotate.angle) {\n this.diagram.undoRedoService.add(\n new diagram.RotateUnit(this.diagram._resizingAdorner, [this], [rotate.angle]), false);\n }\n\n var b = this.bounds(),\n sc = new Point(b.width / 2, b.height / 2),\n deltaAngle,\n newPosition;\n\n if (center) {\n deltaAngle = angle - rotate.angle;\n newPosition = b.center().rotate(center, 360 - deltaAngle).minus(sc);\n this._rotationOffset = this._rotationOffset.plus(newPosition.minus(b.topLeft()));\n this.position(newPosition);\n }\n\n this.visual.rotate(angle, sc);\n this.options.rotation.angle = angle;\n\n if (this.diagram && this.diagram._connectorsAdorner) {\n this.diagram._connectorsAdorner.refresh();\n }\n\n this.refreshConnections();\n\n if (this.diagram) {\n this.diagram.trigger(ITEMROTATE, { item: this });\n }\n }\n\n return rotate;\n },\n\n connections: function(type) { // in, out, undefined = both\n var result = [], i, j, con, cons, ctr;\n\n for (i = 0; i < this.connectors.length; i++) {\n ctr = this.connectors[i];\n cons = ctr.connections;\n for (j = 0, cons; j < cons.length; j++) {\n con = cons[j];\n if (type == \"out\") {\n var source = con.source();\n if (source.shape && source.shape == this) {\n result.push(con);\n }\n } else if (type == \"in\") {\n var target = con.target();\n if (target.shape && target.shape == this) {\n result.push(con);\n }\n } else {\n result.push(con);\n }\n }\n }\n\n return result;\n },\n\n refreshConnections: function() {\n $.each(this.connections(), function() {\n this.refresh();\n });\n },\n /**\n * Gets a connector of this shape either by the connector's supposed name or\n * via a Point in which case the closest connector will be returned.\n * @param nameOrPoint The name of a Connector or a Point.\n * @returns {Connector}\n */\n getConnector: function(nameOrPoint) {\n var i, ctr;\n if (isString(nameOrPoint)) {\n nameOrPoint = nameOrPoint.toLocaleLowerCase();\n for (i = 0; i < this.connectors.length; i++) {\n ctr = this.connectors[i];\n if (ctr.options.name.toLocaleLowerCase() == nameOrPoint) {\n return ctr;\n }\n }\n } else if (nameOrPoint instanceof Point) {\n return closestConnector(nameOrPoint, this.connectors);\n } else {\n return this.connectors.length ? this.connectors[0] : null;\n }\n },\n\n getPosition: function(side) {\n var b = this.bounds(),\n fnName = side.charAt(0).toLowerCase() + side.slice(1);\n\n if (isFunction(b[fnName])) {\n return this._transformPoint(b[fnName]());\n }\n\n return b.center();\n },\n\n redraw: function(options) {\n if (options) {\n var shapeOptions = this.options;\n var boundsChange;\n\n this.shapeVisual.redraw(this._visualOptions(options));\n\n if (this._diffNumericOptions(options, [WIDTH, HEIGHT, X, Y])) {\n this.bounds(new Rect(shapeOptions.x, shapeOptions.y, shapeOptions.width, shapeOptions.height));\n boundsChange = true;\n }\n\n if (options.connectors) {\n shapeOptions.connectors = options.connectors;\n this._updateConnectors();\n }\n\n shapeOptions = deepExtend(shapeOptions, options);\n\n if (options.rotation || boundsChange) {\n this._rotate();\n }\n\n if (shapeOptions.content) {\n this.content(shapeOptions.content);\n }\n }\n },\n\n _updateConnectors: function() {\n var connections = this.connections();\n this.connectors = [];\n this._createConnectors();\n var connection;\n var source;\n var target;\n\n for (var idx = 0; idx < connections.length; idx++) {\n connection = connections[idx];\n source = connection.source();\n target = connection.target();\n if (source.shape && source.shape === this) {\n connection.source(this.getConnector(source.options.name) || null);\n } else if (target.shape && target.shape === this) {\n connection.target(this.getConnector(target.options.name) || null);\n }\n connection.updateModel();\n }\n },\n\n _diffNumericOptions: diagram.diffNumericOptions,\n\n _visualOptions: function(options) {\n return {\n data: options.path,\n source: options.source,\n hover: options.hover,\n fill: options.fill,\n stroke: options.stroke\n };\n },\n\n _triggerBoundsChange: function() {\n if (this.diagram) {\n this.diagram.trigger(ITEMBOUNDSCHANGE, { item: this, bounds: this._bounds.clone() }); // the trigger modifies the arguments internally.\n }\n },\n\n _transformPoint: function(point) {\n var rotate = this.rotate(),\n bounds = this.bounds(),\n tl = bounds.topLeft();\n\n if (rotate.angle) {\n point.rotate(rotate.center().plus(tl), 360 - rotate.angle);\n }\n\n return point;\n },\n\n _transformedBounds: function() {\n var bounds = this.bounds(),\n tl = bounds.topLeft(),\n br = bounds.bottomRight();\n\n return Rect.fromPoints(this.diagram.modelToView(tl), this.diagram.modelToView(br));\n },\n\n _rotatedBounds: function() {\n var bounds = this.bounds().rotatedBounds(this.rotate().angle),\n tl = bounds.topLeft(),\n br = bounds.bottomRight();\n\n return Rect.fromPoints(tl, br);\n },\n\n _rotate: function() {\n var rotation = this.options.rotation;\n\n if (rotation && rotation.angle) {\n this.rotate(rotation.angle);\n }\n\n this._rotationOffset = new Point();\n },\n\n _hover: function(value) {\n var options = this.options,\n hover = options.hover,\n stroke = options.stroke,\n fill = options.fill;\n\n if (value && isDefined(hover.stroke)) {\n stroke = deepExtend({}, stroke, hover.stroke);\n }\n\n if (value && isDefined(hover.fill)) {\n fill = hover.fill;\n }\n\n this.shapeVisual.redraw({\n stroke: stroke,\n fill: fill\n });\n\n if (options.editable && options.editable.connect) {\n this.diagram._showConnectors(this, value);\n }\n },\n\n _hitTest: function(value) {\n if (this.visible()) {\n var bounds = this.bounds(), rotatedPoint,\n angle = this.rotate().angle;\n\n if (value.isEmpty && !value.isEmpty()) { // rect selection\n return Intersect.rects(value, bounds, angle ? angle : 0);\n } else { // point\n rotatedPoint = value.clone().rotate(bounds.center(), angle); // cloning is important because rotate modifies the point inline.\n if (bounds.contains(rotatedPoint)) {\n return this;\n }\n }\n }\n },\n\n toJSON: function() {\n return {\n shapeId: this.options.id\n };\n },\n\n createShapeVisual: function() {\n var options = this.options;\n var visualOptions = this._visualOptions(options);\n var visualTemplate = options.visual;\n var type = (options.type + \"\").toLocaleLowerCase();\n var shapeVisual;\n\n visualOptions.width = options.width;\n visualOptions.height = options.height;\n\n if (isFunction(visualTemplate)) { // custom template\n shapeVisual = visualTemplate.call(this, options);\n } else if (visualOptions.data) {\n shapeVisual = new Path(visualOptions);\n translateToOrigin(shapeVisual);\n } else if (type == \"rectangle\") {\n shapeVisual = new Rectangle(visualOptions);\n } else if (type == \"circle\") {\n shapeVisual = new Circle(visualOptions);\n } else if (type == \"text\") {\n shapeVisual = new TextBlock(visualOptions);\n } else if (type == \"image\") {\n shapeVisual = new Image(visualOptions);\n } else {\n shapeVisual = new Path(visualOptions);\n }\n\n this.shapeVisual = shapeVisual;\n this.visual.append(this.shapeVisual);\n }\n });\n\n /**\n * The visual link between two Shapes through the intermediate of Connectors.\n */\n var Connection = DiagramElement.extend({\n init: function(from, to, options) {\n var that = this;\n DiagramElement.fn.init.call(that, options);\n this.updateOptionsFromModel();\n this._initRouter();\n that.path = new diagram.Polyline(that.options);\n that.path.fill(TRANSPARENT);\n that.visual.append(that.path);\n that._sourcePoint = that._targetPoint = new Point();\n that._setSource(from);\n that._setTarget(to);\n that.content(that.options.content);\n that.definers = [];\n if (defined(options) && options.points) {\n that.points(options.points);\n }\n },\n\n options: {\n hover: {\n stroke: {}\n },\n startCap: NONE,\n endCap: NONE,\n points: [],\n selectable: true,\n fromConnector: AUTO,\n toConnector: AUTO\n },\n\n _setOptionsFromModel: function(model) {\n this.updateOptionsFromModel(model || this.dataItem);\n },\n\n updateOptionsFromModel: function(model) {\n if (this.diagram && this.diagram._isEditable) {\n var dataMap = this.diagram._dataMap;\n var options = filterConnectionDataItem(model || this.dataItem);\n\n if (model) {\n if (defined(options.from)) {\n var from = dataMap[options.from];\n if (from && defined(options.fromConnector)) {\n from = from.getConnector(options.fromConnector);\n }\n this.source(from);\n } else if (defined(options.fromX) && defined(options.fromY)) {\n this.source(new Point(options.fromX, options.fromY));\n }\n\n if (defined(options.to)) {\n var to = dataMap[options.to];\n if (to && defined(options.toConnector)) {\n to = to.getConnector(options.toConnector);\n }\n this.target(to);\n } else if (defined(options.toX) && defined(options.toY)) {\n this.target(new Point(options.toX, options.toY));\n }\n\n if (defined(options.type) && this.type() !== options.type) {\n this.points([]);\n this.type(options.type);\n }\n\n this.dataItem = model;\n\n this._template();\n this.redraw(this.options);\n } else {\n this.options = deepExtend({}, options, this.options);\n }\n }\n },\n\n updateModel: function(syncChanges) {\n if (this.diagram && this.diagram._isEditable) {\n if (this.diagram.connectionsDataSource) {\n var model = this.diagram.connectionsDataSource.getByUid(this.dataItem.uid);\n\n if (model) {\n this.diagram._suspendModelRefresh();\n if (defined(this.options.fromX) && this.options.fromX !== null) {\n clearField(\"from\", model);\n clearField(\"fromConnector\", model);\n model.set(\"fromX\", this.options.fromX);\n model.set(\"fromY\", this.options.fromY);\n } else {\n model.set(\"from\", this.options.from);\n if (defined(model.fromConnector)) {\n model.set(\"fromConnector\", this.sourceConnector ? this.sourceConnector.options.name : null);\n }\n clearField(\"fromX\", model);\n clearField(\"fromY\", model);\n }\n\n if (defined(this.options.toX) && this.options.toX !== null) {\n clearField(\"to\", model);\n clearField(\"toConnector\", model);\n model.set(\"toX\", this.options.toX);\n model.set(\"toY\", this.options.toY);\n } else {\n model.set(\"to\", this.options.to);\n if (defined(model.toConnector)) {\n model.set(\"toConnector\", this.targetConnector ? this.targetConnector.options.name : null);\n }\n clearField(\"toX\", model);\n clearField(\"toY\", model);\n }\n\n if (defined(this.options.type) && defined(model.type)) {\n model.set(\"type\", this.options.type);\n }\n\n this.dataItem = model;\n this.diagram._resumeModelRefresh();\n\n if (syncChanges) {\n this.diagram._syncConnectionChanges();\n }\n }\n }\n }\n },\n\n /**\n * Gets the Point where the source of the connection resides.\n * If the endpoint in Auto-connector the location of the resolved connector will be returned.\n * If the endpoint is floating the location of the endpoint is returned.\n */\n sourcePoint: function() {\n return this._resolvedSourceConnector ? this._resolvedSourceConnector.position() : this._sourcePoint;\n },\n\n _setSource: function(source) {\n var shapeSource = source instanceof Shape;\n var defaultConnector = this.options.fromConnector || AUTO;\n var dataItem;\n if (shapeSource && !source.getConnector(defaultConnector)) {\n return;\n }\n\n if (source !== undefined$1) {\n this.from = source;\n }\n\n this._removeFromSourceConnector();\n\n if (source === null) { // detach\n if (this.sourceConnector) {\n this._sourcePoint = (this._resolvedSourceConnector || this.sourceConnector).position();\n this._clearSourceConnector();\n this._setFromOptions(null, this._sourcePoint);\n }\n } else if (source instanceof Connector) {\n dataItem = source.shape.dataItem;\n if (dataItem) {\n this._setFromOptions(dataItem.id);\n }\n this.sourceConnector = source;\n this.sourceConnector.connections.push(this);\n } else if (source instanceof Point) {\n this._setFromOptions(null, source);\n this._sourcePoint = source;\n if (this.sourceConnector) {\n this._clearSourceConnector();\n }\n\n } else if (shapeSource) {\n dataItem = source.dataItem;\n if (dataItem) {\n this._setFromOptions(dataItem.id);\n }\n\n this.sourceConnector = source.getConnector(defaultConnector);\n this.sourceConnector.connections.push(this);\n }\n },\n\n source: function(source, undoable) {\n if (isDefined(source)) {\n if (undoable && this.diagram) {\n this.diagram.undoRedoService.addCompositeItem(new diagram.ConnectionEditUnit(this, source));\n }\n this._setSource(source);\n this.refresh();\n }\n return this.sourceConnector ? this.sourceConnector : this._sourcePoint;\n },\n\n _setFromOptions: function(from, fromPoint) {\n this.options.from = from;\n if (fromPoint) {\n this.options.fromX = fromPoint.x;\n this.options.fromY = fromPoint.y;\n } else {\n this.options.fromX = null;\n this.options.fromY = null;\n }\n },\n\n /**\n * Gets or sets the PathDefiner of the sourcePoint.\n * The left part of this definer is always null since it defines the source tangent.\n * @param value\n * @returns {*}\n */\n sourceDefiner: function(value) {\n if (value) {\n if (value instanceof diagram.PathDefiner) {\n value.left = null;\n this._sourceDefiner = value;\n this.source(value.point); // refresh implicit here\n } else {\n throw \"The sourceDefiner needs to be a PathDefiner.\";\n }\n } else {\n if (!this._sourceDefiner) {\n this._sourceDefiner = new diagram.PathDefiner(this.sourcePoint(), null, null);\n }\n return this._sourceDefiner;\n }\n },\n\n /**\n * Gets the Point where the target of the connection resides.\n */\n targetPoint: function() {\n return this._resolvedTargetConnector ? this._resolvedTargetConnector.position() : this._targetPoint;\n },\n\n _setTarget: function(target) {\n var shapeTarget = target instanceof Shape;\n var defaultConnector = this.options.toConnector || AUTO;\n var dataItem;\n\n if (shapeTarget && !target.getConnector(defaultConnector)) {\n return;\n }\n\n if (target !== undefined$1) {\n this.to = target;\n }\n\n this._removeFromTargetConnector();\n\n if (target === null) { // detach\n if (this.targetConnector) {\n this._targetPoint = (this._resolvedTargetConnector || this.targetConnector).position();\n this._clearTargetConnector();\n this._setToOptions(null, this._targetPoint);\n }\n } else if (target instanceof Connector) {\n dataItem = target.shape.dataItem;\n if (dataItem) {\n this._setToOptions(dataItem.id);\n }\n this.targetConnector = target;\n this.targetConnector.connections.push(this);\n } else if (target instanceof Point) {\n this._setToOptions(null, target);\n this._targetPoint = target;\n if (this.targetConnector) {\n this._clearTargetConnector();\n }\n } else if (shapeTarget) {\n dataItem = target.dataItem;\n if (dataItem) {\n this._setToOptions(dataItem.id);\n }\n this.targetConnector = target.getConnector(defaultConnector);\n this.targetConnector.connections.push(this);\n }\n },\n\n target: function(target, undoable) {\n if (isDefined(target)) {\n if (undoable && this.diagram) {\n this.diagram.undoRedoService.addCompositeItem(new diagram.ConnectionEditUnit(this, undefined$1, target));\n }\n this._setTarget(target);\n\n this.refresh();\n }\n return this.targetConnector ? this.targetConnector : this._targetPoint;\n },\n\n _setToOptions: function(to, toPoint) {\n this.options.to = to;\n if (toPoint) {\n this.options.toX = toPoint.x;\n this.options.toY = toPoint.y;\n } else {\n this.options.toX = null;\n this.options.toY = null;\n }\n },\n\n /**\n * Gets or sets the PathDefiner of the targetPoint.\n * The right part of this definer is always null since it defines the target tangent.\n * @param value\n * @returns {*}\n */\n targetDefiner: function(value) {\n if (value) {\n if (value instanceof diagram.PathDefiner) {\n value.right = null;\n this._targetDefiner = value;\n this.target(value.point); // refresh implicit here\n } else {\n throw \"The sourceDefiner needs to be a PathDefiner.\";\n }\n } else {\n if (!this._targetDefiner) {\n this._targetDefiner = new diagram.PathDefiner(this.targetPoint(), null, null);\n }\n return this._targetDefiner;\n }\n },\n\n _updateConnectors: function() {\n this._updateConnector(this.source(), \"source\");\n this._updateConnector(this.target(), \"target\");\n },\n\n _updateConnector: function(instance, name) {\n var that = this;\n var diagram = that.diagram;\n if (instance instanceof Connector && !diagram.getShapeById(instance.shape.id)) {\n var dataItem = instance.shape.dataItem;\n var connectorName = instance.options.name;\n var setNewTarget = function() {\n var shape = diagram._dataMap[dataItem.id];\n instance = shape.getConnector(connectorName);\n that[name](instance, false);\n that.updateModel();\n };\n if (diagram._dataMap[dataItem.id]) {\n setNewTarget();\n } else {\n var inactiveItem = diagram._inactiveShapeItems.getByUid(dataItem.uid);\n if (inactiveItem) {\n diagram._deferredConnectionUpdates.push(inactiveItem.onActivate(setNewTarget));\n }\n }\n } else {\n that[name](instance, false);\n }\n },\n\n content: function(content) {\n var result = this._content(content);\n if (defined(content)) {\n this._alignContent();\n }\n return result;\n },\n\n _createContentVisual: function(options) {\n var visual;\n if (isFunction(options.visual)) {\n visual = options.visual.call(this, options);\n } else if (options.text) {\n visual = new TextBlock(options);\n }\n\n if (visual) {\n this._contentVisual = visual;\n visual._includeInBBox = false;\n this.visual.append(visual);\n }\n\n return visual;\n },\n\n _updateContentVisual: function(options) {\n if (isFunction(options.visual)) {\n this.visual.remove(this._contentVisual);\n this._createContentVisual(options);\n } else {\n this._contentVisual.redraw(options);\n }\n },\n\n _alignContent: function() {\n if (this._contentVisual) {\n var offset = CONNECTION_CONTENT_OFFSET;\n var points = this.allPoints();\n var endIdx = math.floor(points.length / 2);\n var startIdx = endIdx - 1;\n\n while (startIdx > 0 && points[startIdx].equals(points[endIdx])) {\n startIdx--;\n endIdx++;\n }\n\n var endPoint = points[endIdx];\n var startPoint = points[startIdx];\n\n var boundingBox = this._contentVisual._measure();\n var width = boundingBox.width;\n var height = boundingBox.height;\n var alignToPath = points.length % 2 === 0;\n var distance = startPoint.distanceTo(endPoint);\n\n if (alignToPath && points.length > 2 && distance > 0 &&\n ((startPoint.y === endPoint.y && distance < width) || (startPoint.x === endPoint.x && distance < height))) {\n alignToPath = false;\n offset = 0;\n }\n\n var point;\n\n if (alignToPath) {\n var angle = draw.util.deg(math.atan2(endPoint.y - startPoint.y, endPoint.x - startPoint.x));\n point = new Point((endPoint.x - startPoint.x) / 2 + startPoint.x, (endPoint.y - startPoint.y) / 2 + startPoint.y);\n\n if (math.abs(angle) === 90) {\n point.x += offset;\n point.y -= height / 2;\n } else if (angle % 180 === 0) {\n point.x -= width / 2;\n point.y -= height + offset;\n } else if (angle < -90 || (0 < angle && angle < 90)) {\n point.y -= height;\n } else if (angle < 0 || angle > 90) {\n point.x -= width;\n point.y -= height;\n }\n } else {\n var midIdx = math.floor(points.length / 2);\n point = points[midIdx].clone();\n startPoint = points[midIdx - 1];\n endPoint = points[midIdx + 1];\n\n var offsetX = startPoint.x <= point.x && endPoint.x <= point.x ? offset : -boundingBox.width - offset;\n var offsetY = startPoint.y <= point.y && endPoint.y <= point.y ? offset : -boundingBox.height - offset;\n\n point.x += offsetX;\n point.y += offsetY;\n }\n\n this._contentVisual.position(point);\n }\n },\n\n /**\n * Selects or unselects this connections.\n * @param value True to select, false to unselect.\n */\n select: function(value) {\n var diagram = this.diagram, selected, deselected;\n if (this._canSelect()) {\n if (this.isSelected !== value) {\n this.isSelected = value;\n selected = [];\n deselected = [];\n if (this.isSelected) {\n this.adorner = new ConnectionEditAdorner(this, this.options.selection);\n diagram._adorn(this.adorner, true);\n diagram._selectedItems.push(this);\n selected.push(this);\n } else {\n if (this.adorner) {\n diagram._adorn(this.adorner, false);\n Utils.remove(diagram._selectedItems, this);\n this.adorner = undefined$1;\n deselected.push(this);\n }\n }\n\n if (this.adorner) {\n this.adorner.refresh();\n }\n\n if (!diagram._internalSelection) {\n diagram._selectionChanged(selected, deselected);\n }\n return true;\n }\n }\n },\n /**\n * Gets or sets the bounds of this connection.\n * @param value A Rect object.\n * @remark This is automatically set in the refresh().\n * @returns {Rect}\n */\n bounds: function(value) {\n if (value && !isString(value)) {\n this._bounds = value;\n } else {\n return this._bounds;\n }\n },\n /**\n * Gets or sets the connection type (see ConnectionType enumeration).\n * @param value A ConnectionType value.\n * @returns {ConnectionType}\n */\n type: function(value) {\n var options = this.options;\n if (value) {\n if (value !== options.type) {\n options.type = value;\n this._initRouter();\n this.refresh();\n }\n } else {\n return options.type;\n }\n },\n\n _initRouter: function() {\n var type = (this.options.type || \"\").toLowerCase();\n if (type == CASCADING) {\n this._router = new CascadingRouter(this);\n } else {\n this._router = new PolylineRouter(this);\n }\n },\n /**\n * Gets or sets the collection of *intermediate* points.\n * The 'allPoints()' property will return all the points.\n * The 'definers' property returns the definers of the intermediate points.\n * The 'sourceDefiner' and 'targetDefiner' return the definers of the endpoints.\n * @param value\n */\n points: function(value) {\n if (value) {\n this.definers = [];\n for (var i = 0; i < value.length; i++) {\n var definition = value[i];\n if (definition instanceof diagram.Point) {\n this.definers.push(new diagram.PathDefiner(definition));\n } else if (definition.hasOwnProperty(\"x\") && definition.hasOwnProperty(\"y\")) { // e.g. Clipboard does not preserve the Point definition and tunred into an Object\n this.definers.push(new diagram.PathDefiner(new Point(definition.x, definition.y)));\n } else {\n throw \"A Connection point needs to be a Point or an object with x and y properties.\";\n }\n }\n\n } else {\n var pts = [];\n if (isDefined(this.definers)) {\n for (var k = 0; k < this.definers.length; k++) {\n pts.push(this.definers[k].point);\n }\n }\n return pts;\n }\n },\n /**\n * Gets all the points of this connection. This is the combination of the sourcePoint, the points and the targetPoint.\n * @returns {Array}\n */\n allPoints: function() {\n var pts = [this.sourcePoint()];\n if (this.definers) {\n for (var k = 0; k < this.definers.length; k++) {\n pts.push(this.definers[k].point);\n }\n }\n pts.push(this.targetPoint());\n return pts;\n },\n\n refresh: function() {\n this._resolveConnectors();\n this._refreshPath();\n this._alignContent();\n\n if (this.adorner) {\n this.adorner.refresh();\n }\n },\n\n _resolveConnectors: function() {\n var connection = this,\n sourcePoint, targetPoint,\n sourceConnectors, targetConnectors,\n source = connection.source(),\n target = connection.target();\n\n if (source instanceof Point) {\n sourcePoint = source;\n } else if (source instanceof Connector) {\n if (isAutoConnector(source)) {\n sourceConnectors = source.shape.connectors;\n } else {\n sourceConnectors = [source];\n }\n }\n\n if (target instanceof Point) {\n targetPoint = target;\n } else if (target instanceof Connector) {\n if (isAutoConnector(target)) {\n targetConnectors = target.shape.connectors;\n } else {\n targetConnectors = [target];\n }\n }\n\n if (sourcePoint) {\n if (targetConnectors) {\n connection._resolvedTargetConnector = closestConnector(sourcePoint, targetConnectors);\n }\n } else if (sourceConnectors) {\n if (targetPoint) {\n connection._resolvedSourceConnector = closestConnector(targetPoint, sourceConnectors);\n } else if (targetConnectors) {\n this._resolveAutoConnectors(sourceConnectors, targetConnectors);\n }\n }\n },\n\n _resolveAutoConnectors: function(sourceConnectors, targetConnectors) {\n var minNonConflict = MAXINT;\n var minDist = MAXINT;\n var minNonConflictSource, minNonConflictTarget;\n var sourcePoint, targetPoint;\n var minSource, minTarget;\n var sourceConnector, targetConnector;\n var sourceIdx, targetIdx;\n var dist;\n\n for (sourceIdx = 0; sourceIdx < sourceConnectors.length; sourceIdx++) {\n sourceConnector = sourceConnectors[sourceIdx];\n if (!isAutoConnector(sourceConnector)) {\n sourcePoint = sourceConnector.position();\n\n for (targetIdx = 0; targetIdx < targetConnectors.length; targetIdx++) {\n targetConnector = targetConnectors[targetIdx];\n if (!isAutoConnector(targetConnector)) {\n targetPoint = targetConnector.position();\n dist = math.round(sourcePoint.distanceTo(targetPoint));\n\n if (dist < minNonConflict && this.diagram && this._testRoutePoints(sourcePoint, targetPoint, sourceConnector, targetConnector)) {\n minNonConflict = dist;\n minNonConflictSource = sourceConnector;\n minNonConflictTarget = targetConnector;\n }\n\n if (dist < minDist) {\n minSource = sourceConnector;\n minTarget = targetConnector;\n minDist = dist;\n }\n }\n }\n }\n }\n\n if (minNonConflictSource) {\n minSource = minNonConflictSource;\n minTarget = minNonConflictTarget;\n }\n\n this._resolvedSourceConnector = minSource;\n this._resolvedTargetConnector = minTarget;\n },\n\n _testRoutePoints: function(sourcePoint, targetPoint, sourceConnector, targetConnector) {\n var router = this._router;\n var passRoute = true;\n if (router instanceof CascadingRouter) {\n var points = router.routePoints(sourcePoint, targetPoint, sourceConnector, targetConnector),\n start, end,\n rect, exclude;\n\n exclude = this._getRouteExclude(sourcePoint, targetPoint, sourceConnector.shape, targetConnector.shape);\n points.unshift(sourcePoint);\n points.push(targetPoint);\n\n\n for (var idx = 1; idx < points.length; idx++) {\n start = points[idx - 1];\n end = points[idx];\n rect = new Rect(math.min(start.x, end.x), math.min(start.y, end.y),\n math.abs(start.x - end.x), math.abs(start.y - end.y));\n if (rect.width > 0) {\n rect.x++;\n rect.width -= 2;\n }\n if (rect.height > 0) {\n rect.y++;\n rect.height -= 2;\n }\n\n if (!rect.isEmpty() && this.diagram._shapesQuadTree.hitTestRect(rect, exclude)) {\n passRoute = false;\n break;\n }\n }\n }\n return passRoute;\n },\n\n _getRouteExclude: function(sourcePoint, targetPoint, sourceShape, targetShape) {\n var exclude = [];\n if (this._isPointInsideShape(sourcePoint, sourceShape)) {\n exclude.push(sourceShape);\n }\n if (this._isPointInsideShape(targetPoint, targetShape)) {\n exclude.push(targetShape);\n }\n return exclude;\n },\n\n _isPointInsideShape: function(point, shape) {\n var bounds = shape.bounds(), rotatedPoint,\n angle = shape.rotate().angle,\n pointX, pointY,\n boundsX = bounds.x,\n boundsY = bounds.y;\n\n rotatedPoint = point.clone().rotate(bounds.center(), angle);\n pointX = rotatedPoint.x;\n pointY = rotatedPoint.y;\n return pointX > boundsX && pointX < (boundsX + bounds.width) && pointY > boundsY && pointY < (boundsY + bounds.height);\n },\n\n redraw: function(options) {\n if (options) {\n this.options = deepExtend({}, this.options, options);\n\n var points = this.options.points;\n\n if (defined(points) && points.length > 0) {\n this.points(points);\n this._refreshPath();\n }\n\n if ((options && options.content) || options.text) {\n this.content(options.content);\n }\n\n this.path.redraw({\n fill: options.fill,\n stroke: options.stroke,\n startCap: options.startCap,\n endCap: options.endCap\n });\n }\n },\n /**\n * Returns a clone of this connection.\n * @returns {Connection}\n */\n clone: function() {\n var json = this.serialize();\n\n if (this.diagram && this.diagram._isEditable && defined(this.dataItem)) {\n json.options.dataItem = cloneDataItem(this.dataItem);\n }\n\n return new Connection(this.from, this.to, json.options);\n },\n /**\n * Returns a serialized connection in json format. Consist of the options and the dataItem.\n * @returns {Connection}\n */\n serialize: function() {\n var from = this.from.toJSON ? this.from.toJSON : this.from.toString(),\n to = this.to.toJSON ? this.to.toJSON : this.to.toString();\n\n var json = deepExtend({}, {\n options: this.options,\n from: from,\n to: to\n });\n\n if (defined(this.dataItem)) {\n json.dataItem = this.dataItem.toString();\n }\n\n json.options.points = this.points();\n return json;\n },\n\n /**\n * Returns whether the given Point or Rect hits this connection.\n * @param value\n * @returns {Connection}\n * @private\n */\n _hitTest: function(value) {\n if (this.visible()) {\n var p = new Point(value.x, value.y), from = this.sourcePoint(), to = this.targetPoint();\n if (value.isEmpty && !value.isEmpty() && value.contains(from) && value.contains(to)) {\n return this;\n }\n if (this._router.hitTest(p)) {\n return this;\n }\n }\n },\n\n _hover: function(value) {\n var color = (this.options.stroke || {}).color;\n\n if (value && isDefined(this.options.hover.stroke.color)) {\n color = this.options.hover.stroke.color;\n }\n\n this.path.redraw({\n stroke: {\n color: color\n }\n });\n },\n\n _refreshPath: function() {\n if (!defined(this.path)) {\n return;\n }\n this._drawPath();\n this.bounds(this._router.getBounds());\n },\n\n _drawPath: function() {\n if (this._router) {\n this._router.route(); // sets the intermediate points\n }\n var source = this.sourcePoint();\n var target = this.targetPoint();\n var points = this.points();\n\n this.path.redraw({\n points: [source].concat(points, [target])\n });\n },\n\n _clearSourceConnector: function() {\n this.sourceConnector = undefined$1;\n this._resolvedSourceConnector = undefined$1;\n },\n\n _clearTargetConnector: function() {\n this.targetConnector = undefined$1;\n this._resolvedTargetConnector = undefined$1;\n },\n\n _removeFromSourceConnector: function() {\n if (this.sourceConnector) {\n Utils.remove(this.sourceConnector.connections, this);\n }\n },\n\n _removeFromTargetConnector: function() {\n if (this.targetConnector) {\n Utils.remove(this.targetConnector.connections, this);\n }\n },\n\n toJSON: function() {\n var connection = this;\n var from, to, point;\n if (connection.from && connection.from.toJSON) {\n from = connection.from.toJSON();\n } else {\n point = connection._sourcePoint;\n from = {\n x: point.x,\n y: point.y\n };\n }\n\n if (connection.to && connection.to.toJSON) {\n to = connection.to.toJSON();\n } else {\n point = connection._targetPoint;\n to = {\n x: point.x,\n y: point.y\n };\n }\n\n return {\n from: from,\n to: to\n };\n }\n });\n\n var Diagram = Widget.extend({\n init: function(element, userOptions) {\n var that = this;\n\n kendo.destroy(element);\n Widget.fn.init.call(that, element, userOptions);\n\n that._initTheme();\n\n that._initElements();\n that._extendLayoutOptions(that.options);\n that._initDefaults(userOptions);\n that._interactionDefaults();\n\n that._initCanvas();\n\n that.mainLayer = new Group({\n id: \"main-layer\"\n });\n that.canvas.append(that.mainLayer);\n\n that._shapesQuadTree = new ShapesQuadTree(that);\n\n that._pan = new Point();\n that._adorners = [];\n that.adornerLayer = new Group({\n id: \"adorner-layer\"\n });\n that.canvas.append(that.adornerLayer);\n\n that._createHandlers();\n\n that._initialize();\n\n that._resizingAdorner = new ResizingAdorner(that, { editable: that.options.editable });\n that._connectorsAdorner = new ConnectorsAdorner(that);\n\n that._adorn(that._resizingAdorner, true);\n that._adorn(that._connectorsAdorner, true);\n\n that.selector = new Selector(that);\n // TODO: We may consider using real Clipboard API once is supported by the standard.\n that._clipboard = [];\n\n that.pauseMouseHandlers = false;\n\n that._fetchFreshData();\n\n that._createGlobalToolBar();\n\n that._createOptionElements();\n\n that.zoom(that.options.zoom);\n\n that.canvas.draw();\n },\n\n options: {\n name: \"Diagram\",\n theme: \"default\",\n layout: \"\",\n zoomRate: 0.1,\n zoom: 1,\n zoomMin: 0,\n zoomMax: 2,\n dataSource: {},\n draggable: true,\n template: \"\",\n autoBind: true,\n editable: {\n rotate: {},\n resize: {},\n text: true,\n tools: [],\n drag: {\n snap: {\n size: 10,\n angle: 10\n }\n },\n remove: true\n },\n pannable: {},\n selectable: {\n key: \"none\"\n },\n tooltip: { enabled: true, format: \"{0}\" },\n copy: {\n enabled: true,\n offsetX: 20,\n offsetY: 20\n },\n shapeDefaults: diagram.shapeDefaults({ undoable: true }),\n connectionDefaults: {\n editable: {\n tools: []\n },\n type: CASCADING\n },\n shapes: [],\n connections: []\n },\n\n events: [\n ZOOM_END,\n ZOOM_START,\n PAN, SELECT,\n ITEMROTATE,\n ITEMBOUNDSCHANGE,\n CHANGE,\n CLICK,\n MOUSE_ENTER,\n MOUSE_LEAVE,\n \"toolBarClick\",\n \"save\",\n \"cancel\",\n \"edit\",\n \"remove\",\n \"add\",\n \"dataBound\",\n DRAG_START,\n DRAG,\n DRAG_END\n ],\n\n items: function() {\n return $();\n },\n\n _createGlobalToolBar: function() {\n var editable = this.options.editable;\n if (editable) {\n var tools = editable.tools;\n if (this._isEditable && tools !== false && (!tools || tools.length === 0)) {\n tools = [\"createShape\", \"undo\", \"redo\", \"rotateClockwise\", \"rotateAnticlockwise\"];\n }\n\n if (tools && tools.length) {\n this.toolBar = new DiagramToolBar(this, {\n tools: tools || {},\n click: this._toolBarClick.bind(this),\n modal: false\n });\n\n this.toolBar.element.css({\n textAlign: \"left\"\n });\n\n this.element.prepend(this.toolBar.element);\n this._resize();\n }\n }\n },\n\n createShape: function() {\n if ((this.editor && this.editor.end()) || !this.editor) {\n var dataSource = this.dataSource;\n var view = dataSource.view() || [];\n var index = view.length;\n var model = createModel(dataSource, {});\n var shape = this._createShape(model, {});\n\n if (!this.trigger(\"add\", { shape: shape })) {\n dataSource.insert(index, model);\n var inactiveItem = this._inactiveShapeItems.getByUid(model.uid);\n inactiveItem.element = shape;\n this.edit(shape);\n }\n }\n },\n\n _createShape: function(dataItem, options) {\n options = deepExtend({}, this.options.shapeDefaults, options);\n options.dataItem = dataItem;\n var shape = new Shape(options, this);\n return shape;\n },\n\n createConnection: function() {\n if (((this.editor && this.editor.end()) || !this.editor)) {\n var connectionsDataSource = this.connectionsDataSource;\n var view = connectionsDataSource.view() || [];\n var index = view.length;\n var model = createModel(connectionsDataSource, {});\n var connection = this._createConnection(model);\n if (!this.trigger(\"add\", { connection: connection })) {\n this._connectionsDataMap[model.uid] = connection;\n connectionsDataSource.insert(index, model);\n this.addConnection(connection, false);\n this.edit(connection);\n }\n }\n },\n\n _createConnection: function(dataItem, source, target) {\n var options = deepExtend({}, this.options.connectionDefaults);\n options.dataItem = dataItem;\n\n var connection = new Connection(source || new Point(), target || new Point(), options);\n\n return connection;\n },\n\n editModel: function(dataItem, editorType) {\n this.cancelEdit();\n var editors, template;\n var editable = this.options.editable;\n\n if (editorType == \"shape\") {\n editors = editable.shapeEditors;\n template = editable.shapeTemplate;\n } else if (editorType == \"connection\") {\n var connectionSelectorHandler = connectionSelector.bind(this);\n editors = deepExtend({}, { from: connectionSelectorHandler, to: connectionSelectorHandler }, editable.connectionEditors);\n template = editable.connectionTemplate;\n } else {\n return;\n }\n\n this.editor = new PopupEditor(this.element, {\n update: this._update.bind(this),\n cancel: this._cancel.bind(this),\n model: dataItem,\n type: editorType,\n target: this,\n editors: editors,\n template: template\n });\n\n this.trigger(\"edit\", this._editArgs());\n },\n\n edit: function(item) {\n if (item.dataItem) {\n var editorType = item instanceof Shape ? \"shape\" : \"connection\";\n this.editModel(item.dataItem, editorType);\n }\n },\n\n cancelEdit: function() {\n if (this.editor) {\n this._getEditDataSource().cancelChanges(this.editor.model);\n\n this._destroyEditor();\n }\n },\n\n saveEdit: function() {\n if (this.editor && this.editor.end() &&\n !this.trigger(\"save\", this._editArgs())) {\n this._getEditDataSource().sync();\n }\n },\n\n _update: function() {\n if (this.editor && this.editor.end() &&\n !this.trigger(\"save\", this._editArgs())) {\n this._getEditDataSource().sync();\n this._destroyEditor();\n }\n },\n\n _cancel: function() {\n if (this.editor && !this.trigger(\"cancel\", this._editArgs())) {\n var model = this.editor.model;\n this._getEditDataSource().cancelChanges(model);\n var element = this._connectionsDataMap[model.uid] || this._dataMap[model.id];\n if (element) {\n element._setOptionsFromModel(model);\n }\n this._destroyEditor();\n }\n },\n\n _getEditDataSource: function() {\n return this.editor.options.type === \"shape\" ? this.dataSource : this.connectionsDataSource;\n },\n\n _editArgs: function() {\n var result = { container: this.editor.wrapper };\n result[this.editor.options.type] = this.editor.model;\n return result;\n },\n\n _destroyEditor: function() {\n if (this.editor) {\n this.editor.close();\n this.editor = null;\n }\n },\n\n _initElements: function() {\n this.wrapper = this.element.empty()\n .css(\"position\", \"relative\")\n .attr(\"tabindex\", 0)\n .addClass(\"k-widget k-diagram\");\n\n this.scrollable = $(\"
\").appendTo(this.element);\n },\n\n _initDefaults: function(userOptions) {\n var options = this.options;\n var editable = options.editable;\n var shapeDefaults = options.shapeDefaults;\n var connectionDefaults = options.connectionDefaults;\n var userShapeDefaults = (userOptions || {}).shapeDefaults;\n if (editable === false) {\n shapeDefaults.editable = false;\n connectionDefaults.editable = false;\n } else {\n copyDefaultOptions(editable, shapeDefaults.editable, [\"drag\", \"remove\", \"connect\"]);\n copyDefaultOptions(editable, connectionDefaults.editable, [\"drag\", \"remove\"]);\n }\n\n if (userShapeDefaults && userShapeDefaults.connectors) {\n options.shapeDefaults.connectors = userShapeDefaults.connectors;\n }\n },\n\n _interactionDefaults: function() {\n var options = this.options;\n var selectable = options.selectable;\n var pannable = options.pannable;\n var mobile = kendo.support.mobileOS;\n\n if (selectable && !defined(selectable.multiple)) {\n options.selectable = deepExtend({\n multiple: mobile ? false : true\n }, options.selectable);\n }\n\n if (pannable && !defined(pannable.key)) {\n options.pannable = deepExtend({\n key: mobile ? \"none\" : \"ctrl\"\n }, options.pannable);\n }\n },\n\n _initCanvas: function() {\n var canvasContainer = $(\"
\").appendTo(this.scrollable)[0];\n var viewPort = this.viewport();\n this.canvas = new Canvas(canvasContainer, {\n width: viewPort.width || DEFAULT_CANVAS_WIDTH,\n height: viewPort.height || DEFAULT_CANVAS_HEIGHT\n });\n },\n\n _createHandlers: function() {\n var that = this;\n var element = that.element;\n\n element.on(MOUSEWHEEL_NS, that._wheel.bind(that))\n .on(\"keydown\" + NS, that._keydown.bind(that));\n\n that._userEvents = new kendo.UserEvents(this.scrollable, {\n multiTouch: true,\n fastTap: true,\n tap: that._tap.bind(that),\n start: that._dragStart.bind(that),\n move: that._drag.bind(that),\n end: that._dragEnd.bind(that),\n gesturestart: that._gestureStart.bind(that),\n gesturechange: that._gestureChange.bind(that),\n gestureend: that._gestureEnd.bind(that),\n doubleTap: that._doubleTap.bind(that),\n supportDoubleTap: true\n });\n\n that.toolService = new ToolService(that);\n\n this.scrollable\n .on(\"mouseover\" + NS, that._mouseover.bind(that))\n .on(\"mouseout\" + NS, that._mouseout.bind(that))\n .on(\"mousemove\" + NS, that._mouseMove.bind(that))\n .on(\"mousedown\" + NS, that._mouseDown.bind(that))\n .on(\"mouseup\" + NS, that._mouseUp.bind(that));\n\n this._syncHandler = that._syncChanges.bind(that);\n\n that._resizeHandler = that.resize.bind(that, false);\n kendo.onResize(that._resizeHandler);\n\n this.bind(ZOOM_START, that._destroyToolBar.bind(that));\n this.bind(PAN, that._destroyToolBar.bind(that));\n },\n\n _dragStart: function(e) {\n this._pauseMouseHandlers = true;\n var point = this._eventPositions(e, true);\n\n var event = e.event;\n if (this.toolService.start(point, this._meta(event))) {\n this._destroyToolBar();\n event.preventDefault();\n }\n },\n\n _drag: function(e) {\n var p = this._eventPositions(e);\n var event = e.event;\n if (this.toolService.move(p, this._meta(event))) {\n event.preventDefault();\n }\n },\n\n _dragEnd: function(e) {\n this._pauseMouseHandlers = false;\n var p = this._eventPositions(e);\n var event = e.event;\n if (this.toolService.end(p, this._meta(event))) {\n this._createToolBar();\n event.preventDefault();\n }\n },\n\n _mouseMove: function(e) {\n if (!this._pauseMouseHandlers) {\n var p = this._eventPositions(e);\n this.toolService._updateHoveredItem(p);\n this.toolService._updateCursor(p);\n }\n },\n\n _mouseDown: function() {\n this._pauseMouseHandlers = true;\n },\n\n _mouseUp: function() {\n this._pauseMouseHandlers = false;\n },\n\n _tap: function(e) {\n var toolService = this.toolService;\n var selectable = this.options.selectable;\n var point = this._eventPositions(e);\n var focused = this.focus();\n\n toolService._updateHoveredItem(point);\n\n if (toolService.hoveredItem) {\n var item = toolService.hoveredItem;\n\n this.trigger(\"click\", {\n item: item,\n point: point,\n meta: this._meta(e.event)\n });\n\n if (selectable && item.options.selectable !== false) {\n var multiple = selectable.multiple !== false;\n var ctrlPressed = kendo.support.mobileOS || this._meta(e.event).ctrlKey;\n\n if (item.isSelected) {\n if (ctrlPressed) {\n this._destroyToolBar();\n item.select(false);\n } else {\n this._createToolBar(focused);\n }\n } else {\n this._destroyToolBar();\n this.select(item, {\n addToSelection: multiple && ctrlPressed\n });\n this._createToolBar(focused);\n }\n }\n } else if (selectable) {\n this._destroyToolBar();\n this.deselect();\n }\n },\n\n _keydown: function(e) {\n if (this.toolService.keyDown(e.keyCode, this._meta(e))) {\n e.preventDefault();\n }\n },\n\n _wheel: function(e) {\n var delta = mwDelta(e),\n p = this._eventPositions(e),\n meta = deepExtend(this._meta(e), { delta: delta });\n\n if (this.toolService.wheel(p, meta)) {\n e.preventDefault();\n }\n },\n\n _meta: function(e) {\n return { ctrlKey: e.ctrlKey, metaKey: e.metaKey, altKey: e.altKey, shiftKey: e.shiftKey, type: e.type };\n },\n\n _eventPositions: function(e, start) {\n var point;\n if (e.touch) {\n var field = start ? \"startLocation\" : \"location\";\n point = new Point(e.x[field], e.y[field]);\n } else {\n var event = e.originalEvent;\n point = new Point(event.pageX, event.pageY);\n }\n\n return this.documentToModel(point);\n },\n\n _gestureStart: function(e) {\n this._destroyToolBar();\n this.scroller.disable();\n var initialCenter = this.documentToModel(new Point(e.center.x, e.center.y));\n var eventArgs = {\n point: initialCenter,\n zoom: this.zoom()\n };\n\n if (this.trigger(ZOOM_START, eventArgs)) {\n return;\n }\n\n this._gesture = e;\n this._initialCenter = initialCenter;\n },\n\n _gestureChange: function(e) {\n var previousGesture = this._gesture;\n var initialCenter = this._initialCenter;\n var center = this.documentToView(new Point(e.center.x, e.center.y));\n var scaleDelta = e.distance / previousGesture.distance;\n var zoom = this._zoom;\n var updateZoom = false;\n\n if (math.abs(scaleDelta - 1) >= MOBILE_ZOOM_RATE) {\n this._zoom = zoom = this._getValidZoom(zoom * scaleDelta);\n this.options.zoom = zoom;\n this._gesture = e;\n updateZoom = true;\n }\n\n var zoomedPoint = initialCenter.times(zoom);\n var pan = center.minus(zoomedPoint);\n if (updateZoom || this._pan.distanceTo(pan) >= MOBILE_PAN_DISTANCE) {\n this._panTransform(pan);\n this._updateAdorners();\n }\n\n e.preventDefault();\n },\n\n _doubleTap: function(e) {\n var diagram = this;\n var pointPosition = this._eventPositions(e);\n var options = diagram.options;\n var zoomRate = options.zoomRate;\n var zoom = diagram.zoom() + zoomRate;\n var meta = this._meta(e);\n var zoomOptions = { point: pointPosition, meta: meta, zoom: zoom };\n\n\n if (diagram.trigger(ZOOM_START, zoomOptions)) {\n return;\n }\n\n zoom = kendo.dataviz.round(Math.max(options.zoomMin, Math.min(options.zoomMax, zoom)), 2);\n zoomOptions.zoom = zoom;\n\n diagram.zoom(zoom, zoomOptions);\n diagram.trigger(ZOOM_END, zoomOptions);\n },\n\n _gestureEnd: function() {\n if (this.options.pannable !== false) {\n this.scroller.enable();\n }\n this.trigger(ZOOM_END, {\n point: this._initialCenter,\n zoom: this.zoom()\n });\n },\n\n _resize: function() {\n var viewport = this.viewport();\n if (this.canvas) {\n this.canvas.size(viewport);\n }\n\n if (this.scrollable && this.toolBar) {\n this.scrollable.height(viewport.height);\n }\n },\n\n _mouseover: function(e) {\n var node = e.target._kendoNode;\n if (node && node.srcElement._hover) {\n node.srcElement._hover(true, node.srcElement);\n }\n },\n\n _mouseout: function(e) {\n var node = e.target._kendoNode;\n if (node && node.srcElement._hover) {\n node.srcElement._hover(false, node.srcElement);\n }\n },\n\n _initTheme: function() {\n var that = this;\n var themeName = ((that.options || {}).theme || \"\").toLowerCase();\n var themes = dataviz.ui.themes || {};\n var themeOptions;\n\n if (dataviz.SASS_THEMES.indexOf(themeName) != -1) {\n themeOptions = dataviz.autoTheme().diagram;\n }\n else {\n themeOptions = (themes[themeName] || {}).diagram;\n }\n\n that.options = deepExtend({}, themeOptions, that.options);\n if (that.options.editable === true) {\n deepExtend(that.options, {\n editable: (themeOptions || {}).editable\n });\n }\n },\n\n _createOptionElements: function() {\n var options = this.options;\n var shapesLength = options.shapes.length;\n\n if (shapesLength) {\n this._createShapes();\n }\n\n if (options.connections.length) {\n this._createConnections();\n }\n\n if (shapesLength && options.layout) {\n this.layout(options.layout);\n }\n },\n\n _createShapes: function() {\n var that = this,\n options = that.options,\n shapes = options.shapes,\n shape, i;\n\n for (i = 0; i < shapes.length; i++) {\n shape = shapes[i];\n that.addShape(shape);\n }\n },\n\n _createConnections: function() {\n var diagram = this,\n options = diagram.options,\n defaults = options.connectionDefaults,\n connections = options.connections,\n conn, source, target, i;\n\n for (i = 0; i < connections.length; i++) {\n conn = connections[i];\n source = diagram._findConnectionTarget(conn.from);\n target = diagram._findConnectionTarget(conn.to);\n\n diagram.connect(source, target, deepExtend({}, defaults, conn));\n }\n },\n\n _findConnectionTarget: function(options) {\n options = options || {};\n var diagram = this;\n var shapeId = isString(options) ? options : options.shapeId || options.id;\n var target;\n if (shapeId) {\n target = diagram.getShapeById(shapeId);\n if (options.connector) {\n target = target.getConnector(options.connector);\n }\n } else {\n target = new Point(options.x || 0, options.y || 0);\n }\n\n return target;\n },\n\n destroy: function() {\n var that = this;\n Widget.fn.destroy.call(that);\n\n if (this._userEvents) {\n this._userEvents.destroy();\n }\n\n kendo.unbindResize(that._resizeHandler);\n\n that.clear();\n that.element.off(NS);\n that.scroller.wrapper.off(NS);\n that.canvas.destroy(true);\n that.canvas = undefined$1;\n\n that._destroyEditor();\n that.destroyScroller();\n that._destroyGlobalToolBar();\n that._destroyToolBar();\n },\n\n destroyScroller: function() {\n var scroller = this.scroller;\n\n if (!scroller) {\n return;\n }\n\n scroller.destroy();\n scroller.element.remove();\n this.scroller = null;\n },\n\n save: function() {\n var json = {\n shapes: [],\n connections: []\n };\n var i, connection, shape;\n\n for (i = 0; i < this.shapes.length; i++) {\n shape = this.shapes[i];\n if (shape.options.serializable) {\n json.shapes.push(shape.options);\n }\n }\n\n for (i = 0; i < this.connections.length; i++) {\n connection = this.connections[i];\n\n json.connections.push(deepExtend({}, connection.options, connection.toJSON()));\n }\n\n return json;\n },\n\n focus: function() {\n if (!this.element.is(kendo._activeElement())) {\n var element = this.element,\n scrollContainer = element[0],\n containers = [],\n offsets = [],\n documentElement = document.documentElement,\n i;\n\n do {\n scrollContainer = scrollContainer.parentNode;\n\n if (scrollContainer.scrollHeight > scrollContainer.clientHeight) {\n containers.push(scrollContainer);\n offsets.push(scrollContainer.scrollTop);\n }\n } while (scrollContainer != documentElement);\n\n element.trigger(\"focus\");\n\n for (i = 0; i < containers.length; i++) {\n containers[i].scrollTop = offsets[i];\n }\n return true;\n }\n },\n\n load: function(options) {\n this.clear();\n\n this.setOptions(options);\n this._createShapes();\n this._createConnections();\n },\n\n setOptions: function(options) {\n deepExtend(this.options, options);\n },\n\n clear: function() {\n var that = this;\n\n that.select(false);\n that.mainLayer.clear();\n that._shapesQuadTree.clear();\n that._initialize();\n },\n /**\n * Connects two items.\n * @param source Shape, Connector, Point.\n * @param target Shape, Connector, Point.\n * @param options Connection options that will be passed to the newly created connection.\n * @returns The newly created connection.\n */\n connect: function(source, target, options) {\n var connection;\n if (this.connectionsDataSource && this._isEditable) {\n var dataItem = this.connectionsDataSource.add({});\n connection = this._connectionsDataMap[dataItem.uid];\n connection.source(source);\n connection.target(target);\n connection.redraw(options);\n connection.updateModel();\n } else {\n connection = new Connection(source, target,\n deepExtend({ }, this.options.connectionDefaults, options));\n\n this.addConnection(connection);\n }\n\n return connection;\n },\n /**\n * Determines whether the the two items are connected.\n * @param source Shape, Connector, Point.\n * @param target Shape, Connector, Point.\n * @returns true if the two items are connected.\n */\n connected: function(source, target) {\n for (var i = 0; i < this.connections.length; i++) {\n var c = this.connections[i];\n if (c.from == source && c.to == target) {\n return true;\n }\n }\n\n return false;\n },\n /**\n * Adds connection to the diagram.\n * @param connection Connection.\n * @param undoable Boolean.\n * @returns The newly created connection.\n */\n addConnection: function(connection, undoable) {\n if (undoable !== false) {\n this.undoRedoService.add(\n new diagram.AddConnectionUnit(connection, this), false);\n }\n\n connection.diagram = this;\n connection._setOptionsFromModel();\n connection.refresh();\n this.mainLayer.append(connection.visual);\n this.connections.push(connection);\n\n this.trigger(CHANGE, {\n added: [connection],\n removed: []\n });\n\n return connection;\n },\n\n _addConnection: function(connection, undoable) {\n var connectionsDataSource = this.connectionsDataSource;\n var dataItem;\n if (connectionsDataSource && this._isEditable) {\n dataItem = createModel(connectionsDataSource, cloneDataItem(connection.dataItem));\n connection.dataItem = dataItem;\n connection.updateModel();\n\n if (!this.trigger(\"add\", { connection: connection })) {\n this._connectionsDataMap[dataItem.uid] = connection;\n\n connectionsDataSource.add(dataItem);\n this.addConnection(connection, undoable);\n connection._updateConnectors();\n\n return connection;\n }\n } else if (!this.trigger(\"add\", { connection: connection })) {\n this.addConnection(connection, undoable);\n connection._updateConnectors();\n return connection;\n }\n },\n\n /**\n * Adds shape to the diagram.\n * @param item Shape, Point. If point is passed it will be created new Shape and positioned at that point.\n * @param options. The options to be passed to the newly created Shape.\n * @returns The newly created shape.\n */\n addShape: function(item, undoable) {\n var shape,\n shapeDefaults = this.options.shapeDefaults;\n\n if (item instanceof Shape) {\n shape = item;\n this._parseBounds(shape.bounds());\n } else if (!(item instanceof kendo.Class)) {\n shapeDefaults = deepExtend({}, shapeDefaults, item || {});\n shape = new Shape(shapeDefaults, this);\n this._parseBounds(shape.bounds());\n } else {\n return;\n }\n\n if (undoable !== false) {\n this.undoRedoService.add(new diagram.AddShapeUnit(shape, this), false);\n }\n\n this.shapes.push(shape);\n if (shape.diagram !== this) {\n this._shapesQuadTree.insert(shape);\n shape.diagram = this;\n }\n this.mainLayer.append(shape.visual);\n\n this.trigger(CHANGE, {\n added: [shape],\n removed: []\n });\n\n return shape;\n },\n\n _addShape: function(shape, undoable) {\n var that = this;\n var dataSource = that.dataSource;\n var dataItem;\n if (dataSource && this._isEditable) {\n dataItem = createModel(dataSource, cloneDataItem(shape.dataItem));\n shape.dataItem = dataItem;\n shape.updateModel();\n\n if (!this.trigger(\"add\", { shape: shape })) {\n this.dataSource.add(dataItem);\n var inactiveItem = this._inactiveShapeItems.getByUid(dataItem.uid);\n inactiveItem.element = shape;\n inactiveItem.undoable = undoable;\n return shape;\n }\n } else if (!this.trigger(\"add\", { shape: shape })) {\n return this.addShape(shape, undoable);\n }\n },\n\n _parseBounds: function(bounds) {\n bounds.x = typeof(bounds.x) == \"string\" ? parseFloat(bounds.x) : bounds.x;\n bounds.y = typeof(bounds.y) == \"string\" ? parseFloat(bounds.y) : bounds.y;\n },\n /**\n * Removes items (or single item) from the diagram.\n * @param items DiagramElement, Array of Items.\n * @param undoable.\n */\n\n remove: function(items, undoable) {\n items = isArray(items) ? items.slice(0) : [items];\n var elements = splitDiagramElements(items);\n var shapes = elements.shapes;\n var connections = elements.connections;\n var i;\n\n if (!defined(undoable)) {\n undoable = true;\n }\n\n if (undoable) {\n this.undoRedoService.begin();\n }\n\n this._suspendModelRefresh();\n for (i = shapes.length - 1; i >= 0; i--) {\n this._removeItem(shapes[i], undoable, connections);\n }\n\n for (i = connections.length - 1; i >= 0; i--) {\n this._removeItem(connections[i], undoable);\n }\n\n this._resumeModelRefresh();\n\n if (undoable) {\n this.undoRedoService.commit(false);\n }\n\n this.trigger(CHANGE, {\n added: [],\n removed: items\n });\n },\n\n _removeShapeDataItem: function(item) {\n if (this._isEditable) {\n this.dataSource.remove(item.dataItem);\n delete this._dataMap[item.dataItem.id];\n }\n },\n\n _removeConnectionDataItem: function(item) {\n if (this._isEditable) {\n this.connectionsDataSource.remove(item.dataItem);\n delete this._connectionsDataMap[item.dataItem.uid];\n }\n },\n\n _triggerRemove: function(items) {\n var toRemove = [];\n var item, args, editable;\n\n for (var idx = 0; idx < items.length; idx++) {\n item = items[idx];\n editable = item.options.editable;\n if (item instanceof Shape) {\n args = { shape: item };\n } else {\n args = { connection: item };\n }\n if (editable && editable.remove !== false && !this.trigger(\"remove\", args)) {\n toRemove.push(item);\n }\n }\n return toRemove;\n },\n\n /**\n * Executes the next undoable action on top of the undo stack if any.\n */\n undo: function() {\n this.undoRedoService.undo();\n },\n /**\n * Executes the previous undoable action on top of the redo stack if any.\n */\n redo: function() {\n this.undoRedoService.redo();\n },\n /**\n * Selects items on the basis of the given input or returns the current selection if none.\n * @param itemsOrRect DiagramElement, Array of elements, \"All\", false or Rect. A value 'false' will deselect everything.\n * @param options\n * @returns {Array}\n */\n select: function(item, options) {\n if (isDefined(item)) {\n options = deepExtend({ addToSelection: false }, options);\n\n var addToSelection = options.addToSelection,\n items = [],\n selected = [],\n i, element;\n\n if (!addToSelection) {\n this.deselect();\n }\n\n this._internalSelection = true;\n\n if (item instanceof Array) {\n items = item;\n } else if (item instanceof DiagramElement) {\n items = [ item ];\n }\n\n for (i = 0; i < items.length; i++) {\n element = items[i];\n if (element.select(true)) {\n selected.push(element);\n }\n }\n\n this._selectionChanged(selected, []);\n\n this._internalSelection = false;\n } else {\n return this._selectedItems;\n }\n },\n\n selectAll: function() {\n this.select(this.shapes.concat(this.connections));\n },\n\n selectArea: function(rect) {\n var i, items, item;\n this._internalSelection = true;\n var selected = [];\n if (rect instanceof Rect) {\n items = this.shapes.concat(this.connections);\n for (i = 0; i < items.length; i++) {\n item = items[i];\n if ((!rect || item._hitTest(rect)) && item.options.enable) {\n if (item.select(true)) {\n selected.push(item);\n }\n }\n }\n }\n\n this._selectionChanged(selected, []);\n this._internalSelection = false;\n },\n\n deselect: function(item) {\n this._internalSelection = true;\n var deselected = [],\n items = [],\n element, i;\n\n if (item instanceof Array) {\n items = item;\n } else if (item instanceof DiagramElement) {\n items.push(item);\n } else if (!isDefined(item)) {\n items = this._selectedItems.slice(0);\n }\n\n for (i = 0; i < items.length; i++) {\n element = items[i];\n if (element.select(false)) {\n deselected.push(element);\n }\n }\n\n this._selectionChanged([], deselected);\n this._internalSelection = false;\n },\n /**\n * Brings to front the passed items.\n * @param items DiagramElement, Array of Items.\n * @param undoable. By default the action is undoable.\n */\n toFront: function(items, undoable) {\n if (!items) {\n items = this._selectedItems.slice();\n }\n\n var result = this._getDiagramItems(items), indices;\n if (!defined(undoable) || undoable) {\n indices = indicesOfItems(this.mainLayer, result.visuals);\n var unit = new ToFrontUnit(this, items, indices);\n this.undoRedoService.add(unit);\n } else {\n this.mainLayer.toFront(result.visuals);\n this._fixOrdering(result, true);\n }\n },\n /**\n * Sends to back the passed items.\n * @param items DiagramElement, Array of Items.\n * @param undoable. By default the action is undoable.\n */\n toBack: function(items, undoable) {\n if (!items) {\n items = this._selectedItems.slice();\n }\n\n var result = this._getDiagramItems(items), indices;\n if (!defined(undoable) || undoable) {\n indices = indicesOfItems(this.mainLayer, result.visuals);\n var unit = new ToBackUnit(this, items, indices);\n this.undoRedoService.add(unit);\n } else {\n this.mainLayer.toBack(result.visuals);\n this._fixOrdering(result, false);\n }\n },\n /**\n * Bring into view the passed item(s) or rectangle.\n * @param items DiagramElement, Array of Items, Rect.\n * @param options. align - controls the position of the calculated rectangle relative to the viewport.\n * \"Center middle\" will position the items in the center. animate - controls if the pan should be animated.\n */\n bringIntoView: function(item, options) { // jQuery|Item|Array|Rect\n var viewport = this.viewport();\n var aligner = new diagram.RectAlign(viewport);\n var current, rect, original, newPan;\n\n if (viewport.width === 0 || viewport.height === 0) {\n return;\n }\n\n options = deepExtend({ animate: false, align: \"center middle\" }, options);\n if (options.align == \"none\") {\n options.align = \"center middle\";\n }\n\n if (item instanceof DiagramElement) {\n rect = item.bounds(TRANSFORMED);\n } else if (isArray(item)) {\n rect = this.boundingBox(item);\n } else if (item instanceof Rect) {\n rect = item.clone();\n }\n\n original = rect.clone();\n\n rect.zoom(this._zoom);\n\n if (rect.width > viewport.width || rect.height > viewport.height) {\n this._zoom = this._getValidZoom(math.min(viewport.width / original.width, viewport.height / original.height));\n rect = original.clone().zoom(this._zoom);\n }\n\n this._zoomMainLayer();\n\n current = rect.clone();\n aligner.align(rect, options.align);\n\n newPan = rect.topLeft().minus(current.topLeft());\n this.pan(newPan.times(-1), options.animate);\n },\n\n alignShapes: function(direction) {\n if (isUndefined(direction)) {\n direction = \"Left\";\n }\n var items = this.select(),\n val,\n item,\n i;\n\n if (items.length === 0) {\n return;\n }\n\n switch (direction.toLowerCase()) {\n case \"left\":\n case \"top\":\n val = MAX_VALUE;\n break;\n case \"right\":\n case \"bottom\":\n val = MIN_VALUE;\n break;\n }\n\n for (i = 0; i < items.length; i++) {\n item = items[i];\n if (item instanceof Shape) {\n switch (direction.toLowerCase()) {\n case \"left\":\n val = math.min(val, item.options.x);\n break;\n case \"top\":\n val = math.min(val, item.options.y);\n break;\n case \"right\":\n val = math.max(val, item.options.x);\n break;\n case \"bottom\":\n val = math.max(val, item.options.y);\n break;\n }\n }\n }\n var undoStates = [];\n var shapes = [];\n for (i = 0; i < items.length; i++) {\n item = items[i];\n if (item instanceof Shape) {\n shapes.push(item);\n undoStates.push(item.bounds());\n switch (direction.toLowerCase()) {\n case \"left\":\n case \"right\":\n item.position(new Point(val, item.options.y));\n break;\n case \"top\":\n case \"bottom\":\n item.position(new Point(item.options.x, val));\n break;\n }\n }\n }\n var unit = new diagram.TransformUnit(shapes, undoStates);\n this.undoRedoService.add(unit, false);\n },\n\n zoom: function(zoom, options) {\n if (zoom) {\n var staticPoint = options ? options.point : new diagram.Point(0, 0);\n // var meta = options ? options.meta : 0;\n zoom = this._zoom = this._getValidZoom(zoom);\n\n if (!isUndefined(staticPoint)) {//Viewpoint vector is constant\n staticPoint = new diagram.Point(math.round(staticPoint.x), math.round(staticPoint.y));\n var zoomedPoint = staticPoint.times(zoom);\n var viewportVector = this.modelToView(staticPoint);\n var raw = viewportVector.minus(zoomedPoint);//pan + zoomed point = viewpoint vector\n this._storePan(new diagram.Point(math.round(raw.x), math.round(raw.y)));\n }\n\n if (options) {\n options.zoom = zoom;\n }\n\n this._panTransform();\n\n this.canvas.surface.hideTooltip();\n\n this._updateAdorners();\n }\n\n return this._zoom;\n },\n\n _getPan: function(pan) {\n var canvas = this.canvas;\n if (!canvas.translate) {\n pan = pan.plus(this._pan);\n }\n return pan;\n },\n\n pan: function(pan, animate) {\n if (pan instanceof Point) {\n var that = this;\n var scroller = that.scroller;\n pan = that._getPan(pan);\n pan = pan.times(-1);\n\n if (animate) {\n scroller.animatedScrollTo(pan.x, pan.y, function() {\n that._updateAdorners();\n });\n } else {\n scroller.scrollTo(pan.x, pan.y);\n that._updateAdorners();\n }\n } else {\n return this._pan.times(-1);\n }\n },\n\n viewport: function() {\n var element = this.element;\n var width = element.width();\n var height = element.height();\n\n if (this.toolBar) {\n height -= outerHeight(this.toolBar.element);\n }\n\n return new Rect(0, 0, width, height);\n },\n copy: function() {\n if (this.options.copy.enabled) {\n this._clipboard = [];\n this._copyOffset = 1;\n for (var i = 0; i < this._selectedItems.length; i++) {\n var item = this._selectedItems[i];\n this._clipboard.push(item);\n }\n }\n },\n cut: function() {\n if (this.options.copy.enabled) {\n this._clipboard = [];\n this._copyOffset = 0;\n for (var i = 0; i < this._selectedItems.length; i++) {\n var item = this._selectedItems[i];\n this._clipboard.push(item);\n }\n this.remove(this._clipboard, true);\n }\n },\n\n paste: function() {\n if (this._clipboard.length > 0) {\n var item, copied, i;\n var mapping = {};\n var elements = splitDiagramElements(this._clipboard);\n var connections = elements.connections;\n var shapes = elements.shapes;\n var offset = {\n x: this._copyOffset * this.options.copy.offsetX,\n y: this._copyOffset * this.options.copy.offsetY\n };\n this.deselect();\n // first the shapes\n for (i = 0; i < shapes.length; i++) {\n item = shapes[i];\n copied = item.clone();\n mapping[item.id] = copied;\n copied.position(new Point(item.options.x + offset.x, item.options.y + offset.y));\n copied.diagram = this;\n copied = this._addShape(copied);\n if (copied) {\n copied.select();\n }\n }\n // then the connections\n for (i = 0; i < connections.length; i++) {\n item = connections[i];\n copied = this._addConnection(item.clone());\n if (copied) {\n this._updateCopiedConnection(copied, item, \"source\", mapping, offset);\n this._updateCopiedConnection(copied, item, \"target\", mapping, offset);\n\n copied.select(true);\n copied.updateModel();\n }\n }\n\n this._syncChanges();\n\n this._copyOffset += 1;\n }\n },\n\n _updateCopiedConnection: function(connection, sourceConnection, connectorName, mapping, offset) {\n var onActivate, inactiveItem, targetShape;\n var target = sourceConnection[connectorName]();\n var diagram = this;\n if (target instanceof Connector && mapping[target.shape.id]) {\n targetShape = mapping[target.shape.id];\n if (diagram.getShapeById(targetShape.id)) {\n connection[connectorName](targetShape.getConnector(target.options.name));\n } else {\n inactiveItem = diagram._inactiveShapeItems.getByUid(targetShape.dataItem.uid);\n if (inactiveItem) {\n onActivate = function(item) {\n targetShape = diagram._dataMap[item.id];\n connection[connectorName](targetShape.getConnector(target.options.name));\n connection.updateModel();\n };\n diagram._deferredConnectionUpdates.push(inactiveItem.onActivate(onActivate));\n }\n }\n } else {\n connection[connectorName](new Point(sourceConnection[connectorName + \"Point\"]().x + offset.x, sourceConnection[connectorName + \"Point\"]().y + offset.y));\n }\n },\n /**\n * Gets the bounding rectangle of the given items.\n * @param items DiagramElement, Array of elements.\n * @param origin Boolean. Pass 'true' if you need to get the bounding box of the shapes without their rotation offset.\n * @returns {Rect}\n */\n boundingBox: function(items, origin) {\n var rect = Rect.empty(), temp,\n di = isDefined(items) ? this._getDiagramItems(items) : { shapes: this.shapes };\n if (di.shapes.length > 0) {\n var item = di.shapes[0];\n rect = item.bounds(ROTATED);\n for (var i = 1; i < di.shapes.length; i++) {\n item = di.shapes[i];\n temp = item.bounds(ROTATED);\n if (origin === true) {\n temp.x -= item._rotationOffset.x;\n temp.y -= item._rotationOffset.y;\n }\n rect = rect.union(temp);\n }\n }\n return rect;\n },\n\n _containerOffset: function() {\n var containerOffset = this.element.offset();\n if (this.toolBar) {\n containerOffset.top += outerHeight(this.toolBar.element);\n }\n return containerOffset;\n },\n\n documentToView: function(point) {\n var containerOffset = this._containerOffset();\n\n return new Point(point.x - containerOffset.left, point.y - containerOffset.top);\n },\n viewToDocument: function(point) {\n var containerOffset = this._containerOffset();\n\n return new Point(point.x + containerOffset.left, point.y + containerOffset.top);\n },\n viewToModel: function(point) {\n return this._transformWithMatrix(point, this._matrixInvert);\n },\n modelToView: function(point) {\n return this._transformWithMatrix(point, this._matrix);\n },\n modelToLayer: function(point) {\n return this._transformWithMatrix(point, this._layerMatrix);\n },\n layerToModel: function(point) {\n return this._transformWithMatrix(point, this._layerMatrixInvert);\n },\n documentToModel: function(point) {\n var viewPoint = this.documentToView(point);\n if (!this.canvas.translate) {\n viewPoint.x = viewPoint.x + this.scroller.scrollLeft;\n viewPoint.y = viewPoint.y + this.scroller.scrollTop;\n }\n return this.viewToModel(viewPoint);\n },\n modelToDocument: function(point) {\n return this.viewToDocument(this.modelToView(point));\n },\n _transformWithMatrix: function(point, matrix) {\n var result = point;\n if (point instanceof Point) {\n if (matrix) {\n result = matrix.apply(point);\n }\n }\n else {\n var tl = this._transformWithMatrix(point.topLeft(), matrix),\n br = this._transformWithMatrix(point.bottomRight(), matrix);\n result = Rect.fromPoints(tl, br);\n }\n return result;\n },\n\n setDataSource: function(dataSource) {\n this.options.dataSource = dataSource;\n this._dataSource();\n if (this.options.autoBind) {\n this.dataSource.fetch();\n }\n },\n\n setConnectionsDataSource: function(dataSource) {\n this.options.connectionsDataSource = dataSource;\n this._connectionDataSource();\n if (this.options.autoBind) {\n this.connectionsDataSource.fetch();\n }\n },\n\n /**\n * Performs a diagram layout of the given type.\n * @param layoutType The layout algorithm to be applied (TreeLayout, LayeredLayout, SpringLayout).\n * @param options Layout-specific options.\n */\n layout: function(options) {\n this._layouting = true;\n // TODO: raise layout event?\n var type;\n if (isUndefined(options)) {\n options = this.options.layout;\n }\n if (isUndefined(options) || isUndefined(options.type)) {\n type = \"Tree\";\n }\n else {\n type = options.type;\n }\n var l;\n switch (type.toLowerCase()) {\n case \"tree\":\n l = new diagram.TreeLayout(this);\n break;\n\n case \"layered\":\n l = new diagram.LayeredLayout(this);\n break;\n\n case \"forcedirected\":\n case \"force\":\n case \"spring\":\n case \"springembedder\":\n l = new diagram.SpringLayout(this);\n break;\n default:\n throw \"Layout algorithm '\" + type + \"' is not supported.\";\n }\n var initialState = new diagram.LayoutState(this);\n var finalState = l.layout(options);\n if (finalState) {\n var unit = new diagram.LayoutUndoUnit(initialState, finalState, options ? options.animate : null);\n this.undoRedoService.add(unit);\n }\n this._layouting = false;\n this._redrawConnections();\n },\n /**\n * Gets a shape on the basis of its identifier.\n * @param id (string) the identifier of a shape.\n * @returns {Shape}\n */\n getShapeById: function(id) {\n var found;\n found = Utils.first(this.shapes, function(s) {\n return s.visual.id === id;\n });\n if (found) {\n return found;\n }\n found = Utils.first(this.connections, function(c) {\n return c.visual.id === id;\n });\n return found;\n },\n\n getShapeByModelId: function(id) {\n var shape;\n if (this._isEditable) {\n shape = this._dataMap[id];\n } else {\n shape = Utils.first(this.shapes, function(shape) {\n return (shape.dataItem || {}).id === id;\n });\n }\n return shape;\n },\n\n getShapeByModelUid: function(uid) {\n var shape;\n if (this._isEditable) {\n shape = Utils.first(this.shapes, function(shape) {\n return (shape.dataItem || {}).uid === uid;\n });\n } else {\n shape = this._dataMap[uid];\n }\n return shape;\n },\n\n getConnectionByModelId: function(id) {\n var connection;\n if (this.connectionsDataSource) {\n connection = Utils.first(this.connections, function(connection) {\n return (connection.dataItem || {}).id === id;\n });\n }\n return connection;\n },\n\n getConnectionByModelUid: function(uid) {\n var connection;\n if (this.connectionsDataSource) {\n connection = this._connectionsDataMap[uid];\n }\n return connection;\n },\n\n _extendLayoutOptions: function(options) {\n if (options.layout) {\n options.layout = deepExtend({}, diagram.LayoutBase.fn.defaultOptions || {}, options.layout);\n }\n },\n\n _selectionChanged: function(selected, deselected) {\n if (selected.length || deselected.length) {\n this.trigger(SELECT, { selected: selected, deselected: deselected });\n }\n },\n _getValidZoom: function(zoom) {\n return math.min(math.max(zoom, this.options.zoomMin), this.options.zoomMax);\n },\n _panTransform: function(pos) {\n var diagram = this,\n pan = pos || diagram._pan;\n\n if (diagram.canvas.translate) {\n diagram.scroller.scrollTo(pan.x, pan.y);\n diagram._zoomMainLayer();\n } else {\n diagram._storePan(pan);\n diagram._transformMainLayer();\n }\n },\n\n _finishPan: function() {\n this.trigger(PAN, { total: this._pan, delta: Number.NaN });\n },\n _storePan: function(pan) {\n this._pan = pan;\n this._storeViewMatrix();\n },\n _zoomMainLayer: function() {\n var zoom = this._zoom;\n\n var transform = new CompositeTransform(0, 0, zoom, zoom);\n transform.render(this.mainLayer);\n this._storeLayerMatrix(transform);\n this._storeViewMatrix();\n },\n _transformMainLayer: function() {\n var pan = this._pan,\n zoom = this._zoom;\n\n var transform = new CompositeTransform(pan.x, pan.y, zoom, zoom);\n transform.render(this.mainLayer);\n this._storeLayerMatrix(transform);\n this._storeViewMatrix();\n },\n _storeLayerMatrix: function(canvasTransform) {\n this._layerMatrix = canvasTransform.toMatrix();\n this._layerMatrixInvert = canvasTransform.invert().toMatrix();\n },\n _storeViewMatrix: function() {\n var pan = this._pan,\n zoom = this._zoom;\n\n var transform = new CompositeTransform(pan.x, pan.y, zoom, zoom);\n this._matrix = transform.toMatrix();\n this._matrixInvert = transform.invert().toMatrix();\n },\n _toIndex: function(items, indices) {\n var result = this._getDiagramItems(items);\n this.mainLayer.toIndex(result.visuals, indices);\n this._fixOrdering(result, false);\n },\n _fixOrdering: function(result, toFront) {\n var shapePos = toFront ? this.shapes.length - 1 : 0,\n conPos = toFront ? this.connections.length - 1 : 0,\n i, item;\n for (i = 0; i < result.shapes.length; i++) {\n item = result.shapes[i];\n Utils.remove(this.shapes, item);\n Utils.insert(this.shapes, item, shapePos);\n }\n for (i = 0; i < result.cons.length; i++) {\n item = result.cons[i];\n Utils.remove(this.connections, item);\n Utils.insert(this.connections, item, conPos);\n }\n },\n _getDiagramItems: function(items) {\n var i, result = {}, args = items;\n result.visuals = [];\n result.shapes = [];\n result.cons = [];\n\n if (!items) {\n args = this._selectedItems.slice();\n } else if (!isArray(items)) {\n args = [items];\n }\n\n for (i = 0; i < args.length; i++) {\n var item = args[i];\n if (item instanceof Shape) {\n result.shapes.push(item);\n result.visuals.push(item.visual);\n } else if (item instanceof Connection) {\n result.cons.push(item);\n result.visuals.push(item.visual);\n }\n }\n\n return result;\n },\n\n _removeItem: function(item, undoable, removedConnections) {\n item.select(false);\n if (item instanceof Shape) {\n this._removeShapeDataItem(item);\n this._removeShape(item, undoable, removedConnections);\n } else if (item instanceof Connection) {\n this._removeConnectionDataItem(item);\n this._removeConnection(item, undoable);\n }\n\n this.mainLayer.remove(item.visual);\n },\n\n _removeShape: function(shape, undoable, removedConnections) {\n var i, connection, connector,\n sources = [], targets = [];\n this.toolService._removeHover();\n\n if (undoable) {\n this.undoRedoService.addCompositeItem(new DeleteShapeUnit(shape));\n }\n Utils.remove(this.shapes, shape);\n this._shapesQuadTree.remove(shape);\n\n for (i = 0; i < shape.connectors.length; i++) {\n connector = shape.connectors[i];\n for (var j = 0; j < connector.connections.length; j++) {\n connection = connector.connections[j];\n if (!removedConnections || !dataviz.inArray(connection, removedConnections)) {\n if (connection.sourceConnector == connector) {\n sources.push(connection);\n } else if (connection.targetConnector == connector) {\n targets.push(connection);\n }\n }\n }\n }\n\n for (i = 0; i < sources.length; i++) {\n sources[i].source(null, undoable);\n sources[i].updateModel();\n }\n for (i = 0; i < targets.length; i++) {\n targets[i].target(null, undoable);\n targets[i].updateModel();\n }\n },\n\n _removeConnection: function(connection, undoable) {\n if (connection.sourceConnector) {\n Utils.remove(connection.sourceConnector.connections, connection);\n }\n if (connection.targetConnector) {\n Utils.remove(connection.targetConnector.connections, connection);\n }\n if (undoable) {\n this.undoRedoService.addCompositeItem(new DeleteConnectionUnit(connection));\n }\n\n Utils.remove(this.connections, connection);\n },\n\n _removeDataItems: function(items, recursive) {\n var item, children, shape, idx;\n items = isArray(items) ? items : [items];\n\n while (items.length) {\n item = items.shift();\n shape = this._dataMap[item.uid];\n if (shape) {\n this._removeShapeConnections(shape);\n this._removeItem(shape, false);\n delete this._dataMap[item.uid];\n if (recursive && item.hasChildren && item.loaded()) {\n children = item.children.data();\n for (idx = 0; idx < children.length; idx++) {\n items.push(children[idx]);\n }\n }\n }\n }\n },\n\n _removeShapeConnections: function(shape) {\n var connections = shape.connections();\n var idx;\n\n if (connections) {\n for (idx = 0; idx < connections.length; idx++) {\n this._removeItem(connections[idx], false);\n }\n }\n },\n\n _addDataItem: function(dataItem, undoable) {\n if (!defined(dataItem)) {\n return;\n }\n\n var shape = this._dataMap[dataItem.id];\n if (shape) {\n return shape;\n }\n\n var options = deepExtend({}, this.options.shapeDefaults);\n options.dataItem = dataItem;\n shape = new Shape(options, this);\n this.addShape(shape, undoable !== false);\n this._dataMap[dataItem.id] = shape;\n return shape;\n },\n\n _addDataItemByUid: function(dataItem) {\n if (!defined(dataItem)) {\n return;\n }\n\n var shape = this._dataMap[dataItem.uid];\n if (shape) {\n return shape;\n }\n\n var options = deepExtend({}, this.options.shapeDefaults);\n options.dataItem = dataItem;\n shape = new Shape(options, this);\n this.addShape(shape);\n this._dataMap[dataItem.uid] = shape;\n return shape;\n },\n\n _addDataItems: function(items, parent) {\n var item, idx, shape, parentShape, connection;\n for (idx = 0; idx < items.length; idx++) {\n item = items[idx];\n shape = this._addDataItemByUid(item);\n parentShape = this._addDataItemByUid(parent);\n if (parentShape && !this.connected(parentShape, shape)) { // check if connected to not duplicate connections.\n connection = this.connect(parentShape, shape);\n }\n }\n },\n\n _refreshSource: function(e) {\n var that = this,\n node = e.node,\n action = e.action,\n items = e.items,\n options = that.options,\n idx,\n dataBound;\n\n if (e.field) {\n for (idx = 0; idx < items.length; idx++) {\n if (this._dataMap[items[idx].uid]) {\n this._dataMap[items[idx].uid].redrawVisual();\n }\n }\n return;\n }\n\n if (action == \"remove\") {\n this._removeDataItems(e.items, true);\n } else {\n\n if ((!action || action === \"itemloaded\") && !this._bindingRoots) {\n this._bindingRoots = true;\n dataBound = true;\n }\n\n if (!action && !node) {\n that.clear();\n }\n\n this._addDataItems(items, node);\n\n for (idx = 0; idx < items.length; idx++) {\n items[idx].load();\n }\n }\n\n if (options.layout && (dataBound || action == \"remove\" || action == \"add\")) {\n that.layout(options.layout);\n }\n\n if (dataBound) {\n this.trigger(\"dataBound\");\n this._bindingRoots = false;\n }\n },\n\n _addItem: function(item) {\n if (item instanceof Shape) {\n this.addShape(item);\n } else if (item instanceof Connection) {\n this.addConnection(item);\n }\n },\n\n _createToolBar: function(preventClosing) {\n var diagram = this.toolService.diagram;\n\n if (!this.singleToolBar && diagram.select().length === 1) {\n var element = diagram.select()[0];\n if (element && element.options.editable !== false) {\n var editable = element.options.editable;\n var tools = editable.tools;\n if (this._isEditable && tools.length === 0) {\n if (element instanceof Shape) {\n tools = [\"edit\", \"rotateClockwise\", \"rotateAnticlockwise\"];\n } else if (element instanceof Connection) {\n tools = [\"edit\"];\n }\n\n if (editable && editable.remove !== false) {\n tools.push(\"delete\");\n }\n }\n\n if (tools && tools.length) {\n var padding = 20;\n var point;\n this.singleToolBar = new DiagramToolBar(diagram, {\n tools: tools,\n click: this._toolBarClick.bind(this),\n modal: true,\n popupZIndex: parseInt(diagram.element.closest(\".k-window\").css(\"zIndex\"), 10) + 10\n });\n var popupWidth = outerWidth(this.singleToolBar._popup.element);\n var popupHeight = outerHeight(this.singleToolBar._popup.element);\n if (element instanceof Shape) {\n var shapeBounds = this.modelToView(element.bounds(ROTATED));\n point = new Point(shapeBounds.x, shapeBounds.y).minus(new Point(\n (popupWidth - shapeBounds.width) / 2,\n popupHeight + padding));\n } else if (element instanceof Connection) {\n var connectionBounds = this.modelToView(element.bounds());\n\n point = new Point(connectionBounds.x, connectionBounds.y)\n .minus(new Point(\n (popupWidth - connectionBounds.width - 20) / 2,\n popupHeight + padding\n ));\n }\n\n if (point) {\n if (!this.canvas.translate) {\n point = point.minus(new Point(this.scroller.scrollLeft, this.scroller.scrollTop));\n }\n point = this.viewToDocument(point);\n point = new Point(math.max(point.x, 0), math.max(point.y, 0));\n this.singleToolBar.showAt(point);\n if (preventClosing) {\n this.singleToolBar._popup.one(\"close\", preventDefault);\n }\n } else {\n this._destroyToolBar();\n }\n }\n }\n }\n },\n\n _toolBarClick: function(e) {\n this.trigger(\"toolBarClick\", e);\n this._destroyToolBar();\n },\n\n _normalizePointZoom: function(point) {\n return point.times(1 / this.zoom());\n },\n\n _initialize: function() {\n this.shapes = [];\n this._selectedItems = [];\n this.connections = [];\n this._dataMap = {};\n this._connectionsDataMap = {};\n this._inactiveShapeItems = new InactiveItemsCollection();\n this._deferredConnectionUpdates = [];\n this.undoRedoService = new UndoRedoService({\n undone: this._syncHandler,\n redone: this._syncHandler\n });\n this.id = diagram.randomId();\n },\n\n _fetchFreshData: function() {\n var that = this;\n that._dataSource();\n\n if (that._isEditable) {\n that._connectionDataSource();\n }\n\n if (that.options.autoBind) {\n if (that._isEditable) {\n this._loadingShapes = true;\n this._loadingConnections = true;\n that.dataSource.fetch();\n that.connectionsDataSource.fetch();\n } else {\n that.dataSource.fetch();\n }\n }\n },\n\n _dataSource: function() {\n if (defined(this.options.connectionsDataSource)) {\n this._isEditable = true;\n var dsOptions = this.options.dataSource || {};\n var ds = isArray(dsOptions) ? { data: dsOptions } : dsOptions;\n\n if (this.dataSource && this._shapesRefreshHandler) {\n this.dataSource\n .unbind(\"change\", this._shapesRefreshHandler)\n .unbind(\"requestStart\", this._shapesRequestStartHandler)\n .unbind(\"error\", this._shapesErrorHandler);\n } else {\n this._shapesRefreshHandler = this._refreshShapes.bind(this);\n this._shapesRequestStartHandler = this._shapesRequestStart.bind(this);\n this._shapesErrorHandler = this._error.bind(this);\n }\n\n this.dataSource = kendo.data.DataSource.create(ds)\n .bind(\"change\", this._shapesRefreshHandler)\n .bind(\"requestStart\", this._shapesRequestStartHandler)\n .bind(\"error\", this._shapesErrorHandler);\n } else {\n this._treeDataSource();\n this._isEditable = false;\n }\n },\n\n _connectionDataSource: function() {\n var dsOptions = this.options.connectionsDataSource;\n if (dsOptions) {\n var ds = isArray(dsOptions) ? { data: dsOptions } : dsOptions;\n\n if (this.connectionsDataSource && this._connectionsRefreshHandler) {\n this.connectionsDataSource\n .unbind(\"change\", this._connectionsRefreshHandler)\n .unbind(\"requestStart\", this._connectionsRequestStartHandler)\n .unbind(\"error\", this._connectionsErrorHandler);\n } else {\n this._connectionsRefreshHandler = this._refreshConnections.bind(this);\n this._connectionsRequestStartHandler = this._connectionsRequestStart.bind(this);\n this._connectionsErrorHandler = this._connectionsError.bind(this);\n }\n\n this.connectionsDataSource = kendo.data.DataSource.create(ds)\n .bind(\"change\", this._connectionsRefreshHandler)\n .bind(\"requestStart\", this._connectionsRequestStartHandler)\n .bind(\"error\", this._connectionsErrorHandler);\n }\n },\n\n _shapesRequestStart: function(e) {\n if (e.type == \"read\") {\n this._loadingShapes = true;\n }\n },\n\n _connectionsRequestStart: function(e) {\n if (e.type == \"read\") {\n this._loadingConnections = true;\n }\n },\n\n _error: function() {\n this._loadingShapes = false;\n },\n\n _connectionsError: function() {\n this._loadingConnections = false;\n },\n\n _refreshShapes: function(e) {\n if (e.action === \"remove\") {\n if (this._shouldRefresh()) {\n this._removeShapes(e.items);\n }\n } else if (e.action === \"itemchange\") {\n if (this._shouldRefresh()) {\n this._updateShapes(e.items, e.field);\n }\n } else if (e.action === \"add\") {\n this._inactiveShapeItems.add(e.items);\n } else if (e.action === \"sync\") {\n this._syncShapes(e.items);\n } else {\n this.refresh();\n }\n },\n\n _shouldRefresh: function() {\n return !this._suspended;\n },\n\n _suspendModelRefresh: function() {\n this._suspended = (this._suspended || 0) + 1;\n },\n\n _resumeModelRefresh: function() {\n this._suspended = math.max((this._suspended || 0) - 1, 0);\n },\n\n refresh: function() {\n this._loadingShapes = false;\n if (!this._loadingConnections) {\n this._rebindShapesAndConnections();\n }\n },\n\n _rebindShapesAndConnections: function() {\n this.clear();\n this._addShapes(this.dataSource.view());\n if (this.connectionsDataSource) {\n this._addConnections(this.connectionsDataSource.view(), false);\n }\n\n if (this.options.layout) {\n this.layout(this.options.layout);\n } else {\n this._redrawConnections();\n }\n this.trigger(\"dataBound\");\n },\n\n refreshConnections: function() {\n this._loadingConnections = false;\n if (!this._loadingShapes) {\n this._rebindShapesAndConnections();\n }\n },\n\n _redrawConnections: function() {\n var connections = this.connections;\n for (var idx = 0; idx < connections.length; idx++) {\n connections[idx].refresh();\n }\n },\n\n _removeShapes: function(items) {\n var dataMap = this._dataMap;\n var item, i;\n for (i = 0; i < items.length; i++) {\n item = items[i];\n if (dataMap[item.id]) {\n this.remove(dataMap[item.id], false);\n dataMap[item.id] = null;\n }\n }\n },\n\n _syncShapes: function() {\n var diagram = this;\n var inactiveItems = diagram._inactiveShapeItems;\n inactiveItems.forEach(function(inactiveItem) {\n var dataItem = inactiveItem.dataItem;\n var shape = inactiveItem.element;\n if (!dataItem.isNew()) {\n if (shape) {\n shape._setOptionsFromModel();\n diagram.addShape(shape, inactiveItem.undoable);\n diagram._dataMap[dataItem.id] = shape;\n } else {\n diagram._addDataItem(dataItem);\n }\n inactiveItem.activate();\n inactiveItems.remove(dataItem);\n }\n });\n },\n\n _updateShapes: function(items, field) {\n for (var i = 0; i < items.length; i++) {\n var dataItem = items[i];\n\n var shape = this._dataMap[dataItem.id];\n if (shape) {\n shape.updateOptionsFromModel(dataItem, field);\n }\n }\n },\n\n _addShapes: function(dataItems) {\n for (var i = 0; i < dataItems.length; i++) {\n this._addDataItem(dataItems[i], false);\n }\n },\n\n _refreshConnections: function(e) {\n if (e.action === \"remove\") {\n if (this._shouldRefresh()) {\n this._removeConnections(e.items);\n }\n } else if (e.action === \"add\") {\n this._addConnections(e.items);\n } else if (e.action === \"sync\") {\n //TO DO: include logic to update the connections with different values returned from the server.\n } else if (e.action === \"itemchange\") {\n if (this._shouldRefresh()) {\n this._updateConnections(e.items);\n }\n } else {\n this.refreshConnections();\n }\n },\n\n _removeConnections: function(items) {\n for (var i = 0; i < items.length; i++) {\n this.remove(this._connectionsDataMap[items[i].uid], false);\n this._connectionsDataMap[items[i].uid] = null;\n }\n },\n\n _updateConnections: function(items) {\n for (var i = 0; i < items.length; i++) {\n var dataItem = items[i];\n\n var connection = this._connectionsDataMap[dataItem.uid];\n connection.updateOptionsFromModel(dataItem);\n }\n },\n\n _addConnections: function(connections, undoable) {\n var length = connections.length;\n\n for (var i = 0; i < length; i++) {\n var dataItem = connections[i];\n this._addConnectionDataItem(dataItem, undoable);\n }\n },\n\n _addConnectionDataItem: function(dataItem, undoable) {\n if (!this._connectionsDataMap[dataItem.uid]) {\n var from = this._validateConnector(dataItem.from);\n if (!defined(from) || from === null) {\n from = new Point(dataItem.fromX, dataItem.fromY);\n }\n\n var to = this._validateConnector(dataItem.to);\n if (!defined(to) || to === null) {\n to = new Point(dataItem.toX, dataItem.toY);\n }\n\n if (defined(from) && defined(to)) {\n var options = deepExtend({}, this.options.connectionDefaults);\n options.dataItem = dataItem;\n var connection = new Connection(from, to, options);\n\n this._connectionsDataMap[dataItem.uid] = connection;\n this.addConnection(connection, undoable);\n }\n }\n },\n\n _validateConnector: function(value) {\n var connector;\n\n if (defined(value) && value !== null) {\n connector = this._dataMap[value];\n }\n\n return connector;\n },\n\n _treeDataSource: function() {\n var that = this,\n options = that.options,\n dataSource = options.dataSource;\n\n dataSource = isArray(dataSource) ? { data: dataSource } : dataSource;\n\n if (dataSource instanceof kendo.data.DataSource && !(dataSource instanceof kendo.data.HierarchicalDataSource)) {\n throw new Error(\"Incorrect DataSource type. If a single dataSource instance is set to the diagram then it should be a HierarchicalDataSource. You should set only the options instead of an instance or a HierarchicalDataSource instance or supply connectionsDataSource as well.\");\n }\n\n if (!dataSource.fields) {\n dataSource.fields = [\n { field: \"text\" },\n { field: \"url\" },\n { field: \"spriteCssClass\" },\n { field: \"imageUrl\" }\n ];\n }\n if (that.dataSource && that._refreshHandler) {\n that._unbindDataSource();\n }\n\n that._refreshHandler = that._refreshSource.bind(that);\n that._errorHandler = that._error.bind(that);\n\n that.dataSource = HierarchicalDataSource.create(dataSource)\n .bind(CHANGE, that._refreshHandler)\n .bind(ERROR, that._errorHandler);\n },\n\n _unbindDataSource: function() {\n var that = this;\n\n that.dataSource.unbind(CHANGE, that._refreshHandler).unbind(ERROR, that._errorHandler);\n },\n\n _adorn: function(adorner, isActive) {\n if (isActive !== undefined$1 && adorner) {\n if (isActive) {\n this._adorners.push(adorner);\n this.adornerLayer.append(adorner.visual);\n }\n else {\n Utils.remove(this._adorners, adorner);\n this.adornerLayer.remove(adorner.visual);\n }\n }\n },\n\n _showConnectors: function(shape, value) {\n if (value) {\n this._connectorsAdorner.show(shape);\n } else {\n this._connectorsAdorner.destroy();\n }\n },\n\n _updateAdorners: function() {\n var adorners = this._adorners;\n\n for (var i = 0; i < adorners.length; i++) {\n var adorner = adorners[i];\n\n if (adorner.refreshBounds) {\n adorner.refreshBounds();\n }\n adorner.refresh();\n }\n },\n\n _refresh: function() {\n for (var i = 0; i < this.connections.length; i++) {\n this.connections[i].refresh();\n }\n },\n\n _destroyToolBar: function() {\n if (this.singleToolBar) {\n this.singleToolBar.hide();\n this.singleToolBar.destroy();\n this.singleToolBar = null;\n }\n },\n\n _destroyGlobalToolBar: function() {\n if (this.toolBar) {\n this.toolBar.hide();\n this.toolBar.destroy();\n this.toolBar = null;\n }\n },\n\n exportDOMVisual: function() {\n var viewBox = this.canvas._viewBox;\n var scrollOffset = geom.transform()\n .translate(-viewBox.x, -viewBox.y);\n\n var viewRect = new geom.Rect([0, 0], [viewBox.width, viewBox.height]);\n var clipPath = draw.Path.fromRect(viewRect);\n var wrap = new draw.Group({ transform: scrollOffset });\n var clipWrap = new draw.Group({ clip: clipPath });\n var root = this.canvas.drawingElement.children[0];\n\n clipWrap.append(wrap);\n\n // Don't reparent the root\n wrap.children.push(root);\n\n return clipWrap;\n },\n\n exportVisual: function() {\n var scale = geom.transform().scale(1 / this._zoom);\n var wrap = new draw.Group({\n transform: scale\n });\n\n var root = this.mainLayer.drawingElement;\n wrap.children.push(root);\n\n return wrap;\n },\n\n _syncChanges: function() {\n this._syncShapeChanges();\n this._syncConnectionChanges();\n },\n\n _syncShapeChanges: function() {\n if (this.dataSource && this._isEditable) {\n this.dataSource.sync();\n }\n },\n\n _syncConnectionChanges: function() {\n var that = this;\n if (that.connectionsDataSource && that._isEditable) {\n $.when.apply($, that._deferredConnectionUpdates).then(function() {\n that.connectionsDataSource.sync();\n });\n that.deferredConnectionUpdates = [];\n }\n }\n });\n\n dataviz.ExportMixin.extend(Diagram.fn, true);\n\n if (kendo.PDFMixin) {\n kendo.PDFMixin.extend(Diagram.fn);\n }\n\n function filterShapeDataItem(dataItem) {\n var result = {};\n\n dataItem = dataItem || {};\n\n if (defined(dataItem.text) && dataItem.text !== null) {\n result.text = dataItem.text;\n }\n\n if (defined(dataItem.x) && dataItem.x !== null) {\n result.x = dataItem.x;\n }\n\n if (defined(dataItem.y) && dataItem.y !== null) {\n result.y = dataItem.y;\n }\n\n if (defined(dataItem.width) && dataItem.width !== null) {\n result.width = dataItem.width;\n }\n\n if (defined(dataItem.height) && dataItem.height !== null) {\n result.height = dataItem.height;\n }\n\n if (defined(dataItem.type) && dataItem.type !== null) {\n result.type = dataItem.type;\n }\n\n return result;\n }\n\n function filterConnectionDataItem(dataItem) {\n var result = {};\n\n dataItem = dataItem || {};\n\n if (defined(dataItem.text) && dataItem.text !== null) {\n result.content = dataItem.text;\n }\n\n if (defined(dataItem.type) && dataItem.type !== null) {\n result.type = dataItem.type;\n }\n\n if (defined(dataItem.from) && dataItem.from !== null) {\n result.from = dataItem.from;\n }\n\n if (defined(dataItem.fromConnector) && dataItem.fromConnector !== null) {\n result.fromConnector = dataItem.fromConnector;\n }\n\n if (defined(dataItem.fromX) && dataItem.fromX !== null) {\n result.fromX = dataItem.fromX;\n }\n\n if (defined(dataItem.fromY) && dataItem.fromY !== null) {\n result.fromY = dataItem.fromY;\n }\n\n if (defined(dataItem.to) && dataItem.to !== null) {\n result.to = dataItem.to;\n }\n\n if (defined(dataItem.toConnector) && dataItem.toConnector !== null) {\n result.toConnector = dataItem.toConnector;\n }\n\n if (defined(dataItem.toX) && dataItem.toX !== null) {\n result.toX = dataItem.toX;\n }\n\n if (defined(dataItem.toY) && dataItem.toY !== null) {\n result.toY = dataItem.toY;\n }\n\n return result;\n }\n\n\n var DiagramToolBar = kendo.Observable.extend({\n init: function(diagram, options) {\n kendo.Observable.fn.init.call(this);\n this.diagram = diagram;\n this.options = deepExtend({}, this.options, options);\n this._tools = [];\n this.createToolBar();\n this.createTools();\n this.appendTools();\n\n if (this.options.modal) {\n this.createPopup();\n }\n\n this.bind(this.events, options);\n },\n\n events: [\"click\"],\n\n createPopup: function() {\n this.container = $(\"
\").append(this.element);\n this._popup = this.container.kendoPopup({}).getKendoPopup();\n },\n\n appendTools: function() {\n for (var i = 0; i < this._tools.length; i++) {\n var tool = this._tools[i];\n if (tool.buttons && tool.buttons.length || !defined(tool.buttons)) {\n this._toolBar.add(tool);\n }\n }\n },\n\n createToolBar: function() {\n this.element = $(\"
\");\n this._toolBar = this.element\n .kendoToolBar({\n click: this.click.bind(this),\n resizable: false\n }).getKendoToolBar();\n\n this.element.css(\"border\", \"none\");\n },\n\n createTools: function() {\n for (var i = 0; i < this.options.tools.length; i++) {\n this.createTool(this.options.tools[i]);\n }\n },\n\n createTool: function(tool) {\n if (!isPlainObject(tool)) {\n tool = {\n name: tool\n };\n }\n var toolName = tool.name + \"Tool\";\n if (this[toolName]) {\n this[toolName](tool);\n } else {\n this._tools.push(deepExtend({}, tool, {\n attributes: this._setAttributes({ action: tool.name })\n }));\n }\n },\n\n showAt: function(point) {\n var popupZIndex = parseInt(this.options.popupZIndex, 10);\n\n if (this._popup) {\n this._popup.open(point.x, point.y);\n\n if (popupZIndex) {\n this._popup.wrapper.css(\"zIndex\", popupZIndex);\n }\n }\n },\n\n hide: function() {\n if (this._popup) {\n this._popup.close();\n }\n },\n\n newGroup: function() {\n return {\n type: \"buttonGroup\",\n buttons: []\n };\n },\n\n editTool: function() {\n this._tools.push({\n icon: \"pencil\",\n showText: \"overflow\",\n type: \"button\",\n text: \"Edit\",\n attributes: this._setAttributes({ action: \"edit\" })\n });\n },\n\n deleteTool: function() {\n this._tools.push({\n icon: \"x\",\n showText: \"overflow\",\n type: \"button\",\n text: \"Delete\",\n attributes: this._setAttributes({ action: \"delete\" })\n });\n },\n\n rotateAnticlockwiseTool: function(options) {\n this._appendGroup(\"rotate\");\n this._rotateGroup.buttons.push({\n icon: \"rotate-left\",\n showText: \"overflow\",\n text: \"RotateAnticlockwise\",\n group: \"rotate\",\n attributes: this._setAttributes({ action: \"rotateAnticlockwise\", step: options.step })\n });\n },\n\n rotateClockwiseTool: function(options) {\n this._appendGroup(\"rotate\");\n this._rotateGroup.buttons.push({\n icon: \"rotate-right\",\n attributes: this._setAttributes({ action: \"rotateClockwise\", step: options.step }),\n showText: \"overflow\",\n text: \"RotateClockwise\",\n group: \"rotate\"\n });\n },\n\n createShapeTool: function() {\n this._appendGroup(\"create\");\n this._createGroup.buttons.push({\n icon: \"shapes\",\n showText: \"overflow\",\n text: \"CreateShape\",\n group: \"create\",\n attributes: this._setAttributes({ action: \"createShape\" })\n });\n },\n\n createConnectionTool: function() {\n this._appendGroup(\"create\");\n this._createGroup.buttons.push({\n icon: \"connector\",\n showText: \"overflow\",\n text: \"CreateConnection\",\n group: \"create\",\n attributes: this._setAttributes({ action: \"createConnection\" })\n });\n },\n\n undoTool: function() {\n this._appendGroup(\"history\");\n this._historyGroup.buttons.push({\n icon: \"undo\",\n showText: \"overflow\",\n text: \"Undo\",\n group: \"history\",\n attributes: this._setAttributes({ action: \"undo\" })\n });\n },\n\n redoTool: function() {\n this._appendGroup(\"history\");\n this._historyGroup.buttons.push({\n icon: \"redo\",\n showText: \"overflow\",\n text: \"Redo\",\n group: \"history\",\n attributes: this._setAttributes({ action: \"redo\" })\n });\n },\n\n _appendGroup: function(name) {\n var prop = \"_\" + name + \"Group\";\n if (!this[prop]) {\n this[prop] = this.newGroup();\n this._tools.push(this[prop]);\n }\n },\n\n _setAttributes: function(attributes) {\n var attr = {};\n\n if (attributes.action) {\n attr[kendo.attr(\"action\")] = attributes.action;\n }\n\n if (attributes.step) {\n attr[kendo.attr(\"step\")] = attributes.step;\n }\n\n return attr;\n },\n\n _getAttributes: function(element) {\n var attr = {};\n\n var action = element.attr(kendo.attr(\"action\"));\n if (action) {\n attr.action = action;\n }\n\n var step = element.attr(kendo.attr(\"step\"));\n if (step) {\n attr.step = step;\n }\n\n return attr;\n },\n\n click: function(e) {\n var attributes = this._getAttributes($(e.target));\n var action = attributes.action;\n\n if (action && this[action]) {\n this[action](attributes);\n }\n\n this.trigger(\"click\", this.eventData(action, e.target));\n },\n\n eventData: function(action, target) {\n var elements = this.selectedElements(),\n length = elements.length,\n shapes = [], connections = [], element;\n\n for (var idx = 0; idx < length; idx++) {\n element = elements[idx];\n if (element instanceof Shape) {\n shapes.push(element);\n } else {\n connections.push(element);\n }\n }\n\n return {\n shapes: shapes,\n connections: connections,\n action: action,\n target: target\n };\n },\n\n \"delete\": function() {\n var diagram = this.diagram;\n var toRemove = diagram._triggerRemove(this.selectedElements());\n if (toRemove.length) {\n this.diagram.remove(toRemove, true);\n this.diagram._syncChanges();\n }\n },\n\n edit: function() {\n var selectedElemens = this.selectedElements();\n if (selectedElemens.length === 1) {\n this.diagram.edit(selectedElemens[0]);\n }\n },\n\n rotateClockwise: function(options) {\n var angle = parseFloat(options.step || 90);\n this._rotate(angle);\n },\n\n rotateAnticlockwise: function(options) {\n var angle = parseFloat(options.step || 90);\n this._rotate(-angle);\n },\n\n _rotate: function(angle) {\n var adorner = this.diagram._resizingAdorner;\n adorner.angle(adorner.angle() + angle);\n adorner.rotate();\n },\n\n selectedElements: function() {\n return this.diagram.select();\n },\n\n createShape: function() {\n this.diagram.createShape();\n },\n\n createConnection: function() {\n this.diagram.createConnection();\n },\n\n undo: function() {\n this.diagram.undo();\n },\n\n redo: function() {\n this.diagram.redo();\n },\n\n destroy: function() {\n this.diagram = null;\n this.element = null;\n this.options = null;\n\n if (this._toolBar) {\n this._toolBar.destroy();\n }\n\n if (this._popup) {\n this._popup.destroy();\n }\n }\n });\n\n var Editor = kendo.Observable.extend({\n init: function(element, options) {\n kendo.Observable.fn.init.call(this);\n\n this.options = extend(true, {}, this.options, options);\n this.element = element;\n this.model = this.options.model;\n this.fields = this._getFields();\n this._initContainer();\n this.createEditable();\n },\n\n options: {\n editors: {}\n },\n\n _initContainer: function() {\n this.wrapper = this.element;\n },\n\n createEditable: function() {\n var options = this.options;\n\n this.editable = new kendo.ui.Editable(this.wrapper, {\n fields: this.fields,\n target: options.target,\n clearContainer: false,\n model: this.model\n });\n },\n\n _isEditable: function(field) {\n return this.model.editable && this.model.editable(field);\n },\n\n _getFields: function() {\n var fields = [];\n var modelFields = this.model.fields;\n\n for (var field in modelFields) {\n var result = {};\n if (this._isEditable(field)) {\n var editor = this.options.editors[field];\n if (editor) {\n result.editor = editor;\n }\n result.field = field;\n fields.push(result);\n }\n }\n\n return fields;\n },\n\n end: function() {\n return this.editable.end();\n },\n\n destroy: function() {\n this.editable.destroy();\n this.editable.element.find(\"[\" + kendo.attr(\"container-for\") + \"]\").empty();\n this.model = this.wrapper = this.element = this.columns = this.editable = null;\n }\n });\n\n var PopupEditor = Editor.extend({\n init: function(element, options) {\n Editor.fn.init.call(this, element, options);\n this.bind(this.events, this.options);\n\n this.open();\n },\n\n events: [ \"update\", \"cancel\" ],\n\n options: {\n window: {\n modal: true,\n resizable: false,\n draggable: true,\n title: \"Edit\",\n visible: false\n }\n },\n\n _initContainer: function() {\n var that = this;\n this.wrapper = $('
')\n .attr(kendo.attr(\"uid\"), this.model.uid);\n\n var formContent = \"\";\n\n if (this.options.template) {\n formContent += this._renderTemplate();\n this.fields = [];\n } else {\n formContent += this._renderFields();\n }\n\n formContent += this._renderButtons();\n\n this.wrapper.append(\n $('
').append(formContent));\n\n this.window = new kendo.ui.Window(this.wrapper.appendTo(this.element), this.options.window);\n this.window.bind(\"close\", function(e) {\n //The bellow line is required due to: draggable window in IE, change event will be triggered while the window is closing\n if (e.userTriggered) {\n e.sender.element.trigger(\"focus\");\n that._cancelClick(e);\n }\n });\n\n this._attachButtonEvents();\n },\n\n _renderTemplate: function() {\n var template = this.options.template;\n\n if (typeof template === \"string\") {\n template = kendo.unescape(template);\n }\n\n template = kendo.template(template)(this.model);\n\n return template;\n },\n\n _renderFields: function() {\n var form = \"\";\n for (var i = 0; i < this.fields.length; i++) {\n var field = this.fields[i];\n\n form += '
';\n\n if (this._isEditable(field.field)) {\n form += '
';\n }\n }\n\n return form;\n },\n\n _renderButtons: function() {\n var form = '
';\n form += this._createButton(\"update\");\n form += this._createButton(\"cancel\");\n form += '
';\n return form;\n },\n\n _createButton: function(name) {\n return kendo.template(BUTTON_TEMPLATE)(defaultButtons[name]);\n },\n\n _attachButtonEvents: function() {\n this._cancelClickHandler = this._cancelClick.bind(this);\n this.window.element.on(CLICK + NS, \"button.k-diagram-cancel\", this._cancelClickHandler);\n\n this._updateClickHandler = this._updateClick.bind(this);\n this.window.element.on(CLICK + NS, \"button.k-diagram-update\", this._updateClickHandler);\n },\n\n _updateClick: function(e) {\n e.preventDefault();\n this.trigger(\"update\");\n },\n\n _cancelClick: function(e) {\n e.preventDefault();\n this.trigger(\"cancel\");\n },\n\n open: function() {\n this.window.center().open();\n },\n\n close: function() {\n this.window.bind(\"deactivate\", this.destroy.bind(this)).close();\n },\n\n destroy: function() {\n this.window.close().destroy();\n this.window.element.off(CLICK + NS, \"a.k-diagram-cancel\", this._cancelClickHandler);\n this.window.element.off(CLICK + NS, \"a.k-diagram-update\", this._updateClickHandler);\n this._cancelClickHandler = null;\n this._editUpdateClickHandler = null;\n this.window = null;\n Editor.fn.destroy.call(this);\n }\n });\n\n function connectionSelector(container, options) {\n var model = this.dataSource.reader.model;\n if (model) {\n var textField = model.fn.fields.text ? \"text\" : model.idField;\n $(\"\")\n .appendTo(container).kendoDropDownList({\n dataValueField: model.idField,\n dataTextField: textField,\n dataSource: this.dataSource.data().toJSON(),\n optionLabel: \" \",\n valuePrimitive: true\n });\n }\n }\n\n function InactiveItem(dataItem) {\n this.dataItem = dataItem;\n this.callbacks = [];\n }\n\n InactiveItem.fn = InactiveItem.prototype = {\n onActivate: function(callback) {\n var deffered = $.Deferred();\n this.callbacks.push({\n callback: callback,\n deferred: deffered\n });\n return deffered;\n },\n\n activate: function() {\n var callbacks = this.callbacks;\n var item;\n for (var idx = 0; idx < callbacks.length; idx++) {\n item = this.callbacks[idx];\n item.callback(this.dataItem);\n item.deferred.resolve();\n }\n this.callbacks = [];\n }\n };\n\n function InactiveItemsCollection() {\n this.items = {};\n }\n\n InactiveItemsCollection.fn = InactiveItemsCollection.prototype = {\n add: function(items) {\n for (var idx = 0; idx < items.length; idx++) {\n this.items[items[idx].uid] = new InactiveItem(items[idx]);\n }\n },\n\n forEach: function(callback) {\n for (var uid in this.items) {\n callback(this.items[uid]);\n }\n },\n\n getByUid: function(uid) {\n return this.items[uid];\n },\n\n remove: function(item) {\n delete this.items[item.uid];\n }\n };\n\n var QuadRoot = Class.extend({\n init: function() {\n this.shapes = [];\n },\n\n _add: function(shape, bounds) {\n this.shapes.push({\n bounds: bounds,\n shape: shape\n });\n shape._quadNode = this;\n },\n\n insert: function(shape, bounds) {\n this._add(shape, bounds);\n },\n\n remove: function(shape) {\n var shapes = this.shapes;\n var length = shapes.length;\n\n for (var idx = 0; idx < length; idx++) {\n if (shapes[idx].shape === shape) {\n shapes.splice(idx, 1);\n break;\n }\n }\n },\n\n hitTestRect: function(rect, exclude) {\n var shapes = this.shapes;\n var length = shapes.length;\n\n for (var i = 0; i < length; i++) {\n if (this._testRect(shapes[i].shape, rect) && !dataviz.inArray(shapes[i].shape, exclude)) {\n return true;\n }\n }\n },\n\n _testRect: function(shape, rect) {\n var angle = shape.rotate().angle;\n var bounds = shape.bounds();\n var hit;\n if (!angle) {\n hit = bounds.overlaps(rect);\n } else {\n hit = Intersect.rects(rect, bounds, -angle);\n }\n return hit;\n }\n });\n\n var QuadNode = QuadRoot.extend({\n init: function(rect) {\n QuadRoot.fn.init.call(this);\n this.children = [];\n this.rect = rect;\n },\n\n inBounds: function(rect) {\n var nodeRect = this.rect;\n var nodeBottomRight = nodeRect.bottomRight();\n var bottomRight = rect.bottomRight();\n var inBounds = nodeRect.x <= rect.x && nodeRect.y <= rect.y && bottomRight.x <= nodeBottomRight.x &&\n bottomRight.y <= nodeBottomRight.y;\n return inBounds;\n },\n\n overlapsBounds: function(rect) {\n return this.rect.overlaps(rect);\n },\n\n insert: function(shape, bounds) {\n var inserted = false;\n var children = this.children;\n var length = children.length;\n if (this.inBounds(bounds)) {\n if (!length && this.shapes.length < 4) {\n this._add(shape, bounds);\n } else {\n if (!length) {\n this._initChildren();\n }\n\n for (var idx = 0; idx < children.length; idx++) {\n if (children[idx].insert(shape, bounds)) {\n inserted = true;\n break;\n }\n }\n\n if (!inserted) {\n this._add(shape, bounds);\n }\n }\n inserted = true;\n }\n\n return inserted;\n },\n\n _initChildren: function() {\n var rect = this.rect,\n children = this.children,\n shapes = this.shapes,\n center = rect.center(),\n halfWidth = rect.width / 2,\n halfHeight = rect.height / 2,\n childIdx, shapeIdx;\n\n children.push(\n new QuadNode(new Rect(rect.x, rect.y, halfWidth, halfHeight)),\n new QuadNode(new Rect(center.x, rect.y, halfWidth, halfHeight)),\n new QuadNode(new Rect(rect.x, center.y, halfWidth, halfHeight)),\n new QuadNode(new Rect(center.x, center.y, halfWidth, halfHeight))\n );\n for (shapeIdx = shapes.length - 1; shapeIdx >= 0; shapeIdx--) {\n for (childIdx = 0; childIdx < children.length; childIdx++) {\n if (children[childIdx].insert(shapes[shapeIdx].shape, shapes[shapeIdx].bounds)) {\n shapes.splice(shapeIdx, 1);\n break;\n }\n }\n }\n },\n\n hitTestRect: function(rect, exclude) {\n var idx;\n var children = this.children;\n var length = children.length;\n var hit = false;\n\n if (this.overlapsBounds(rect)) {\n if (QuadRoot.fn.hitTestRect.call(this, rect, exclude)) {\n hit = true;\n } else {\n for (idx = 0; idx < length; idx++) {\n if (children[idx].hitTestRect(rect, exclude)) {\n hit = true;\n break;\n }\n }\n }\n }\n\n return hit;\n }\n });\n\n var ShapesQuadTree = Class.extend({\n ROOT_SIZE: 1000,\n\n init: function(diagram) {\n var boundsChangeHandler = this._boundsChange.bind(this);\n diagram.bind(ITEMBOUNDSCHANGE, boundsChangeHandler);\n diagram.bind(ITEMROTATE, boundsChangeHandler);\n this.initRoots();\n },\n\n initRoots: function() {\n this.rootMap = {};\n this.root = new QuadRoot();\n },\n\n clear: function() {\n this.initRoots();\n },\n\n _boundsChange: function(e) {\n if (e.item._quadNode) {\n e.item._quadNode.remove(e.item);\n }\n this.insert(e.item);\n },\n\n insert: function(shape) {\n var bounds = shape.bounds(ROTATED);\n var rootSize = this.ROOT_SIZE;\n var sectors = this.getSectors(bounds);\n var x = sectors[0][0];\n var y = sectors[1][0];\n\n if (this.inRoot(sectors)) {\n this.root.insert(shape, bounds);\n } else {\n if (!this.rootMap[x]) {\n this.rootMap[x] = {};\n }\n\n if (!this.rootMap[x][y]) {\n this.rootMap[x][y] = new QuadNode(\n new Rect(x * rootSize, y * rootSize, rootSize, rootSize)\n );\n }\n\n this.rootMap[x][y].insert(shape, bounds);\n }\n },\n\n remove: function(shape) {\n if (shape._quadNode) {\n shape._quadNode.remove(shape);\n }\n },\n\n inRoot: function(sectors) {\n return sectors[0].length > 1 || sectors[1].length > 1;\n },\n\n getSectors: function(rect) {\n var rootSize = this.ROOT_SIZE;\n var bottomRight = rect.bottomRight();\n var bottomX = math.floor(bottomRight.x / rootSize);\n var bottomY = math.floor(bottomRight.y / rootSize);\n var sectors = [[],[]];\n for (var x = math.floor(rect.x / rootSize); x <= bottomX; x++) {\n sectors[0].push(x);\n }\n for (var y = math.floor(rect.y / rootSize); y <= bottomY; y++) {\n sectors[1].push(y);\n }\n return sectors;\n },\n\n hitTestRect: function(rect, exclude) {\n var sectors = this.getSectors(rect);\n var xIdx, yIdx, x, y;\n var root;\n\n if (this.root.hitTestRect(rect, exclude)) {\n return true;\n }\n\n for (xIdx = 0; xIdx < sectors[0].length; xIdx++) {\n x = sectors[0][xIdx];\n for (yIdx = 0; yIdx < sectors[1].length; yIdx++) {\n y = sectors[1][yIdx];\n root = (this.rootMap[x] || {})[y];\n if (root && root.hitTestRect(rect, exclude)) {\n return true;\n }\n }\n }\n\n return false;\n }\n });\n\n function cloneDataItem(dataItem) {\n var result = dataItem;\n if (dataItem instanceof kendo.data.Model) {\n result = dataItem.toJSON();\n result[dataItem.idField] = dataItem._defaultId;\n }\n return result;\n }\n\n function splitDiagramElements(elements) {\n var connections = [];\n var shapes = [];\n var element, idx;\n for (idx = 0; idx < elements.length; idx++) {\n element = elements[idx];\n if (element instanceof Shape) {\n shapes.push(element);\n } else {\n connections.push(element);\n }\n }\n return {\n shapes: shapes,\n connections: connections\n };\n }\n\n function createModel(dataSource, model) {\n if (dataSource.reader.model) {\n return new dataSource.reader.model(model);\n }\n\n return new kendo.data.ObservableObject(model);\n }\n\n function clearField(field, model) {\n if (defined(model[field])) {\n model.set(field, null);\n }\n }\n\n function copyDefaultOptions(mainOptions, elementOptions, fields) {\n var field;\n for (var idx = 0; idx < fields.length; idx++) {\n field = fields[idx];\n if (elementOptions && !defined(elementOptions[field])) {\n elementOptions[field] = mainOptions[field];\n }\n }\n }\n\n function translateToOrigin(visual) {\n var bbox = visual.drawingContainer().clippedBBox(null);\n if (bbox.origin.x !== 0 || bbox.origin.y !== 0) {\n visual.position(-bbox.origin.x, -bbox.origin.y);\n }\n }\n\n function preventDefault(e) {\n e.preventDefault();\n }\n\n dataviz.ui.plugin(Diagram);\n\n deepExtend(diagram, {\n Shape: Shape,\n Connection: Connection,\n Connector: Connector,\n DiagramToolBar: DiagramToolBar,\n QuadNode: QuadNode,\n QuadRoot: QuadRoot,\n ShapesQuadTree: ShapesQuadTree,\n PopupEditor: PopupEditor\n });\n })(window.kendo.jQuery);\n\n var __meta__ = {\n id: \"dataviz.diagram\",\n name: \"Diagram\",\n category: \"dataviz\",\n description: \"The Kendo DataViz Diagram \",\n depends: [ \"data\", \"userevents\", \"mobile.scroller\", \"draganddrop\", \"drawing\", \"dataviz.core\", \"dataviz.themes\", \"toolbar\" ],\n features: [{\n id: \"dataviz.diagram-pdf-export\",\n name: \"PDF export\",\n description: \"Export Diagram as PDF\",\n depends: [ \"pdf\" ]\n },{\n id: \"dataviz.diagram-editing\",\n name: \"Editing\",\n description: \"Support for model editing\",\n depends: [ \"editable\", \"window\", \"dropdownlist\" ]\n }]\n };\n var kendo$1 = kendo;\n\n return kendo$1;\n\n}));\n"]}