From c686f605e6813333920cd2cafe302c53b985a16f Mon Sep 17 00:00:00 2001 From: Luigi Teschio Date: Thu, 11 Jan 2024 15:32:16 +0100 Subject: [PATCH] [CYS - Core] Update the homepage with default patterns when the assembler is loaded (#43457) CYS - Core: Setup the site with a default homepage when the assembler is loaded --- .../customize-store/assembler-hub/layout.tsx | 4 +- .../assembler-hub/onboarding-tour/index.tsx | 48 ++++++-- .../onboarding-tour/test/index.tsx | 15 ++- .../client/customize-store/data/actions.ts | 71 +++++++++++ .../design-with-ai/services.ts | 58 +-------- .../design-without-ai/actions.ts | 47 ++++++++ .../design-without-ai/index.tsx | 74 ++++++++++++ .../design-without-ai/services.ts | 31 +++++ .../design-without-ai/state-machine.tsx | 111 ++++++++++++++++++ .../design-without-ai/types.ts | 12 ++ .../client/customize-store/index.tsx | 108 ++++++++++------- .../client/customize-store/intro/index.tsx | 7 +- .../customize-store/intro/intro-banners.tsx | 58 ++++++--- ...ault-patterns-when-the-assembler-is-loaded | 4 + 14 files changed, 515 insertions(+), 133 deletions(-) create mode 100644 plugins/woocommerce-admin/client/customize-store/data/actions.ts create mode 100644 plugins/woocommerce-admin/client/customize-store/design-without-ai/actions.ts create mode 100644 plugins/woocommerce-admin/client/customize-store/design-without-ai/index.tsx create mode 100644 plugins/woocommerce-admin/client/customize-store/design-without-ai/services.ts create mode 100644 plugins/woocommerce-admin/client/customize-store/design-without-ai/state-machine.tsx create mode 100644 plugins/woocommerce-admin/client/customize-store/design-without-ai/types.ts create mode 100644 plugins/woocommerce/changelog/43457-43420-cys-core-update-homepage-with-default-patterns-when-the-assembler-is-loaded diff --git a/plugins/woocommerce-admin/client/customize-store/assembler-hub/layout.tsx b/plugins/woocommerce-admin/client/customize-store/assembler-hub/layout.tsx index 97e6350af7a..eef96c5b31b 100644 --- a/plugins/woocommerce-admin/client/customize-store/assembler-hub/layout.tsx +++ b/plugins/woocommerce-admin/client/customize-store/assembler-hub/layout.tsx @@ -243,11 +243,13 @@ export const Layout = () => { { ! isEditorLoading && shouldTourBeShown && - ! showAiOfflineModal && ( + ( FlowType.AIOnline === context.flowType || + FlowType.noAI === context.flowType ) && ( ) } diff --git a/plugins/woocommerce-admin/client/customize-store/assembler-hub/onboarding-tour/index.tsx b/plugins/woocommerce-admin/client/customize-store/assembler-hub/onboarding-tour/index.tsx index b07d4db41b9..6a426ea4c77 100644 --- a/plugins/woocommerce-admin/client/customize-store/assembler-hub/onboarding-tour/index.tsx +++ b/plugins/woocommerce-admin/client/customize-store/assembler-hub/onboarding-tour/index.tsx @@ -10,6 +10,7 @@ import { recordEvent } from '@woocommerce/tracks'; * Internal dependencies */ export * from './use-onboarding-tour'; +import { FlowType } from '~/customize-store/types'; type OnboardingTourProps = { onClose: () => void; @@ -17,18 +18,53 @@ type OnboardingTourProps = { takeTour: () => void; showWelcomeTour: boolean; setIsResizeHandleVisible: ( isVisible: boolean ) => void; + flowType: FlowType.AIOnline | FlowType.noAI; +}; + +const getLabels = ( flowType: FlowType.AIOnline | FlowType.noAI ) => { + switch ( flowType ) { + case FlowType.AIOnline: + return { + heading: __( + 'Welcome to your AI-generated store!', + 'woocommerce' + ), + descriptions: { + desktop: __( + 'This is where you can start customizing the look and feel of your store, including adding your logo, and changing colors and layouts. Take a quick tour to discover what’s possible.', + 'woocommerce' + ), + }, + }; + case FlowType.noAI: + return { + heading: __( + "Discover what's possible with the store designer", + 'woocommerce' + ), + descriptions: { + desktop: __( + "Start designing your store, including adding your logo, changing color schemes, and choosing layouts. Take a quick tour to discover what's possible.", + 'woocommerce' + ), + }, + }; + } }; export const OnboardingTour = ( { onClose, skipTour, takeTour, + flowType, showWelcomeTour, setIsResizeHandleVisible, }: OnboardingTourProps ) => { const [ placement, setPlacement ] = useState< TourKitTypes.WooConfig[ 'placement' ] >( 'left' ); + const { heading, descriptions } = getLabels( flowType ); + if ( showWelcomeTour ) { return ( ( { recordEvent: jest.fn() } ) ); jest.mock( '../../', () => ( { @@ -26,6 +27,7 @@ describe( 'OnboardingTour', () => { takeTour: jest.Mock; setShowWelcomeTour: jest.Mock; showWelcomeTour: boolean; + flowType: FlowType.AIOnline | FlowType.noAI; setIsResizeHandleVisible: ( isVisible: boolean ) => void; }; @@ -37,10 +39,11 @@ describe( 'OnboardingTour', () => { setShowWelcomeTour: jest.fn(), showWelcomeTour: true, setIsResizeHandleVisible: jest.fn(), + flowType: FlowType.AIOnline, }; } ); - it( 'should render welcome tour', () => { + it( 'should render welcome tour mentioning the AI when the flowType is AIOnline', () => { render( ); expect( @@ -48,6 +51,16 @@ describe( 'OnboardingTour', () => { ).toBeInTheDocument(); } ); + it( 'should render welcome tour not mentioning the AI when the flowType is AIOnline', () => { + render( ); + + expect( + screen.getByText( + /Discover what's possible with the store designer/i + ) + ).toBeInTheDocument(); + } ); + it( 'should render step 1', () => { render( ); diff --git a/plugins/woocommerce-admin/client/customize-store/data/actions.ts b/plugins/woocommerce-admin/client/customize-store/data/actions.ts new file mode 100644 index 00000000000..a4b839f9883 --- /dev/null +++ b/plugins/woocommerce-admin/client/customize-store/data/actions.ts @@ -0,0 +1,71 @@ +/* eslint-disable @woocommerce/dependency-group */ +/* eslint-disable @typescript-eslint/ban-ts-comment */ +/** + * External dependencies + */ +import { resolveSelect, dispatch } from '@wordpress/data'; +// @ts-ignore No types for this exist yet. +import { store as coreStore } from '@wordpress/core-data'; +// @ts-ignore No types for this exist yet. + +/** + * Internal dependencies + */ +import { + patternsToNameMap, + getTemplatePatterns, +} from '../assembler-hub/hooks/use-home-templates'; +import { setLogoWidth } from '../utils'; +import { HOMEPAGE_TEMPLATES } from './homepageTemplates'; + +// Update the current theme template +export const updateTemplate = async ( { + homepageTemplateId, +}: { + homepageTemplateId: keyof typeof HOMEPAGE_TEMPLATES; +} ) => { + // @ts-ignore No types for this exist yet. + const { invalidateResolutionForStoreSelector } = dispatch( coreStore ); + + // Ensure that the patterns are up to date because we populate images and content in previous step. + invalidateResolutionForStoreSelector( 'getBlockPatterns' ); + invalidateResolutionForStoreSelector( '__experimentalGetTemplateForLink' ); + + const patterns = ( await resolveSelect( + coreStore + // @ts-ignore No types for this exist yet. + ).getBlockPatterns() ) as Pattern[]; + const patternsByName = patternsToNameMap( patterns ); + const homepageTemplate = getTemplatePatterns( + HOMEPAGE_TEMPLATES[ homepageTemplateId ].blocks, + patternsByName + ); + + let content = [ ...homepageTemplate ] + .filter( Boolean ) + .map( ( pattern ) => pattern.content ) + .join( '\n\n' ); + + // Replace the logo width with the default width. + content = setLogoWidth( content ); + + const currentTemplate = await resolveSelect( + coreStore + // @ts-ignore No types for this exist yet. + ).__experimentalGetTemplateForLink( '/' ); + + // @ts-ignore No types for this exist yet. + const { saveEntityRecord } = dispatch( coreStore ); + + await saveEntityRecord( + 'postType', + currentTemplate.type, + { + id: currentTemplate.id, + content, + }, + { + throwOnError: true, + } + ); +}; diff --git a/plugins/woocommerce-admin/client/customize-store/design-with-ai/services.ts b/plugins/woocommerce-admin/client/customize-store/design-with-ai/services.ts index b5c2f72cdba..e947c20d54d 100644 --- a/plugins/woocommerce-admin/client/customize-store/design-with-ai/services.ts +++ b/plugins/woocommerce-admin/client/customize-store/design-with-ai/services.ts @@ -19,12 +19,8 @@ import { mergeBaseAndUserConfigs } from '@wordpress/edit-site/build-module/compo import { designWithAiStateMachineContext } from './types'; import { FONT_PAIRINGS } from '../assembler-hub/sidebar/global-styles/font-pairing-variations/constants'; import { COLOR_PALETTES } from '../assembler-hub/sidebar/global-styles/color-palette-variations/constants'; -import { - patternsToNameMap, - getTemplatePatterns, -} from '../assembler-hub/hooks/use-home-templates'; import { HOMEPAGE_TEMPLATES } from '../data/homepageTemplates'; -import { setLogoWidth } from '../utils'; +import { updateTemplate } from '../data/actions'; const { escalate } = actions; @@ -396,58 +392,6 @@ const updateGlobalStyles = async ( { ); }; -// Update the current theme template -const updateTemplate = async ( { - homepageTemplateId, -}: { - homepageTemplateId: keyof typeof HOMEPAGE_TEMPLATES; -} ) => { - // @ts-ignore No types for this exist yet. - const { invalidateResolutionForStoreSelector } = dispatch( coreStore ); - - // Ensure that the patterns are up to date because we populate images and content in previous step. - invalidateResolutionForStoreSelector( 'getBlockPatterns' ); - invalidateResolutionForStoreSelector( '__experimentalGetTemplateForLink' ); - - const patterns = ( await resolveSelect( - coreStore - // @ts-ignore No types for this exist yet. - ).getBlockPatterns() ) as Pattern[]; - const patternsByName = patternsToNameMap( patterns ); - const homepageTemplate = getTemplatePatterns( - HOMEPAGE_TEMPLATES[ homepageTemplateId ].blocks, - patternsByName - ); - - let content = [ ...homepageTemplate ] - .filter( Boolean ) - .map( ( pattern ) => pattern.content ) - .join( '\n\n' ); - - // Replace the logo width with the default width. - content = setLogoWidth( content ); - - const currentTemplate = await resolveSelect( - coreStore - // @ts-ignore No types for this exist yet. - ).__experimentalGetTemplateForLink( '/' ); - - // @ts-ignore No types for this exist yet. - const { saveEntityRecord } = dispatch( coreStore ); - - await saveEntityRecord( - 'postType', - currentTemplate.type, - { - id: currentTemplate.id, - content, - }, - { - throwOnError: true, - } - ); -}; - export const assembleSite = async ( context: designWithAiStateMachineContext ) => { diff --git a/plugins/woocommerce-admin/client/customize-store/design-without-ai/actions.ts b/plugins/woocommerce-admin/client/customize-store/design-without-ai/actions.ts new file mode 100644 index 00000000000..08a42f356b3 --- /dev/null +++ b/plugins/woocommerce-admin/client/customize-store/design-without-ai/actions.ts @@ -0,0 +1,47 @@ +/** + * External dependencies + */ +import { getNewPath } from '@woocommerce/navigation'; +/** + * Internal dependencies + */ +import { attachIframeListeners, onIframeLoad } from '../utils'; + +const redirectToAssemblerHub = async () => { + const assemblerUrl = getNewPath( {}, '/customize-store/assembler-hub', {} ); + const iframe = document.createElement( 'iframe' ); + iframe.classList.add( 'cys-fullscreen-iframe' ); + iframe.src = assemblerUrl; + + const showIframe = () => { + if ( iframe.style.opacity === '1' ) { + // iframe is already visible + return; + } + + const loader = document.getElementsByClassName( + 'woocommerce-onboarding-loader' + ); + if ( loader[ 0 ] ) { + ( loader[ 0 ] as HTMLElement ).style.display = 'none'; + } + + iframe.style.opacity = '1'; + }; + + iframe.onload = () => { + // Hide loading UI + attachIframeListeners( iframe ); + onIframeLoad( showIframe ); + + // Ceiling wait time set to 60 seconds + setTimeout( showIframe, 60 * 1000 ); + window.history?.pushState( {}, '', assemblerUrl ); + }; + + document.body.appendChild( iframe ); +}; + +export const actions = { + redirectToAssemblerHub, +}; diff --git a/plugins/woocommerce-admin/client/customize-store/design-without-ai/index.tsx b/plugins/woocommerce-admin/client/customize-store/design-without-ai/index.tsx new file mode 100644 index 00000000000..5a913343c37 --- /dev/null +++ b/plugins/woocommerce-admin/client/customize-store/design-without-ai/index.tsx @@ -0,0 +1,74 @@ +/** + * External dependencies + */ +import { useMachine, useSelector } from '@xstate/react'; +import { AnyInterpreter, Sender } from 'xstate'; +import { useEffect, useState } from '@wordpress/element'; + +/** + * Internal dependencies + */ +import { customizeStoreStateMachineEvents } from '..'; +import { + CustomizeStoreComponent, + customizeStoreStateMachineContext, +} from '../types'; +import { designWithNoAiStateMachineDefinition } from './state-machine'; +import { findComponentMeta } from '~/utils/xstate/find-component'; +import { AssembleHubLoader } from '../design-with-ai/pages'; + +export type DesignWithoutAiComponent = typeof AssembleHubLoader; +export type DesignWithoutAiComponentMeta = { + component: DesignWithoutAiComponent; +}; + +export const DesignWithNoAiController = ( { + parentMachine, +}: { + parentMachine?: AnyInterpreter; + sendEventToParent?: Sender< customizeStoreStateMachineEvents >; + parentContext?: customizeStoreStateMachineContext; +} ) => { + const [ , , service ] = useMachine( designWithNoAiStateMachineDefinition, { + devTools: process.env.NODE_ENV === 'development', + parent: parentMachine, + } ); + + // eslint-disable-next-line react-hooks/exhaustive-deps -- false positive due to function name match, this isn't from react std lib + const currentNodeMeta = useSelector( service, ( currentState ) => + findComponentMeta< DesignWithoutAiComponentMeta >( + currentState?.meta ?? undefined + ) + ); + + const [ CurrentComponent, setCurrentComponent ] = + useState< DesignWithoutAiComponent | null >( null ); + useEffect( () => { + if ( currentNodeMeta?.component ) { + setCurrentComponent( () => currentNodeMeta?.component ); + } + }, [ CurrentComponent, currentNodeMeta?.component ] ); + + return ( + <> +
+ { CurrentComponent ? :
} +
+ + ); +}; + +//loader should send event 'THEME_SUGGESTED' when it's done +export const DesignWithoutAi: CustomizeStoreComponent = ( { + parentMachine, + context, +} ) => { + return ( + <> + + + ); +}; diff --git a/plugins/woocommerce-admin/client/customize-store/design-without-ai/services.ts b/plugins/woocommerce-admin/client/customize-store/design-without-ai/services.ts new file mode 100644 index 00000000000..ff5d5121009 --- /dev/null +++ b/plugins/woocommerce-admin/client/customize-store/design-without-ai/services.ts @@ -0,0 +1,31 @@ +/** + * External dependencies + */ +import { Sender } from 'xstate'; +/** + * Internal dependencies + */ +import { updateTemplate } from '../data/actions'; +import { HOMEPAGE_TEMPLATES } from '../data/homepageTemplates'; + +const assembleSite = async () => { + await updateTemplate( { + homepageTemplateId: 'template1' as keyof typeof HOMEPAGE_TEMPLATES, + } ); +}; + +const browserPopstateHandler = + () => ( sendBack: Sender< { type: 'EXTERNAL_URL_UPDATE' } > ) => { + const popstateHandler = () => { + sendBack( { type: 'EXTERNAL_URL_UPDATE' } ); + }; + window.addEventListener( 'popstate', popstateHandler ); + return () => { + window.removeEventListener( 'popstate', popstateHandler ); + }; + }; + +export const services = { + assembleSite, + browserPopstateHandler, +}; diff --git a/plugins/woocommerce-admin/client/customize-store/design-without-ai/state-machine.tsx b/plugins/woocommerce-admin/client/customize-store/design-without-ai/state-machine.tsx new file mode 100644 index 00000000000..d497d7e0b14 --- /dev/null +++ b/plugins/woocommerce-admin/client/customize-store/design-without-ai/state-machine.tsx @@ -0,0 +1,111 @@ +/** + * External dependencies + */ +import { EventObject, createMachine } from 'xstate'; +import { getQuery } from '@woocommerce/navigation'; + +/** + * Internal dependencies + */ + +import { AssembleHubLoader } from '../design-with-ai/pages'; + +import { FlowType } from '../types'; +import { DesignWithoutAIStateMachineContext } from './types'; +import { services } from './services'; +import { actions } from './actions'; + +export const hasStepInUrl = ( + _ctx: unknown, + _evt: unknown, + { cond }: { cond: unknown } +) => { + const { path = '' } = getQuery() as { path: string }; + const pathFragments = path.split( '/' ); + return ( + pathFragments[ 2 ] === // [0] '', [1] 'customize-store', [2] design step slug + ( cond as { step: string | undefined } ).step + ); +}; + +export const designWithNoAiStateMachineDefinition = createMachine( + { + id: 'designWithoutAI', + predictableActionArguments: true, + preserveActionOrder: true, + schema: { + context: {} as DesignWithoutAIStateMachineContext, + events: {} as EventObject, + }, + invoke: { + src: 'browserPopstateHandler', + }, + on: { + EXTERNAL_URL_UPDATE: { + target: 'navigate', + }, + }, + context: { + startLoadingTime: null, + flowType: FlowType.noAI, + apiCallLoader: { + hasErrors: false, + }, + }, + initial: 'navigate', + states: { + navigate: { + always: [ + { + cond: { + type: 'hasStepInUrl', + step: 'design', + }, + target: 'preAssembleSite', + }, + ], + }, + preAssembleSite: { + type: 'parallel', + states: { + assembleSite: { + initial: 'pending', + states: { + pending: { + invoke: { + src: 'assembleSite', + onDone: { + target: 'done', + }, + onError: { + actions: [ 'assignAPICallLoaderError' ], + }, + }, + }, + done: { + type: 'final', + }, + }, + onDone: { + target: '#designWithoutAI.showAssembleHub', + }, + }, + }, + }, + showAssembleHub: { + meta: { + component: AssembleHubLoader, + }, + entry: [ 'redirectToAssemblerHub' ], + type: 'final', + }, + }, + }, + { + actions, + services, + guards: { + hasStepInUrl, + }, + } +); diff --git a/plugins/woocommerce-admin/client/customize-store/design-without-ai/types.ts b/plugins/woocommerce-admin/client/customize-store/design-without-ai/types.ts new file mode 100644 index 00000000000..1fc8e5863e5 --- /dev/null +++ b/plugins/woocommerce-admin/client/customize-store/design-without-ai/types.ts @@ -0,0 +1,12 @@ +/** + * Internal dependencies + */ +import { FlowType } from '../types'; + +export type DesignWithoutAIStateMachineContext = { + startLoadingTime: number | null; + apiCallLoader: { + hasErrors: boolean; + }; + flowType: FlowType.noAI; +}; diff --git a/plugins/woocommerce-admin/client/customize-store/index.tsx b/plugins/woocommerce-admin/client/customize-store/index.tsx index 8bafb258128..ddad8b381bf 100644 --- a/plugins/woocommerce-admin/client/customize-store/index.tsx +++ b/plugins/woocommerce-admin/client/customize-store/index.tsx @@ -28,6 +28,8 @@ import { actions as introActions, } from './intro'; import { DesignWithAi, events as designWithAiEvents } from './design-with-ai'; +import { DesignWithoutAi } from './design-without-ai'; + import { AssemblerHub, events as assemblerHubEvents } from './assembler-hub'; import { events as transitionalEvents, @@ -193,6 +195,13 @@ export const customizeStoreStateMachineDefinition = createMachine( { step: 'design-with-ai', }, }, + { + target: 'designWithoutAi', + cond: { + type: 'hasStepInUrl', + step: 'design', + }, + }, { target: 'assemblerHub', cond: { @@ -222,64 +231,59 @@ export const customizeStoreStateMachineDefinition = createMachine( { // eslint-disable-next-line xstate/prefer-always '': [ { - target: 'intro', + target: 'fetchIntroData', cond: 'isNotWooExpress', actions: 'assignNoAI', }, { - target: 'preIntro', + target: 'checkAiStatus', cond: 'isWooExpress', }, ], }, }, - preIntro: { - type: 'parallel', + checkAiStatus: { + initial: 'pending', states: { - checkAiStatus: { - initial: 'pending', - states: { - pending: { - invoke: { - src: 'fetchAiStatus', - onDone: { - actions: 'assignAiStatus', - target: 'success', - }, - onError: { - actions: 'assignAiOffline', - target: 'success', - }, - }, + pending: { + invoke: { + src: 'fetchAiStatus', + onDone: { + actions: 'assignAiStatus', + target: 'success', + }, + onError: { + actions: 'assignAiOffline', + target: 'success', }, - success: { type: 'final' }, }, }, - fetchIntroData: { - initial: 'pending', - states: { - pending: { - invoke: { - src: 'fetchIntroData', - onError: { - actions: - 'assignFetchIntroDataError', - target: 'success', - }, - onDone: { - target: 'success', - actions: [ - 'assignThemeData', - 'assignActiveThemeHasMods', - 'assignCustomizeStoreCompleted', - 'assignCurrentThemeIsAiGenerated', - ], - }, - }, + success: { type: 'final' }, + }, + onDone: 'fetchIntroData', + }, + fetchIntroData: { + initial: 'pending', + states: { + pending: { + invoke: { + src: 'fetchIntroData', + onError: { + actions: 'assignFetchIntroDataError', + target: 'success', + }, + onDone: { + target: 'success', + actions: [ + 'assignThemeData', + 'assignActiveThemeHasMods', + 'assignCustomizeStoreCompleted', + 'assignCurrentThemeIsAiGenerated', + ], }, - success: { type: 'final' }, }, }, + success: { type: 'final' }, }, onDone: 'intro', }, @@ -297,6 +301,10 @@ export const customizeStoreStateMachineDefinition = createMachine( { actions: [ 'recordTracksDesignWithAIClicked' ], target: 'designWithAi', }, + DESIGN_WITHOUT_AI: { + actions: [ 'recordTracksDesignWithAIClicked' ], + target: 'designWithoutAi', + }, SELECTED_NEW_THEME: { actions: [ 'recordTracksThemeSelected' ], target: 'appearanceTask', @@ -313,6 +321,22 @@ export const customizeStoreStateMachineDefinition = createMachine( { }, }, }, + designWithoutAi: { + initial: 'preDesignWithoutAi', + states: { + preDesignWithoutAi: { + always: { + target: 'designWithoutAi', + }, + }, + designWithoutAi: { + entry: [ { type: 'updateQueryStep', step: 'design' } ], + meta: { + component: DesignWithoutAi, + }, + }, + }, + }, designWithAi: { initial: 'preDesignWithAi', states: { diff --git a/plugins/woocommerce-admin/client/customize-store/intro/index.tsx b/plugins/woocommerce-admin/client/customize-store/intro/index.tsx index 50609e6cf8f..1eb358cdbd7 100644 --- a/plugins/woocommerce-admin/client/customize-store/intro/index.tsx +++ b/plugins/woocommerce-admin/client/customize-store/intro/index.tsx @@ -30,7 +30,7 @@ import { DefaultBanner, ExistingAiThemeBanner, ExistingThemeBanner, - CoreBanner, + NoAIBanner, } from './intro-banners'; export type events = @@ -39,7 +39,8 @@ export type events = | { type: 'CLICKED_ON_BREADCRUMB' } | { type: 'SELECTED_BROWSE_ALL_THEMES' } | { type: 'SELECTED_ACTIVE_THEME'; payload: { theme: string } } - | { type: 'SELECTED_NEW_THEME'; payload: { theme: string } }; + | { type: 'SELECTED_NEW_THEME'; payload: { theme: string } } + | { type: 'DESIGN_WITHOUT_AI' }; export * as actions from './actions'; export * as services from './services'; @@ -52,7 +53,7 @@ const BANNER_COMPONENTS = { 'jetpack-offline': JetpackOfflineBanner, 'existing-ai-theme': ExistingAiThemeBanner, 'existing-theme': ExistingThemeBanner, - [ FlowType.noAI ]: CoreBanner, + [ FlowType.noAI ]: NoAIBanner, default: DefaultBanner, }; diff --git a/plugins/woocommerce-admin/client/customize-store/intro/intro-banners.tsx b/plugins/woocommerce-admin/client/customize-store/intro/intro-banners.tsx index 56385f87180..498986906c9 100644 --- a/plugins/woocommerce-admin/client/customize-store/intro/intro-banners.tsx +++ b/plugins/woocommerce-admin/client/customize-store/intro/intro-banners.tsx @@ -21,6 +21,7 @@ export const BaseIntroBanner = ( { bannerTitle, bannerText, bannerClass, + showAIDisclaimer, buttonIsLink, bannerButtonOnClick, bannerButtonText, @@ -30,6 +31,7 @@ export const BaseIntroBanner = ( { bannerTitle: string; bannerText: string; bannerClass: string; + showAIDisclaimer: boolean; buttonIsLink?: boolean; bannerButtonOnClick?: () => void; bannerButtonText?: string; @@ -58,23 +60,25 @@ export const BaseIntroBanner = ( { ) } { secondaryButton } -

- { interpolateComponents( { - mixedString: __( - 'Powered by experimental AI. {{link}}Learn more{{/link}}', - 'woocommerce' - ), - components: { - link: ( - + { showAIDisclaimer && ( +

+ { interpolateComponents( { + mixedString: __( + 'Powered by experimental AI. {{link}}Learn more{{/link}}', + 'woocommerce' ), - }, - } ) } -

+ components: { + link: ( + + ), + }, + } ) } +

+ ) }
{ children } @@ -95,6 +99,7 @@ export const NetworkOfflineBanner = () => { ) } bannerClass="offline-banner" bannerButtonOnClick={ () => {} } + showAIDisclaimer={ true } /> ); }; @@ -122,6 +127,7 @@ export const JetpackOfflineBanner = ( { } ); } } bannerButtonText={ __( 'Find out how', 'woocommerce' ) } + showAIDisclaimer={ true } /> ); }; @@ -147,6 +153,7 @@ export const ExistingThemeBanner = ( { setOpenDesignChangeWarningModal( true ); } } bannerButtonText={ __( 'Design with AI', 'woocommerce' ) } + showAIDisclaimer={ true } /> ); }; @@ -174,6 +181,7 @@ export const DefaultBanner = ( { } ); } } bannerButtonText={ __( 'Design with AI', 'woocommerce' ) } + showAIDisclaimer={ true } /> ); }; @@ -199,11 +207,16 @@ export const ThemeHasModsBanner = ( { setOpenDesignChangeWarningModal( true ); } } bannerButtonText={ __( 'Design with AI', 'woocommerce' ) } + showAIDisclaimer={ true } /> ); }; -export const CoreBanner = () => { +export const NoAIBanner = ( { + sendEvent, +}: { + sendEvent: React.ComponentProps< typeof Intro >[ 'sendEvent' ]; +} ) => { return ( { 'Quickly create a beautiful store using our built-in store designer. Choose your layout, select a style, and much more.', 'woocommerce' ) } - bannerClass="core-banner" - bannerButtonOnClick={ () => {} } + bannerClass="no-ai-banner" + bannerButtonText={ __( 'Start designing', 'woocommerce' ) } + bannerButtonOnClick={ () => { + sendEvent( { + type: 'DESIGN_WITHOUT_AI', + } ); + } } + showAIDisclaimer={ false } /> ); }; @@ -260,6 +279,7 @@ export const ExistingAiThemeBanner = ( { } } bannerButtonText={ __( 'Customize', 'woocommerce' ) } secondaryButton={ secondaryButton } + showAIDisclaimer={ true } >
diff --git a/plugins/woocommerce/changelog/43457-43420-cys-core-update-homepage-with-default-patterns-when-the-assembler-is-loaded b/plugins/woocommerce/changelog/43457-43420-cys-core-update-homepage-with-default-patterns-when-the-assembler-is-loaded new file mode 100644 index 00000000000..747a6030baf --- /dev/null +++ b/plugins/woocommerce/changelog/43457-43420-cys-core-update-homepage-with-default-patterns-when-the-assembler-is-loaded @@ -0,0 +1,4 @@ +Significance: minor +Type: add + +[CYS - Core] Update the homepage with default patterns when the assembler is loaded. \ No newline at end of file