Разработка блока Гутенберга: сохраняется только одно содержимое RichText

Я добавил в свой блок два RichText компонента.

registerBlockType( 'hallmark/gray-content-container', {
        title: __( 'Gray Content Container' ),
        icon: 'grid-view',
        category: 'hallmark-blocks',
        keywords: [
            __( 'Hallmark gray content' ),
            __( 'Hallmark' ),
            __( 'Gray content container' ),
        ],

        attributes:{
            contentHeading: {
                type: 'string',
                source: 'children',
                selector: 'h1,h2,h3,h4,h5,h6'
            },
            textContent: {
                type: 'string'
            }
        },

        edit: function( props ) {

            var textContent = props.attributes.textContent;
            var contentHeading = props.attributes.contentHeading;

            function onChangeTextContent( content ) {
                props.setAttributes( { textContent: content } );
            }

            function onChangeHeading (heading) {
                props.setAttributes( { contentHeading: heading} );
            }

            return (
                <div className={ props.className }>
                    <label className="editor-content-section-label">Content for gray section</label>
                    <RichText
                        tagName="h1"
                        value={contentHeading}
                        onChange={onChangeHeading}
                        placeholder={ __( 'Add a heading' ) }
                        keepPlaceholderOnFocus
                    />
                    <RichText
                        tagName="p"
                        className={props.className}
                        onChange={onChangeTextContent}
                        value={textContent}
                        placeholder={ __( 'Add content' ) }
                        keepPlaceholderOnFocus
                    />
                </div>
            );
        },

        save: function( props ) {
            //return null;
            return(
                <div className={props.className}>
                    <div className="gray-bg">
                        <div className="constrain content">
                            <RichText.Content tagName="h1" value={ attributes.contentHeading } />
                            <RichText.Content tagName="p" value={ attributes.textContent } />
                        </div>
                    </div>
                </div>
            );

        },
    } );

Я пробовал два разных подхода к сохранению данных.

Использование функции save() по умолчанию

save: function( props ) {
      return(
         <div className={props.className}>
            <div className="gray-bg">
                <div className="constrain content">
                    <RichText.Content tagName="h1" value={ attributes.contentHeading } />
                    <RichText.Content tagName="p" value={ attributes.textContent } />
                 </div>
            </div>
         </div>
     );
},

Сохранение в PHP:

Использование метода render_callback (Использование return null; из функции save() по умолчанию блока.

register_block_type( 'hallmark/white-content-container', array(
    'render_callback' => 'hall_render_white_content'
) );

function hall_render_white_content( $atts ) {
   $heading = $atts['contentHeading'];
   $raw_content = $atts['textContent'];
   $full_content = $heading . $raw_content;
   // var_dump($full_content);

   $content = hall_clean_shortcode_block_content( $full_content );

   return '<div class="gray-bg"><div class="constrain content">' . $content . '</div></div>';
}

Элемент atts['contentHeading'] вообще не существует в массиве $atts. Когда я проверяю var_dump( $attas );, присутствует textContentelement.

Проблема в том, что оба подхода сохраняют только textContent. contentHeading совсем не спасает.

Что мне не хватает?


person Subrata Sarkar    schedule 28.02.2019    source источник
comment
Для отладки используйте console.log(props.attributes) внутри вашей функции редактирования и наблюдайте, изменяются ли значения contentHeading при редактировании. edit() функция будет вызываться каждый раз при изменении состояния или свойств компонента. По моему счастливому предположению, источником contentHeading должен быть «текст», а не «дети».   -  person Mehmood Ahmad    schedule 05.03.2019
comment
Вы спасли мою жизнь. Большое спасибо @MehmoodAhmad :)   -  person Subrata Sarkar    schedule 05.03.2019
comment
Рад вот что. Добавив ниже правильный ответ для других, примите это, чтобы он мог помочь другим.   -  person Mehmood Ahmad    schedule 05.03.2019
comment
Один вопрос. Хотел сохранить со стороны сервера с помощью render_callback. Моя функция function hall_render_gray_content( $atts ) {...}. Но он никогда не получает значение $atts['contentHeading'];, даже когда он у меня есть. Когда я пытаюсь это сделать, появляется красное Publish error уведомление. Что может быть причиной?   -  person Subrata Sarkar    schedule 05.03.2019
comment
Извините, я не работал с serverSideRendering до сих пор. Я выяснил, что в основном нам не нужно serverSideRendering. Не могли бы вы объяснить, почему вы это используете, чтобы мы могли обсудить, нужно ли вам это или нет. Нам нужен рендеринг на стороне сервера только тогда, когда наш живой контент меняется со временем, как и наши последние сообщения, если контент статичен и нам нужно только редактировать его из бэкэнда, тогда нет необходимости в рендеринге на стороне сервера.   -  person Mehmood Ahmad    schedule 05.03.2019
comment
Я не использую компонент serverSideRendering. Я написал подход в моем исходном вопросе, помеченном как Сохранение его в PHP.   -  person Subrata Sarkar    schedule 05.03.2019
comment
вы используете acf?   -  person Mehmood Ahmad    schedule 05.03.2019
comment
нет. в нем нет настраиваемых полей.   -  person Subrata Sarkar    schedule 05.03.2019
comment
Хорошо, тогда это серверный блок рендеринга, и у меня до сих пор нет опыта с ним. Для получения информации просмотрите последний пост-компонент Gutenberg из репозитория GitHub, потому что он поможет вам найти проблему.   -  person Mehmood Ahmad    schedule 05.03.2019
comment
сегодня я работал с динамическими блоками и столкнулся с той же проблемой. Я заметил, что я получу значения, только если обновлю атрибуты хотя бы один раз через setAttributes. Вы уверены, что делаете это?   -  person Mehmood Ahmad    schedule 07.03.2019


Ответы (2)


Для отладки используйте console.log(props.attributes) внутри вашей функции редактирования и наблюдайте, изменяются ли значения contentHeading при редактировании. Функция edit () будет вызываться каждый раз при изменении состояния или свойств компонента. По моему счастливому предположению, источником contentHeading должен быть текст вместо children.

person Mehmood Ahmad    schedule 05.03.2019

Попробуйте установить

attributes:{ contentHeading: { type: 'string', source: 'children', selector: 'h1' }, textContent: { type: 'string' selector: 'p' } },

Я думаю, что селекторы должны точно соответствовать тому, что установлено в методе save.

<div className="constrain content"> <RichText.Content tagName="h1" value={ attributes.contentHeading } /> <RichText.Content tagName="p" value={ attributes.textContent } /> </div>

Я думаю, вам также нужен уникальный селектор, поэтому, если у вас есть два абзаца RichText, вы можете сделать

textContentA: { type: 'string' selector: 'p.content-a' } textContentB: { type: 'string' selector: 'p.content-b' }

person user2835033    schedule 09.03.2019