Skip to content
  1. Tutorials

Interactions API

Basics

Ogma has a built-in system of events and interaction states. It also provides tools for convenient node and edge selection and basic state management.

States/Mouse events

You can subscribe to basic mouse/touch interactions on nodes, edges and with the background.

Click

js
// subscribe to click events
ogma.events.on('click', function (evt) {
  if (evt.target === null) {
    // you have clicked on the background
    // use the click position to coordinate your UI, move nodes etc.
    console.log('clicked on background at coordinates', evt.x, evt.y);
  } else if (evt.target.isNode) {
    // you have clicked on a node
    console.log('clicked on a node with id', evt.target.getId());

    // show the context menu for a particular node at the
    // calculated screen coordinate
    const position = ogma.view.graphToScreenCoordinates({ x: evt.x, y: evt.y });

    // showContextMenu is a user-defined function that shows an UI
    showContextMenu(evt.target, position.x, position.y);
  } else {
    // it's an edge
    const edge = evt.target;
    console.log(
      'clicked on an edge between ',
      edge.getSource().getId(),
      ' and',
      edge.getTarget().getId()
    );
  }
});

Right click

You can also access the mouse event parameters, such as which button was clicked, by accessing the event parameter provided by the onClick event handler:

js
const currentNode;
ogma.events.on('click', function (evt) {
  const target = evt.target;
  // check for right click and raise a context menu with the items
  // depending on what is currently selected
  if (evt.button === 'right' && target && target.isNode) {
    const selected = ogma.getSelectedNodes();
    let group = false;

    // show different menu tems for groups and single nodes
    if (selected.includes(target)) {
      currentNode = selected;
      group = true;
    } else {
      currentNode = target;
    }

    // get screen coordinates to position the context menu
    const position = ogma.view.graphToScreenCoordinates(target.getPosition());

    // The user-defined showMenu function displays the menu
    showMenu(position.x, position.y, group);
  }
});

Hover elements

Hovering elements follows the same idea. The logic is coded in the handler. The function ogma.getHoveredElement() can also be used to get the element under the pointer.

js
// get the container to show information
const hoveredContainer = document.getElementById('hovered-nodes');
ogma.events.on('mousemove', function (evt) {
  const hovered = ogma.getHoveredElement();
  if (hovered && hovered.isNode) {
    // an element is hovered and it's a node
    // show information about the node in the UI
    const color = hovered.getAttribute('color');
    const text = hovered.getAttribute('text');
    hoveredContainer.innerHTML =
      '<span class="node" style="background-color: ' +
      color +
      '">' +
      text +
      '</span>';
  } else {
    hoveredContainer.innerHTML = '';
  }
});

Drag elements

Dragging nodes is a built-in interaction. It allows re-positioning nodes using the mouse or touch. Dragging emits events (dragStart, dragProgress and dragEnd) that store information about the elements being dragged and their positions. Here, we use a custom class to change the visual style of nodes and edges that are dragged. Take a look at styling API tutorial to learn how to use styles and classes in a CSS-like way.

js
// 'dragged' is a built-in class for the dragged nodes
ogma.events.on('nodesDragStart', function (evt) {
  console.log('Start dragging', evt.nodes.size, 'nodes');
  // add visual style to the nodes that are dragged.
  const nodes = evt.nodes;
  nodes.addClass('dragged');
  // add visual style to the nodes that are not dragged.
  nodes.inverse().addClass('static');
});
ogma.events.on('nodesDragend', function (evt) {
  const nodes = evt.nodes;
  // reset visual styles for the nodes
  nodes.removeClass('dragged');
  nodes.inverse().removeClass('static');
});

Selection

API

The selection can be accessed/modified programmatically:

js
ogma.getNodes(['n1', 'n2', 'n3']).setSelected(true);
console.log(ogma.getSelectedNodes().getId()); // ['n1', 'n2', 'n3']
ogma.getSelectedNodes().setSelected(false);
console.log(ogma.getSelectedNodes().getId()); // []

You may find useful the methods for selection inversion, i.e. to retrieve the elements that are not selected:

js
ogma.getNonSelectedNodes(); // all nodes minus the selected ones selected

// these 3 lines of code will invert your selection
const selected = ogma.getSelectedNodes();
ogma.getNonSelectedNodes().setSelected(true);
selected.setSelected(false);

Default Selection

Ogma implements a default selection mechanism that behaves the following way: Maintain the 'ctrl' key to add nodes to the selection. Click on the background to reset the selection.

Custom Selection behavior It is also possible to use the API to customize the selection behavior. Here we add clicked items to the selection, and clear the selection on a background click.

js
// deactivate the default selection mode
ogma.setOptions({ interactions: { selection: { enabled: false } } });

ogma.events.on('click', function (event) {
  // if target exists (i.e. a node or edge is clicked) add to selection
  if (event.target) {
    console.log('Click on ', event.target.isNode ? 'node' : 'edge');
    event.target.setSelected(true);
  } else {
    console.log('Click on background.');
    ogma.clearSelection();
  }
});

Lasso tool

Lasso tool allows to select the nodes by freehand drawing an outline around them:

js
// subscribe to selection change event, it will be triggered when
// lasso selection is done
ogma.events.on('nodesSelected', () => {
  console.log(ogma.getSelectedNodes().getId()); // ['id1', 'id2', ...]
});
ogma.tools.lasso.enable(); // enables lasso
// perform some freehand selection

Rectangle selection tool

Sometimes it is convenient to use a rectangular selection for the nodes. It is a familiar tool for novice users and is widely used in graph editors.

js
// subscribe to selection change event, it will be triggered once
// rectangle selection is done
ogma.events.on('nodesSelected', () => {
  console.log(ogma.getSelectedNodes().getId()); // ['id1', 'id2', ...]
});
// switch rectangle select on drag start with the 'ctrl' key pressed
ogma.events.on('dragStart', () => {
  if (ogma.keyboard.isKeyPressed('ctrl')) {
    ogma.tools.rectangleSelect.enable();
  }
});

Keyboards events

Keyboard events can be subscribed to and trigger custom actions. For instance, you can assign a keyboard shortcut to call one of the selection tools:

js
function toggleLasso() {
  if (ogma.tools.lasso.enabled()) {
    ogma.tools.lasso.disable();
  } else {
    ogma.tools.lasso.enable();
  }
}
ogma.events.onKeyPress('l', toggleLasso); // toggles lasso tool on/off

// '+' and '-' keys are used to zoom in and out with a short animation
ogma.events
  .onKeyPress('+', () => ogma.view.zoomIn({ duration: 200 }))
  .onKeyPress('-', () => ogma.view.zoomOut({ duration: 200 }));

Graph events end methods.

Ogma triggers several events that can be useful to bind custom interactions to. These can include notifications, stats or UI feedback.

For instance, you can get notified on nodesAdded, nodesRemoved events to show information about your graph:

js
// shows graph size stats
function showStats() {
  document.getElementById('stats').innerHTML =
    ogma.getNodes().size + ' nodes, ' + ogma.getEdges().size + 'edges';
}
ogma.events
  .onEdgesAdded(showStats)
  .onNodesAdded(showStats)
  .onNodesRemoved(showStats);

There are events that can allow you to listen to the viewport changes, to synchronize the position with your UI elements (tooltips, additional graphs and charts).

dragStart, dragProgress, dragEnd, zoomStart, zoomProgress, zoomEnd, can be used to synchronise additional graphics with the position and scale of ogma viewer. viewChanged is triggered with a delay after both zooming and panning are complete.

You can find full documentation on these and more events in the "Events" section.