ガイドStefan VaskevichStefan Vaskevich

Kimodo.cpp: NVIDIA のテキスト to モーションを GPU なしでもローカル実行

NVIDIA Kimodo を C++ と GGML に移植。Vulkan でも普通の CPU でも動作し、2 GB 未満で済み、SOMA と G1 のモデルは商用利用が可能なライセンスです。Windows のセットアップ手順とリターゲットのメモ付き。

Unreal Engine 上の 4 体の異なるキャラクターリグが、Kimodo がテキストプロンプトから生成したモーションを再生している

この記事で使用したツール

「人が回転しながら回し蹴りをする」と入力すれば、使えるアニメーションが手に入ります。自分のマシン上で、Python 環境もネットワーク通信もなしにです。これが NVIDIA のモーション拡散モデル Kimodo で、誰かがこれを C++ と GGML に移植したため、Vulkan でも普通のプロセッサでも、2 GB 未満のメモリで動くようになりました。

私は丸一日かけて Windows にゼロから導入し、クリップを生成し、その結果を Mixamo のリグと Unreal Engine に流し込みました。このガイドはそこで学んだことのすべてです。もっとも時間を奪われ、どの README にも書かれていない 2 点、つまり実際に使ってよいモデルはどれかということと、なぜこの処理全体がグラフィックスカードではなくディスクに縛られるのか、も含みます。

ワークフロー全体を一行で
テキストプロンプト → Vulkan または CPU 上の kimodo.cpp(2 GB 未満、実演算は約 20 秒)→ GLB → 2 本のスクリプトで Unreal の mannequin へ、または名前マップで Mixamo リグへ → 完成したアニメーション。SOMA と G1 のチェックポイントは NVIDIA Open Model License なので、商用利用が可能です。

1. Kimodo とは何か、C++ 移植で何が変わったか

NVIDIA は 2026 年 3 月に Kimodo を公開しました。商用利用可能な光学式モーションキャプチャ 700 時間で学習された運動学的モーション拡散モデルで、テキストプロンプトと疎な運動学的制約から 3D の人体およびヒューマノイドロボットのモーションを生成します。骨格フォーマットは 3 種類あり、NVIDIA 独自の SOMA パラメトリックボディ、Unitree G1 ヒューマノイドロボット、そして SMPL-X です。

オリジナルの公開版は PyTorch プロジェクトです。クリップを一本生成するだけでも、まず CUDA スタック一式を立ち上げる必要がありました。機械学習ではなく 3D 制作向けに組んだマシンを使っている人にとって、これは現実的な障壁です。

kimodo.cpp はネイティブな C++ と GGML への移植版です。GGUF の重みを読み込み、Vulkan またはプロセッサ上で動作し、小さなローカル Web インターフェースが同梱されています。生成時に Python は不要、CUDA も不要、ネットワークも不要。話はそれだけですが、聞こえる以上に大きな意味があります。Kimodo が「機械学習の人が動かすもの」から「自分のワークステーションで開くもの」に変わったからです。

kimodo.cpp のローカル Web インターフェース。モーションモデルの選択、プロンプト入力、3D スケルトンのプレビューが表示されている
同梱の Web インターフェース。モデル選択、プロンプト、フレーム数、リアルタイムのスケルトンプレビュー、そして Download GLB ボタン。すべて localhost から配信されます。

2. ライセンス事情、8 月 26 日に動いたばかり

ここは多くの記事が間違えている部分です。つい最近動いたうえに、二方向へ同時に動いたからです。

移植版は当初、変換済みの SMPL-X の重みを同梱していました。これは取り下げられました。作者が、そのチェックポイントの上流にある NVIDIA のライセンスが派生モデルの配布を明確に禁じていることに気づき、GGUF とマニフェスト、チェックサムを削除したためです。差し替えられたモデルカードは、謎の 404 を残す代わりに理由をはっきり書いています。この点は予想以上に好感が持てました。

ほぼ同じタイミングで、まったく別のライセンスのチェックポイントが 4 つ公開され、移植版もそれらへの対応を取り込みました。

モデル骨格ライセンス商用利用
SOMA RP v1.1SOMA、30 ジョイントNVIDIA Open Model
SOMA SEED v1.1SOMA、30 ジョイントNVIDIA Open Model
G1 RP v1Unitree G1、34 ジョイントNVIDIA Open Model
G1 SEED v1Unitree G1、34 ジョイントNVIDIA Open Model
SMPL-X RP v1SMPL-X、22 ジョイントNVIDIA Internal Scientific R&D研究用途のみ
成果物を世に出すつもりなら SOMA か G1 を使うこと
SMPL-X のチェックポイントは社内の非商用研究に限定され、再配布もできません。Hugging Face で自分で NVIDIA のライセンスに同意し、リポジトリ内のコンバーターでローカル変換すれば使うこと自体は可能ですが、それで商用の権利が得られるわけではありません。製品に組み込めるのは SOMA と G1 のチェックポイントです。

インターフェースはこの点に正直で、週末プロジェクトの移植版としては予想外でした。モデルを選ぶと、何かを生成する前にどのライセンス下にいるかを教えてくれます。

kimodo.cpp のモデル選択画面。SOMA 骨格の説明と商用利用のライセンス表記が見えている
モデル選択画面には骨格、上流のチェックポイント、ライセンス条件が表示されます。非商用モデルではこの行の代わりに警告が出ます。

3. 実際に必要なハードウェア

要求は低めです。しかもその「低さ」は、表を読み流すだけでなく理由を理解しておく価値があります。

リソース最小余裕のある構成
空きディスク25 GB35 GB、NVMe ドライブ上
システムメモリ4 GB32 GB、第 5 節も参照
VRAM(GPU 経路)1.2 GB2 GB
CPU2 コア6 コア

GPU でもプロセッサでも、どの構成でもピークメモリは 2 GB 未満に収まります。調整つまみは KIMODO_TEXT_LAYER_CHUNK で、渡す数字は ギガバイトではなくレイヤー数です。chunk 2 で VRAM 1.2 GB、chunk 4 で 1.8 GB、既定の chunk 8 で 3.5 GB。大きくしても速くはなりません。chunk の大小にかかわらず、エンコーダーは 1 回の実行につき一度しか読まれないからです。

およそ 1.3 GB が絶対的な下限です。埋め込みテーブルは 1.05 GB の単一アロケーションで、どの chunk サイズでも分割できないため、それを下回るとプログラムはそもそも起動しません。

グラフィックスカードの効果は思ったより小さい
作者のベンチでは、RTX 5090 Laptop が 3 秒のクリップを 25.9 秒、16 コアのプロセッサが 33.7 秒、内蔵の Intel Arc グラフィックスが 32.5 秒で処理しました。フラッグシップカードと CPU の差は 1.3 倍にすぎません。処理を支配しているのは 15.2 GB のテキストエンコーダーの読み込みであって、演算ではありません。カードが効いてくるのはデノイズのステップ数が多いときで、クリップの長さではありません。

4. Windows へのインストール

プロジェクトのドキュメントは Linux 向けです。Windows でも動きますし、CMake ファイルには明示的な MSVC 分岐もありますが、1 時間を失いかねない箇所が 4 つあります。以下は要約で、完全な手順はこの節の最後からダウンロードできます。

1

ツールチェーンを入れて、新しいターミナルを開く

Git、C++ ワークロード付きの Visual Studio Build Tools、Vulkan SDK、そして Web インターフェースを使いたいなら Go。

winget install Git.Git
winget install Microsoft.VisualStudio.2022.BuildTools --override "--quiet --wait --norestart --add Microsoft.VisualStudio.Workload.VCTools --add Microsoft.VisualStudio.Component.VC.CMake.Project --includeRecommended"
winget install KhronosGroup.VulkanSDK
winget install GoLang.Go

VC.CMake.Project コンポーネントは省略できません。これがないとコンパイラは入るのに CMake も Ninja も入らず、そのあと出るエラーメッセージにはその事実がどこにも書かれません。そして必ずすべてのターミナルを閉じてください。Vulkan のインストーラーが設定する VULKAN_SDK はマシン全体のもので、すでに開いているターミナルからは永久に見えません。

2

サブモジュールごとクローンする

git clone --recurse-submodules https://github.com/localai-org/kimodo.cpp
cd kimodo.cpp

GGML はサブモジュールです。普通のクローンでは空のままになりますし、同じ理由でリポジトリを ZIP でダウンロードしてもまったく動きません。

3

ソースを 2 か所直してからビルドする

src/denoiser.cppsrc/generate.cppsrc/llm_tokenizer.cpp #include <stdexcept> を追加し、src/llm_text_encoder.cpp path.c_str() path.string().c_str() に変えます。どちらもすべてのプラットフォームで正しい修正で、単に上流にマージされていないだけです。そのうえで vcvars64.bat を実行済みのターミナルから:

cmake -S . -B build-win -G Ninja -DCMAKE_BUILD_TYPE=Release -DKIMODO_ENABLE_VULKAN=ON -DKIMODO_BUILD_TESTS=OFF
cmake --build build-win
4

重みをダウンロードする

テキストエンコーダーは全モデル共通なので、15.2 GB のダウンロードは一度きりです。モーションモデルはその上に 1 つあたり約 1.13 GB。

pip install huggingface_hub
hf download LocalAI-io/Llama-3-Kimodo-GGML --local-dir . --include "generated/llm2vec-text-bundle/*"
hf download LocalAI-io/Kimodo-SOMA-RP-v1.1-GGML --local-dir . --include "models/*"

オープンライセンスの 4 モデルを全部足しても約 4.5 GB で、17 GB の 4 倍にはなりません。エンコーダーを共有しているからです。

1 時間を溶かした、音もなく起きる失敗
SMPL-X のときのように Hugging Face のリポジトリが上流で空にされていると、--include 付きの hf download は何にもマッチせず、成功として終了します。エラーもファイルもなく、終了コードはゼロ。私のセットアップスクリプトは正常終了を報告し、生成が失敗して初めてモデルが無いことに気づきました。.gguf が実際に models\ に落ちているかを必ず確認してください。
Windows セットアップ完全ガイドをダウンロード

すべてのコマンド、2 か所のソース修正とそれが防ぐエラーの実際の文面、環境変数の一覧、そして症状から本当の原因を引ける対処表。コンパイラが一切入っていないマシンで実際にやり切ったあとに書いたものです。

kimodo-windows-setup.md

5. 最初のクリップを生成する

コマンドラインの引数は位置指定で、GGML の DLL は実行ファイルの隣ではなくビルドツリーの bin フォルダにあります。ここを外すとプログラムは何も出力せず即座に終了し、見た目はクラッシュそのものですが、実際は Windows が DLL を読み込めていないだけです。

Command Prompt
set PATH=%CD%\build-win\bin;%PATH%
build-win\kmd-generate.exe models\kimodo-soma-rp-v1.1-f32.gguf generated\llm2vec-text-bundle prompt.txt 90 20 41 out

これは 30 fps で 90 フレーム、つまり 3 秒、デノイズ 20 ステップ、シード 41 です。Web インターフェースを使う場合は:

go run ./demo -addr 127.0.0.1:8094 -generator build-win/kmd-generate.exe

出来上がりの質を決める数字は 2 つです。フレーム数は約 300、つまり 10 秒までなら破綻しません。400 では揺れが出はじめ、600 ではおよそ 300 フレームを過ぎたあたりでノイズに崩れます。直感に反しますが、短いクリップのほうが動きは鋭くなります。同じプロンプトでも 120 フレームのほうが 300 フレームより切れがあり運動的に見えるのは、モデルが余った時間を埋めようとして、同じ動作をより強くやるわけではないからです。

ステップ数はデノイズの回数で、20 あれば下書きにも最終版にも足ります。コストは線形なので、100 ステップは 5 倍かかるのに見た目の差はありません。同梱のインターフェースは今のところ demo/index.html に 100 を直書きしているので、本格的に使う前に 20 へ変えておく価値があります。

最初の実行に数分かかる理由、それはモデルのせいではない
生成のたびに 15.2 GB のエンコーダーが読み込まれます。ファイルキャッシュに収まらなければ、この読み込みは毎回繰り返されます。

私の環境、Ryzen 7 7800X3D にメモリ 31 GB、重みは SATA SSD 上で、3 秒のクリップに 399 秒かかりました。うち約 380 秒がディスク読み込みCPU はわずか 10 秒。RTX 4070 SUPER は最後まで遊んでいました。ドライブの実効速度は 40 MB/s で、15.2 GB を 40 MB/s で割るとちょうど 380 秒。計算がぴったり合います。

効果の大きい順に対策は 2 つ。重みを NVMe ドライブに置くこと、そして生成前にメモリを空けることです。エンコーダーが常駐するにはおよそ 16 GB の空きファイルキャッシュが必要で、32 GB のマシンでもブラウザとチャットクライアントを開いていると空きは 7 GB 程度しかなく、16 GB のマシンと同じ挙動になります。

6. モーションを実際のリグに載せる

生成は簡単なほうの半分です。この移植版が研究者ではなく 3D アーティストにとって面白いのは、出力がほとんど格闘せずに普通のキャラクターリグに載るからです。

Web インターフェースには Download GLB ボタンがあります。デモサーバーが自前で glTF を組み立てるので、Blender で開けばボーン階層とキーフレームがすでに入った状態のファイルが手に入ります。たいていの用途ではこれで話は終わりで、以下のフォーマットの細かい話はすべて飛ばせます。

5 体の異なる Mixamo キャラクターが、それぞれ Kimodo で生成された別々のモーションを再生している
5 つの Mixamo リグ、5 つのプロンプト、1 つのモデル。ここに手付けのアニメーションは一つもありません。

ここで SOMA が思わぬ幸運になります。SMPL-X の命名規則をまったく使っていないのです。30 のジョイントは HipsSpine1LeftShoulderLeftForeArm といった名前で、これはほぼ Mixamo の流儀そのものです。ほとんどのボーンは mixamorig: を前に付けるだけで対応が取れ、それ以外は何もいりません。

脚は罠で、名前が衝突している
SOMA の LeftLeg太ももです。Mixamo の mixamorig:LeftLegすねです。正しい対応は SOMA の LeftLeg mixamorig:LeftUpLeg へ、SOMA の LeftShin mixamorig:LeftLeg へ、です。前置詞を足すだけのマッピングだと、膝が股関節から曲がるキャラクターができあがります。リターゲットがおかしいときに最初に見るべきはここです。

Unreal については手作業をやめました。下に、クリップのフォルダを渡すと mannequin 上に焼き込み済みの Anim Sequence を残してくれる 2 本組のスクリプトがあります。ジョイント数で骨格が確定するので、3 種類とも設定なしで通ります。

1

ステップ 1: クリップからファイルへ、自分のデスクトップで

Python 3.8 以降だけで動きます。Blender も追加パッケージも不要です。Kimodo が書き出したフォルダを指定すれば .glb が得られます。

python kimodo_to_glb.py path/to/clip
python kimodo_to_glb.py clips/* --outdir glb

書き出す前に自分で検証します。作ったばかりのファイルからポーズを再構築して入力と突き合わせるので、軸の取り違えやクォータニオンの成分順の誤りは Unreal に持ち込む前にここで捕まります。表示される数値は 1e-08 前後になるはずです。

2

ステップ 2: ファイルからキャラクターへ、Unreal の中で

Output Log を開き、下部の入力ボックスを Cmd から Python に切り替えて貼り付けます:

py "C:/path/to/unreal_retarget.py" "C:/path/to/walk_150.glb"

これでファイルを取り込み、IK Rig と IK Retargeter を組み立て、下記 2 つの補正を当て、ベイクして /Game/Kimodo/Retargeted/ に Anim Sequence を残します。mannequin をレベルに置き、Animation Mode を Use Animation Asset にしてそのシーケンスを選ぶだけです。複数のパスを渡せばまとめて処理でき、最後に Skeletal Mesh のパスを足せば別のキャラクターを対象にできます。

目視に頼らず、クリップごとに結果を報告してくれます:

kick_120: SMPL-X, 22 joints
    9 chains mapped, 19 left at rest (Root, LeftThumb, ...)
    reach 102 cm to 95 cm, arms corrected by up to 48 deg
    arms match 0.998 (worst lowerarm_r), pelvis 93 cm, lowest toe -1 cm,
    travelled 123 cm over 4.0 s

arms match は、キャラクターの腕がソースの腕と同じ方向を向いている度合いを、クリップ全体でサンプリングした値です。0.95 を超えていれば良好。lowest toe はゼロ付近であるべきで、大きく上振れすればキャラクターは浮き、下振れすれば沈みます。

2 つの補正と、手組みのリターゲッターがこれを飛ばすと壊れる理由
ソースは半分地面に埋まっている。Kimodo は腰を原点に置き脚をその下にぶら下げるため、リグは床にめり込んだ状態から始まり、リターゲッターに垂直方向の余裕が残りません。スクリプトは静止姿勢の脚の長さぶんだけ持ち上げます。静止姿勢であって最初のアニメーションフレームではない点に注意してください。そうしないと、しゃがみから始まるクリップが直立でベイクされてしまいます。

両者の静止姿勢が食い違っている。mannequin は A ポーズで静止しますが Kimodo は違います。放置するとリターゲッターはその差をモーションとして読み取り、クリップ全体で腕の位置がずれます。スクリプトは両方を計測し、腕のセグメントごとに親から子の順で打ち消します。だいたい 45 から 55 度に相当します。
注意すべきは G1
3 種類とも mannequin にリターゲットできますが、Unitree G1 はロボットです。鎖骨も首も頭もないため、キャラクター側のその 4 チェーンは静止姿勢のまま残ります。さらに mannequin では 1 つの股関節を 3 つの単軸ジョイントに分割しているので、股関節の回転は一部失われます。腕と脚は問題なく移ります。SOMA と SMPL-X は完全にマッピングされます。
Unreal Engine 上の大型の非人型クリーチャーが Kimodo 生成のモーションを再生し、頭上に元のプロンプトが浮かんでいる
リターゲットの対象は人間に限りません。このクリーチャーも、上の Mixamo キャラクターとまったく同じ 30 ジョイントの出力で動いています。
Unreal Engine 上に並んだ多数の異なるキャラクターリグが、それぞれ個別に生成されたアニメーションを再生している
バッチ実行の様子。キャラクターごとに固有のプロンプトがあり、その文言が頭上に描画されているので、テキストとモーションの対応を読み取れます。
SMPL-X 用のリターゲットコードを持っているなら、それは壊れます
生の出力は float32 のファイル 2 つです。local_rotations_xyzw.f32 [FRAMES, JOINTS, 4]root_positions.f32 [FRAMES, 3]。公開されているフォーマット表には 22 ジョイントとありますが、それは SMPL-X 専用です。SOMA は 30、G1 は 34 です。

90 フレームの SOMA クリップはちょうど 90 x 30 x 4 x 4 = 43,200 バイトになります。これを 22 ジョイントのストライドで読んでも例外も警告も出ず、リグが痙攣しているようなアニメーションが返ってくるだけです。ジョイント数は決め打ちせず、ファイルサイズから導き出してください。
ツールとフォーマットのメモをダウンロード

2 本のスクリプト、まず何も生成せずに Unreal 側だけ試せるサンプルクリップ、そしてメモ。親インデックス付きの 30 ジョイント SOMA 階層、きれいに対応しないボーンを含む完全な Mixamo 名称マップ、クォータニオン順序の落とし穴、そして Blender での手順です。

3D AI ツールの実際の順位を見る
Kimodo が生成するのはモーションであってメッシュではありません。パイプラインのモデル側については、当サイトの ブラインド Arena が各ジェネレーターを匿名の対戦で競わせ、宣伝ではなく投票で順位を付けています。また リーダーボード では、メッシュ品質、ローポリ、テクスチャリングにわたるコミュニティ評価を集計しています。

まとめ

工程コスト補足
ツールチェーン導入約 30 分、約 3 GBBuild Tools、Vulkan SDK、Go
ビルド約 2 分先に 1 行ずつのソース修正を 2 か所
重み15.2 GB + 各 1.13 GBエンコーダーは全モデル共通
生成(キャッシュ済み)実演算 約 20 秒加えてディスク読み込み、第 5 節参照
Mixamo へのリターゲット数分名称マップと脚の修正

要点は「テキストからモーションを作るモデルが存在する」ことではありません。このモデルが、すでに手元にあるハードウェアで動き、成果物を世に出せるライセンスを持ち、午後いっぱいで Mixamo リグに載るということです。いちばん意外だったのは、ボトルネックがグラフィックスカードではなくディスク読み込みだったこと。つまり本気で取り組む人にとって、いちばん安上がりなアップグレードは高性能な GPU ではなく NVMe ドライブだということです。

ここに至るまでのパイプラインの残りについては、次のガイドがあります。 AI 3D キャラクターパイプラインの全体像非人型キャラクターの AI リギング、そして HY-Motion、知っておく価値のあるもう一つのテキスト to アニメーションモデル

よくある質問

Kimodo はグラフィックスカードなしで動きますか?

動きます。KIMODO_BACKEND=cpu を設定すればプロセッサ上で実行されます。処理全体は 15.2 GB のテキストエンコーダーの読み込みが支配的で、演算量ではありません。そのため作者のベンチでは、3 秒のクリップで RTX 5090 が 16 コアのプロセッサより約 1.3 倍速いだけでした。ドキュメント上の最小構成は 2 コアです。

Kimodo.cpp にはどれくらいの VRAM が必要ですか?

どの構成でもピークメモリは 2 GB 未満に収まります。調整は KIMODO_TEXT_LAYER_CHUNK で行います。chunk 2 で 1.2 GB、2 GB のカードでも安全です。chunk 4 で 1.8 GB、既定の chunk 8 で 3.5 GB です。

Kimodo で生成したアニメーションは商用利用できますか?

使用したチェックポイントによります。SOMA と G1 のモデルは NVIDIA Open Model License で公開されており、商用利用が許可されています。SMPL-X のチェックポイントは NVIDIA Internal Scientific Research and Development Model License で、社内の非商用研究に限定され、再配布は禁止されています。成果物を公開する前に、どのモデルで生成したか確認してください。

最初の生成がとても遅いのはなぜですか?

実行のたびに 15.2 GB のテキストエンコーダーをディスクから読み込みます。ファイルキャッシュに収まらない場合、この読み込みが毎回繰り返されます。Ryzen 7 7800X3D で重みを SATA SSD に置いた環境では、3 秒のクリップに 399 秒かかり、そのうち約 380 秒がディスク読み込み、CPU 時間はわずか 10 秒でした。重みを NVMe ドライブに置き、生成前にメモリを空けてください。

SOMA に切り替えたらリターゲットのスクリプトが壊れたのはなぜですか?

ジョイント数が変わったからです。SMPL-X は 22、SOMA は 30、G1 は 34 で、生の出力フォーマット自体はどれなのかを教えてくれません。SOMA のファイルを 22 ジョイントのストライドで読むと、エラーも出ないまま静かに壊れます。ジョイント数は決め打ちせず、ファイルサイズから導き出してください。

これらのツールを自分で比較してみませんか?3D AIアリーナをご覧ください。

Kimodo.cpp: NVIDIA のテキスト to モーションを GPU なしでもローカル実行 | Top 3D AI