我发现这段代码做了我需要它做的事情,只是它不会将信息添加到邮箱中,也不会添加订单细节.

因此,作为背景,我们正在销售门票,并希望收集每个门票持有者的信息.

//Custom WooCommerce Checkout Fields based on Quantity
    add_action( 'woocommerce_before_order_notes', 'person_details' );

    function person_details($checkout) {
        global $woocommerce;
    $count = $woocommerce->cart->cart_contents_count;
    $i = 1;
       for($k=2; $k<= $count; $k++) {
        $i++;
           print ('<h3>Please enter details of attendee '.$i.'</h3>');
        woocommerce_form_field( 'cstm_full_name'.$i, array(
            'type'          => 'text',
            'class'         => array('my-field-class form-row-wide'),
            'label'         => __('Full name'),
            'placeholder'   => __('Enter full name'),
            ),
            $checkout->get_value( 'cstm_full_name'.$i ));
        echo '<div class="clear"></div>';
        woocommerce_form_field( 'cstm_phone'.$i, array(
            'type'          => 'text',
            'class'         => array('my-field-class form-row-first'),
            'label'         => __('Phone'),
            'placeholder'   => __('Enter phone number'),
            ),
            $checkout->get_value( 'cstm_phone'.$i ));
        woocommerce_form_field( 'cstm_email'.$i, array(
            'type'          => 'email',
            'class'         => array('my-field-class form-row-last'),
            'label'         => __('Email address'),
            'placeholder'   => __('Enter email address'),
            ),
            $checkout->get_value( 'cstm_email'.$i ));
        echo '<div class="clear"></div>';
        woocommerce_form_field( 'cstm_address'.$i, array(
            'type'          => 'textarea',
            'class'         => array('my-field-class form-row-wide'),
            'label'         => __('Full address'),
            'placeholder'   => __('Enter full address'),
            ),
            $checkout->get_value( 'cstm_address'.$i ));
    }
    }

    /**
     * Save value of fields
     */
 
    add_action('woocommerce_checkout_update_order_meta',     'customise_checkout_field_update_order_meta');
 
    function customise_checkout_field_update_order_meta($order_id) {
    global $woocommerce;
    $count = $woocommerce->cart->cart_contents_count;
    $i = 1;
       for($k=2; $k<= $count; $k++) {
        $i++;
    if (!empty($_POST['cstm_full_name'.$i])) {
        update_post_meta($order_id, 'Name of Attendee'.$i, sanitize_text_field($_POST['cstm_full_name'.$i]));
    }
    if (!empty($_POST['cstm_phone'.$i])) {
        update_post_meta($order_id, 'Phone of Attendee'.$i, sanitize_text_field($_POST['cstm_phone'.$i]));
    }
    if (!empty($_POST['cstm_email'.$i])) {
        update_post_meta($order_id, 'Email of Attendee'.$i, sanitize_text_field($_POST['cstm_email'.$i]));
    }
    if (!empty($_POST['cstm_address'.$i])) {
        update_post_meta($order_id, 'Address of Attendee'.$i,               sanitize_text_field($_POST['cstm_address'.$i]));
        }
    }
    }

    /**
     * Add fields to order emails
     **/
    add_filter('woocommerce_email_order_meta_keys', 'my_custom_checkout_field_order_meta_keys');
    function my_custom_checkout_field_order_meta_keys( $keys ) {
    $i = 1;
    for($k=2; $k<= 50; $k++) {
    $i++;
    $keys[] = 'Name of Attendee'.$i;
    $keys[] = 'Phone of Attendee'.$i;
    $keys[] = 'Email of Attendee'.$i;
    $keys[] = 'Email of Participant '.$i;
    $keys[] = 'Address of Attendee'.$i;
    }   
    return $keys;
    }

我认为其中一些可能会被贬低,但我试图让它达到标准的try 都失败了.

推荐答案

我已经修改了代码,简化了.我已经添加了必要的代码来显示管理订单、客户订单和邮箱通知上的与会者.

// Custom WooCommerce Checkout Fields based on Quantity
add_action( 'woocommerce_before_order_notes', 'attendees_checkout_fields' );
function attendees_checkout_fields( $checkout ) {
    echo '<h3>'.__('Attendees details').'</h3>';

    for($i = 1; $i <= WC()->cart->get_cart_contents_count(); $i++) {
        printf( '<h4>%s %d</h4>', __('Please enter details of the attendees'), $i );

        woocommerce_form_field( 'cstm_full_name'.$i, array(
            'type'          => 'text',
            'class'         => array('my-field-class form-row-wide'),
            'label'         => __('Full name'),
            'placeholder'   => __('Enter full name'),
        ), $checkout->get_value( 'cstm_full_name'.$i ));

        echo '<div class="clear"></div>';

        woocommerce_form_field( 'cstm_phone'.$i, array(
            'type'          => 'text',
            'class'         => array('my-field-class form-row-first'),
            'label'         => __('Phone'),
            'placeholder'   => __('Enter phone number'),
        ), $checkout->get_value( 'cstm_phone'.$i ));

        woocommerce_form_field( 'cstm_email'.$i, array(
            'type'          => 'email',
            'class'         => array('my-field-class form-row-last'),
            'label'         => __('Email address'),
            'placeholder'   => __('Enter email address'),
        ), $checkout->get_value( 'cstm_email'.$i ));

        echo '<div class="clear"></div>';

        woocommerce_form_field( 'cstm_address'.$i, array(
            'type'          => 'textarea',
            'class'         => array('my-field-class form-row-wide'),
            'label'         => __('Full address'),
            'placeholder'   => __('Enter full address'),
        ), $checkout->get_value( 'cstm_address'.$i ));
    }
}

// Utility function
function attendee_fields_keys_labels() {
    return array(
        'cstm_full_name' => __('Name'),
        'cstm_phone'     => __('Phone'),
        'cstm_email'     => __('Email'),
        'cstm_address'   => __('Address'),
    );
}

// Save value of fields
add_action('woocommerce_checkout_create_order', 'save_custom_checkout_fields_data');
function save_custom_checkout_fields_data($order) {
    $count = WC()->cart->get_cart_contents_count();
    $order->update_meta_data('items_count', $count );

    for($i = 1; $i <= WC()->cart->get_cart_contents_count(); $i++) {
        foreach( attendee_fields_keys_labels() as $field_key => $field_label ) {
            if ( isset($_POST[$field_key.$i]) && !empty($_POST[$field_key.$i]) ) {
                if( $field_key !== 'cstm_address' ) {
                    $order->update_meta_data($field_key.$i, sanitize_text_field($_POST[$field_key.$i]) );
                } else {
                    $order->update_meta_data($field_key.$i, sanitize_textarea_field($_POST[$field_key.$i]) );
                }
            }
        }
    }
}

// Display attendees on email notifications
add_action('woocommerce_email_order_details', 'action_after_email_order_details', 25, 4 );
function action_after_email_order_details( $order, $sent_to_admin, $plain_text, $email )
{
    $count = $order->get_meta('items_count');

    if ( ! $count ) return;

    // The HTML Structure
    $html_output = '<h2>' . __('Attendees details') . '</h2>
    <div class="discount-info">';

    // Loop though the data array to set the fields
    for($i = 1; $i <= $count; $i++) {
        $html_output .= '<table cellspacing="0" cellpadding="6">
        <thead><tr><th colspan="2"><h4>' . __('Attendee') . ' ' . $i . '</h4></th></tr></thead>
        <tbody>';

        foreach( attendee_fields_keys_labels() as $field_key => $field_label ) {
            if( $meta_value = $order->get_meta($field_key.$i) ){
                $html_output .= '<tr>
                    <th>' . $field_label . '</th>
                    <td>' . $meta_value . '</td>
                </tr>';
            }
        }
        $html_output .= '</tbody></table>';
    }
    $html_output .= '</div><br>'; // HTML (end)

    // The CSS styling
    $styles = '<style>
        .discount-info table{width: 100%; font-family: \'Helvetica Neue\', Helvetica, Roboto, Arial, sans-serif;
            color: #737373; border: 1px solid #e4e4e4; margin-bottom:8px;}
        .discount-info table th, table.tracking-info td{text-align: left; border-top-width: 4px;
            color: #737373; border: 1px solid #e4e4e4; padding: 12px; width:58%;}
        .discount-info table td{text-align: left; border-top-width: 4px; color: #737373; border: 1px solid #e4e4e4; padding: 12px;}
    </style>';

    // The Output CSS + HTML
    echo $styles . $html_output;
}

// Display attendees on Customer orders
add_action( 'woocommerce_view_order', 'woocommerce_order_attendees_table', 15 );
add_action( 'woocommerce_thankyou', 'woocommerce_order_attendees_table', 15 );
function woocommerce_order_attendees_table( $order_id ) {
    $order = wc_get_order($order_id);
    $count = $order->get_meta('items_count');

    if ( ! $count ) return;

    echo '<section class="woocommerce-attendees">
    <h2 class="woocommerce-attendees__title">' . esc_html__( 'Attendees', 'woocommerce' ) . '</h2>
    <table class="woocommerce-table woocommerce-table--attendees shop_table attendees">
    <tbody>';
    // Loop though the data array to set the fields
    for($i = 1; $i <= $count; $i++) {
        echo '<tr><th colspan="4">
            <h4>' . __('Attendee') . ' ' . $i . '</h4>
        </th></tr><tr>';
        
        foreach( attendee_fields_keys_labels() as $field_key => $field_label ) {
            echo '<th>'. $field_label .'</th>';
        }
        echo '</tr><tr>';

        foreach( attendee_fields_keys_labels() as $field_key => $field_label ) {
            if( $meta_value = $order->get_meta($field_key.$i) ){
                echo '<td>'. $meta_value .'</td>';
            }
        }
        echo '</tr>';
    }
    echo '</tbody></table></section>';
}

// Display attendees on Admin Order edit pages: Custom metabox (right column)
add_action( 'add_meta_boxes', 'add_attendees_metabox' );
function add_attendees_metabox(){
    add_meta_box(
        'attendees',
        __('Attendees'),
        'attendees_metabox_content',
        'shop_order',
        'side', // or 'normal'
        'default' // or 'high'
    );
}

// Adding the content for the custom metabox
function attendees_metabox_content() {
    $order = wc_get_order(get_the_id());
    $count = $order->get_meta('items_count');

    if ( ! $count ) return;

    for($i = 1; $i <= $order->get_meta('items_count'); $i++) {
        echo '<div style="background-color:#eee;padding:2px;margin-bottom:.4em;">
        <h4 style="margin:.5em 0;padding:2px;">Attendee '.$i.'</h4>
        <table style="text-align:left;margin-bottom:.7em;" cellpadding="2"><tbody>';
        
        foreach( attendee_fields_keys_labels() as $field_key => $field_label ) {
            if( $meta_value = $order->get_meta($field_key.$i) ){
                echo '<tr><th valign="top">'.$field_label.':</th><td>'.$meta_value.'</td></tr>';
            }
        }
        echo '</tbody></table></div>';
    }
}

代码放在子主题的functions.php文件中(或插件中).测试和作品.

Customer orders:

enter image description here

Email notifications:

enter image description here

Admin Orders

enter image description here

Php相关问答推荐

为什么PHP输出\n而不是实际创建一个新元素?

CodeIgniter AJAX表格提交中的CSRF token 再生问题

允许Laravel路由指定`withTrashed`,尽管有显式的模型绑定

启用额外的WooCommerce产品库存位置

无法使用DOMPDF在PDF中呈现非ANSI字符

PHP日期操作,将多个日期输出为格式化字符串

我有一个显示记录的表格,每行在最右边有两个按钮.如何才能以正确的顺序获得表的值?

在 Woocommerce 邮箱订单中显示产品 GTIN

htaccess 重定向子域错误的 url

WooCommerce 按产品运输插件:仅收取较高的运输费用

VS Code 对 PHP 上从父类继承的方法报告误报

如何在 PHP 中对具有相同数组值的值求和

根据所选付款方式更改 WooCommerce 提交结帐按钮文本

带有分类术语数组的 WordPress Elementor 自定义查询 - 如何要求所有术语都在返回的帖子中

如何在WooCommerce中为访客购买者分配自定义客户代码

Woocommerce API 的 PHP Curl 附加参数

PHP / DOM : 解析 HTML 以提取基于类的数​​据

Laravel 从嵌套数组的第二级获取最后一项

如何在 Laravel 中验证多个输入?

如何使用先前 SELECT 的结果来 SELECT SQL 数据