skip to content
usubeni fantasy logo Usubeni Fantasy

Webページにプロフェッショナルなマインドマップ機能を簡単に統合 - Mind Elixir

/ 17 min read

This Post is Available In: CN EN ES JA KO RU

情報爆発の時代において、私たちは日々大量の複雑な情報やアイデアを処理しなければなりません。従来の線形ノートでは思考の飛躍性や関連性を表現することが困難ですが、マインドマップは半自動的なノートツールとして、思考の整理、知識構造の体系化、創造的インスピレーションの刺激に役立ち、同時にホワイトボードや描画ソフトウェアよりも操作が便利です。

知識管理プラットフォーム、オンライン教育サイト、コラボレーションツールの構築において、マインドマップ機能の統合はユーザーエクスペリエンスを大幅に向上させ、複雑な情報の表示とインタラクションをより直感的で効率的にします。

あなたのWebプロジェクトにマインドマップ機能を統合したい場合、Mind Elixirを活用すれば、わずか数行のコードでWebサイトにプロフェッショナルレベルのマインドマップ機能を追加できます。例えば個人ブログでは、記事の知識構造を表示したり、インタラクティブな学習ノートを作成したりできます。このような機能はコンテンツをより生き生きと興味深くするだけでなく、ブログの専門性を大幅に向上させます。

Mind Elixir 内核

オープンソースのJavaScriptマインドマップコアMind Elixirは、以下の主要機能を備えています:

  • スムーズなユーザーエクスペリエンス 滑らかなインタラクション、自然なフィードバック、モバイル対応。
  • 軽量かつ高性能 小さなファイルサイズ、高速読み込みとレンダリング、複雑なグラフィックでも高フレームレートを維持。
  • フレームワーク非依存 React、Vue、Svelte、またはネイティブプロジェクトのいずれでも簡単に統合または独立実行が可能。
  • プラグイン式アーキテクチャ 柔軟なプラグインシステム、公式拡張機能やカスタムプラグインをサポート、機能モジュールの自由な組み合わせ。
  • PNG / HTML エクスポート対応 マインドマップを画像やHTMLページとしてエクスポート、共有と埋め込みが簡単。
  • ノード要約 / ノード接続 ノード要約、接続線、タグなど多様なノードスタイルをサポート、様々なニーズに対応。
  • 元に戻す / やり直し対応 完全な操作履歴スタック、あらゆる変更を素早く元に戻すまたはやり直し可能、安心して操作。
  • 効率的なショートカットキー対応 豊富なキーボードショートカット、プロフェッショナルユーザーの操作効率を向上。
  • CSS変数によるスタイルカスタマイズ CSS変数でノードスタイルと全体テーマを簡単に制御、高度にカスタマイズされた美しいレイアウトを実現。

それでは、プロジェクトにMind Elixirを素早く統合する方法を簡単にご紹介しましょう!🤗

超簡単統合

依存関係のインストール:

Terminal window
npm i mind-elixir -S

Mind Elixirのインポート:

import MindElixir from "mind-elixir";
import "mind-elixir/style"; // 5.0 后的版本需要主动引入样式

もちろん、scriptタグで直接インポートすることも可能です:

<script type="module" src="https://cdn.jsdelivr.net/npm/mind-elixir/dist/MindElixir.js"></script>

初期化前に、マウント対象要素のスタイルを調整する必要があります。具体的には明確な幅と高さを設定する必要があり、特に高さに注意が必要です。CSSに苦労したことのあるフロントエンド開発者なら誰でも知っているように、高さ100%は扱いにくい設定です。以下では高さ500pxのdivを例に説明します。

<div id="map"></div>
<style>
#map {
height: 500px;
width: 100%;
}
</style>

続いて正式な初期化です。他の初期化オプションを考慮しない場合、マウント要素を渡すだけで完了です!

import MindElixir from "mind-elixir";
import "mind-elixir/style";
let options = {
el: "#map", // or HTMLDivElement
};
let mei = new MindElixir(options);
const data = MindElixir.new("new topic");
mei.init(data);

これで最も基本的な統合が完了しました!

TIP

在 Codepen 试玩:https://codepen.io/ssshooter/pen/vEOqWjE

イベントリスニング

プロジェクトでマインドマップを使用した後、最も一般的な要件はイベントリスニングです。様々なノード操作を監視し、ユーザーの操作に応答する必要があります。例えば、ユーザーが新しいノードを作成した場合、それを適時保存する必要があります。

Mind Elixirはbusを使用してイベントを配信します。この用語は「バス」という概念に由来し、すべてのイベントはこの「バス」によって配信されます。使用方法はブラウザのaddEventListenerと似ており、busにアクセスできれば、どこからでもイベントを監視できます。

最新版Mind Elixir 5.0では、以下のイベントが利用可能です:

type EventMap = {
operation: (info: Operation) => void;
selectNode: (nodeObj: NodeObj, e?: MouseEvent) => void;
selectNewNode: (nodeObj: NodeObj) => void;
selectNodes: (nodeObj: NodeObj[]) => void;
unselectNodes: (nodeObj: NodeObj[]) => void;
expandNode: (nodeObj: NodeObj) => void;
linkDiv: () => void;
scale: (scale: number) => void;
move: (data: { dx: number; dy: number }) => void;
updateArrowDelta: (arrow: Arrow) => void;
showContextMenu: (e: MouseEvent) => void;
};

ほとんどのノード操作イベントはoperationイベントにまとめられています。百聞は一見に如かず!プロジェクトに追加してノードを操作してみれば、すぐに理解できます:

mei.bus.addListener("operation", (operation) => {
console.log(operation);
});

時にはイベントリスニングだけでは不十分で、データがデータベースに挿入された後に表示させたい場合は、操作インターセプトを使用する必要があります。optionsbeforeオプションを追加します。これはオブジェクトで、キーはインターセプトしたい操作です。addChild操作をインターセプトしたい場合は、以下のように書きます:

let mei = new MindElixir({
// ...
before: {
async addChild(el, obj) {
try {
await saveToDatabase(obj);
return true;
} catch (error) {
console.error("Error adding child:", error);
return false;
}
},
},
});

このようにsaveToDatabase()が正常に実行された後にのみ子ノードが実際に追加され、実行に失敗した場合は挿入操作がキャンセルされます。

TIP

在 Codepen 试玩:https://codepen.io/ssshooter/pen/EajBbrM

マインドマップの再描画

Mind Elixirコアのデフォルト動作を使用してマインドマップを更新する以外に、ノードデータを直接更新してマインドマップを再描画することも可能です。

完全なノードデータ構造は以下の通りです:

export interface NodeObj {
topic: string;
id: Uid;
style?: {
fontSize?: string;
color?: string;
background?: string;
fontWeight?: string;
};
children?: NodeObj[];
tags?: string[];
icons?: string[];
hyperLink?: string;
expanded?: boolean;
direction?: Left | Right;
image?: {
url: string;
width: number;
height: number;
fit?: "fill" | "contain" | "cover";
};
branchColor?: string;
dangerouslySetInnerHTML?: string;
note?: string;
}

ノードデータを変更することで、ノードに画像、タグ、ハイパーリンクなどの要素を挿入できます。例えば、Mind ElixirインスタンスのnodeDataを読み取って現在のマインドマップデータを取得し、それを変更してからrefreshメソッドを呼び出してマインドマップを再描画できます。

const data = mind.nodeData;
console.log(data);
data.topic = data.topic + "new Data";
mind.refresh();

しかし、マインドマップ全体を全く新しいデータに更新したい場合はどうでしょうか?それも可能です!Mind Elixir形式に準拠したデータをrefreshメソッドに渡すことで、即座に全体を更新できます。

import data from "https://esm.sh/mind-elixir/dist/example.js";
mind.refresh(data);

TIP

在 Codepen 试玩:https://codepen.io/ssshooter/pen/vEOqpOX

再設計の自由

Mind Elixirはマインドマップを再設計する自由を提供します。

まず、themecssVarを使用してマインドマップ全体のスタイルを簡単に調整できます。コアには明暗2つのテーマMindElixir.DARK_THEMEMindElixir.THEMEが組み込まれており、カスタムテーマが必要な場合は、テーマ形式に従ってオブジェクトを作成してMind Elixirに渡すことができます。

完全なMind Elixirテーマと使用方法は以下の通りです:

const PROFESSIONAL_THEME = {
name: "Professional",
type: "light",
palette: ["#2c2c2c", "#404040", "#555555", "#6a6a6a", "#7f7f7f", "#949494", "#a9a9a9"],
cssVar: {
"--node-gap-x": "32px",
"--node-gap-y": "12px",
"--main-gap-x": "68px",
"--main-gap-y": "48px",
"--root-radius": "8px",
"--main-radius": "6px",
"--root-color": "#ffffff",
"--root-bgcolor": "#1a1a1a",
"--root-border-color": "#333333",
"--main-color": "#2c2c2c",
"--main-bgcolor": "#ffffff",
"--topic-padding": "4px",
"--color": "#4a4a4a",
"--bgcolor": "#fafafa",
"--selected": "#666666",
"--panel-color": "#2c2c2c",
"--panel-bgcolor": "#ffffff",
"--panel-border-color": "#e0e0e0",
},
};
let mind = new MindElixir({
el: "#map",
theme: PROFESSIONAL_THEME,
});

注意:data自体もthemeを含むことができ、optionsthemeを上書きします。これは各マインドマップが独立したテーマを持てるようにするためです。固定テーマが必要な場合は、初期化時にdatathemeundefinedに設定することを忘れないでください。

P.S. 初期化後にテーマを再度変更したい場合は、changeThemeメソッドを使用できます。

cssVarでよく使用されるmain-gapは、メインノード間の間隔を調整できます:

Mind Elixir main-gap

node-gapはノード内部の間隔を調整できます:

Mind Elixir node-gap

TIP

在 Codepen 试玩:https://codepen.io/ssshooter/pen/azOgVKX

CSS変数で調整できないその他のパラメータについても、CSSオーバーライドで直接微調整できます。

さらに深く掘り下げると、generateMainBranchgenerateSubBranchを使用して接続線のスタイルを調整できます。(例については下記のcodepenリンクをご覧ください)

適切なgenerateMainBranchgenerateSubBranchを作成した後、展開・折りたたみボタンの位置が正しくない場合は、CSSで微調整できます。デフォルトスタイルは以下の通りです:

// 主节点(根节点的下一级节点)的展开收缩按钮样式
me-main > me-wrapper > me-parent > me-epd {
top: 50%;
transform: translateY(-50%);
}
// 其他子节点的展开收缩按钮样式
me-epd {
top: 100%;
transform: translateY(-50%);
}
// 左侧的展开收缩按钮专用调整
.lhs {
& > me-wrapper > me-parent > me-epd {
left: -10px;
}
me-epd {
left: 5px;
}
}
// 右侧的展开收缩按钮专用调整
.rhs {
& > me-wrapper > me-parent > me-epd {
right: -10px;
}
me-epd {
right: 5px;
}
}

TIP

在 Codepen 试玩:https://codepen.io/ssshooter/pen/WNmZMmq

ノードスタイル

全体的なスタイル以外にも、ノードにカスタマイズ要件がある場合、ノード自体にstyleを設定できます:

//...
{
fontSize?: string
color?: string
background?: string
fontWeight?: string
}
// ...

ノードに非常に強いカスタマイズ要件があり、この程度のstyle設定では全く不十分だと感じる場合でも、問題ありません。それにも対応できます!

dangerouslySetInnerHTMLを使用してより高度なカスタマイズも可能です。例えば:

const data = {
nodeData: {
id: "me-root",
topic: "Mind Elixir",
tags: ["Mind Map Core"],
children: [
{
topic: "Customized Div",
id: "c00a2264f4532615",
children: [
{
topic: "",
id: "c00a2264f4532614",
dangerouslySetInnerHTML:
'<div><style>.title{font-size:50px}</style><div class="title">Title</div><div style="color: red; font-size: 20px;">Hello world</div></div>',
},
],
},
],
},
};

TIP

在 Codepen 试玩:https://codepen.io/ssshooter/pen/MYwMrjZ

画像エクスポート

modern-screenshotのおかげで、SVGを巧妙に利用してdivをそのまま画像に変換できます。基本的に、あまりにも極端なdangerouslySetInnerHTML(例:動画)を使用していなければ、正常に画像をエクスポートできます。@ssshooter/modern-screenshotにはpaddingオプションが追加されており、スクリーンショットの余白を調整できます。

import { domToPng } from "@ssshooter/modern-screenshot";
const download = async () => {
const dataUrl = await domToPng(mind.nodes, {
onCloneNode: (node) => {
const n = node as HTMLDivElement;
n.style.position = "";
n.style.top = "";
n.style.left = "";
n.style.bottom = "";
n.style.right = "";
},
padding: 300,
quality: 1,
});
const link = document.createElement("a");
link.download = "screenshot.png";
link.href = dataUrl;
link.click();
};

modern-screenshotまたは最近リリースされたsnapdomを直接使用することも可能です。スクリーンショットが不完全な場合(主に要約と接続線が不完全な場合)は、cssVar--map-paddingを調整できます。

import { snapdom } from "@zumer/snapdom";
const dl2 = async () => {
const result = await snapdom(mind.nodes);
await result.download({ format: "jpg", filename: "my-capture" });
};
Mind Elixir map-padding

それでも画像の一部しかキャプチャされない場合は、scaleが1でないことが原因の可能性があります。スクリーンショット前にscaleを1に設定し、完了後に元のサイズに戻すことを試してください。

TIP

在 Codepen 试玩:https://codepen.io/ssshooter/pen/NPqZXXB

サーバーサイドレンダリングフレームワークでの使用

Next.jsなどのサーバーサイドレンダリングフレームワークでMind Elixirを使用する際、window is not definedなどの問題によく遭遇します。これはMind ElixirがDOM操作に大きく依存しており、SSR環境では正常に動作しないためです。

この問題を解決するために、useEffectを使用してクライアントサイドレンダリング時にMind Elixirを読み込むことができます。以下は簡単な例です:

"use client";
import { useEffect } from "react";
import { mindMapExample } from "./mapExample";
export const MindMap = ({ className }: { className: string }) => {
useEffect(() => {
import("mind-elixir").then((MindElixir) => {
const theme = MindElixir.default.DARK_THEME;
theme.cssVar["--bgcolor"] = "rgba(0,0,0,0)";
const mei = new MindElixir.default({
el: "#map",
direction: 2,
theme,
});
mei.init({
nodeData: mindMapExample,
});
mei.toCenter();
window.addEventListener("resize", () => {
mei.toCenter();
});
});
}, []);
return (
<div id="wrapper" className={className}>
<div
id="map"
className="pointer-events-none h-[50vh] w-screen"
onScroll={(e) => e.preventDefault()}
></div>
</div>
);
};

その他のMind Elixirオプション

Mind Elixirには他にも多くの設定可能なオプションがあります:

interface Options {
// ...
direction?: number; // 节点排布方向,0 左 1 右 2 两侧
locale?: Locale; // 语言选择
contextMenu?: boolean | ContextMenuOption; // 是否启用右键菜单,可添加选项
toolBar?: boolean; // 是否启动内置工具栏
keypress?: boolean | KeypressOptions; // 是否启用快捷键,可添加自定义快捷键
mouseSelectionButton?: 0 | 2; // 拖拽按键,默认右键拖拽
before?: Before; // 上面提到的操作拦截
newTopicName?: string; // 新增节点的默认值
allowUndo?: boolean; // 是否启用撤消/重做
overflowHidden?: boolean; // 画面是否可以移动,显示思维导图卡片时可用
alignment?: Alignment; // 设为 nodes 时画面中心为思维导图中心,设为 root 时画面中心为根节点中心,默认 root
scaleSensitivity?: number; // 滚轮和菜单的放大缩小敏感度
draggable?: boolean; // 是否可以拖拽节点
editable?: boolean; // 是否可编辑
// ...
}

まとめ

本記事の紹介を通じて、Mind Elixirの基本的な使用から高度なカスタマイズまでの様々なテクニックを習得できたと思います。使用中に問題が発生したり、より良いアイデアや提案がある場合は、コメント欄で共有していただくか、GitHubでディスカッションに参加してPRを提出してください!一緒にMind Elixirをより完璧にしていきましょう!

评论组件加载中……