Cargo.lock 🔗
@@ -2121,6 +2121,7 @@ dependencies = [
"settings2",
"smol",
"theme2",
+ "ui2",
"util",
]
Piotr Osiewicz created
Cargo.lock | 1
crates/copilot2/Cargo.toml | 1
crates/copilot2/src/sign_in.rs | 278 ++++++++++++++++++--------------
crates/ui2/src/components/icon.rs | 3
4 files changed, 164 insertions(+), 119 deletions(-)
@@ -2121,6 +2121,7 @@ dependencies = [
"settings2",
"smol",
"theme2",
+ "ui2",
"util",
]
@@ -28,6 +28,7 @@ theme = { package = "theme2", path = "../theme2" }
lsp = { package = "lsp2", path = "../lsp2" }
node_runtime = { path = "../node_runtime"}
util = { path = "../util" }
+ui = { package = "ui2", path = "../ui2" }
async-compression = { version = "0.3", features = ["gzip", "futures-bufread"] }
async-tar = "0.4.2"
anyhow.workspace = true
@@ -11,11 +11,15 @@
const COPILOT_SIGN_UP_URL: &'static str = "https://github.com/features/copilot";
-use crate::{Copilot, Status};
+use crate::{request::PromptUserDeviceFlow, Copilot, Status};
use gpui::{
- px, size, AppContext, Bounds, Div, GlobalPixels, Point, Render, ViewContext, VisualContext,
- WindowBounds, WindowHandle, WindowKind, WindowOptions,
+ div, px, red, size, AnyElement, AppContext, Bounds, ClipboardItem, Div, Element, GlobalPixels,
+ InteractiveElement, IntoElement, MouseButton, ParentElement, Point, Render, Stateful,
+ StatefulInteractiveElement, Styled, ViewContext, VisualContext, WindowBounds, WindowHandle,
+ WindowKind, WindowOptions,
};
+use theme::ActiveTheme;
+use ui::{h_stack, v_stack, Button, Clickable, Icon, IconElement, Label};
pub fn init(cx: &mut AppContext) {
if let Some(copilot) = Copilot::global(cx) {
@@ -72,13 +76,14 @@ fn create_copilot_auth_window(
center: true,
focus: true,
show: true,
- kind: WindowKind::Normal,
+ kind: WindowKind::PopUp,
is_movable: true,
display_id: None,
};
- cx.open_window(window_options, |cx| {
+ let window = cx.open_window(window_options, |cx| {
cx.build_view(|_| CopilotCodeVerification::new(status.clone()))
- })
+ });
+ window
}
pub struct CopilotCodeVerification {
@@ -99,119 +104,138 @@ impl CopilotCodeVerification {
cx.notify();
}
- // fn render_device_code(
- // data: &PromptUserDeviceFlow,
- // style: &theme::Copilot,
- // cx: &mut ViewContext<Self>,
- // ) -> impl IntoAnyElement<Self> {
- // let copied = cx
- // .read_from_clipboard()
- // .map(|item| item.text() == &data.user_code)
- // .unwrap_or(false);
-
- // let device_code_style = &style.auth.prompting.device_code;
-
- // MouseEventHandler::new::<Self, _>(0, cx, |state, _cx| {
- // Flex::row()
- // .with_child(
- // Label::new(data.user_code.clone(), device_code_style.text.clone())
- // .aligned()
- // .contained()
- // .with_style(device_code_style.left_container)
- // .constrained()
- // .with_width(device_code_style.left),
- // )
- // .with_child(
- // Label::new(
- // if copied { "Copied!" } else { "Copy" },
- // device_code_style.cta.style_for(state).text.clone(),
- // )
- // .aligned()
- // .contained()
- // .with_style(*device_code_style.right_container.style_for(state))
- // .constrained()
- // .with_width(device_code_style.right),
- // )
- // .contained()
- // .with_style(device_code_style.cta.style_for(state).container)
- // })
- // .on_click(gpui::platform::MouseButton::Left, {
- // let user_code = data.user_code.clone();
- // move |_, _, cx| {
- // cx.platform()
- // .write_to_clipboard(ClipboardItem::new(user_code.clone()));
- // cx.notify();
- // }
- // })
- // .with_cursor_style(gpui::platform::CursorStyle::PointingHand)
- // }
+ fn render_device_code(
+ data: &PromptUserDeviceFlow,
+ cx: &mut ViewContext<Self>,
+ ) -> impl IntoElement {
+ let copied = cx
+ .read_from_clipboard()
+ .map(|item| item.text() == &data.user_code)
+ .unwrap_or(false);
+ h_stack()
+ .cursor_pointer()
+ .justify_between()
+ .on_mouse_down(gpui::MouseButton::Left, {
+ let user_code = data.user_code.clone();
+ move |_, cx| {
+ dbg!("Copied");
+ cx.write_to_clipboard(ClipboardItem::new(user_code.clone()));
+ cx.notify();
+ }
+ })
+ .child(Label::new(data.user_code.clone()))
+ .child(Label::new(if copied { "Copied!" } else { "Copy" }))
- // fn render_prompting_modal(
- // connect_clicked: bool,
- // data: &PromptUserDeviceFlow,
- // style: &theme::Copilot,
- // cx: &mut ViewContext<Self>,
- // ) -> AnyElement<Self> {
- // enum ConnectButton {}
+ // MouseEventHandler::new::<Self, _>(0, cx, |state, _cx| {
+ // Flex::row()
+ // .with_child(
+ // Label::new(data.user_code.clone(), device_code_style.text.clone())
+ // .aligned()
+ // .contained()
+ // .with_style(device_code_style.left_container)
+ // .constrained()
+ // .with_width(device_code_style.left),
+ // )
+ // .with_child(
+ // Label::new(
+ // if copied { "Copied!" } else { "Copy" },
+ // device_code_style.cta.style_for(state).text.clone(),
+ // )
+ // .aligned()
+ // .contained()
+ // .with_style(*device_code_style.right_container.style_for(state))
+ // .constrained()
+ // .with_width(device_code_style.right),
+ // )
+ // .contained()
+ // .with_style(device_code_style.cta.style_for(state).container)
+ // })
+ // .on_click(gpui::platform::MouseButton::Left, {
+ //
+ // move |_, _, cx| {
+ //
+ // }
+ // })
+ // .with_cursor_style(gpui::platform::CursorStyle::PointingHand)
+ }
- // Flex::column()
- // .with_child(
- // Flex::column()
- // .with_children([
- // Label::new(
- // "Enable Copilot by connecting",
- // style.auth.prompting.subheading.text.clone(),
- // )
- // .aligned(),
- // Label::new(
- // "your existing license.",
- // style.auth.prompting.subheading.text.clone(),
- // )
- // .aligned(),
- // ])
- // .align_children_center()
- // .contained()
- // .with_style(style.auth.prompting.subheading.container),
- // )
- // .with_child(Self::render_device_code(data, &style, cx))
- // .with_child(
- // Flex::column()
- // .with_children([
- // Label::new(
- // "Paste this code into GitHub after",
- // style.auth.prompting.hint.text.clone(),
- // )
- // .aligned(),
- // Label::new(
- // "clicking the button below.",
- // style.auth.prompting.hint.text.clone(),
- // )
- // .aligned(),
- // ])
- // .align_children_center()
- // .contained()
- // .with_style(style.auth.prompting.hint.container.clone()),
- // )
- // .with_child(theme::ui::cta_button::<ConnectButton, _, _, _>(
- // if connect_clicked {
- // "Waiting for connection..."
- // } else {
- // "Connect to GitHub"
- // },
- // style.auth.content_width,
- // &style.auth.cta_button,
- // cx,
- // {
- // let verification_uri = data.verification_uri.clone();
- // move |_, verification, cx| {
- // cx.platform().open_url(&verification_uri);
- // verification.connect_clicked = true;
- // }
- // },
- // ))
- // .align_children_center()
- // .into_any()
- // }
+ fn render_prompting_modal(
+ connect_clicked: bool,
+ data: &PromptUserDeviceFlow,
+ cx: &mut ViewContext<Self>,
+ ) -> impl Element {
+ let connect_button_label = if connect_clicked {
+ "Waiting for connection..."
+ } else {
+ "Connect to Github"
+ };
+ v_stack()
+ .child(
+ v_stack()
+ .flex_1()
+ .w_full()
+ .items_center()
+ .justify_between()
+ .children([
+ h_stack()
+ .items_center()
+ .child(Label::new("Enable Copilot by connecting")),
+ h_stack()
+ .items_center()
+ .child(Label::new("your existing license")),
+ ]),
+ )
+ .child(Self::render_device_code(data, cx))
+ .child(Label::new("Paste this code into GitHub after").size(ui::LabelSize::Small))
+ .child(Label::new("clicking the button below.").size(ui::LabelSize::Small))
+ .child(
+ Button::new("connect-button", connect_button_label).on_click({
+ let verification_uri = data.verification_uri.clone();
+ cx.listener(move |this, _, cx| {
+ cx.open_url(&verification_uri);
+ this.connect_clicked = true;
+ })
+ }),
+ )
+ // Flex::column()
+ // .with_child(Self::render_device_code(data, &style, cx))
+ // .with_child(
+ // Flex::column()
+ // .with_children([
+ // Label::new(
+ // "Paste this code into GitHub after",
+ // style.auth.prompting.hint.text.clone(),
+ // )
+ // .aligned(),
+ // Label::new(
+ // "clicking the button below.",
+ // style.auth.prompting.hint.text.clone(),
+ // )
+ // .aligned(),
+ // ])
+ // .align_children_center()
+ // .contained()
+ // .with_style(style.auth.prompting.hint.container.clone()),
+ // )
+ // .with_child(theme::ui::cta_button::<ConnectButton, _, _, _>(
+ // if connect_clicked {
+ // "Waiting for connection..."
+ // } else {
+ // "Connect to GitHub"
+ // },
+ // style.auth.content_width,
+ // &style.auth.cta_button,
+ // cx,
+ // {
+ // let verification_uri = data.verification_uri.clone();
+ // move |_, verification, cx| {
+ // cx.platform().open_url(&verification_uri);
+ // verification.connect_clicked = true;
+ // }
+ // },
+ // ))
+ // .align_children_center()
+ }
// fn render_enabled_modal(
// style: &theme::Copilot,
@@ -316,10 +340,26 @@ impl CopilotCodeVerification {
}
impl Render for CopilotCodeVerification {
- type Element = Div;
+ type Element = Stateful<Div>;
fn render(&mut self, cx: &mut ViewContext<Self>) -> Self::Element {
- todo!()
+ let prompt = match &self.status {
+ Status::SigningIn { prompt } => prompt.as_ref(),
+ _ => None,
+ };
+ div()
+ .id("copilot code verification")
+ .flex()
+ .flex_col()
+ .size_full()
+ .items_center()
+ .p_10()
+ .bg(cx.theme().colors().element_background)
+ .child(ui::Label::new("Connect Copilot to Zed"))
+ .child(IconElement::new(Icon::ZedXCopilot))
+ .children(
+ prompt.map(|data| Self::render_prompting_modal(self.connect_clicked, data, cx)),
+ )
}
}
@@ -81,6 +81,7 @@ pub enum Icon {
Shift,
Option,
Return,
+ ZedXCopilot,
}
impl Icon {
@@ -109,6 +110,7 @@ impl Icon {
Icon::Close => "icons/x.svg",
Icon::Collab => "icons/user_group_16.svg",
Icon::Copilot => "icons/copilot.svg",
+
Icon::CopilotInit => "icons/copilot_init.svg",
Icon::CopilotError => "icons/copilot_error.svg",
Icon::CopilotDisabled => "icons/copilot_disabled.svg",
@@ -155,6 +157,7 @@ impl Icon {
Icon::Shift => "icons/shift.svg",
Icon::Option => "icons/option.svg",
Icon::Return => "icons/return.svg",
+ Icon::ZedXCopilot => "icons/zed_x_copilot.svg",
}
}
}