NetworkGraph

Data Visualization

노드-링크 네트워크 그래프.

Usage

사람·개념·서비스 같은 노드 사이의 연결 관계를 탐색할 때 사용한다.

import

import

import { NetworkGraph } from '@mildang/design-system/Chart';

예제를 복사해 쓸 때 필요한 준비

@mildang/styled-system 은 이 저장소에서 Panda 가 생성하는 산출물이다. 저장소 안에서는 turbo run ship 이후 쓸 수 있고, 패키지 소비자는 자기 Panda 산출물이나 다른 레이아웃 수단으로 바꿔야 한다.

API Reference

NetworkGraph Props

Prop

Type

Default

links
필수

NetworkGraphLink[]

지정 안 함

nodes
필수

NetworkGraphNode[]

지정 안 함

className

string

지정 안 함

colors

string[]

지정 안 함

degreeLabel

string

연결

groupLabel

string

그룹

layout

"circular"

지정 안 함

legendPosition

"bottom" | "left" | "right" | "top"

bottom

linkColor

string

지정 안 함

margin

Partial<ChartMargin>

지정 안 함

nodeRadius

number

8

showLabels

boolean

true

showLegend

boolean

false

showTooltip

boolean

false

sizeByDegree

boolean

false

예제

기본 (개념 연관 네트워크)

import { NetworkGraph } from '@mildang/design-system/Chart';
import { NetworkGraphLink, NetworkGraphNode } from '@mildang/design-system/Chart';

// 중1 수학 개념 연관 네트워크 — weight는 연계 문항 수
const conceptNodes: NetworkGraphNode[] = [
  { id: 'prime', label: '소인수분해', group: '수와 연산' },
  { id: 'gcd', label: '최대공약수', group: '수와 연산' },
  { id: 'integer', label: '정수와 유리수', group: '수와 연산' },
  { id: 'expr', label: '문자의 사용', group: '문자와 식' },
  { id: 'lineq', label: '일차방정식', group: '문자와 식' },
  { id: 'coord', label: '좌표평면', group: '좌표와 그래프' },
  { id: 'prop', label: '정비례·반비례', group: '좌표와 그래프' },
  { id: 'graph', label: '그래프 해석', group: '좌표와 그래프' },
];

const conceptLinks: NetworkGraphLink[] = [
  { source: 'prime', target: 'gcd', weight: 8 },
  { source: 'prime', target: 'integer', weight: 5 },
  { source: 'integer', target: 'expr', weight: 4 },
  { source: 'expr', target: 'lineq', weight: 9 },
  { source: 'lineq', target: 'prop', weight: 6 },
  { source: 'coord', target: 'prop', weight: 7 },
  { source: 'coord', target: 'graph', weight: 5 },
  { source: 'prop', target: 'graph', weight: 3 },
  { source: 'lineq', target: 'graph', weight: 2 },
];

const NetworkGraphDefaultExample = () => <NetworkGraph nodes={conceptNodes} links={conceptLinks} showLegend />;

export default NetworkGraphDefaultExample;

Hover Tooltip

import { NetworkGraph } from '@mildang/design-system/Chart';
import { NetworkGraphLink, NetworkGraphNode } from '@mildang/design-system/Chart';

// 중1 수학 개념 연관 네트워크 — weight는 연계 문항 수
const conceptNodes: NetworkGraphNode[] = [
  { id: 'prime', label: '소인수분해', group: '수와 연산' },
  { id: 'gcd', label: '최대공약수', group: '수와 연산' },
  { id: 'integer', label: '정수와 유리수', group: '수와 연산' },
  { id: 'expr', label: '문자의 사용', group: '문자와 식' },
  { id: 'lineq', label: '일차방정식', group: '문자와 식' },
  { id: 'coord', label: '좌표평면', group: '좌표와 그래프' },
  { id: 'prop', label: '정비례·반비례', group: '좌표와 그래프' },
  { id: 'graph', label: '그래프 해석', group: '좌표와 그래프' },
];

const conceptLinks: NetworkGraphLink[] = [
  { source: 'prime', target: 'gcd', weight: 8 },
  { source: 'prime', target: 'integer', weight: 5 },
  { source: 'integer', target: 'expr', weight: 4 },
  { source: 'expr', target: 'lineq', weight: 9 },
  { source: 'lineq', target: 'prop', weight: 6 },
  { source: 'coord', target: 'prop', weight: 7 },
  { source: 'coord', target: 'graph', weight: 5 },
  { source: 'prop', target: 'graph', weight: 3 },
  { source: 'lineq', target: 'graph', weight: 2 },
];

const NetworkGraphHoverTooltipExample = () => (
    <NetworkGraph nodes={conceptNodes} links={conceptLinks} showTooltip showLabels={false} />
  );

export default NetworkGraphHoverTooltipExample;

노드 크기 = 연결 가중치

import { NetworkGraph } from '@mildang/design-system/Chart';
import { NetworkGraphLink, NetworkGraphNode } from '@mildang/design-system/Chart';

// 중1 수학 개념 연관 네트워크 — weight는 연계 문항 수
const conceptNodes: NetworkGraphNode[] = [
  { id: 'prime', label: '소인수분해', group: '수와 연산' },
  { id: 'gcd', label: '최대공약수', group: '수와 연산' },
  { id: 'integer', label: '정수와 유리수', group: '수와 연산' },
  { id: 'expr', label: '문자의 사용', group: '문자와 식' },
  { id: 'lineq', label: '일차방정식', group: '문자와 식' },
  { id: 'coord', label: '좌표평면', group: '좌표와 그래프' },
  { id: 'prop', label: '정비례·반비례', group: '좌표와 그래프' },
  { id: 'graph', label: '그래프 해석', group: '좌표와 그래프' },
];

const conceptLinks: NetworkGraphLink[] = [
  { source: 'prime', target: 'gcd', weight: 8 },
  { source: 'prime', target: 'integer', weight: 5 },
  { source: 'integer', target: 'expr', weight: 4 },
  { source: 'expr', target: 'lineq', weight: 9 },
  { source: 'lineq', target: 'prop', weight: 6 },
  { source: 'coord', target: 'prop', weight: 7 },
  { source: 'coord', target: 'graph', weight: 5 },
  { source: 'prop', target: 'graph', weight: 3 },
  { source: 'lineq', target: 'graph', weight: 2 },
];

const NetworkGraphSizeByDegreeExample = () => (
    <NetworkGraph nodes={conceptNodes} links={conceptLinks} sizeByDegree nodeRadius={10} showLegend showTooltip />
  );

export default NetworkGraphSizeByDegreeExample;

가중치 없는 링크 (스터디 짝꿍)

import { NetworkGraph } from '@mildang/design-system/Chart';
import { NetworkGraphLink, NetworkGraphNode } from '@mildang/design-system/Chart';

// 반별 스터디 짝꿍 관계 — weight 없는 단순 링크
const studyNodes: NetworkGraphNode[] = [
  { id: '김민준' },
  { id: '이서연' },
  { id: '박지훈' },
  { id: '최수아' },
  { id: '정도윤' },
  { id: '한지민' },
];

const studyLinks: NetworkGraphLink[] = [
  { source: '김민준', target: '이서연' },
  { source: '김민준', target: '박지훈' },
  { source: '이서연', target: '최수아' },
  { source: '박지훈', target: '정도윤' },
  { source: '최수아', target: '한지민' },
  { source: '정도윤', target: '한지민' },
];

const NetworkGraphNoWeightsExample = () => <NetworkGraph nodes={studyNodes} links={studyLinks} showTooltip />;

export default NetworkGraphNoWeightsExample;

커스텀 색·링크 색

import { NetworkGraph } from '@mildang/design-system/Chart';
import { token } from '@mildang/styled-system/tokens';
import { NetworkGraphLink, NetworkGraphNode } from '@mildang/design-system/Chart';

// 중1 수학 개념 연관 네트워크 — weight는 연계 문항 수
const conceptNodes: NetworkGraphNode[] = [
  { id: 'prime', label: '소인수분해', group: '수와 연산' },
  { id: 'gcd', label: '최대공약수', group: '수와 연산' },
  { id: 'integer', label: '정수와 유리수', group: '수와 연산' },
  { id: 'expr', label: '문자의 사용', group: '문자와 식' },
  { id: 'lineq', label: '일차방정식', group: '문자와 식' },
  { id: 'coord', label: '좌표평면', group: '좌표와 그래프' },
  { id: 'prop', label: '정비례·반비례', group: '좌표와 그래프' },
  { id: 'graph', label: '그래프 해석', group: '좌표와 그래프' },
];

const conceptLinks: NetworkGraphLink[] = [
  { source: 'prime', target: 'gcd', weight: 8 },
  { source: 'prime', target: 'integer', weight: 5 },
  { source: 'integer', target: 'expr', weight: 4 },
  { source: 'expr', target: 'lineq', weight: 9 },
  { source: 'lineq', target: 'prop', weight: 6 },
  { source: 'coord', target: 'prop', weight: 7 },
  { source: 'coord', target: 'graph', weight: 5 },
  { source: 'prop', target: 'graph', weight: 3 },
  { source: 'lineq', target: 'graph', weight: 2 },
];

const NetworkGraphCustomColorsExample = () => (
    <NetworkGraph
      nodes={conceptNodes}
      links={conceptLinks}
      colors={[
        token('colors.blue.light.400'),
        token('colors.green.light.400'),
        token('colors.orange.light.400'),
      ]}
      linkColor={token('colors.info.border.base')}
      showLegend
    />
  );

export default NetworkGraphCustomColorsExample;

라벨 숨김

import { NetworkGraph } from '@mildang/design-system/Chart';
import { NetworkGraphLink, NetworkGraphNode } from '@mildang/design-system/Chart';

// 중1 수학 개념 연관 네트워크 — weight는 연계 문항 수
const conceptNodes: NetworkGraphNode[] = [
  { id: 'prime', label: '소인수분해', group: '수와 연산' },
  { id: 'gcd', label: '최대공약수', group: '수와 연산' },
  { id: 'integer', label: '정수와 유리수', group: '수와 연산' },
  { id: 'expr', label: '문자의 사용', group: '문자와 식' },
  { id: 'lineq', label: '일차방정식', group: '문자와 식' },
  { id: 'coord', label: '좌표평면', group: '좌표와 그래프' },
  { id: 'prop', label: '정비례·반비례', group: '좌표와 그래프' },
  { id: 'graph', label: '그래프 해석', group: '좌표와 그래프' },
];

const conceptLinks: NetworkGraphLink[] = [
  { source: 'prime', target: 'gcd', weight: 8 },
  { source: 'prime', target: 'integer', weight: 5 },
  { source: 'integer', target: 'expr', weight: 4 },
  { source: 'expr', target: 'lineq', weight: 9 },
  { source: 'lineq', target: 'prop', weight: 6 },
  { source: 'coord', target: 'prop', weight: 7 },
  { source: 'coord', target: 'graph', weight: 5 },
  { source: 'prop', target: 'graph', weight: 3 },
  { source: 'lineq', target: 'graph', weight: 2 },
];

const NetworkGraphWithoutLabelsExample = () => <NetworkGraph nodes={conceptNodes} links={conceptLinks} showLabels={false} showLegend />;

export default NetworkGraphWithoutLabelsExample;

노드 1개

import { NetworkGraph } from '@mildang/design-system/Chart';

const NetworkGraphSingleNodeExample = () => <NetworkGraph nodes={[{ id: '소인수분해', group: '수와 연산' }]} links={[]} showLegend />;

export default NetworkGraphSingleNodeExample;

빈 데이터

import { NetworkGraph } from '@mildang/design-system/Chart';

const NetworkGraphEmptyExample = () => <NetworkGraph nodes={[]} links={[]} showLegend />;

export default NetworkGraphEmptyExample;

반응형 (너비 자동 조정)

import { NetworkGraph } from '@mildang/design-system/Chart';
import { NetworkGraphLink, NetworkGraphNode } from '@mildang/design-system/Chart';

// 중1 수학 개념 연관 네트워크 — weight는 연계 문항 수
const conceptNodes: NetworkGraphNode[] = [
  { id: 'prime', label: '소인수분해', group: '수와 연산' },
  { id: 'gcd', label: '최대공약수', group: '수와 연산' },
  { id: 'integer', label: '정수와 유리수', group: '수와 연산' },
  { id: 'expr', label: '문자의 사용', group: '문자와 식' },
  { id: 'lineq', label: '일차방정식', group: '문자와 식' },
  { id: 'coord', label: '좌표평면', group: '좌표와 그래프' },
  { id: 'prop', label: '정비례·반비례', group: '좌표와 그래프' },
  { id: 'graph', label: '그래프 해석', group: '좌표와 그래프' },
];

const conceptLinks: NetworkGraphLink[] = [
  { source: 'prime', target: 'gcd', weight: 8 },
  { source: 'prime', target: 'integer', weight: 5 },
  { source: 'integer', target: 'expr', weight: 4 },
  { source: 'expr', target: 'lineq', weight: 9 },
  { source: 'lineq', target: 'prop', weight: 6 },
  { source: 'coord', target: 'prop', weight: 7 },
  { source: 'coord', target: 'graph', weight: 5 },
  { source: 'prop', target: 'graph', weight: 3 },
  { source: 'lineq', target: 'graph', weight: 2 },
];

const NetworkGraphResponsiveExample = () => (
    <div style={{ display: 'flex', flexDirection: 'column', gap: 32, width: '100%' }}>
      {([280, 440, 640] as const).map((w) => (
        <div key={w} style={{ width: w }}>
          <div style={{ marginBottom: 4, fontSize: 11, color: '#888' }}>{w}px</div>
          <div style={{ width: w, height: 280 }}>
            <NetworkGraph nodes={conceptNodes} links={conceptLinks} showLegend />
          </div>
        </div>
      ))}
    </div>
  );

export default NetworkGraphResponsiveExample;