Skip to content

NodeEngineHub/IntellijReactFlow

Repository files navigation

Intellij React Flow

An embedded React Flow-based graph viewer/editor for IntelliJ Platform plugins, built on top of JCEF (Chromium). This module provides:

  • A Swing component (ReactFlowPanel) that hosts a lightweight web UI using React Flow
  • A Java service bridge (ReactFlowService) to push nodes/edges, invoke actions (fitView, connect, etc.), and receive events/messages from the UI

This module is designed to be used as a library inside your IntelliJ plugin project. It is not a standalone plugin by itself.

You can find an example plugin using this library here

Features

  • Render nodes and edges using a bundled React Flow UI
  • Programmatic API to set/update the graph from Java
  • Event bridge from the web UI back to Java (graph changes, custom messages)
  • Ships its own HTML resource (no external server), loads via JCEF

Getting started

1) Add as a composite build/module dependency

build.gradle.kts (of your plugin module)

repositories {
    mavenCentral()
}

dependencies {
    implementation("ca.nodeengine:intellijreactflow:1.0.1")
}

This library uses JCEF and IntelliJ Platform APIs. Your plugin must target an IntelliJ Platform build that provides JCEF (2025.2+).

2) Basic usage

Create the panel, attach the service, and add it to your ToolWindow or dialog/panel.

import ca.nodeengine.intellijreactflow.ui.ReactFlowPanel;
import ca.nodeengine.intellijreactflow.services.ReactFlowService;

// ... inside your UI setup (e.g., ToolWindowFactory#createToolWindowContent)
ReactFlowPanel panel = new ReactFlowPanel();
ReactFlowService service = new ReactFlowService();
service.attachPanel(panel); // wires the bridge and JS calls

// Add the Swing component to your container
JComponent component = panel.getComponent();
contentPanel.add(component, BorderLayout.CENTER);

// Optionally, listen for events from the web UI
service.addListener(new ReactFlowService.Listener() {
    @Override public void onReady() {
        // The UI finished loading; you can now push nodes/edges
    }
    @Override public void onGraphChanged(String payloadJson) {
        // React Flow emitted a graph change (positions, connections, etc.)
        // payloadJson is a JSON string coming from JS
    }
    @Override public void onMessage(String type, String payloadJson) {
        // Custom messages from the UI bridge
    }
});

3) Pushing a graph (nodes and edges)

You can send nodes/edges in bulk or incrementally.

// Define nodes
List<ReactFlowService.Node> nodes = new ArrayList<>();
nodes.add(new ReactFlowService.Node("n1", "First", 100, 150));
nodes.add(new ReactFlowService.Node("n2", "Second", 300, 150));

// Define edges
List<ReactFlowService.Edge> edges = new ArrayList<>();
edges.add(new ReactFlowService.Edge("e1", "n1", "n2", "connects", Map.of()));

// Send to UI
service.setGraph(nodes, edges);

// Alternatively set separately
// service.setNodes(nodes);
// service.setEdges(edges);

// Fit the view after setting the graph
service.fitView();

You can also add a single node or connect nodes programmatically:

service.addNode("n3", "Third", 500, 100, Map.of("color", "#6c5ce7"));
service.connect("n2", "n3");

4) Data payloads

Both nodes and edges accept a Map<String, Object> for arbitrary data. The bridge converts primitive types, strings, maps, and lists into JSON to send to the React Flow UI.

  • Node(id, label, position(x, y), data)
  • Edge(id, source, target, label, data)

On the JS side, this data is accessible as part of the node/edge objects.

5) Lifecycle and disposal

ReactFlowPanel implements Disposable. In IntelliJ Platform, ensure you dispose the panel when the UI is torn down (e.g., when the ToolWindow content is removed) to properly release the JCEF browser.

Example: ToolWindow integration

public class MyToolWindowFactory implements ToolWindowFactory {
  @Override
  public void createToolWindowContent(Project project, ToolWindow toolWindow) {
    ReactFlowPanel panel = new ReactFlowPanel();
    ReactFlowService service = new ReactFlowService();
    service.attachPanel(panel);

    ContentFactory cf = ContentFactory.getInstance();
    Content content = cf.createContent(panel.getComponent(), "Graph", false);
    toolWindow.getContentManager().addContent(content);

    // Wait for onReady or post a delayed runnable to set your graph
    service.addListener(new ReactFlowService.Listener() {
      @Override public void onReady() {
        List<ReactFlowService.Node> nodes = List.of(
          new ReactFlowService.Node("a", "Alpha", 100, 100),
          new ReactFlowService.Node("b", "Beta", 300, 200)
        );
        List<ReactFlowService.Edge> edges = List.of(
          new ReactFlowService.Edge("ab", "a", "b")
        );
        service.setGraph(nodes, edges);
        service.fitView();
      }
      @Override public void onGraphChanged(String payloadJson) {}
      @Override public void onMessage(String type, String payloadJson) {}
    });
  }
}

API surface (Java)

Key entry points you may use:

  • ReactFlowPanel
    • JComponent getComponent()
  • ReactFlowService
    • void attachPanel(ReactFlowPanel panel)
    • void setGraph(List, List)
    • void setNodes(List)
    • void setEdges(List)
    • void addNode(String id, String label, int x, int y, Map<String, Object> data)
    • void connect(String fromId, String toId)
    • void fitView()
    • void addListener(Listener l) / removeListener(Listener l)
    • void requestGraph() // ask UI to send back current graph as JSON

Under the hood

  • JCEF hosts the HTML found at: src/main/resources/intellijreactflow/index.html
  • A JS bridge (JBCefJSQuery) connects Java to the page, enabling function calls and message passing
  • Console messages from the web UI are forwarded to the IntelliJ log to assist with debugging

Limitations

  • The library currently exposes a curated subset of React Flow features via Java methods
  • The web UI is bundled and loaded with resources; customizing the UI requires modifying the resource files
  • Requires IntelliJ distributions that ship with JCEF enabled (most modern IDEs)

TODO

  • Full ReactFlow API support

Contributions

I'm but a single developer, so all contributions are welcome.

About

An intellij plugin library which adds support for ReactFlow within a tool window.

Topics

Resources

License

Stars

Watchers

Forks