agent: Improve end of trial card display (#35789)

Now rendering the backdrop behind the card to clean up the UI, bring
focus to the card's content, and direct the user to act on it, either by
ignoring it or upgrading.

<img width="500" height="1242" alt="CleanShot 2025-08-07 at 10  30
58@2x"
src="https://github.com/user-attachments/assets/8c6b9c34-eb22-4f01-b3fa-158ac78b7439"
/>

Release Notes:

- N/A
This commit is contained in:
Danilo Leal 2025-08-07 10:53:15 -03:00 committed by GitHub
parent 305c653c62
commit a5c25e0366
No known key found for this signature in database
GPG key ID: B5690EEEBB952194

View file

@ -2343,6 +2343,16 @@ impl AgentPanel {
) )
} }
fn render_backdrop(&self, cx: &mut Context<Self>) -> impl IntoElement {
div()
.size_full()
.absolute()
.inset_0()
.bg(cx.theme().colors().panel_background)
.opacity(0.8)
.block_mouse_except_scroll()
}
fn render_trial_end_upsell( fn render_trial_end_upsell(
&self, &self,
_window: &mut Window, _window: &mut Window,
@ -2352,7 +2362,15 @@ impl AgentPanel {
return None; return None;
} }
Some(EndTrialUpsell::new(Arc::new({ Some(
v_flex()
.absolute()
.inset_0()
.size_full()
.bg(cx.theme().colors().panel_background)
.opacity(0.85)
.block_mouse_except_scroll()
.child(EndTrialUpsell::new(Arc::new({
let this = cx.entity(); let this = cx.entity();
move |_, cx| { move |_, cx| {
this.update(cx, |_this, cx| { this.update(cx, |_this, cx| {
@ -2360,7 +2378,8 @@ impl AgentPanel {
cx.notify(); cx.notify();
}); });
} }
}))) }))),
)
} }
fn render_empty_state_section_header( fn render_empty_state_section_header(
@ -3210,9 +3229,10 @@ impl Render for AgentPanel {
// - Scrolling in all views works as expected // - Scrolling in all views works as expected
// - Files can be dropped into the panel // - Files can be dropped into the panel
let content = v_flex() let content = v_flex()
.key_context(self.key_context()) .relative()
.justify_between()
.size_full() .size_full()
.justify_between()
.key_context(self.key_context())
.on_action(cx.listener(Self::cancel)) .on_action(cx.listener(Self::cancel))
.on_action(cx.listener(|this, action: &NewThread, window, cx| { .on_action(cx.listener(|this, action: &NewThread, window, cx| {
this.new_thread(action, window, cx); this.new_thread(action, window, cx);
@ -3255,14 +3275,12 @@ impl Render for AgentPanel {
.on_action(cx.listener(Self::toggle_burn_mode)) .on_action(cx.listener(Self::toggle_burn_mode))
.child(self.render_toolbar(window, cx)) .child(self.render_toolbar(window, cx))
.children(self.render_onboarding(window, cx)) .children(self.render_onboarding(window, cx))
.children(self.render_trial_end_upsell(window, cx))
.map(|parent| match &self.active_view { .map(|parent| match &self.active_view {
ActiveView::Thread { ActiveView::Thread {
thread, thread,
message_editor, message_editor,
.. ..
} => parent } => parent
.relative()
.child( .child(
if thread.read(cx).is_empty() && !self.should_render_onboarding(cx) { if thread.read(cx).is_empty() && !self.should_render_onboarding(cx) {
self.render_thread_empty_state(window, cx) self.render_thread_empty_state(window, cx)
@ -3299,21 +3317,10 @@ impl Render for AgentPanel {
}) })
.child(h_flex().relative().child(message_editor.clone()).when( .child(h_flex().relative().child(message_editor.clone()).when(
!LanguageModelRegistry::read_global(cx).has_authenticated_provider(cx), !LanguageModelRegistry::read_global(cx).has_authenticated_provider(cx),
|this| { |this| this.child(self.render_backdrop(cx)),
this.child(
div()
.size_full()
.absolute()
.inset_0()
.bg(cx.theme().colors().panel_background)
.opacity(0.8)
.block_mouse_except_scroll(),
)
},
)) ))
.child(self.render_drag_target(cx)), .child(self.render_drag_target(cx)),
ActiveView::ExternalAgentThread { thread_view, .. } => parent ActiveView::ExternalAgentThread { thread_view, .. } => parent
.relative()
.child(thread_view.clone()) .child(thread_view.clone())
.child(self.render_drag_target(cx)), .child(self.render_drag_target(cx)),
ActiveView::History => parent.child(self.history.clone()), ActiveView::History => parent.child(self.history.clone()),
@ -3352,7 +3359,8 @@ impl Render for AgentPanel {
)) ))
} }
ActiveView::Configuration => parent.children(self.configuration.clone()), ActiveView::Configuration => parent.children(self.configuration.clone()),
}); })
.children(self.render_trial_end_upsell(window, cx));
match self.active_view.which_font_size_used() { match self.active_view.which_font_size_used() {
WhichFontSize::AgentFont => { WhichFontSize::AgentFont => {