diff --git a/projects/plugins/jetpack/changelog/update-jetpack-ai-image-image-block-entrypoint b/projects/plugins/jetpack/changelog/update-jetpack-ai-image-image-block-entrypoint new file mode 100644 index 0000000000000..661378aac3046 --- /dev/null +++ b/projects/plugins/jetpack/changelog/update-jetpack-ai-image-image-block-entrypoint @@ -0,0 +1,4 @@ +Significance: minor +Type: other + +Jetpack AI Image: include new entrypoint as a button on the image/gallery/slideshow block. diff --git a/projects/plugins/jetpack/extensions/plugins/ai-assistant-plugin/components/ai-image/index.ts b/projects/plugins/jetpack/extensions/plugins/ai-assistant-plugin/components/ai-image/index.ts index 96dae8e4fb4e2..8eda7aef961f4 100644 --- a/projects/plugins/jetpack/extensions/plugins/ai-assistant-plugin/components/ai-image/index.ts +++ b/projects/plugins/jetpack/extensions/plugins/ai-assistant-plugin/components/ai-image/index.ts @@ -1,5 +1,10 @@ import FeaturedImage from './featured-image'; import GeneralPurposeImage from './general-purpose-image'; -import { PLACEMENT_MEDIA_SOURCE_DROPDOWN } from './types'; +import { PLACEMENT_MEDIA_SOURCE_DROPDOWN, PLACEMENT_BLOCK_PLACEHOLDER_BUTTON } from './types'; -export { FeaturedImage, PLACEMENT_MEDIA_SOURCE_DROPDOWN, GeneralPurposeImage }; +export { + FeaturedImage, + PLACEMENT_MEDIA_SOURCE_DROPDOWN, + PLACEMENT_BLOCK_PLACEHOLDER_BUTTON, + GeneralPurposeImage, +}; diff --git a/projects/plugins/jetpack/extensions/plugins/ai-assistant-plugin/components/ai-image/types.ts b/projects/plugins/jetpack/extensions/plugins/ai-assistant-plugin/components/ai-image/types.ts index effb62dd27e07..f0c0c5ae3d125 100644 --- a/projects/plugins/jetpack/extensions/plugins/ai-assistant-plugin/components/ai-image/types.ts +++ b/projects/plugins/jetpack/extensions/plugins/ai-assistant-plugin/components/ai-image/types.ts @@ -3,3 +3,4 @@ export const GENERAL_IMAGE_FEATURE_NAME = 'general-image' as const; export const IMAGE_GENERATION_MODEL_STABLE_DIFFUSION = 'stable-diffusion' as const; export const IMAGE_GENERATION_MODEL_DALL_E_3 = 'dall-e-3' as const; export const PLACEMENT_MEDIA_SOURCE_DROPDOWN = 'media-source-dropdown' as const; +export const PLACEMENT_BLOCK_PLACEHOLDER_BUTTON = 'block-placeholder-button' as const; diff --git a/projects/plugins/jetpack/extensions/shared/external-media/constants.js b/projects/plugins/jetpack/extensions/shared/external-media/constants.js index 731b27676c815..43e68812377e7 100644 --- a/projects/plugins/jetpack/extensions/shared/external-media/constants.js +++ b/projects/plugins/jetpack/extensions/shared/external-media/constants.js @@ -8,7 +8,10 @@ export const SOURCE_OPENVERSE = 'openverse'; export const SOURCE_PEXELS = 'pexels'; export const SOURCE_JETPACK_APP_MEDIA = 'jetpack_app_media'; export const SOURCE_JETPACK_AI_FEATURED_IMAGE = 'jetpack_ai_featured_image'; -export const SOURCE_JETPACK_AI_GENERAL_PURPOSE_IMAGE = 'jetpack_ai_general_purpose_image'; +export const SOURCE_JETPACK_AI_GENERAL_PURPOSE_IMAGE_FOR_MEDIA_SOURCE = + 'jetpack_ai_general_purpose_image_for_media_source'; +export const SOURCE_JETPACK_AI_GENERAL_PURPOSE_IMAGE_FOR_BLOCK = + 'jetpack_ai_general_purpose_image_for_block'; export const PATH_RECENT = 'recent'; export const PATH_ROOT = '/'; diff --git a/projects/plugins/jetpack/extensions/shared/external-media/editor.scss b/projects/plugins/jetpack/extensions/shared/external-media/editor.scss index b66031d31ebb7..deaa53f64996f 100644 --- a/projects/plugins/jetpack/extensions/shared/external-media/editor.scss +++ b/projects/plugins/jetpack/extensions/shared/external-media/editor.scss @@ -558,15 +558,17 @@ $grid-size: 8px; } } +// Set the wrapper as a flex container to allow displaying multiple buttons side by side. +.jetpack-external-media-button-wrapper { + display: flex; +} + // Reset placeholder button margin. .components-placeholder__fieldset, .editor-post-featured-image { .components-dropdown .jetpack-external-media-button-menu { width: auto; - margin-right: 8px; margin-bottom: 1em; - padding-left: 6px; - padding-right: 6px; > svg { display: none; diff --git a/projects/plugins/jetpack/extensions/shared/external-media/media-button/index.js b/projects/plugins/jetpack/extensions/shared/external-media/media-button/index.js index 48018e8a2f521..be15c29bb2a44 100644 --- a/projects/plugins/jetpack/extensions/shared/external-media/media-button/index.js +++ b/projects/plugins/jetpack/extensions/shared/external-media/media-button/index.js @@ -1,5 +1,7 @@ +import { useBlockEditContext } from '@wordpress/block-editor'; import { useState } from '@wordpress/element'; import { getExternalLibrary } from '../sources'; +import MediaAiButton from './media-ai-button'; import MediaButtonMenu from './media-menu'; const isFeaturedImage = props => @@ -7,10 +9,25 @@ const isFeaturedImage = props => ( props.modalClass && props.modalClass.indexOf( 'featured-image' ) !== -1 ); const isReplaceMenu = props => props.multiple === undefined && ! isFeaturedImage( props ); +const blocksWithAiButtonSupport = [ 'core/image', 'core/gallery', 'jetpack/slideshow' ]; + +/** + * Temporary feature flag to control generalPurposeImageExclusiveMediaSources + * visibility. + */ +const GENERAL_PURPOSE_IMAGE_GENERATOR_BETA_FLAG = 'ai-general-purpose-image-generator'; +const isGeneralPurposeImageGeneratorBetaEnabled = + window?.Jetpack_Editor_Initial_State?.available_blocks?.[ + GENERAL_PURPOSE_IMAGE_GENERATOR_BETA_FLAG + ]?.available === true; + function MediaButton( props ) { + const { name } = useBlockEditContext(); const { mediaProps } = props; const [ selectedSource, setSelectedSource ] = useState( null ); const ExternalLibrary = getExternalLibrary( selectedSource ); + const isFeatured = isFeaturedImage( mediaProps ); + const hasAiButtonSupport = blocksWithAiButtonSupport.includes( name ); const closeLibrary = event => { if ( event ) { @@ -29,14 +46,20 @@ function MediaButton( props ) { return ( // No added functionality, just capping event propagation. // eslint-disable-next-line jsx-a11y/click-events-have-key-events, jsx-a11y/no-static-element-interactions -