Building a Featured Gallery component for Gutenberg

Question

I’m building a Featured Gallery component for Gutenberg. As a guide, I’m using the existing Featured Image component from Gutenberg. Basically, instead of storing a single image id, the component stores an array of image ids in a dedicated meta field (of type array) called _featured_gallery.
Apparently, the getting and setting part is working, but I’m unable to show the grid of selected images (the featured-gallery-grid part in the code).
Any ideas? My knowledge of Gutenberg and React is limited, so I’m a bit lost here. Any help would be appreciated.

FeaturedGallery:

/**
 * WordPress dependencies
 */
const { __ } = wp.i18n;
const {
    BaseControl,
    Button,
    withNotices,
} = wp.components;
const { compose } = wp.compose;
const { withSelect, withDispatch } = wp.data;
const { MediaUpload, MediaUploadCheck }  = wp.blockEditor;

/**
 * Internal dependencies
 */

import GalleryImage from './';

const ALLOWED_MEDIA_TYPES = [ 'image' ];

function FeaturedGallery( {
    currentPostId,
    featuredGalleryIds,
    onUpdateGallery,
    noticeUI,
} ) {
    const instructions = (
        <p>
            { __(
                'To edit the featured gallery, you need permission to upload media.', 'my-featured-gallery'
            ) }
        </p>
    );

    return (
        <BaseControl
            className="my-featured-gallery"
        >
            { noticeUI }
            <div className="editor-post-featured-gallery">
                <MediaUploadCheck fallback={ instructions }>
                    <div className="editor-post-featured-gallery__container">
                        { !! featuredGalleryIds && (
                            <ul className="featured-gallery-grid">
                            { featuredGalleryIds.forEach( ( img, index ) => {
                                <GalleryImage
                                    id={ img }
                                />
                            } ) }
                            </ul>
                        ) }
                    </div>
                    <MediaUpload
                        title={ __( 'Featured gallery', 'my-featured-gallery' ) }
                        multiple
                        onSelect={ onUpdateGallery }
                        allowedTypes={ ALLOWED_MEDIA_TYPES }
                        render={ ( { open } ) => (
                                <Button
                                    onClick={ open }
                                    isSecondary
                                >
                                    { 
                                        __( 'Add gallery images', 'my-featured-gallery' )
                                    }
                                </Button>
                        ) }
                        value={ featuredGalleryIds }
                    />
                </MediaUploadCheck>
            </div>
        </BaseControl>            
    );
}

const applyWithSelect = withSelect( ( select ) => {
    const { getPostType } = select( 'core' );
    const { getCurrentPostId, getEditedPostAttribute } = select(
        'core/editor'
    );
    const meta = getEditedPostAttribute( 'meta' );
    const featuredGalleryIds = meta._featured_gallery;

    return {
        currentPostId: getCurrentPostId(),
        postType: getPostType( getEditedPostAttribute( 'type' ) ),
        featuredGalleryIds,
    };
} );

const applyWithDispatch = withDispatch( ( dispatch ) => {
        const { editPost } = dispatch( 'core/editor' );
        return {
            onUpdateGallery( images ) {
                const items = images.map( ( item ) => item['id'] );
                const meta = { _featured_gallery: items };
                editPost( { meta } );
            },
        };
    }
);

export default compose(
    withNotices,
    applyWithSelect,
    applyWithDispatch,
)( FeaturedGallery );

GalleryImage:

/**
 * WordPress dependencies
 */
const { withSelect } = wp-data;
const { compose } = wp-compose;

/**
 * Internal dependencies
 */

function GalleryImage( {
    image,
} ) {

    return (
        <figure>
            { image && ( <div className="img-container">
                <img
                    src={ image.media_details.sizes.thumbnail.source_url }
                    width={ image.media_details.sizes.thumbnail.width }
                    height={ image.media_details.sizes.thumbnail.height }
                    alt={ __( 'Thumbnail of the image.', 'my-featured-gallery' ) }
                    style={ {
                        display: 'block',
                        marginBottom: '8px',
                    } }
                />
            </div> ) }
        </figure>
    );

}

const applyWithSelect = withSelect( ( select, ownProps ) => {
    const { getMedia } = select( 'core' );
    const { id } = ownProps;
    return {
        image: id ? getMedia( parseInt( id, 10 ) ) : null,
    };
} );
    
export default compose( [
    applyWithSelect
] )( GalleryImage );
0
, , leemon 1 year 2020-07-11T06:10:20-05:00 0 Answers 65 views 0

Leave an answer

Browse
Browse