如何在自定义插件中覆盖主题功能?

发布于 2025-02-13 00:17:09 字数 2200 浏览 0 评论 0原文

首先,我的问题

  • 我在W3C验证器平台上有一个WooCommerce错误。
  • 我通过重定向该特定文件的WooCommerce的模板路径来覆盖文件。

问题

  • 我当前正在使用的WordPress主题也与我的自定义插件相同的文件覆盖了相同的文件 覆盖取消我的插件的覆盖功能。

代码

这是我的一些代码

这是我使用内置的WordPress函数添加的函数/functions/add_filter/“ rel =“ nofollow noreferrer”> add_filter()高优先级值为“ 1”,以及文件i的路径i Am覆盖是... wooCommerce/templates/单产品/add-to-to-cart/variable.php

function wc_locate_template( $template, $template_name, $template_path ) {
    // Check if WooCommerce is present on the website
        if ( empty( $template ) || ! is_callable( 'WC' ) || ( defined( 'WC_TEMPLATE_DEBUG_MODE' ) && WC_TEMPLATE_DEBUG_MODE ) ) {
            return $template;
        }

    // Variables
        $default_path = WC()->plugin_path() . '/templates/';
        $plugin_path  = untrailingslashit( plugin_dir_path( __FILE__ ) ) . '/templates/';
        $template_new = str_replace( $default_path, $plugin_path, $template );

    // Processing
        if (
            false !== strpos( $template, $default_path )
            && file_exists( $template_new )
        ) {
            $template = $template_new;
        }
    // Output
    return $template;
}
add_filter( 'woocommerce_locate_template', 'wc_locate_template', 1, 3 );

问题

我如何确保我的插件以这种方式或这里升的方式覆盖文件,以使主题的覆盖不会重叠?


有用的链接

谢谢您提前时间

To begin with, my problem:

  • I have a WooCommerce error on the W3C Validator platform.
  • I overwrite the file by redirecting the template path of WooCommerce for that specific file.

Problem:

  • The Wordpress Theme that I am currently using is also overwritting the same file as my Custom plugin, as a result the Theme's overwriting cancels out my plugin's overwritting functionality.

CODE:

Here's some of my code:

This is the function I add using the built in wordpress function add_filter() with high priority value of "1" plus the path of the file I am overwritting is... woocommerce/templates/single-product/add-to-cart/variable.php

function wc_locate_template( $template, $template_name, $template_path ) {
    // Check if WooCommerce is present on the website
        if ( empty( $template ) || ! is_callable( 'WC' ) || ( defined( 'WC_TEMPLATE_DEBUG_MODE' ) && WC_TEMPLATE_DEBUG_MODE ) ) {
            return $template;
        }

    // Variables
        $default_path = WC()->plugin_path() . '/templates/';
        $plugin_path  = untrailingslashit( plugin_dir_path( __FILE__ ) ) . '/templates/';
        $template_new = str_replace( $default_path, $plugin_path, $template );

    // Processing
        if (
            false !== strpos( $template, $default_path )
            && file_exists( $template_new )
        ) {
            $template = $template_new;
        }
    // Output
    return $template;
}
add_filter( 'woocommerce_locate_template', 'wc_locate_template', 1, 3 );

Questions:

How can I make sure that my plugin will overwrite the file of in such way or prority so that the theme's overwritting won't overlap it?


Useful links:

Thank you in advance for your time.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

这个俗人 2025-02-20 00:17:09

这是如何使用插件覆盖WooCommerce模板的一个示例:

add_filter( 'woocommerce_locate_template', 'woo_custom_template', 1, 3 );
   function woo_custom_template( $template, $template_name, $template_path ) {
     global $woocommerce;
     $_template = $template;
     if ( ! $template_path ) 
        
        $template_path = $woocommerce->template_url;
        $plugin_path  = untrailingslashit( plugin_dir_path( __FILE__ ) )  . '/templates/';
 
    // Within passed path within the theme - this is priority
    $template = locate_template(
    array(
      $template_path . $template_name,
      $template_name
    )
   );
 // Processing
   if( ! $template && file_exists( $plugin_path . $template_name ) )
    $template = $plugin_path . $template_name;
 
   if ( ! $template )
    $template = $_template;
   //Output
   return $template;
}

然后,您应该能够通过复制要覆盖插件文件夹中的模板来实现目标。
示例:

your_plugin/template/woocommerce/单产品/add-to-to-cart/variable.php

That's an example on how to override a woocommerce template with a plugin:

add_filter( 'woocommerce_locate_template', 'woo_custom_template', 1, 3 );
   function woo_custom_template( $template, $template_name, $template_path ) {
     global $woocommerce;
     $_template = $template;
     if ( ! $template_path ) 
        
        $template_path = $woocommerce->template_url;
        $plugin_path  = untrailingslashit( plugin_dir_path( __FILE__ ) )  . '/templates/';
 
    // Within passed path within the theme - this is priority
    $template = locate_template(
    array(
      $template_path . $template_name,
      $template_name
    )
   );
 // Processing
   if( ! $template && file_exists( $plugin_path . $template_name ) )
    $template = $plugin_path . $template_name;
 
   if ( ! $template )
    $template = $_template;
   //Output
   return $template;
}

Then you should be able to reach your goal by copying the template you want to override in your plugin folder.
Example:

your_plugin/template/WooCommerce/single-product/add-to-cart/variable.php

离鸿 2025-02-20 00:17:09

优先级1表示您的函数将首先应用,因此附加到过滤器上的任何其他功能高于1的数字都可以覆盖您的功能。

您需要放置最高的数字,以确保您的功能将是最后一个应用的功能。

使用php_int_max使您的功能成为最后一个应用。

add_filter( 'woocommerce_locate_template', 'wc_locate_template', PHP_INT_MAX, 3 );

priority 1 means your function will be applied first, so any other function attached to the filter with a number higher than 1 will simply overwrite your function.

You need to put highest possible number to make sure your function will be the last one applied.

use PHP_INT_MAX to make your function the last one applied.

add_filter( 'woocommerce_locate_template', 'wc_locate_template', PHP_INT_MAX, 3 );
Hello爱情风 2025-02-20 00:17:09

挂钩和过滤器是根据优先级运行的修改,
被称为“最终的优先级”将是其最终输出,

这是一个示例
我有此

function youFree() {
  $imFree = apply_filters('free_filter', 'I am free' );
  return $imFree;
}

假设

add_filter('free_filter', function() {
  return 'You are not 1';
}, 1);


add_filter('free_filter', function() {
  return 'You are not 10';
}, 10);


add_filter('free_filter', function() {
  return 'You are not 999';
}, 999);

add_action('init', function() {
  add_filter('free_filter', function() {
    return 'You are not init 999';
  }, 999);
});

add_action('wp_footer', function() {
  add_filter('free_filter', function() {
    return 'You are not wp_footer';
  }, 999);
});

功能
如果您调用youfree() on wp_head

add_action('wp_head', function() {
  echo '<pre>', print_r(youFree(), 1), '</pre>';
});
//the output is "You are not init 999" 
//because the add_filter that runs on wp_footer did not take effect 
//as the function is already called way higher specifically in wp_head
//and the final value is last filter being called thats added on init hook with 999 priority

但是如果您调用该youfree()wp_footer上,

add_action('wp_footer', function() {
  echo '<pre>', print_r(youFree(), 1), '</pre>';
}, 20);
//the output is "You are not wp_footer"
//as this was the very last filter before that function is called on wp_footer

请在您的中情况,

  1. 您必须确定主题进行修改的何时何时及时调用值。
  2. 然后,您需要在主题修改和WooCommerce调用之前将过滤器注入过滤器。通常,这就像查看主题调用过滤器的位置并在过滤器上添加优先级一样容易,该过滤器比主题过滤器上的内容更高。

但是,如果您很难注入它,则最好的选择是使用 QUERY MONITE a>

Hooks and filter are modification which runs based on priority,
the highest the priority before its being called will be the its final output

Here's an example
Assuming I have this function

function youFree() {
  $imFree = apply_filters('free_filter', 'I am free' );
  return $imFree;
}

then I have all these filters with different priorities

add_filter('free_filter', function() {
  return 'You are not 1';
}, 1);


add_filter('free_filter', function() {
  return 'You are not 10';
}, 10);


add_filter('free_filter', function() {
  return 'You are not 999';
}, 999);

add_action('init', function() {
  add_filter('free_filter', function() {
    return 'You are not init 999';
  }, 999);
});

add_action('wp_footer', function() {
  add_filter('free_filter', function() {
    return 'You are not wp_footer';
  }, 999);
});

Here is the output
if you call youFree() on wp_head

add_action('wp_head', function() {
  echo '<pre>', print_r(youFree(), 1), '</pre>';
});
//the output is "You are not init 999" 
//because the add_filter that runs on wp_footer did not take effect 
//as the function is already called way higher specifically in wp_head
//and the final value is last filter being called thats added on init hook with 999 priority

but if you call that youFree() function on wp_footer

add_action('wp_footer', function() {
  echo '<pre>', print_r(youFree(), 1), '</pre>';
}, 20);
//the output is "You are not wp_footer"
//as this was the very last filter before that function is called on wp_footer

So in your situation,

  1. You have to determine at which point the theme do the modification and at which point the value is being called.
  2. Then you need to inject your filter after your theme modifies it and before it was called by woocommerce. Usually, this is as easy as looking at where the theme calls the filter and adding a priority on your filter which is higher than whats on the theme filter.

but if your having a hard at where to inject it your best option is to find it using query monitor

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文