Paper
constructor​
joint.dia.Paper is the view for the joint.dia.Graph model. It inherits from mvc.View. Accepts an options object in its constructor with numerous settings.
When a paper is associated with a graph, the paper makes sure that all the cells added to the graph are automatically rendered.
const graph = new joint.dia.Graph
const paper = new joint.dia.Paper({
el: $('#paper'),
width: 600,
height: 400,
gridSize: 10,
model: graph
});
const rect = new joint.shapes.basic.Rect({
position: { x: 50, y: 70 },
size: { width: 100, height: 40 }
});
graph.addCell(rect);
Paper automatically handles this change and renders the rectangle to the SVG document that it internally holds.
afterRender()​
afterRender?: dia.Paper.AfterRenderCallback;
[optional] A callback function of type AfterRenderCallback executed after all scheduled updates had been processed (both asynchronous and synchronous rendering). The callback function is provided with the following arguments:
| stats | dia.Paper.UpdateStats | Statistics about the current update. |
| options | object | Parameters the current updates were scheduled with. |
| paper | dia.Paper | This paper instance. |
allowLink​
allowLink - expects a function returning a boolean. The function is run when the user stops interacting with a linkView's arrowhead (source or target). If the function returns false, the link is either removed (for links which are created during the interaction) or reverted to the state before the interaction.
// Return `false` if a graph cycle is detected (`graphlib` refers to a dependency of the DirectedGraph plugin).
paper.options.allowLink = function(linkView, paper) {
const graph = paper.model;
return graphlib.alg.findCycles(graph.toGraphLib()).length === 0;
}
anchorNamespace​
anchorNamespace - built-in anchors are defined by default on the joint.anchors namespace. It is also possible to define custom anchors on this namespace. If you would like JointJS to look for anchor definitions under a different namespace, you can set the anchorNamespace option to your desired namespace.
async​
async?: boolean;
[optional] When true, the paper uses asynchronous rendering to display graph cells (i.e. cells added either with graph.resetCells() or graph.addCells() methods).
This is very useful for adding a large number of cells into the graph. The rendering performance boost is significant and it doesn't block the UI. However, asynchronous rendering brings about some caveats – at the time when you call another function...
- ...the views of freshly added cell models may not have yet been added to this paper's DOM.
- ...some views may have been removed from the DOM by the
paper.options.cellVisibilityfunction. - ...views already present in the DOM may not have been updated to reflect changes made in this paper's graph since the last render.
- ...re-rendering may have been manually disabled with
paper.options.frozenorpaper.freeze().
This is an issue because certain CellView/Paper methods require the view to be updated and present in the DOM to function
properly (e.g. paper.findViewByModel() or cell.findView(), as well
as paper.getContentBBox() and elementView.getBBox()
/linkView.getBBox()).
The problem may be circumvented in several Paper methods via the useModelGeometry option to force using model calculations instead of view measurements (e.g. paper.getContentBBox(), paper.getContentArea(), paper.scaleContentToFit(), paper.fitToContent()). In this case, the methods refer to the (always up-to-date) model data.
For the methods that truly need a to refer to a CellView, one way to prevent inconsistencies is to rely on the 'render:done' paper event. This event signals that all scheduled updates are done and that the state of cell views is consistent with the state of the cell models.
Alternatively, you may trigger a manual update immediately before a sensitive function call. JointJS offers several suitable methods:
paper.requireView()- bring a single cell view into the DOM and update it.paper.updateCellsVisibility({ cellVisibility: () => true })- bring all cell views into the DOM and update them.paper.updateViews()- update all views.
autoFreeze​
autoFreeze?: boolean
[optional] If this option is enabled, the paper automatically enters the idle state when there are no cell view updates to process (i.e. when hasScheduledUpdates() returns false). Thus, the autoFreeze option reduces CPU usage:
- It stops the
asyncrendering loop when it is not needed. - It enables garbage collection to run sooner, improving resource efficiency.
If the paper is in the frozen state, it performs no cell view update/visibility checks.
If the paper is unfrozen, then it may be either in the rendering state or the idle state:
- In the rendering state, the paper checks visibility of each cell view with the
cellVisibility()callback. - When there are no scheduled updates and visibility has been checked for all cell views, the paper enters the idle state (announced by triggering the
'render:idle'event), and performs no further cell view visibility checks. - The paper automatically exits the idle state when there is a new cell view to update.
- You can check the current idle status with
paper.isIdle(). - If you need the paper to re-check cell view visibility while it is in the idle state (e.g. to take scrolling or zooming into account), you must tell it to do so with the
wakeUp()method.
Legacy mode differences:
Legacy mode is deprecated and will be removed in JointJS v5.
In legacy mode, there is no unfrozen idle state - the paper enters the frozen state when there are no scheduled updates (i.e. the autoFreeze option overrides the frozen option):
- In the unfrozen state, the paper checks visibility of each view with the
viewport()callback. - When there are no scheduled updates and visibility has been checked for all views, the paper enters the frozen state (announced by triggering the
'render:idle'event), and performs no further view visibility checks. - The paper automatically exits the frozen state when there is a new view to update.
- You can check the current frozen status with
paper.isFrozen(). - If you need the paper to re-check view visibility while it is in the frozen state (e.g. to take scrolling or zooming into account), you must tell it to do so with the
checkViewport()orunfreeze()methods.
background​
An object defining the paper background color and image. It defaults to false meaning there is no background set. The configuration object can have the following properties.
- color
property sets the paper background color. It accepts all the values accepted by the CSS
background-colorproperty. e.g'red','rgba(255, 255, 0, 0.5)','radial-gradient(ellipse at center, red, green);' - image
property defines the path to the background image file. e.g.
'/my-background.png'. - position
is an object
{ x: Number, y: Number }defining the background image position. It also allows to use all the CSSbackground-positionproperty values. In that case all the paper transformations have no impact on the background image position. It defaults tocenter. - size
is an object
{ width: Number, height: Number }defining the background image size. It also allows to use all the CSSbackground-sizeproperty values. In that case all the paper transformations have no impact on the background size. It defaults toauto auto. - repeat
property defines how the background image is repeated. The value could be any value accepted by the CSS
background-repeatproperty and few more defined by JointJS. Those areflip-x,flip-y,flip-xyandwatermark. It defaults tono-repeat. - quality
is a coefficient specifying the quality of the image (e.g
0.5uses only 50% the image size for creating a pattern). Applicable only for the JointJSrepeatoption values. It defaults to1. - opacity
is a number in the range
[0,1]specifying the transparency of the background image (0is fully transparent and1is fully opaque). It defaults to1. - watermarkAngle
is an angle in degrees specifying the slope of the watermark image. Applicable only for the
'watermark'repeatoption. It defaults to20deg.
background: {
color: '#6764A7',
image: 'jointjs-logo.png',
repeat: 'watermark',
opacity: 0.3
}
beforeRender()​
beforeRender?: dia.Paper.BeforeRenderCallback;
[optional] A callback function of type BeforeRenderCallback executed before processing scheduled updates (both asynchronous and synchronous rendering). The callback function is provided with the following arguments:
| options | object | Parameters the current updates were scheduled with. |
| paper | dia.Paper | This paper instance. |
cellViewNamespace​
cellViewNamespace - In order for the JointJS paper to read cell view definitions from the correct location, the paper option cellViewNamespace must be provided. Built-in cell view definitions are usually located in the joint.shapes namespace, so this is a common namespace to use. It's possible to a add custom cell view to this namespace, or alternatively, you may like to use a different namespace completely.
For example, if joint.shapes is provided as the value of cellViewNamespace, and a cell is of type 'custom.Element', then the paper looks up the joint.shapes.custom.ElementView object type when rendering the cell onto the screen. If cellViewNamespace is set with a value of myCustomNamespace, the paper will read view definitions from the myCustomNamespace.custom.ElementView object instead. This option is often used in combination with the cellNamespace option on the joint.dia.Graph object.
cellVisibility()​
cellVisibility?: dia.Paper.CellVisibilityCallback | null;
[optional] A callback function of type CellVisibilityCallback that determines whether cells should be visible in the paper. By default, all cells are visible.
If the function returns true, the cell's view is rendered by the paper and attached to the DOM; if it returns false, the cell's view is detached from the DOM and disposed of by the paper (i.e. removed from memory). The callback function is provided with three arguments:
| cell | dia.Cell | The cell in question |
| isMounted | boolean | Is the cell's view currently visible in the paper? |
| paper | dia.Paper | This paper (for context) |
This callback option allows you to specify logic to filter what is inside the paper's model vs. what is rendered in the paper. For example, in most situations, it is unnecessary to render cells which are not visible to the user. Detaching the views of these cells from the DOM and disposing them from memory dramatically improves rendering times of huge graphs (thousands of cells) and improves smoothness of user interaction.
If you need to show a cell view that was hidden by this callback, you can manually force the cell view to be shown using paper.requireView(). If you need to show all cell views according to different visibility logic, use paper.updateCellsVisibility.
Example usage:
const viewportRect = new g.Rect(0, 0, 600, 400);
const graph = new joint.dia.Graph({}, { cellNamespace: joint.shapes });
const paper = new joint.dia.Paper({
model: graph,
cellViewNamespace: joint.shapes,
async: true,
cellVisibility: (model) => {
const bbox = model.getBBox();
if (model.isLink()) {
// vertical/horizontal links have zero width/height
// we need to manually inflate the bounding box
bbox.inflate(1);
}
// Return `true` if there is an intersection
// Return `true` if bbox is within `viewportRect`
return viewportRect.intersect(bbox);
}
});
The cellVisibility() callback option can also be used to support collapsing/uncollapsing behavior:
const graph = new joint.dia.Graph({}, { cellNamespace: joint.shapes });
const paper = new joint.dia.Paper({
model: graph,
cellViewNamespace: joint.shapes,
async: true,
cellVisibility: (model) => {
// Return `true` if model is not hidden
return !model.get('hidden');
}
});
paper.on('element:pointerclick', (view, evt) => {
evt.stopPropagation();
toggleBranch(view.model);
});
function toggleBranch(root) {
const shouldHide = !root.get('collapsed');
root.set('collapsed', shouldHide);
graph.getSuccessors(root).forEach((successor) => {
successor.set('hidden', shouldHide);
successor.set('collapsed', false);
});
}
Legacy mode differences:
Legacy mode is deprecated and will be removed in JointJS v5.
The cellVisibility() callback option is ignored in favor of the viewport() callback option.
The viewport() callback runs for all views within the paper, including views other than cell views.
clickThreshold​
clickThreshold - When number of mousemove events exceeds the clickThreshold there is no pointerclick event triggered after mouseup. It defaults to 0.
connectionPointNamespace​
connectionPointNamespace - built-in connectionPoints are defined by default on the joint.connectionPoints namespace. It is also possible to define custom connectionPoints on this namespace. If you would like JointJS to look for connectionPoint definitions under a different namespace, you can set the connectionPointNamespace option to your desired namespace.
connectionStrategy​
connectionStrategy - the connection strategy to use on this paper. It can either be a function or null. JointJS provides a collection of built-in connection strategies in the joint.connectionStrategies namespace; alternatively, a custom function may be provided. See the link geometry connectionStrategy documentation for more information.
connectorNamespace​
connectorNamespace - built-in connectors are defined by default on the joint.connectors namespace. It is also possible to define custom connectors on this namespace. If you would like JointJS to look for connector definitions under a different namespace, you can set the connectorNamespace option to your desired namespace.
defaultAnchor​
defaultAnchor - an anchor function that is used by links if no anchor property is defined for a link end. It can either be an object (with a name and optional args) or a function. JointJS provides a collection of built-in anchor functions in the joint.anchors namespace; alternatively, a custom function may be provided. See the link geometry anchor documentation for more information.
defaultConnectionPoint​
defaultConnectionPoint - a connection point function that is used by links if no connectionPoint property is defined for a link end. It can either be an object or a function. JointJS provides a collection of built-in connection point functions in the joint.connectionPoints namespace; alternatively, a custom function may be provided. See the link geometry connectionPoint documentation for more information.
defaultConnector​
defaultConnector - a connector that is used by links if no connector property is defined on them. It can either be an object or a function. JointJS provides a collection of built-in connectors in the joint.connectors namespace; alternatively, a custom function may be provided. See the link geometry connector documentation for more information.
defaultLink​
defaultLink - link that should be created when the user clicks and drags an active magnet (when creating a link from a port via the UI). Defaults to new joint.shapes.standard.Link(). It can also be a function with signature function(cellView, magnet) {} that must return an object of type joint.dia.Link.
defaultLinkAnchor​
defaultLinkAnchor - a link anchor function that is used by links if no linkAnchor property is defined for a link end. It can either be an object (with a name and optional args) or a function. JointJS provides a collection of built-in link anchor functions in the joint.linkAnchors namespace; alternatively, a custom function may be provided. See the link geometry linkAnchor documentation for more information.
defaultRouter​
defaultRouter - a router that is used by links if no router property is defined on them. It can either be an object or a function. JointJS provides a collection of built-in routers in the joint.routers namespace; alternatively, a custom function may be provided. See the link geometry router documentation for more information.
drawGrid​
drawGrid - option whether the paper grid should be drawn or not. It could be a boolean or an object. It defaults to false.
Define color and thickness to adjust the default grid pattern:
| color | string | color of the default grid pattern. |
|---|---|---|
| thickness | number | thickness of the default grid pattern. |
There are also some pre-defined grid patterns: dot, fixedDot, mesh, doubleMesh. If you'd like to use these patterns, define drawGrid options as follows:
| name | string | name of the pre-defined pattern. Can be either dot, fixedDot, mesh, doubleMesh |
|---|---|---|
| args | object | array | an extra argument for the pre-defined grid patterns. It can be either an object (e.g. dot, mesh) or an array (e.g. doubleMesh) |
Pre-defined grids with default settings:
The paper from the images below has been scaled 2 times and has gridSize set to 10.
dot
fixedDot
mesh
doubleMesh
drawGrid: true // default pattern (dot) with default settings
drawGrid: 'mesh' // pre-defined pattern with default settings
drawGrid: { name: 'mesh', args: { color: 'black' }}
drawGrid: {
name: 'doubleMesh',
args: [
{ color: 'red', thickness: 1 }, // settings for the primary mesh
{ color: 'green', scaleFactor: 5, thickness: 5 } //settings for the secondary mesh
]}
drawGridSize​
drawGridSize - the size of the visual grid drawn using the drawGrid option. If this option is set to null (default), the gridSize option is used instead. If the option is changed after the paper has been initialized, call drawGrid to update the grid.
el​
el - CSS selector, or a DOM element holding the container for the paper
elementView​
elementView - object that is responsible for rendering an element model into the paper. Defaults to joint.dia.ElementView. It can also be a function of the form function(element) that takes an element model and should return an object responsible for rendering that model onto the screen (in most cases a subtype of joint.dia.ElementView)
embeddingMode​
embeddingMode - when set to true, the paper is set to embedding mode. In this mode, when you drag an element and drop into another element, the element below becomes a parent of the dropped element (the dropped element gets automatically embedded into the parent element). Similarly, when you drag an element out of its parent, the element gets automatically unembedded from its parent. The embedding mode also makes sure all the connected links and child elements have proper z index set so that they stay visible. To control what elements can be embedded into what other elements, use the validateEmbedding() function on the paper (see below). This is useful for hierarchical diagrams. See the Devs demo on how this can be used.
findParentBy​
findParentBy - determines the way how a cell finds a suitable parent when it's dragged over the paper. The cell with the highest z-index (visually on the top) will be chosen. findParentBy option comes to play when the paper is in embedding mode. All possible values are
| Value | Description |
|---|---|
'bbox' (default) | Choose the parent from the elements under the element rectangle. |
'pointer' | Choose the parent from the elements under the cursor (pointer). |
'center' | 'origin' | 'corner' | 'topRight' | 'bottomLeft' | Choose the parent from the elements under a specific point of the element rectangle. |
function | The function accepts an |
frontParentOnly​
frontParentOnly - when set to the default true, only the element at the very front is taken into account for embedding. If disabled, the elements under the dragged view are tested one by one (from front to back) until a valid parent is found.
// If a child element is embedded and covers the area of 'app.Container', a third element is unable to be embedded
validateEmbedding: function(childView, parentView) {
const model = parentView.model;
if (model.get('type') === 'app.Container') return true;
return false;
},
frontParentOnly: true,
frozen​
frozen?: boolean;
[optional] Return true on an async paper when the paper is in the frozen state. This means that changes made in this paper's model are not reflected by the paper until the state is reversed.
Legacy mode differences:
Legacy mode is deprecated and will be removed in JointJS v5.
The frozen state is exited automatically by the autoFreeze option logic when there is a new view to update.
You can check the current frozen status with paper.isFrozen().
Use paper.unfreeze() to unfreeze the paper, and paper.freeze() to freeze it again. (You may also use paper.updateViews() to manually refresh the paper and leave it frozen.)
Example:
const graph = new joint.dia.Graph({}, { cellNamespace: joint.shapes });
graph.resetCells([cell1, cell2]);
const paper = new joint.dia.Paper({
el: document.getElementById('paper-holder'),
model: graph,
cellViewNamespace: joint.shapes,
frozen: true
});
paper.unfreeze();
gridSize​
gridSize - size of the grid in pixels
guard​
guard - guard paper from handling a browser UI event. This function is of the form function(evt, view) and should return true if you want to prevent the paper from handling the event evt, false otherwise. This is an advanced option that can be useful if you have your own logic for handling events.
height​
height - height of the paper (see setDimensions()).
highlighterNamespace​
highlighterNamespace - built-in highlighters are defined by default on the joint.highlighters namespace. Existing and custom highlighters are defined by extending the base class. If you would like JointJS to look for highlighter definitions under a different namespace, you can set the highlighterNamespace option to your desired namespace.
highlighting​
highlighting - Configure which highlighter to use (if any) for each type of interaction.
List of highlighting interactions:
-
default
joint.dia.CellView.Highlighting.DEFAULT– The default highlighter to use (and options) when none is specified. Default:{
name: 'stroke',
options: {
padding: 3
}
} -
connecting
joint.dia.CellView.Highlighting.CONNECTING– When a valid link connection can be made to an element. -
embedding
joint.dia.CellView.Highlighting.EMBEDDING– When a cell is dragged over another cell in embedding mode. -
magnetAvailability
joint.dia.CellView.Highlighting.MAGNET_AVAILABILITY– When showing all magnets to which a valid connection can be made. Default:{
name: 'addClass',
options: {
className: 'available-magnet'
}
} -
elementAvailability
joint.dia.CellView.Highlighting.ELEMENT_AVAILABILITY– When showing all elements to which a valid connection can be made. Default:{
name: 'addClass',
options: {
className: 'available-cell'
}
}
If a type is set to false, no highlighter is used.
If a type is set to null | undefined, the default highlighter is used.
Example usages:
new joint.dia.Paper({
highlighting: {
'default': {
name: 'stroke', // `joint.highlighters.stroke`
options: {
padding: 2
}
},
'connecting': {
name: 'addClass', // `joint.highlighters.addClass`
options: {
className: 'highlight-connecting'
}
},
// Disable highlighter for embedding
'embedding': false
}
});
new joint.dia.Paper({
// Disable all highlighters
highlighting: false
});
List of available highlighters and their options:
- joint.highlighters.mask
- joint.highlighters.stroke
- joint.highlighters.addClass
- joint.highlighters.opacity
If you need to highlight an element or a link differently based on the cell type or one of its attribute, you can disable the paper highlighting and add a highlighter manually.
// Disable Embedding
paper.options.highlighting.embedding = false;
const MyHighlighters = {
EMBEDDING: 'embedding-highlighter'
};
paper.on('cell:highlight', (cellView, node, { type }) => {
if (type === joint.dia.CellView.Highlighting.EMBEDDING) {
const isLink = cellView.model.isLink();
joint.highlighters.mask.add(cellView, node, MyHighlighters.EMBEDDING, {
attrs: {
'stroke': isLink ? 'red' : 'blue'
}
});
}
});
paper.on('cell:unhighlight', (cellView, node, { type }) => {
if (type === joint.dia.CellView.Highlighting.EMBEDDING) {
joint.highlighters.mask.remove(cellView, MyHighlighters.EMBEDDING);
}
});
By default, when a user connects a link, the target node for the highlighter is either the root of the cell or a magnet. To change this use highlighterSelector attribute.
const element = new joint.shapes.standard.Rectangle({
attrs: {
root: {
highlighterSelector: 'body'
}
}
});
// When a user tries to connect a link to the element.
paper.on('cell:highlight', (elementView, node) => {
assert.notOk(node === elementView.el);
assert.ok(node === elementView.el.querySelector('[joint-selector="body"]'));
});
interactive​
interactive - Configure which of the default interactions with elements and links should be enabled.
The property value defaults to { labelMove: false }. This can be overwritten in three ways: with a boolean value, with an object specifying interaction keys, or with a function.
If set to false, all interactions with elements and links are disabled. If set to true, all interactions are enabled.
// disable all interaction
const paper = new joint.dia.Paper({
// ...
interactive: false,
});
// enable all interaction (including labelMove)
const paper = new joint.dia.Paper({
// ...
interactive: true,
});
Using an object, specific interactions may be disabled by assigning false to their corresponding property name. It is not necessary to pass true values; all omitted properties are assigned true by default. (Note that the passed object is not merged with the default; unless labelMove is explicitly excluded, it becomes enabled.) A full list of recognized interaction keys is provided below.
// disable labelMove
const paper = new joint.dia.Paper({
// ...
interactive: { labelMove: false }
});
// disable all element interactions
const paper = new joint.dia.Paper({
// ...
interactive: { elementMove: false, addLinkFromMagnet: false }
});
If defined as a function, the function is passed cellView (the elementView/linkView the user is about to interact with) as the first parameter, followed by the name of the event ('pointerdown', 'pointermove', ...) that triggered the interaction. The return value of the function is then interpreted in the way specified above (false causes all interaction to be disabled, an object disables specific interactions, etc.).
// disable link interactions for cellViews when a custom property is set
const paper = new joint.dia.Paper({
// ...
interactive: function(cellView) {
if (cellView.model.get('disableLinkInteractions')) {
return {
linkMove: false,
labelMove: false,
};
}
// otherwise
return true;
}
});
The example below has all interactions on the link and on the elements enabled. This is the default behavior:
The following tables present a list of all recognized interaction keys, followed by an example of a paper with only the related interactive property set to true (and all other properties set to false).
Links:
| linkMove | Is the user allowed to move the link? |
|---|---|
| labelMove | Is the user allowed to move the link label? Use the |
Elements:
| elementMove | Is the user allowed to move the element? |
|---|---|
| addLinkFromMagnet | Is the user allowed to add connections from magnets/ports? |
The stopDelegation option is special. If it is true (default), the element's elementMove option determines whether the element responds to user drag.
However, if stopDelegation is false and the element is embedded within a parent, the user's dragging is delegated to the embedding parent. The parent's elementMove option then determines whether both elements respond to user drag. The behavior is recursive. If the embedding parent has stopDelegation: false, it delegates to its own embedding parent's elementMove option and so on. If all children within an embedding have stopDelegation set to false, then no matter which element is dragged by the user, the whole embedding is dragged.
If the element is not embedded within an element, the stopDelegation option is ignored (treated as true). There is no other element to delegate to. Then elementMove determines whether the element responds to user drag.
In the following example, both embedded elements have stopDelegation: false. Thus, when the embedded element is dragged by the user, the parent ancestor (Movable) is dragged instead. When the parent ancestor has elementMove disabled (Not movable), nothing happens.
| stopDelegation |
|---|
labelsLayer​
labelsLayer - controls the stacking context of the link labels.
| Value | Description |
|---|---|
| false (default) | The labels are rendered as part of the links. Overlapping links with a larger z can cover link labels with a smaller one. |
| true | The labels are rendered into its own layer on top of other elements and links. A link's connection can cover no label. |
layerViewNamespace​
layerViewNamespace - this is an object that maps layer view types to their constructors. If layer view options doesn't have a type, type of its model with View postfix is used. By default, if type is not specified, dia.LayerView is used. This option is merged with the default layerViewNamespace object:
// Default layerViewNamespace
{
'LayerView': dia.LayerView,
'GraphLayerView': dia.GraphLayerView,
'GridLayerView': dia.GridLayerView,
}
linkAnchorNamespace​
linkAnchorNamespace - built-in linkAnchors are defined by default on the joint.linkAnchors namespace. It is also possible to define custom linkAnchors on this namespace. If you would like JointJS to look for linkAnchor definitions under a different namespace, you can set the linkAnchorNamespace option to your desired namespace.
linkPinning​
linkPinning - when set to true (the default), links can be pinned to the paper meaning a source or target of a link can be a point. If you do not want to let the user drag a link and drop it somewhere in a blank paper area, set this to false. The effect is that the link will be returned to its original position whenever the user drops it somewhere in a blank paper area.
linkView​
linkView - object that is responsible for rendering a link model into the paper. Defaults to joint.dia.LinkView. It can also be a function of the form function(link) that takes a link model and should return an object responsible for rendering that model onto the screen (in most cases a subtype of joint.dia.LinkView).
magnetThreshold​
magnetThreshold - When defined as a number, it denotes the required mousemove events before a new link is created from a magnet. When defined as keyword 'onleave', the link is created when the pointer leaves the magnet DOM element. It defaults to 0.