GPUI Community Edition (gpui-ce)

#rust #gui

GPUIのコミュニティフォーク。2025年12月にZedのソースからフォークされ、cargo add gpui-ceだけで使えるよう独立配布されている。ライセンスApache-2.0、GitHub Starsは約1,000(2026年9月時点)。READMEでは「今はほぼAPI互換だが、これから変えていく」と明言している。

公式gpuiがcrates.ioで0.2.2(2025-10-22)から止まっていることへの対応として選択肢に挙がるが、単なるスナップショット再配布(gpui-preやgpui-unofficial)とは違い、upstreamに入っていない機能を独自に足しているのがこのフォークの性格。

なぜフォークしたのか

READMEのFAQに目的が明記されている。

What is the long-term goal of GPUI-CE? To be the premiere Rust GUI library. We were born out of Zed’s hard work, and we will always pull their fixes and hard work, they remain a huge inspiration. And yet, our ambitions are larger than supporting the use-cases of two applications. (…) Our roots are in the web, and we want to take on the current application monster that is Electron, head to head, but with order-of-magnitude performance improvements and platform integrations.

「Zedを壊さない・Zedを支えるという制約から外れて、GPUIを汎用GUIフレームワークとして先に進める」ための場、という位置づけ。GPUI自体がZedとテキスト編集を念頭に作られており、Zed Industriesがコミュニティ専用の作業に工数を割くのを正当化しにくい、という事情の裏返しでもある。

他のフォークとの関係についてもFAQで触れていて、WGPUIなどは「それぞれが使われているプロジェクトの利害に沿って分岐していて、多様だが断片化したエコシステムになっている」とし、gpui-ceは安定性を重視しつつ他フォークの良いアイデアを継続的に取り込む、としている。

リポジトリの形からして違う

  • ワークスペースは21クレートで、中身はGPUIとその周辺だけ。Zedのエディタ関連クレートは丸ごと落としている(初期のcleanup/remove-non-apache-cratesでApache-2.0でないものも除去)。
  • ルートのCargo.tomlにgitソース依存が0件。upstream Zedはalacritty_terminal・tree-sitter・lsp-typesなどgit依存を多数持っており、これがそのままだとcrates.ioに出せない。gpui-ceは「crates.ioだけで解決できる」状態を維持することを公開の前提にしている。
  • gpui_elementsという独立クレートがある(後述のテキスト入力要素の置き場)。
  • crates.ioでのgpui-ceは0.2.2(2026-08-28)。0.3.2/0.3.3(2025-12-27)はyank済みなのでcargo add gpui-ceは0.2.2を拾う。docs/releasing.mdによると、main のCIが通るたびに1.0.0-alpha.Nという開発スナップショットをcrates.ioに出す方針(prereleaseなので通常の解決からは外れ、明示的にcargo add gpui-ce@1.0.0-alpha.3する必要がある)。2026年9月初旬時点ではまだalphaは公開されていない。

独自機能

以下は2026年9月初旬時点でZed本流(zed-industries/zed)のツリーに見当たらず、gpui-ce側にだけあるもの。

スタイルのトランジション

CSSのtransition相当。upstreamにはアニメーション(Animation)はあるがスタイル変化の補間APIは無い。

div()
    .id(self.id)
    .bg(base_color)
    .transitions(|transitions| {
        transitions.bg(Duration::from_millis(200).with_easing(ease_in_out))
    })
    .hover(|refinement| refinement.bg(hover_color))
    .active(|refinement| refinement.bg(active_color))

自動サイズ(auto)に対するトランジションのスナップ処理まで入っている(style_transitions.rs)。

filter / backdrop-filter(ぼかし)

StyledにCSS相当のフィルタAPIがある。

  • .blur(radius) — 要素とその子をグループとしてぼかす。CSSのfilter: blur()。サブツリーをオフスクリーンに分離してから合成する
  • .backdrop_blur(radius) — 要素の背後をぼかす。CSSのbackdrop-filter: blur()。すりガラス。半透明の.bg()と組み合わせて使う
  • .filter(...) / .backdrop_filter(...) — チェーン全体を置き換える

Filter enumは現状Blur(Pixels)のみ。Filter::is_identity()が真になるフィルタはレンダラに届く前に落とされ、全部が恒等ならオフスクリーン分離自体を省く、という作りになっている。

wgpuのテクスチャをGPUI要素として貼れる

upstreamのSurfaceSourceはmacOSのCVPixelBuffer(CoreVideoの映像バッファ)専用。gpui-ceはここに「型消去したGPUテクスチャハンドル」のvariantを足していて、Linux/FreeBSDと、Windows(wgpu-surfaces feature)で自前のwgpu描画をGPUIのレイアウトに載せられる。

関連して、

  • gpui_windowsのwgpu featureでWindowsのwgpuレンダラが使える
  • Window::gpu_device_lost()でデバイスロスト状態を問い合わせられる(upstreamはWindowsプラットフォーム内部にしか無い)

3Dビューやカスタムシェーダの描画を埋め込みたい場合、これがupstreamとの一番大きな機能差になる。

テキスト入力要素(gpui_ce_elements)

gpui_ce_elements::editable_text::{text_input, text_area}。HTMLの<input>/<textarea>に相当する要素で、素のGPUIには存在しない(Zedは自前のeditorクレート、GPUI Kitは自前のInputコンポーネントで賄っている)。

use gpui_ce_elements::editable_text::text_input;

text_input("my_input")
    .placeholder("empty text")
    .w_5()
    .min_h_auto()
    .whitespace_nowrap()

ドキュメンテーションコメントによれば、文字/単語/行/文書単位のキーボード移動、ダブル・トリプルクリックとドラッグでの選択、IME入力(日本語・中国語・韓国語)、カット/コピー/ペースト、点滅キャレット、フィールド内でのundo/redoまで含む。ストレージは既定でStringだが、大きな文書向けにUnicodeTextStorageを自前実装して差し替えられる。フォーカスハンドルを要素が内部に持つ点だけ他の要素と違う。

macOSのactivation policy

pub enum MacActivationPolicy {
    Regular,    // Dockに出る通常のアプリ
    Accessory,  // Dockにもメニューバーにも出ないが、ウィンドウのクリック等で有効化できる
    Prohibited, // Dockに出ず、ウィンドウ生成も有効化もできない
}

Platform::set_mac_activation_policy()。upstreamには無い。Dockアイコンを出さない常駐型ツールを作るのに要る。

その他のプラットフォームAPI

API 内容
supports_haptic_feedback() / 触覚フィードバック再生 macOSのハプティクス
set_keyring_label() OSキーリングに出るラベルの指定
Waylandのキネティックスクロール 慣性スクロール
Waylandのウィンドウアイコン アイコン設定
win32のstart_window_move タイトルバー相当領域からのウィンドウ移動

テキストスタイルの追加

Styled::letter_spacing()とStyled::text_transform()。どちらもupstreamのstyled.rsには無い。

色の型がpaletteクレートに置き換わっている

一番大きな非互換。GPUI独自実装のRgba/Hslaを捨て、paletteクレートの型をそのまま再エクスポートしている。

use palette::{IntoColor, OklabHue, Oklcha, RgbHue};
pub use palette::{Hsla, rgb::Rgba};

グラデーションの既定の補間色空間もoklabになった。「ほぼAPI互換」と言いつつ、色を構造体リテラルで組み立てているコードは書き換えが必要になる。実際、後述のコンポーネントライブラリのフォークではこの追随作業が commit の大半を占めている。

コンポーネントライブラリも別系統でフォークしている

2026年8月末、gpui-ceはGPUI Kit(旧longbridge/gpui-component)を取り込み、gpui-ce/gpui-componentという別リポジトリのフォークとして持ち、crates.ioにgpui_ce_components系として公開した。

クレート 対応する本家
gpui_ce_components gpui-component
gpui_ce_components_base gpui-base
gpui_ce_components_shell gpui-shell
gpui_ce_components_webview crates/webview(gpui-wry)
gpui_ce_components_assets / _fps / _macros 同名の補助クレート

つまり「GPUI Kitのコンポーネントをgpui-ceの上で使う」という道は一応開いた。ただしダウンロード数は各数十件で、本家(gpui-componentはrecentだけで4.5万)とは実績も追随の速さも桁が違う。

なぜコンポーネント側までフォークが要ったか

機械的な理由は、GPUIの再配布元がCargo.tomlにハードコードされていること。

gpui = { package = "gpui-pre", version = "0.3.1" }   # 本家 longbridge/gpui-kit
gpui = { package = "gpui-ce", version = "0.2.2" }    # gpui-ce/gpui-component

Rustではパッケージが違えば同じstructでも別の型なので、本家のコンポーネントはgpui-ceの上で1行も使えない。コンポーネントが欲しければフォークするしかない。

上流で解決しようとした形跡はある。Discussion #1856「Feature flag to use gpui-ce」で、gpui-componentの利用者がコンパイル時にgpuiとgpui-ceをfeature flagで選べるようにしてはどうか、という提案が出た。メンテナ(huacnlee)はIssue #2234(gpui-unofficialを使う提案)へ誘導し、そちらは Closed as not planned。結局longbridgeはどちらにも乗らず自前のgpui-preを作った。上流でスイッチャブルにする道が閉じたのでフォークした、という流れに見える(フォーク側に明文の説明は見当たらないので、ここは経緯からの推測)。

フォークの中身もそれを裏付ける。upstreamの0e2fb7a(2026-08-29)から分岐し、フォーク独自のコミットは13個。内訳はクレート名のリネーム(Package GPUI CE components)と色APIのpalette化への追随(Adapt base palette colors、Adapt UI palette APIsなど)、あとはCI修正。136ファイルの変更のうち大半がCargo.lockとcrates/ui/src/theme/color.rsと各Cargo.tomlで、機能追加は1つも無い。独自路線を歩むためのフォークではなく、純粋な互換ポート。

追随体制も弱い。分岐点はGPUI Kitへの改名前(crates/uiのままの構成)で、本家の更新をそのまま取り込めるわけでもない。

誤解しやすい点

  • システムトレイ/ステータスバー常駐はgpui-ceにも無い。 NSStatusBar・Shell_NotifyIcon・StatusNotifierItemのいずれの実装も、upstream・gpui-ceどちらのツリーにも見当たらない(2026年9月初旬時点)。「Zed本体に要らない機能はgpui-ceへ」という案内から、トレイ対応がgpui-ceにあると思われがちだが、そこは埋まっていない。この誤解の出所はおそらく前述のDiscussion #1856で、そこでは「Zedのスコープ外として弾かれる機能」の例としてカスタムシェーダ・トレイ対応・Waylandのタッチイベント変換が挙げられている。あくまで要望として挙がっただけで、実装されたわけではない。同じくメニュー周りも、macOS以外でOSのメニューバーを出す手段は無い(GPUI Kitでのクロスプラットフォームなメニュー)。
  • Waylandのinput_region・exclusive_zone・layer shellはupstreamにも入っている。gpui-ce側のPRとして議論されたものの一部は本流にも取り込まれている。
  • upstreamもspring.rsやelements/surface.rsは持っている。差分は「surfaceの入力元にGPUテクスチャがあるか」といった中身の側にある。

選ぶかどうか

トランジション・ぼかし・テキスト入力・wgpu合成のどれかが要るなら、これらはupstreamに無いのでgpui-ceが実質唯一の選択肢になる。逆に、コンポーネントが揃った状態でデスクトップアプリを早く作りたいだけならGPUI Kitの方が実績もコンポーネント数も上。両者は参照するGPUIの再配布元が違うため型として混ざらないので、最初にどちらかを選ぶ必要がある(詳細はGPUI Kitの「系統は混ぜられない」節)。

出典

作成日時: 2026-09-05 15:09 / 更新日時: 2026-09-06 01:33