How to create custom node shapes in G6/Graphin
Tags: webdev, graphs, javascript, react
Published: 2023-02-11 10:59:24

So, [Graphin](https://graphin.antv.vision/en-US/) is an awesome library, it is indeed a React toolkit for the [G6 library](https://g6.antv.antgroup.com/en) which is and I quote: 

> _G6 is graph visualization engine with simplicity and convenience. Based on the ability of customize, it provides a set of elegant graph visualization solutions, and helps developers to build up applications for graph visualization, graph analysis, and graph editor._

While I was working with it on a new project, I had the necessity to render nodes with different shapes, in order to a user differentiate them at first sight and therefore improve the UX.

Graphin docs are great but it took me some time to find this section of it to create a custom node shape and it was even harder to create some side effect interaction which I will get to in another article. Let's get to the code.

```js
import Graphin, { Utils, GraphinData } from '@antv/graphin'; 

Graphin.registerNode(
  'custom-node', // This is the shape name, you can choose yours.
  {
    options: {
      style: {},
      stateStyles: {
        hover: {},
        selected: {},
      },
    },
    draw(cfg, group) {
      console.log(cfg);
      const keyshape = group.addShape('rect', { // This the node configuration and 'rect' stands for rectangle, and you can modify its shape to a square changing the width and height properties as I have done.
        attrs: {
          id: 'circle-floor',
          x: 0,
          y: 0,
          width: 20,
          height: 20,
          fill: 'black',
        },
        draggable: true,
        name: 'circle-floor',
      });
      group.addShape('text', { // This is the label configuration.
        attrs: {
          fontSize: 12,
          x: 0,
          y: 0,
          text: cfg.id, // This stands for the node ID
          fill: '#ddd',
        },
        draggable: true,
        name: 'text',
      });
      return keyshape;
    },
  },
  'single-node', // This is to tell Graphin whether this is a single node or a combo.
);
```

Ok, we got our square node but how can you tell Graphin to use this node shape instead of the default (graphin-circle) one?

Graphin nodes have the "type" attribute, which by default is graphin-circle.

So there are 2 ways you can change the nodes type or default shape. If you want to render all the nodes using your custom shape, you can change the default node configuration and therefore you don't have to add the type property to every single node of yours which will save you some parsing time.

Screenshot of how to do: 
![Passing default node type to Graphin](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/il17g4jlkhk4y7ct3af8.png)

But let's say you want to have both the graphin-circle and square-node shapes in your network graph, obviously the nodes will either be your custom shape or the graphin-circle default conditionally, then you'll have to loop through the nodes and add the type property.
Such as:

```js
data.nodes.forEach((node) => {
  node.type = conditional ? 'graphin-circle' : 'square-node'
})
```

And bum! You'll have some black squared nodes and some default circle nodes as you can see here:

![Square nodes and circle nodes](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/j596hiizgfjhdm30xbcz.png)

And as you can see in the previous drawing custom shapes code, there are a lot of attributes you can change and customize to your custom node-shapes!

I hope you've enjoyed so far and now you can create cool shapes using Graphin!!