如何在Dokan产品表单添加新旧商品字段并实现筛选功能
修复Dokan产品状态字段及添加筛选功能
原代码问题分析
- 产品编辑页面选中状态判断错误:将变量
$new_field误写为字符串"new_field",且else分支错误输出文本,破坏HTML结构 - 保存元数据时未检查字段是否存在:直接调用
$postdata['new_field']会在表单未提交该字段时触发PHP警告 - 单产品页面错误使用
exit:会直接终止页面渲染,导致页面加载不完整 - 表单元素缺少
id和for属性,不符合HTML规范 - 多语言文本复用Dokan官方文本域,易引发翻译冲突
修复后的完整代码
// ****添加产品状态字段 START**** // 在新增产品表单添加字段 add_action( 'dokan_new_product_after_product_tags', 'dokan_add_item_condition_field', 10 ); // 在编辑产品表单添加字段 add_action( 'dokan_product_edit_after_product_tags', 'dokan_add_item_condition_field_edit', 99, 2 ); // 新增产品表单字段渲染 function dokan_add_item_condition_field() { ?> <div class="dokan-form-group"> <label class="dokan-control-label" for="item_condition"><?php _e( '商品状态', 'custom-dokan' ); ?></label> <div class="dokan-input-group"> <select name="item_condition" id="item_condition" class="dokan-form-control"> <option value=""><?php _e( '请选择', 'custom-dokan' ); ?></option> <option value="new"><?php _e( '全新', 'custom-dokan' ); ?></option> <option value="used"><?php _e( '二手', 'custom-dokan' ); ?></option> </select> </div> </div> <?php } // 编辑产品表单字段渲染(带选中状态) function dokan_add_item_condition_field_edit( $post, $post_id ) { $item_condition = get_post_meta( $post_id, 'item_condition', true ); ?> <div class="dokan-form-group"> <label class="dokan-control-label" for="item_condition"><?php _e( '商品状态', 'custom-dokan' ); ?></label> <div class="dokan-input-group"> <select name="item_condition" id="item_condition" class="dokan-form-control"> <option value=""><?php _e( '请选择', 'custom-dokan' ); ?></option> <option value="new" <?php selected( $item_condition, 'new' ); ?>><?php _e( '全新', 'custom-dokan' ); ?></option> <option value="used" <?php selected( $item_condition, 'used' ); ?>><?php _e( '二手', 'custom-dokan' ); ?></option> </select> </div> </div> <?php } // 保存产品状态元数据 add_action( 'dokan_new_product_added', 'dokan_save_item_condition_meta', 10, 2 ); add_action( 'dokan_product_updated', 'dokan_save_item_condition_meta', 10, 2 ); function dokan_save_item_condition_meta( $product_id, $postdata ) { // 验证当前用户是卖家 if ( ! dokan_is_user_seller( get_current_user_id() ) ) { return; } // 检查字段是否存在,避免警告 if ( isset( $postdata['item_condition'] ) ) { $condition = sanitize_text_field( $postdata['item_condition'] ); update_post_meta( $product_id, 'item_condition', $condition ); } else { // 如果未选择,清空元数据 delete_post_meta( $product_id, 'item_condition' ); } } // 在单产品页面显示商品状态 add_action( 'woocommerce_single_product_summary', 'dokan_show_item_condition_single', 13 ); function dokan_show_item_condition_single() { global $product; if ( empty( $product ) ) { return; } $item_condition = get_post_meta( $product->get_id(), 'item_condition', true ); if ( empty( $item_condition ) ) { return; // 用return替代exit,避免中断页面 } // 转换为友好显示文本 $display_text = $item_condition === 'new' ? __( '全新', 'custom-dokan' ) : __( '二手', 'custom-dokan' ); ?> <span class="item-condition"> <?php echo esc_attr__( '商品状态:', 'custom-dokan' ); ?> <strong><?php echo esc_html( $display_text ); ?></strong> </span> <?php } // ****添加产品状态字段 END**** // ****添加商品状态筛选功能 START**** // 在商店页和搜索结果页添加筛选表单 add_action( 'woocommerce_before_shop_loop', 'dokan_add_item_condition_filter', 20 ); function dokan_add_item_condition_filter() { // 获取当前筛选的状态 $selected_condition = isset( $_GET['item_condition'] ) ? sanitize_text_field( $_GET['item_condition'] ) : ''; ?> <div class="item-condition-filter dokan-form-group"> <label for="filter_item_condition"><?php _e( '筛选商品状态:', 'custom-dokan' ); ?></label> <select id="filter_item_condition" class="dokan-form-control" onchange="this.form.submit()"> <option value=""><?php _e( '全部状态', 'custom-dokan' ); ?></option> <option value="new" <?php selected( $selected_condition, 'new' ); ?>><?php _e( '全新', 'custom-dokan' ); ?></option> <option value="used" <?php selected( $selected_condition, 'used' ); ?>><?php _e( '二手', 'custom-dokan' ); ?></option> </select> <input type="hidden" name="post_type" value="product"> </div> <style> .item-condition-filter { margin-bottom: 15px; display: flex; align-items: center; gap: 10px; } .item-condition-filter label { margin: 0; } </style> <?php } // 修改产品查询,应用筛选条件 add_action( 'pre_get_posts', 'dokan_filter_products_by_condition' ); function dokan_filter_products_by_condition( $query ) { // 仅在前台产品查询中生效 if ( ! is_admin() && $query->is_main_query() && ( is_shop() || is_product_category() || is_product_tag() || is_search() ) ) { if ( isset( $_GET['item_condition'] ) && ! empty( $_GET['item_condition'] ) ) { $condition = sanitize_text_field( $_GET['item_condition'] ); $query->set( 'meta_query', array( array( 'key' => 'item_condition', 'value' => $condition, 'compare' => '=' ) ) ); } } } // ****添加商品状态筛选功能 END****
使用说明
- 将代码添加到子主题
functions.php或自定义插件主文件中 - 替换文本域
custom-dokan为你的主题/插件专属文本域,方便多语言翻译 - 可根据需求调整筛选器样式,修改
<style>标签内的CSS代码
内容的提问来源于stack exchange,提问作者David
相关产品推荐
相关产品推荐

