• Resolved Jamie

    (@rabillion)


    i’ve an own custom field to select a date from dropdown lists and i would like save the value to an hidden field. But the field is only updating after a second time saving the post

    here is my code:

    public function cmb2_render_date_select_field_callback( $field, $value, $object_id, $object_type, $field_type ) {
    
            // make sure we specify each part of the value we need.
            $value = wp_parse_args( $value, array(
                'day'           => '',
                'month'         => '',
                'year'          => '',
                'datetimestamp' => '',
            ) );
    
            ?>
            <div class="alignleft">
                <?php echo $field_type->select( array(
                    'name'    => $field_type->_name( '[day]' ),
                    'id'      => $field_type->_id( '_day' ),
                    'options' => self::cmb2_get_day_options( $value['day'] ),
                    'desc'    => '',
                    'class'   => 'form-control',
                ) );
                ?>
            </div>
            <div class="alignleft">
                <?php echo $field_type->select( array(
                    'name'    => $field_type->_name( '[month]' ),
                    'id'      => $field_type->_id( '_month' ),
                    'options' => self::cmb2_get_month_options( $value['month'] ),
                    'desc'    => '',
                    'class'   => 'form-control',
                ) );
    
                ?>
            </div>
            <div class="alignleft">
                <?php echo $field_type->select( array(
                    'name'    => $field_type->_name( '[year]' ),
                    'id'      => $field_type->_id( '_year' ),
                    'options' => self::cmb2_get_year_options( $value['year'] ),
                    'desc'    => '',
                    'class'   => 'form-control',
                ) );
                ?>
            </div>
            <div class="alignleft hidden">
                <?php echo $field_type->input( array(
                    'name'  => $field_type->_name( '[datetimestamp]' ),
                    'id'    => $field_type->_id( '_datetimestamp' ),
                    'value' => strtotime( $value['day'] . '-' . $value['month'] . '-' . $value['year'] ),
                    'type'  => 'hidden',
                ) ); ?>
            </div>
    
            <div class="alignleft">
                <input type="hidden">
            </div>
            <br class="clear">
            <?php
            echo $field_type->_desc( true );
    
        }
    public function cmb2_sanitize_date_select_field_callback( $override_value, $value, $object_id, $field_args ) {
            if ( empty( $field_args['wp_date_end_datetimestamp'] ) && ( isset( $value['day'] ) && isset( $value['month'] ) && isset( $value['year'] ) ) ) {
                $datetimestamp = strtotime( $value['day'] . '-' . $value['month'] . '-' . $value['year'] );
                update_post_meta( $object_id, 'wp_date_end_datetimestamp', $datetimestamp );
            }
            return $value;
        }
    • This topic was modified 8 years, 1 month ago by Jamie.
Viewing 7 replies - 1 through 7 (of 7 total)
  • Plugin Contributor Michael Beckwith

    (@tw2113)

    The BenchPresser

    Can you provide the complete CMB2 configuration, something that I could install/activate or load via a php include() ?

    From what I recall, hidden fields can be surprisingly tricky. Curious if part of cmb2_sanitize_date_select_field_callback isn’t set quite yet until the 2nd save

    Thread Starter Jamie

    (@rabillion)

    <?php
    
    namespace Copa\CustomFields;
    
    use Copa;
    
    /**
     * Class EventFields
     *
     * @package Copa\EventFields
     *
     */
    class EventFields {
    
        private static $prefix = Copa\PREFIX;
    
        /**
         * Initiate our hooks.
         */
        public static function init() {
    
            // Split seaialized String and saves meta for the object.
            add_filter( 'cmb2_override_meta_save', array( MetaSplit::instance(), 'meta_save' ), 100, 3 );
            add_action( 'cmb2_init', array( __CLASS__, '_register_events_formfields_metabox' ) );
            add_filter( 'cmb2_render_date_select', array( __CLASS__, 'cmb2_render_date_select_field_callback' ), 10, 5 );
    
            add_filter( 'cmb2_sanitize_date_select', array(
                __CLASS__,
                'cmb2_sanitize_date_select_field_callback',
            ), 10, 4 );
    
        }
    
        /**
         * events field
         * Hook in and add a metabox to select templates
         */
        public function _register_events_formfields_metabox() {
            $metabox = new_cmb2_box( array(
                'id'           => self::$prefix . 'eventform',
                'title'        => __( 'Termine', 'copa' ),
                'object_types' => array( 'events_posts', ),
                'classes'      => 'event-form',
                'show_names'   => true,
                'cmb_styles'   => false,
                'fields'       => array(
                    array(
                        'name'       => __( 'Ragulary Event', 'copa' ),
                        'id'         => self::$prefix . 'date_regular',
                        'type'       => 'checkbox',
                        'attributes' => array(
                            'class' => 'checkbox',
                        ),
                    ),
                    array(
                        'name'       => __( 'Email *', 'copa' ),
                        'id'         => self::$prefix . 'email',
                        'type'       => 'text_email',
                        'attributes' => array(
                            'required' => 'required',
                            'class'    => 'form-control',
                        ),
                    ),
                    array(
                        'name'       => __( 'Phone', 'copa' ),
                        'id'         => self::$prefix . 'phone',
                        'type'       => 'text',
                        'attributes' => array(
                            'class' => 'form-control',
                        ),
                    ),
                    array(
                        'name'       => __( 'Website', 'copa' ),
                        'id'         => self::$prefix . 'text_url',
                        'type'       => 'text_url',
                        'protocols'  => array( 'http', 'https' ),
                        'attributes' => array(
                            'class' => 'form-control',
                        ),
                    ),
                    array(
                        'name' => __( 'Date from', 'copa' ),
                        'id'   => self::$prefix . 'date_start',
                        'type' => 'date_select',
                    ),
                    array(
                        'name'    => __( 'Date to', 'copa' ),
                        'id'      => self::$prefix . 'date_end',
                        'type'    => 'date_select',
                        'default' => 'save_timestamp',
                    ),
                    array(
                        'name'         => 'Google Maps *',
                        'id'           => self::$prefix . 'location',
                        'type'         => 'pw_map',
                        'split_values' => true, // Save latitude and longitude as two separate fields
                        'attributes'   => array(
                            'placeholder' => __( 'Please enter your address', 'copa' ),
                            'required'    => 'required',
                        ),
                    ),
                ),
            ) );
            if ( !is_admin() ) {
                $metabox->add_field( array(
                    'name'       => __( 'Titel *', 'copa' ),
                    'id'         => self::$prefix . 'title',
                    'type'       => 'text',
                    'attributes' => array(
                        'autocomplete' => 'off',
                        'required'     => 'required',
                    ),
                ), 1 );
                $metabox->add_field( array(
                    'name'       => __( 'Text *', 'copa' ),
                    'id'         => self::$prefix . 'content',
                    'type'       => 'textarea',
                    'options'    => array(
                        'textarea_rows' => 12,
                    ),
                    'attributes' => array(
                        'maxlength' => '900',
                        'cols'      => '70',
                        'required'  => 'required',
                    ),
                ), 2 );
                $metabox->add_field( array(
                    'id'         => 'form_type',
                    'type'       => 'hidden',
                    'attributes' => array(
                        'value' => 'event',
                    ),
                ), 8 );
            }
        }
    
        /**
         * Returns options markup for a month select field.
         *
         * @param  mixed $value Selected/saved month
         *
         * @return string       html string containing all month options
         */
        public function cmb2_get_month_options( $value ) {
            $month_list = array(
                '01' => __( 'January', 'copa' ),
                '02' => __( 'February', 'copa' ),
                '03' => __( 'March', 'copa' ),
                '04' => __( 'April', 'copa' ),
                '05' => __( 'May', 'copa' ),
                '06' => __( 'June', 'copa' ),
                '07' => __( 'July', 'copa' ),
                '08' => __( 'August', 'copa' ),
                '09' => __( 'September', 'copa' ),
                '10' => __( 'October', 'copa' ),
                '11' => __( 'November', 'copa' ),
                '12' => __( 'December', 'copa' ),
            );
    
            $month_options = '';
            $month_options .= '<option disabled selected>' . __( 'Month', 'copa' ) . '</option>';
            foreach ( $month_list as $key => $month ) {
                $month_options .= '<option value="' . $key . '" ' . selected( $value, $key, false ) . '>' . $month . '</option>';
            }
    
            return $month_options;
        }
    
        /**
         * Returns options markup for a day select field.
         *
         * @param  mixed $value Selected/saved day
         *
         * @return string       html string containing all day options
         */
        public function cmb2_get_day_options( $value ) {
            $day_list    = range( 1, 31 );
            $day_options = '';
    
            $day_options .= '<option disabled selected>' . __( 'Day', 'copa' ) . '</option>';
            foreach ( $day_list as $day ) {
                $day_options .= '<option value="' . $day . '" ' . selected( $value, $day, false ) . '>' . $day . '</option>';
            }
    
            return $day_options;
        }
    
        /**
         * Returns options markup for a year select field.
         *
         * @param  mixed $value Selected/saved year
         *
         * @return string       html string containing all year options
         */
        public function cmb2_get_year_options( $value ) {
    
            $curyear      = date( 'Y' );
            $year_list    = range( $curyear, $curyear + 5 );
            $year_options = '';
    
            $year_options .= '<option disabled selected>' . __( 'Year', 'copa' ) . '</option>';
            foreach ( $year_list as $year ) {
                $year_options .= '<option value="' . $year . '" ' . selected( $value, $year, false ) . '>' . $year . '</option>';
            }
    
            return $year_options;
        }
    
        /**
         * Render Date Field.
         * @see https://github.com/WebDevStudios/CMB2/wiki/Adding-your-own-field-types#example-4-multiple-inputs-one-field-lets-create-an-address-field
         *
         * @param $field
         * @param $value
         * @param $object_id
         * @param $object_type
         * @param $field_type
         */
        public function cmb2_render_date_select_field_callback( $field, $value, $object_id, $object_type, $field_type ) {
    
            // make sure we specify each part of the value we need.
            $value = wp_parse_args( $value, array(
                'day'           => '',
                'month'         => '',
                'year'          => '',
                'datetimestamp' => '',
            ) );
    
            ?>
            <div class="alignleft">
                <?php echo $field_type->select( array(
                    'name'    => $field_type->_name( '[day]' ),
                    'id'      => $field_type->_id( '_day' ),
                    'options' => self::cmb2_get_day_options( $value['day'] ),
                    'desc'    => '',
                    'class'   => 'form-control',
                ) );
                ?>
            </div>
            <div class="alignleft">
                <?php echo $field_type->select( array(
                    'name'    => $field_type->_name( '[month]' ),
                    'id'      => $field_type->_id( '_month' ),
                    'options' => self::cmb2_get_month_options( $value['month'] ),
                    'desc'    => '',
                    'class'   => 'form-control',
                ) );
                ?>
            </div>
            <div class="alignleft">
                <?php echo $field_type->select( array(
                    'name'    => $field_type->_name( '[year]' ),
                    'id'      => $field_type->_id( '_year' ),
                    'options' => self::cmb2_get_year_options( $value['year'] ),
                    'desc'    => '',
                    'class'   => 'form-control',
                ) );
                ?>
            </div>
            <?php
            $day   = isset( $value['day'] ) ? $value['day'] : '';
            $month = isset( $value['month'] ) ? $value['month'] : '';
            $year  = isset( $value['year'] ) ? $value['year'] : '';
            ?>
            <div class="alignleft hidden">
                <?php echo $field_type->input( array(
                    'name'  => $field_type->_name( '[datetimestamp]' ),
                    'id'    => $field_type->_id( '_datetimestamp' ),
                    'value' => strtotime( $day . '-' . $month . '-' . $year ),
                    'type'  => 'hidden',
                ) ); ?>
            </div>
    
            <div class="alignleft">
                <input type="hidden">
            </div>
            <br class="clear">
            <?php
            echo $field_type->_desc( true );
    
        }
    
        /**
         * Save the datetimestap if end date not exist.
         * 
         * @param $override_value
         * @param $value
         * @param $object_id
         * @param $field_args
         *
         * @return mixed
         */
        public function cmb2_sanitize_date_select_field_callback( $override_value, $value, $object_id, $field_args ) {
    
            if ( empty( $field_args['kradblatt_date_regular'] ) && ( isset( $value['datetimestamp'] ) && ( isset( $value['day'] ) && isset( $value['month'] ) && isset( $value['year'] ) ) ) ) {
                $datetimestamp = strtotime( $value['datetimestamp'] );
                update_post_meta( $object_id, 'kradblatt_date_end_datetimestamp', $datetimestamp );
            }
    
            return $value;
        }
    }
    Plugin Contributor Michael Beckwith

    (@tw2113)

    The BenchPresser

    From what I can see, the strtotime() call in cmb2_sanitize_date_select_field_callback() is returning false. It looks like the value is already a UTC timestamp, and wouldn’t need to be re-converted.

    Also, based on what I’m experiencing, I’m seeing filled in hidden values after 1 click of update: https://cloudup.com/cobS0CBuOBE

    However, I did have to modify slight details of the code since I didn’t have all the classes available, and some minor namespace issues with regards to the prefix. I don’t foresee that drastically changing the results, but it’s something to be aware of.

    So I’m wondering if perhaps you’re trying to re-fetch the value before it’s ready?

    Thread Starter Jamie

    (@rabillion)

    it’s now working with this address field example and split_values true
    But the saved option is not selected

    • This reply was modified 8 years, 1 month ago by Jamie.
    Plugin Contributor Michael Beckwith

    (@tw2113)

    The BenchPresser

    Have you verified you have meta rows for everything in your database? After that, it’d just be a matter of making sure selected() could match up properly.

    Thread Starter Jamie

    (@rabillion)

    the serialized values has been overwritten after update post meta

    i’ve solved it by saving the additional fields without splitting them

    It’s probably not the best solution, but it works me

        /**
         * @param $override_value
         * @param $value
         * @param $object_id
         * @param $field_args
         *
         * @return mixed
         */
        public function cmb2_sanitize_date_select_field_callback( $override_value, $value, $object_id, $field_args ) {
    
            $date_select_keys = array( 'day', 'month', 'year', 'datetime' );
            
            foreach ( $date_select_keys as $key ) {
            
                if ( !empty( $value[ $key ] ) ) {
                
                    $date = strtotime( $value['day'] . '-' . $value['month'] . '-' . $value['year'] );
                    // save datetimestamp
                    // split values
                    update_post_meta( $object_id, $field_args['id'] . '_datetime', $date );
                    update_post_meta( $object_id, $field_args['id'] . '_' . $key, $value[ $key ] );
                    
                    // if only select the start date
                    // then save only the datetimestamp for end date
                    if ( $field_args['id'] != 'copa_date_end' ) {
                        update_post_meta( $object_id, 'copa_date_end' . '_datetime', $date );
                    }
                }
                
            }
            
            // in the addres-field example return was true
            return $value;
        }
    • This reply was modified 8 years, 1 month ago by Jamie.
    Plugin Contributor Michael Beckwith

    (@tw2113)

    The BenchPresser

    Sometimes what actually works is better than what is elegant. Good to hear you have something working here.

Viewing 7 replies - 1 through 7 (of 7 total)
  • The topic ‘Save sleceted value in hidden field’ is closed to new replies.