На многих сайтах ресторанов с доставкой я встречал отдельные поля для ввода «дома», «этажа» и так далее.
Вот к примеру сайт грузинского ресторана:
В WooCommerce у нас по умолчанию есть только два поля – «Адрес 1» и «Адрес 2». Ну типа того:
Дело в том, что когда и «крыло», и «подъезд», и «этаж», и «т.д.» заполняются в одном поле, это может быть не супер-удобно обрабатывать менеджерам вашего магазина. Поэтому давайте разберёмся, как их разделить и чтобы всё классно работало.
Обратите внимание, что я бы не хотел усложнять и фактически добавлять три (или два) поля на страницу оформления заказа, потом добавлять значения этих полей в метабокс заказа в админке и в емейлы. Ведь для администратора нам по сути не важно, будет ли информация записана в разные поля или в одно – главное, чтобы она была удобочитаема, в этом и есть цель. Поэтому ниже я решил поделиться вариантом, который прекрасно работает на парочке проектов, хотя он и не кажется мне супер-красивым. Также хочу порекомендовать видеоурок по полной кастомизации страницы «Оформление заказа» в WooCommerce.
Фактически мы не будем добавлять новые поля тут, а при помощи хука превратим поле «Адрес 2» (billing_address_2
) в целых три!
Для этого нам может пригодится хук WooCommerce, который называется woocommerce_form_field_{ТИП ПОЛЯ}
, а так как billing_address_2
– это текстовое поле, то и хук будет woocommerce_form_field_text
. То есть по сути мы перезапишем HTML поля billing_address_2
.
HTML поля адрес 2 по умолчанию выглядит так:
<p class="form-row address-field form-row-wide" id="billing_address_2_field" data-priority="60"> <label for="billing_address_2" class="screen-reader-text">Крыло, подъезд, этаж и т.д. <span class="optional">(необязательно)</span></label> <span class="woocommerce-input-wrapper"> <input type="text" class="input-text " name="billing_address_2" id="billing_address_2" placeholder="Крыло, подъезд, этаж и т.д. (необязательно)" value="" autocomplete="address-line2" data-placeholder="Крыло, подъезд, этаж и т.д. (необязательно)"> </span> </p>
Я предлагаю в этом HTML сильно ничего не менять, только это:
<span class="woocommerce-input-wrapper true-wrapper"> <input type="number" name="billing_address_2" id="billing_address_2" placeholder="Парадная" value=""> <input type="number" name="billing_address_3" id="billing_address_3" placeholder="Этаж" value=""> <input type="number" name="billing_address_4" id="billing_address_4" placeholder="Квартира" value=""> </span>
Тогда наш код с хуком будет вот таким:
add_filter( 'woocommerce_form_field_text', 'true_fields', 25, 4 ); function true_fields( $field, $key, $args, $value ) { if( 'billing_address_2' === $key ) { $field = '<p class="form-row address-field form-row-wide" data-priority="60"> <span class="woocommerce-input-wrapper true-wrapper"> <input type="number" name="billing_address_2" id="billing_address_2" placeholder="Парадная" value=""> <input type="number" name="billing_address_3" id="billing_address_3" placeholder="Этаж" value=""> <input type="number" name="billing_address_4" id="billing_address_4" placeholder="Квартира" value=""> </span> </p>'; } return $field; }
Не знаете, куда вставлять код кстати?
И да, немножно CSS на класс .true-wrapper
.
.true-wrapper{ display: flex; justify-content: space-between; } .true-wrapper input{ max-width: 30%; flex-basis: 30%; }
В итоге получаем вполне годный вариант:
Как я вам уже сказал в начале урока, наша цель – провернуть всё это с минимальными усилиями. Поэтому сейчас мы воспользуемся хуком woocommerce_checkout_posted_data
, чтобы перед сохранением полей в базу данных перезаписать их так, как нам нужно.
add_filter( 'woocommerce_checkout_posted_data', 'true_process_fields' ); function true_process_fields( $data ) { // в поле billing_address_2 мы и будем записывать новые значения полей $data[ 'billing_address_2' ] = ''; $fields = array(); // получаем данные из глобального $_POST, сначала парадную (подъезд) if( ! empty( $_POST[ 'billing_address_2' ] ) ) { $fields[] = 'подъезд ' . absint( $_POST[ 'billing_address_2' ] ); } // затем этаж if( ! empty( $_POST[ 'billing_address_3' ] ) ) { $fields[] = 'этаж ' . absint( $_POST[ 'billing_address_3' ] ); } // затем квартиру if( ! empty( $_POST[ 'billing_address_4' ] ) ) { $fields[] = 'квартира ' . absint( $_POST[ 'billing_address_4' ] ); } // объединяем все заполненные данные запятой $data[ 'billing_address_2' ] = join( ', ', $fields ); // возвращаем результат return $data; }
В этом коде я использовал функцию absint() для очистки пользовательского ввода. Подробнее о том, зачем нужна очистка – в этом уроке.
Чтобы оставить комментарий, пожалуйста, зарегистрируйтесь или войдите.