问题描述
我想修改插件中的一个函数。它在插件的主文件中声明如下:
class WCPGSK_Main {
...
public function wcpgsk_email_after_order_table($order) {
...
}
}
从这里添加调用:
add_action( 'woocommerce_email_after_order_table', array($this, 'wcpgsk_email_after_order_table') );
我想这是可以替换它,如果有访问在 functions.php 中的类。然后我可以写这样的东西:
$wcpgsk = new WCPGSK_Main;
remove_action( 'woocommerce_email_after_order_table', array($wcpgsk, 'wcpgsk_email_after_order_table') );
function customized_wcpgsk_email_after_order_table($order) {
...
}
add_action( 'woocommerce_email_after_order_table', array($wcpgsk, 'customized_wcpgsk_email_after_order_table') );
我想要在 functions.php 文件中获取类的访问是包含在 functions.php 中声明类的文件:
require_once('/wp-content/plugins/woocommerce-poor-guys-swiss-knife/woocommerce-poor-guys-swiss-knife.php');
$wcpgsk = new WCPGSK_Main;
...
但是这并不奏效,因为当插件在 WordPress 中被初始化时,插件的文件被包含在内。
有没有办法重写功能,而不会触摸插件的文件?
最佳解决方案
这应该工作:
add_action( 'woocommerce_init', 'remove_wcpgsk_email_order_table' );
function remove_wcpgsk_email_order_table() {
global $wcpgsk;
remove_action( 'woocommerce_email_after_order_table', array( $wcpgsk, 'wcpgsk_email_after_order_table' ) );
}
次佳解决方案
如果你的插件是这样注册的:
class Test_Class_Parent {
function __construct() {
add_action('wp_head',array($this,'test_method'));
}
function test_method() {
echo 'Echoed from the parent';
}
}
$p = new Test_Class_Parent();
那么你应该可以通过访问全局来删除过滤器:
class Test_Class_Child extends Test_Class_Parent {
function __construct() {
$this->unregister_parent_hook();
add_action('wp_head',array($this,'test_method'));
}
function unregister_parent_hook() {
global $p;
remove_action('wp_head',array($p,'test_method'));
}
function test_method() {
echo 'Echoed from the child';
}
}
$c = new Test_Class_Child();
否则,您将需要爬行 $wp_filter
global
作为注册码:
class Test_Class_Child extends Test_Class_Parent {
function __construct() {
$this->unregister_parent_hook();
add_action('wp_head',array($this,'test_method'));
}
function unregister_parent_hook() {
global $wp_filter;
if (!empty($wp_filter['wp_head'])) {
foreach($wp_filter['wp_head'] as $cb) {
foreach ($cb as $k => $v) {
if (
isset($v['function'])
&& is_a($v['function'][0],'Test_Class_Parent')
&& isset($v['function'][1])
&& 'test_method' == $v['function'][1]
) {
remove_action('wp_head',$k);
}
}
}
}
}
function test_method() {
echo 'Echoed from the child';
}
}
$c = new Test_Class_Child();
这是资源密集型的,除非你没有其他选择,否则应该没有办法。
参考文献
注:本文内容整合自 Google/Baidu/Bing 辅助翻译的英文资料结果。如果您对结果不满意,可以加入我们改善翻译效果:薇晓朵技术论坛。