gpui-components
Compare original and translation side by side
🇺🇸
Original
English🇨🇳
Translation
ChineseGPUI Components Skill
GPUI组件开发技能
Generates production-ready Rust code for GPUI desktop UI components following patterns from Zed editor and gpui-component library.
生成遵循Zed编辑器和gpui-component库模式的可用于生产环境的GPUI桌面UI组件Rust代码。
When to Use This Skill
何时使用该技能
- Building desktop UI applications with GPUI framework
- Creating custom components using or
RenderOncetraitsRender - Implementing themed components with
ActiveTheme - Building autocomplete/completion menus
- Creating command palettes and popup menus
- Working with crate
gpui-component
- 使用GPUI框架构建桌面UI应用
- 使用或
RenderOncetrait创建自定义组件Render - 基于实现主题化组件
ActiveTheme - 构建自动补全菜单
- 创建命令面板和弹出菜单
- 使用crate
gpui-component
Core GPUI Concepts
GPUI核心概念
Application Setup
应用程序设置
rust
use gpui::{Application, Window, Context, div, px, rgb};
use gpui_component::{init, Root, Theme};
fn main() {
Application::new().run(|cx| {
// Initialize gpui-component
gpui_component::init(cx);
cx.open_window(
WindowOptions::default(),
|window, cx| Root::new(MyApp::new(cx), window, cx)
);
});
}rust
use gpui::{Application, Window, Context, div, px, rgb};
use gpui_component::{init, Root, Theme};
fn main() {
Application::new().run(|cx| {
// Initialize gpui-component
gpui_component::init(cx);
cx.open_window(
WindowOptions::default(),
|window, cx| Root::new(MyApp::new(cx), window, cx)
);
});
}Component Patterns
组件模式
RenderOnce (Stateless)
RenderOnce(无状态)
rust
use gpui::{IntoElement, RenderOnce, Styled, div};
#[derive(IntoElement)]
pub struct MyButton {
label: SharedString,
variant: ButtonVariant,
}
impl RenderOnce for MyButton {
fn render(self, window: &mut Window, cx: &mut App) -> impl IntoElement {
div()
.px_3()
.py_2()
.bg(cx.theme().primary)
.text_color(cx.theme().primary_foreground)
.rounded_md()
.child(self.label)
}
}rust
use gpui::{IntoElement, RenderOnce, Styled, div};
#[derive(IntoElement)]
pub struct MyButton {
label: SharedString,
variant: ButtonVariant,
}
impl RenderOnce for MyButton {
fn render(self, window: &mut Window, cx: &mut App) -> impl IntoElement {
div()
.px_3()
.py_2()
.bg(cx.theme().primary)
.text_color(cx.theme().primary_foreground)
.rounded_md()
.child(self.label)
}
}Render with Entity (Stateful)
基于Entity的Render(有状态)
rust
use gpui::{Entity, Render, Context};
pub struct Counter {
count: i32,
}
impl Render for Counter {
fn render(&mut self, window: &mut Window, cx: &mut Context<Self>) -> impl IntoElement {
div()
.flex()
.gap_2()
.child(Button::new("dec").on_click(cx.listener(|this, _, _, cx| {
this.count -= 1;
cx.notify();
})))
.child(format!("Count: {}", self.count))
.child(Button::new("inc").on_click(cx.listener(|this, _, _, cx| {
this.count += 1;
cx.notify();
})))
}
}rust
use gpui::{Entity, Render, Context};
pub struct Counter {
count: i32,
}
impl Render for Counter {
fn render(&mut self, window: &mut Window, cx: &mut Context<Self>) -> impl IntoElement {
div()
.flex()
.gap_2()
.child(Button::new("dec").on_click(cx.listener(|this, _, _, cx| {
this.count -= 1;
cx.notify();
})))
.child(format!("Count: {}", self.count))
.child(Button::new("inc").on_click(cx.listener(|this, _, _, cx| {
this.count += 1;
cx.notify();
})))
}
}Available Components (gpui-component)
可用组件(gpui-component)
Form Components
表单组件
- - Buttons with variants (primary, danger, ghost, link)
Button - - Text input with LSP completion support
Input - - Numeric input with step controls
NumberInput - - Checkbox with label
Checkbox - - Toggle switch
Switch - - Radio button groups
Radio - - Dropdown select
Select - - Range slider
Slider
- - 包含多种变体的按钮(primary、danger、ghost、link)
Button - - 支持LSP补全的文本输入框
Input - - 带步进控制的数字输入框
NumberInput - - 带标签的复选框
Checkbox - - 切换开关
Switch - - 单选按钮组
Radio - - 下拉选择框
Select - - 范围滑块
Slider
Layout Components
布局组件
- - Modal dialogs
Dialog - - Popup popovers
Popover - /
Menu- Menus and context menusPopupMenu - - Tab navigation
Tab - - Collapsible sections
Accordion - - Sidebar navigation
Sidebar - - Dockable panels
Dock
- - 模态对话框
Dialog - - 弹出式气泡框
Popover - /
Menu- 菜单和上下文菜单PopupMenu - - 标签页导航
Tab - - 可折叠面板
Accordion - - 侧边栏导航
Sidebar - - 可停靠面板
Dock
Display Components
展示组件
- - Status badges
Badge - - User avatars
Avatar - - Icon display (IconName enum)
Icon - - Text labels
Label - - Tooltips
Tooltip - - Toast notifications
Notification
- - 状态徽章
Badge - - 用户头像
Avatar - - 图标展示(IconName枚举)
Icon - - 文本标签
Label - - 提示框
Tooltip - - 消息通知框
Notification
Data Components
数据组件
- - Data tables
Table - /
List- Scrollable listsVirtualList - - Tree view
Tree - - Charts and plots
Chart
- - 数据表格
Table - /
List- 可滚动列表VirtualList - - 树形视图
Tree - - 图表与绘图
Chart
Theming
主题设置
Accessing Theme
访问主题
rust
use gpui_component::ActiveTheme;
fn render(&mut self, window: &mut Window, cx: &mut App) -> impl IntoElement {
div()
.bg(cx.theme().background)
.text_color(cx.theme().foreground)
.border_1()
.border_color(cx.theme().border)
}rust
use gpui_component::ActiveTheme;
fn render(&mut self, window: &mut Window, cx: &mut App) -> impl IntoElement {
div()
.bg(cx.theme().background)
.text_color(cx.theme().foreground)
.border_1()
.border_color(cx.theme().border)
}Theme Colors
主题颜色
rust
// Background colors
cx.theme().background // Primary background
cx.theme().secondary // Secondary background
cx.theme().muted // Muted background
cx.theme().card // Card background
// Foreground colors
cx.theme().foreground // Primary text
cx.theme().muted_foreground // Muted text
// Semantic colors
cx.theme().primary // Primary accent
cx.theme().destructive // Danger/error
cx.theme().success // Success
cx.theme().warning // Warning
// Border colors
cx.theme().border // Default border
cx.theme().ring // Focus ringrust
// Background colors
cx.theme().background // Primary background
cx.theme().secondary // Secondary background
cx.theme().muted // Muted background
cx.theme().card // Card background
// Foreground colors
cx.theme().foreground // Primary text
cx.theme().muted_foreground // Muted text
// Semantic colors
cx.theme().primary // Primary accent
cx.theme().destructive // Danger/error
cx.theme().success // Success
cx.theme().warning // Warning
// Border colors
cx.theme().border // Default border
cx.theme().ring // Focus ringComponent Examples
组件示例
Button Usage
按钮使用示例
rust
use gpui_component::button::{Button, ButtonVariants};
Button::new("save")
.label("Save")
.icon(IconName::Save)
.primary()
.on_click(cx.listener(|this, _, window, cx| {
this.save(window, cx);
}))rust
use gpui_component::button::{Button, ButtonVariants};
Button::new("save")
.label("Save")
.icon(IconName::Save)
.primary()
.on_click(cx.listener(|this, _, window, cx| {
this.save(window, cx);
}))Input with State
带状态的输入框
rust
use gpui_component::input::{Input, InputState};
// Create state
let input_state = cx.new(|cx| InputState::new(cx));
// In render:
Input::new(&self.input_state)
.placeholder("Enter text...")
.cleanable(true)rust
use gpui_component::input::{Input, InputState};
// Create state
let input_state = cx.new(|cx| InputState::new(cx));
// In render:
Input::new(&self.input_state)
.placeholder("Enter text...")
.cleanable(true)PopupMenu / Command Palette
弹出菜单/命令面板
rust
use gpui_component::menu::{PopupMenu, PopupMenuItem};
let menu = cx.new(|cx| {
PopupMenu::build(cx, |menu, window, cx| {
menu.menu_item(PopupMenuItem::new("New File")
.icon(IconName::FilePlus)
.action(Box::new(NewFile)))
.separator()
.menu_item(PopupMenuItem::new("Save")
.icon(IconName::Save)
.action(Box::new(Save)))
})
});rust
use gpui_component::menu::{PopupMenu, PopupMenuItem};
let menu = cx.new(|cx| {
PopupMenu::build(cx, |menu, window, cx| {
menu.menu_item(PopupMenuItem::new("New File")
.icon(IconName::FilePlus)
.action(Box::new(NewFile)))
.separator()
.menu_item(PopupMenuItem::new("Save")
.icon(IconName::Save)
.action(Box::new(Save)))
})
});Completion Provider
补全提供器
rust
use gpui_component::input::{CompletionProvider, InputState};
struct MyCompletionProvider;
impl CompletionProvider for MyCompletionProvider {
fn completions(
&self,
text: &Rope,
offset: usize,
trigger: CompletionContext,
window: &mut Window,
cx: &mut Context<InputState>,
) -> Task<Result<CompletionResponse>> {
let items = vec![
CompletionItem {
label: "option1".into(),
..Default::default()
},
];
Task::ready(Ok(CompletionResponse::Array(items)))
}
fn is_completion_trigger(
&self,
offset: usize,
new_text: &str,
cx: &mut Context<InputState>,
) -> bool {
new_text == "/" || new_text == "@"
}
}rust
use gpui_component::input::{CompletionProvider, InputState};
struct MyCompletionProvider;
impl CompletionProvider for MyCompletionProvider {
fn completions(
&self,
text: &Rope,
offset: usize,
trigger: CompletionContext,
window: &mut Window,
cx: &mut Context<InputState>,
) -> Task<Result<CompletionResponse>> {
let items = vec![
CompletionItem {
label: "option1".into(),
..Default::default()
},
];
Task::ready(Ok(CompletionResponse::Array(items)))
}
fn is_completion_trigger(
&self,
offset: usize,
new_text: &str,
cx: &mut Context<InputState>,
) -> bool {
new_text == "/" || new_text == "@"
}
}Reference Files
参考文档
For detailed patterns, read:
- - Full component API
reference/components.md - - Theme system details
reference/theming.md - - Input with completions
reference/input-lsp.md - - Menu and command palette
reference/menus.md
如需了解详细模式,请阅读:
- - 完整组件API
reference/components.md - - 主题系统详情
reference/theming.md - - 带补全的输入框
reference/input-lsp.md - - 菜单与命令面板
reference/menus.md
Project Setup
项目设置
Cargo.toml
Cargo.toml
toml
[dependencies]
gpui = "0.2"
gpui-component = { version = "0.4", features = ["webview"] }toml
[dependencies]
gpui = "0.2"
gpui-component = { version = "0.4", features = ["webview"] }Basic App Structure
基础应用结构
rust
use gpui::*;
use gpui_component::*;
struct App {
// state
}
impl Render for App {
fn render(&mut self, window: &mut Window, cx: &mut Context<Self>) -> impl IntoElement {
Root::new(
div()
.size_full()
.flex()
.flex_col()
.bg(cx.theme().background)
.child(self.render_toolbar(window, cx))
.child(self.render_content(window, cx)),
window,
cx
)
}
}
fn main() {
Application::new().run(|cx| {
gpui_component::init(cx);
cx.open_window(WindowOptions::default(), |window, cx| {
cx.new(|cx| App::new(cx))
});
});
}rust
use gpui::*;
use gpui_component::*;
struct App {
// state
}
impl Render for App {
fn render(&mut self, window: &mut Window, cx: &mut Context<Self>) -> impl IntoElement {
Root::new(
div()
.size_full()
.flex()
.flex_col()
.bg(cx.theme().background)
.child(self.render_toolbar(window, cx))
.child(self.render_content(window, cx)),
window,
cx
)
}
}
fn main() {
Application::new().run(|cx| {
gpui_component::init(cx);
cx.open_window(WindowOptions::default(), |window, cx| {
cx.new(|cx| App::new(cx))
});
});
}