Introduction

KeyLines transforms connected data into charts that highlight connections, patterns or outliers which would be difficult to spot in the raw data.

Visualising a dataset involves a layout algorithm that lays out the nodes and links in optimal positions to create readable, unobstructed and insightful view of the data. This allows chart users to analyse the data at a glance and quickly reveal the key insights. There are several layouts available, each with multiple customisation options.

Depending on the data, a chart can depict a single connected component, or even multiple separate components (for example, two company departments that don't interact at all).

Running a layout

When data is first loaded into KeyLines, nodes are given default coordinates. To avoid overlapping nodes, it's almost always a good idea to call chart.layout() after the data is loaded:

// pass layout name as the first argument of the layout() function
chart.layout('layout name');

If you're adding new data and want to minimise the movement of existing nodes as much as possible, consider using chart.expand(), which uses adaptive behaviour by default.

See our Layouts demo to compare the layouts and the layout options API to explore the options you can use to customise your layouts.

Force-directed layouts

Force-directed layouts position nodes by running a simulation of three forces - repulsion, springs, and network energy. These calculations repel unconnected nodes apart, attract connected nodes together, and move all nodes to optimal positions.

Organic

The organic layout is used by default when you run chart.layout() or chart.expand().

Organic untangles complex networks by placing connected nodes closer together and reducing link crossings. It is a clear and reliable all-rounder for any type or size of data, and it delivers great performance even for very large datasets.

When your data dynamically changes on the chart, for example when nodes are removed or added, organic can be used in adaptive mode. This means that the node positions respond to the new nodes or links without re-laying out the whole graph, reducing movement on the chart to visualise data changes.

Explore the organic layout in our Mafia Network and Visualising Big Data demos.

example of chart with organic layout

Structural

The structural layout groups together nodes with the same neighbouring nodes. This makes it easier to see the general organisation of a network.

Structural gives you an overview of the clusters within a network, and allows you to see groupings and patterns without the need to focus on any one element.

Explore the structural layout in our Donuts and Email traffic demo.

example of chart with structural layout

Lens

The lens layout arranges nodes in a circular pattern that pushes highly-connected nodes into the centre and forces less connected nodes out into the periphery.

The circular outline makes good use of the available space and generally creates denser networks. This results in an attractive 'lens' view which highlights the key nodes in large networks.

Lens is the default arrangement inside open combos. See also the Combining Nodes demo and Arranging nodes inside open combos documentation.

example of chart with lens layout

Level layouts

Level layouts visualise data that is organised in tiers and hierarchies, or that flows from one level to another. They can use different mechanisms to assign levels to nodes:

  • Assigning levels automatically to minimise link crossings and maximise the use of available space. If links have arrows, their direction is used to infer the levels.
  • Assigning levels according to the content of the level option.
  • Assigning top (sequential) / root (radial) node(s) to those specified in the top option. This only lays out the component(s) for which top is specified.

Sequential

The sequential layout is designed to display data that contains a clear sequence of links between distinct levels of nodes, or data where information flows from one level to another.

It examines link directions across the network and automatically works out where to place nodes in the hierarchy of levels in order to minimise link crossings and use all of the available screen space.

Alternatively, sequential layout options let you set positions of nodes within levels manually, and also set their position in relation to each other within each level.

Sequential works well with various link shapes that enhance the clarity and impact of the dataset.

Explore the sequential layout in the Display Hierarchies and Navigate Large Hierarchies demos.

example of chart with sequential layout

Radial

The radial layout arranges nodes in concentric circles around the original subject in a radial tree. Each 'generation' of node becomes a new ring surrounding the previous generations.

Radial is a great option for networks containing a large number of child nodes compared to the number of parents as it makes use of any available space. As with sequential, radial can be customised using the top and level options.

Explore the radial layout in the Light Monochrome view of the Styling Charts demo.

example of chart with radial layout

Packing of components

Packing is a step run during the layout that determines how unconnected chart components are placed relative to each other. It takes the unconnected components and packs them together on the chart to minimise any large gaps.

Packing is available for all layouts except the lens layout. Different layouts have different default packing, but you can also control it manually using the packing option.

'circle'

Default for organic, structural and radial layouts. Lays out the components in a circular pattern. Great for space efficiency. Also suitable for sequential layout when hierarchy levels between unconnected components are irrrelevant as it makes better use of screen space.

example of chart with circle packing

'rectangle'

Lays out the components in a grid-like rectangular pattern. Great for space efficiency and use with other rectangle-biased features such as rectangular combos. Also suitable for sequential layout when hierarchy levels between unconnected components are irrrelevant as it makes better use of screen space.

example of chart with rectangle packing

'aligned'

Default for sequential layout. Lays out the components in a single line with same level items aligned to preserve the information about hierarchy of levels.

example of chart with aligned packing

'adaptive'

Minimally adjusts positions of components to make space for new items or to use space created by removed items. See also Adaptive behaviour.

example of chart with adaptive packing

Arrangements - layouts inside combos

Items inside open combos are laid out using arrangements. Some arrangements are based on existing layouts (e.g. 'lens' or 'sequential'), others are for combos only (e.g. 'concentric' or 'grid').

See Arranging nodes inside open combos for more details.

Performance

Our default organic layout offers the best overall performance for any size of dataset. It is especially suitable for very large charts and would be our first recommendation for most datasets.

If you need to visualise very large hierarchical data, we recommend using the sequential layout with the top or level options specified. This makes layout calculations faster than if the levels are assigned automatically.

For more tips and details, see also the Performance documentation.

Layout options

Layout options can be used to fine-tune the appearance and behaviour of layouts. Options are set in the second argument of the layout API:

// brings the nodes closer together
chart.layout('layout name', { tightness: 10 });

Note that not all layout options apply to every layout.

Adaptive behaviour

Adaptive behaviour is the layout's ability to respond to changes in the data while minimising unnecessary movement and preserving as much of the original layout as possible. Different layouts achieve the best adaptive behaviour using different options.

Use Case ExampleOrganicSequentialLensRadialStructural
Adaptive behaviour when adding data with expand()fix: 'adaptive'packing: 'aligned' / 'adaptive' *Xpacking: 'adaptive'packing: 'adaptive'
Adaptive behaviour when loading or changing data with layout()mode: 'adaptive'mode: 'adaptive'Xpacking: 'adaptive'packing: 'adaptive'
Consistent layout with unchanged componentsconsistent: trueXconsistent: trueXX
Fix existing nodes when adding data with expand()fix: 'all'XXXX
Fix existing nodes when loading or changing data with layout()fixed: []XXXX
* Depending on whether hierarchy of levels between unconnected components is relevant or not. See Packing of components.

consistent

This option produces the same chart display for the same chart structure each time the layout is run, provided that the exact same data and options were used. This can be useful for providing undo-redo support for a chart.

fix

This option specifies which nodes should be fixed in position when the layout is run during chart.expand().

fixed

This option fixes set nodes during chart.layout(). Fixed nodes will keep their position relative to other fixed nodes in the component, although the component itself may move.

mode

This option runs a short force-directed layout instead of random initialisation layout when chart.layout() is run. A short force-directed layout uses the current node positions as a starting point and adapts them in a minimal way to respond to changes in the data. This is ideal for visualising data evolving with time with the show function and the time bar, just like in the Credit Card Fraud demo.

packing

This option controls how unconnected chart components are placed relative to each other during the layout. See Packing of components.

Sequential layout options

Sequential automatically places nodes according to the orientation of the layout and the direction of arrows on links. Alternatively, you can customise the node positions using top or level options:

top

This option specifies the id(s) of the node(s) at the top of the hierarchy. Ignored if level is also set.

level

This option can take the name of a property in a node's custom data object, d, whose value is used to set that node's level. As an example, with this data:

{ 
  id: 'node1', 
  type: 'node',
  d: { levelProperty: 1 }   // this node will be in the first level
}, 
{ 
  id: 'node2', 
  type: 'node',
  d: { levelProperty: 2 }   // this node will be in the subsequent level
}

we can run:

chart.layout('sequential', { level: 'levelProperty' })
// puts node1 above node2 in the hierarchy

orderBy

The string specified in the property option gives the name of a property in a node's custom data object, d. Sequential uses the value of that property to order nodes relative to each other within the same level.

stacking

This option controls positions of nodes that share the same neighbours, level and property value in orderBy (if specified). The arrange property lets you stack such nodes into grids.

Use this option for visualising very wide family trees as it makes better use of space and shows wide networks at more readable zoom levels. See our Navigate Large Hierarchies demo.

chart.layout(
  'sequential', {
    orderBy: { property: 'orderByProperty', sortBy: 'ascending' },
    stacking: { arrange: 'grid' },
})

See layout options for a full list of sequential layout options.