diff --git a/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/assistant_body/empty_convo.tsx b/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/assistant_body/empty_convo.tsx index ef2b75e86d64f..50e8cadc199ab 100644 --- a/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/assistant_body/empty_convo.tsx +++ b/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/assistant_body/empty_convo.tsx @@ -5,11 +5,12 @@ * 2.0. */ -import React, { Dispatch, SetStateAction } from 'react'; +import React, { Dispatch, SetStateAction, useMemo } from 'react'; import { EuiFlexGroup, EuiFlexItem, EuiPanel, EuiText } from '@elastic/eui'; import { css } from '@emotion/react'; import { PromptResponse } from '@kbn/elastic-assistant-common'; import { AssistantBeacon } from '@kbn/ai-assistant-icon'; +import { useVerticalBreakpoint } from './use_vertical_breakpoint'; import { useAssistantContext } from '../../..'; import { StarterPrompts } from './starter_prompts'; import { SystemPrompt } from '../prompt_editor/system_prompt'; @@ -39,12 +40,15 @@ export const EmptyConvo: React.FC = ({ setUserPrompt, }) => { const { assistantAvailability } = useAssistantContext(); + const breakpoint = useVerticalBreakpoint(); + const compressed = useMemo(() => breakpoint !== 'tall', [breakpoint]); return ( = ({ text-align: center; `} > - + - + - +

{i18n.EMPTY_SCREEN_TITLE}

{i18n.EMPTY_SCREEN_DESCRIPTION}

@@ -71,17 +80,22 @@ export const EmptyConvo: React.FC = ({ isSettingsModalVisible={isSettingsModalVisible} onSystemPromptSelectionChange={setCurrentSystemPromptId} setIsSettingsModalVisible={setIsSettingsModalVisible} + compressed={compressed} />
- +
{assistantAvailability.isStarterPromptsEnabled && ( - + )}
diff --git a/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/assistant_body/starter_prompts.tsx b/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/assistant_body/starter_prompts.tsx index d4dafe174afb8..7700683e865f8 100644 --- a/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/assistant_body/starter_prompts.tsx +++ b/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/assistant_body/starter_prompts.tsx @@ -6,21 +6,14 @@ */ import React, { useMemo, useCallback } from 'react'; -import { - EuiFlexGroup, - EuiFlexItem, - EuiIcon, - EuiPanel, - EuiSpacer, - EuiText, - EuiTitle, -} from '@elastic/eui'; +import { EuiFlexGroup, EuiFlexItem, EuiIcon, EuiPanel, EuiSpacer, EuiText } from '@elastic/eui'; import { css } from '@emotion/css'; import { PromptItemArray } from '@kbn/elastic-assistant-common/impl/schemas/security_ai_prompts/common_attributes.gen'; import { useAssistantContext, useFindPrompts } from '../../..'; interface Props { connectorId?: string; + compressed?: boolean; setUserPrompt: React.Dispatch>; } const starterPromptClassName = css` @@ -65,7 +58,11 @@ export const promptGroups = [ }, ]; -export const StarterPrompts: React.FC = ({ connectorId, setUserPrompt }) => { +export const StarterPrompts: React.FC = ({ + compressed = false, + connectorId, + setUserPrompt, +}) => { const { assistantAvailability: { isAssistantEnabled }, assistantTelemetry, @@ -116,7 +113,7 @@ export const StarterPrompts: React.FC = ({ connectorId, setUserPrompt }) {fetchedPromptGroups.map(({ description, title, icon, prompt }) => ( = ({ connectorId, setUserPrompt }) className={starterPromptInnerClassName} > - + - -

{title}

-
- {description} + +

{title}

+

{description}

+
))} diff --git a/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/assistant_body/use_vertical_breakpoint.test.ts b/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/assistant_body/use_vertical_breakpoint.test.ts new file mode 100644 index 0000000000000..dbbd1391eba5e --- /dev/null +++ b/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/assistant_body/use_vertical_breakpoint.test.ts @@ -0,0 +1,58 @@ +/* + * Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one + * or more contributor license agreements. Licensed under the Elastic License + * 2.0; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { act, renderHook } from '@testing-library/react'; +import { useVerticalBreakpoint } from './use_vertical_breakpoint'; + +describe('useVerticalBreakpoint', () => { + beforeEach(() => { + jest.useFakeTimers(); + }); + + afterEach(() => { + jest.useRealTimers(); + }); + + function setWindowHeight(height: number) { + Object.defineProperty(window, 'innerHeight', { + writable: true, + configurable: true, + value: height, + }); + window.dispatchEvent(new Event('resize')); + } + + it('returns "short" for height < 600', () => { + setWindowHeight(500); + const { result } = renderHook(() => useVerticalBreakpoint()); + expect(result.current).toBe('short'); + }); + + it('returns "medium" for 600 <= height < 1100', () => { + setWindowHeight(800); + const { result } = renderHook(() => useVerticalBreakpoint()); + expect(result.current).toBe('medium'); + }); + + it('returns "tall" for height >= 1100', () => { + setWindowHeight(1200); + const { result } = renderHook(() => useVerticalBreakpoint()); + expect(result.current).toBe('tall'); + }); + + it('updates value on window resize once debounced', () => { + setWindowHeight(1200); + const { result } = renderHook(() => useVerticalBreakpoint()); + expect(result.current).toBe('tall'); + setWindowHeight(500); + expect(result.current).toBe('tall'); + act(() => { + jest.advanceTimersByTime(100); // debounce + }); + expect(result.current).toBe('short'); + }); +}); diff --git a/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/assistant_body/use_vertical_breakpoint.ts b/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/assistant_body/use_vertical_breakpoint.ts new file mode 100644 index 0000000000000..059966e0ee587 --- /dev/null +++ b/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/assistant_body/use_vertical_breakpoint.ts @@ -0,0 +1,30 @@ +/* + * Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one + * or more contributor license agreements. Licensed under the Elastic License + * 2.0; you may not use this file except in compliance with the Elastic License + * 2.0. + */ + +import { useEffect } from 'react'; +import useRafState from 'react-use/lib/useRafState'; + +export type VerticalBreakpoint = 'short' | 'medium' | 'tall'; + +export function useVerticalBreakpoint(): VerticalBreakpoint { + const [height, setHeight] = useRafState(() => window.innerHeight); + + useEffect(() => { + const handleResize = () => { + const newHeight = window.innerHeight; + setHeight((prev) => (prev !== newHeight ? newHeight : prev)); + }; + window.addEventListener('resize', handleResize, { passive: true }); + return () => { + window.removeEventListener('resize', handleResize); + }; + }, [setHeight]); + + if (height < 600) return 'short'; + if (height < 1100) return 'medium'; + return 'tall'; +} diff --git a/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/prompt_editor/system_prompt/index.tsx b/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/prompt_editor/system_prompt/index.tsx index 1cf00944d51de..f951fcdc28984 100644 --- a/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/prompt_editor/system_prompt/index.tsx +++ b/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/prompt_editor/system_prompt/index.tsx @@ -13,6 +13,7 @@ interface Props { allSystemPrompts: PromptResponse[]; currentSystemPromptId: string | undefined; isSettingsModalVisible: boolean; + compressed?: boolean; onSystemPromptSelectionChange: (systemPromptId: string | undefined) => void; setIsSettingsModalVisible: React.Dispatch>; } @@ -21,6 +22,7 @@ const SystemPromptComponent: React.FC = ({ allSystemPrompts, currentSystemPromptId, isSettingsModalVisible, + compressed = false, onSystemPromptSelectionChange, setIsSettingsModalVisible, }) => { @@ -43,6 +45,7 @@ const SystemPromptComponent: React.FC = ({ data-test-subj="systemPrompt" isClearable={true} isSettingsModalVisible={isSettingsModalVisible} + compressed={compressed} onSystemPromptSelectionChange={onSystemPromptSelectionChange} selectedPrompt={selectedPrompt} setIsSettingsModalVisible={setIsSettingsModalVisible} diff --git a/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/prompt_editor/system_prompt/select_system_prompt/index.tsx b/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/prompt_editor/system_prompt/select_system_prompt/index.tsx index 884b195fce3d0..736e0f14e5d46 100644 --- a/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/prompt_editor/system_prompt/select_system_prompt/index.tsx +++ b/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/prompt_editor/system_prompt/select_system_prompt/index.tsx @@ -144,6 +144,7 @@ const SelectSystemPromptComponent: React.FC = ({ prepend={!isSettingsModalVisible ? PROMPT_CONTEXT_SELECTOR_PREFIX : undefined} css={css` padding-right: 56px !important; + ${compressed ? 'font-size: 0.9rem;' : ''} `} /> diff --git a/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/translations.ts b/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/translations.ts index c0ebd81550579..f793c37473b53 100644 --- a/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/translations.ts +++ b/x-pack/platform/packages/shared/kbn-elastic-assistant/impl/assistant/translations.ts @@ -37,10 +37,10 @@ export const EMPTY_SCREEN_TITLE = i18n.translate( ); export const EMPTY_SCREEN_DESCRIPTION = i18n.translate( - 'xpack.elasticAssistant.assistant.emptyScreen.description', + 'xpack.elasticAssistant.assistant.emptyScreen.descriptionV2', { defaultMessage: - 'Ask me anything from "Summarize this alert" to "Help me build a query" using the following system prompt:', + 'Ask me anything in the chat box, or choose one of the prompts below to jump right in.', } ); diff --git a/x-pack/platform/plugins/private/translations/translations/fr-FR.json b/x-pack/platform/plugins/private/translations/translations/fr-FR.json index 0a7fef99d88fd..350712d4837f8 100644 --- a/x-pack/platform/plugins/private/translations/translations/fr-FR.json +++ b/x-pack/platform/plugins/private/translations/translations/fr-FR.json @@ -16174,7 +16174,6 @@ "xpack.elasticAssistant.assistant.deleteConversationModal.deleteButtonText": "Supprimer", "xpack.elasticAssistant.assistant.deleteConversationModal.deleteConversationTitle": "Supprimer cette conversation", "xpack.elasticAssistant.assistant.disclaimer": "Les réponses des systèmes d'IA ne sont pas toujours tout à fait exactes, même si elles peuvent sembler convaincantes. Pour en savoir plus sur la fonctionnalité d'assistant et son utilisation, consultez la documentation.", - "xpack.elasticAssistant.assistant.emptyScreen.description": "Demandez-moi tout ce que vous voulez, de \"Résumez cette alerte\" à \"Aidez-moi à construire une requête\" en utilisant l'invite suivante du système :", "xpack.elasticAssistant.assistant.emptyScreen.title": "Comment puis-je vous aider ?", "xpack.elasticAssistant.assistant.firstPromptEditor.addNewSystemPrompt": "Ajouter une nouvelle invite système...", "xpack.elasticAssistant.assistant.firstPromptEditor.clearSystemPrompt": "Effacer une invite système", diff --git a/x-pack/platform/plugins/private/translations/translations/ja-JP.json b/x-pack/platform/plugins/private/translations/translations/ja-JP.json index c3e1a87ae7c51..c7e4ef90eabad 100644 --- a/x-pack/platform/plugins/private/translations/translations/ja-JP.json +++ b/x-pack/platform/plugins/private/translations/translations/ja-JP.json @@ -16151,7 +16151,6 @@ "xpack.elasticAssistant.assistant.deleteConversationModal.deleteButtonText": "削除", "xpack.elasticAssistant.assistant.deleteConversationModal.deleteConversationTitle": "この会話を削除", "xpack.elasticAssistant.assistant.disclaimer": "AIシステムからの応答は、納得できるように思われる場合であっても、必ずしも完全に正確であるとは限りません。アシスタント機能とその使用方法の詳細については、ドキュメントを参照してください。", - "xpack.elasticAssistant.assistant.emptyScreen.description": "次のシステムプロンプトを使用して、「このアラートを要約してください」から「クエリの作成を手伝ってください」まで、何でも依頼してください。", "xpack.elasticAssistant.assistant.emptyScreen.title": "お手伝いできることはありますか?", "xpack.elasticAssistant.assistant.firstPromptEditor.addNewSystemPrompt": "新しいシステムプロンプトを追加...", "xpack.elasticAssistant.assistant.firstPromptEditor.clearSystemPrompt": "システムプロンプトを消去", diff --git a/x-pack/platform/plugins/private/translations/translations/zh-CN.json b/x-pack/platform/plugins/private/translations/translations/zh-CN.json index 4d2d2c81cb5a6..bbad3e8344533 100644 --- a/x-pack/platform/plugins/private/translations/translations/zh-CN.json +++ b/x-pack/platform/plugins/private/translations/translations/zh-CN.json @@ -16191,7 +16191,6 @@ "xpack.elasticAssistant.assistant.deleteConversationModal.deleteButtonText": "删除", "xpack.elasticAssistant.assistant.deleteConversationModal.deleteConversationTitle": "删除此对话", "xpack.elasticAssistant.assistant.disclaimer": "虽然来自 AI 系统的响应不可能始终完全准确,但它们似乎令人信服。有关辅助功能及其用法的详细信息,请参阅文档。", - "xpack.elasticAssistant.assistant.emptyScreen.description": "使用以下系统提示向我提出任何要求,从“汇总此告警”到“帮助我构建查询”:", "xpack.elasticAssistant.assistant.emptyScreen.title": "我如何帮助您?", "xpack.elasticAssistant.assistant.firstPromptEditor.addNewSystemPrompt": "添加新系统提示……", "xpack.elasticAssistant.assistant.firstPromptEditor.clearSystemPrompt": "清除系统提示",