I have this situation:
parent theme:
functions.php
require_once(dirname(__FILE__) . "/includes/theme-functions.php");
require_once(dirname(__FILE__) . "/includes/theme-hooks.php");
theme-function.php
function name_of_this_function() {
// DO SOMETHING
}
add_action ('hook','name_of_this_function');
theme-hooks.php
function hook() {
do_action('hook');
}
How can I override that action in my child functions.php given that mine is called before? I tried:
remove_action ('hook','name_of_this_function');
but of course this return false
I came to an answer after many attempts (miserably failed) and a lot of reading of documentation online.
The solution resides in the "after_setup_theme" hook.
Before I was adding my actions "on top" of the parent's, meaning that i had two headers, two footers and so on. Of course the problem was that my functions.php was not able to remove something that was not added yet.
This was caused by wordpress behavior that runs functions.php of the child before the one of the parent theme.
The solution to this problem is to add a function after the setup of theme with a priority that force it to runs after the one of the parent. In this way ALL functions of the parent would be initialized (the after setup of parent is called as last function) and I would be able to remove some actions.
This is the syntax:
add_action('after_setup_theme', 'my_setup', 3);
function my_setup(){
/* CUSTOM FOOTER */
remove_action('footer_hook','parent_site_info',99);
add_action('footer_hook','site_info',99);
}
That solved the problem.
Related
There is not a specific answer for this exact issue so i am going to try this.
So in the parent theme of a wordpress website there is a php file named helpers-icons.php. The exact path for this file is /wp-content/themes/parent/inc/helpers/helpers-icons.php, and the content of that file is
function get_flatsome_icon($name, $size = null) {
if($size) $size = 'style="font-size:'.$size.';"';
return '<i class="'.$name.'" '.$size.'></i>';
}
This file is then inlcuded in functions.php of that parent theme.
Now i want to override a function inside and being more specific, just this line of code
return '<i class="'.$name.'" '.$size.'></i>'; to return '<span class="'.$name.'" '.$size.'></span>';
how could i do that on child theme without messing with the php files of parent?
Thanks in advance
EDIT
EDIT 2
EDIT - Different Approach
You can copy the file /inc/helpers/helpers-icons.php into your child theme (keep the folder structure - e.g. /child-theme/inc/helpers/helpers-icons.php). That way it will be called instead of the original file and you can change the function there.
(Original Answer) Removing Functions From Hooks:
You’ll need to de-hook the parent function and hook your child theme function instead by using remove_action() and remove_filter().
The one you use will depend on whether the function is attached to an action hook or filter hook in the parent theme.
To remove a function, use:
remove_action( 'init', 'parent_function' );
However, this won’t work on its own, you will need to attach this function to a hook which will fire after the hook which the parent theme function is attached to. This is because you can’t remove the action before it’s been fired.
function child_remove_parent_function() {
remove_action( 'init', 'parent_function', [priority level] );
}
add_action( 'wp_loaded', 'child_remove_parent_function' );
NOTE: If the parent_function() was loaded using a priority level, you have to unloaded by stating the same level as well. That’s why [priority level] is in square brackets.
As you may imagine, wp-loaded is a hook that comes after init, so remove_action() can really remove the parent_function() that was loaded to init.
Now you’re free to write whatever new function you’d like.
function child_function() {
// your function
}
add_action( 'init', 'child_function' );
Source and further reading: https://obsessive-coffee-disorder.com/how-to-override-parent-theme-functions-in-wordpress/
My parent theme prints inline styles in header. One I want to remove.
Inside controls.php in public function hook():
add_action( 'wp_head', array($this, 'display_customization') );
This function looks like this:
public function display_customization()
{
do_action('zoom_customizer_display_customization_css', $this->get_css_rules());
$css = zoom_customizer_get_css()->build();
if (!empty($css)) {
echo "\n<!-- Begin Theme Custom CSS -->\n<style type=\"text/css\" id=\"" . WPZOOM::$theme_raw_name . "-custom-css\">\n";
echo $css;
echo "\n</style>\n<!-- End Theme Custom CSS -->\n";
}
}
It adds inline style with id="foodica-pro-custom-css"
I tried
remove_action( 'wp_head','display_customization', 120);
and it didn't work.
The main issue above is that the action is added using the class method callback syntax
array($this, 'display_customization') so you can't remove it using directly the function name
https://gist.github.com/tripflex/c6518efc1753cf2392559866b4bd1a53
Here you can find an implementation of remove_class_action and remove_class_filter that allow you to remove actions and filters that have been created using the class syntax.
Once you have the above code in your project using the following syntax:
remove_class_action('wp_head', 'NameOfClassThatThisRefersToInControlsFile', 'display_customization');
Some other things to note:
remove_action and remove_class_action from above need to have the same signature as add action, so please keep the priority the same. If the add call has no priority as above (so it has the default priority of 10), please keep the remove call the same.
Another issue that you could encounter here is to make sure the remove_action or remove_class_action calls are in fact called after the add_action.
Depending on where the add_action is called, you might have to put your remove call inside a specific hook, to make sure the remove call is executed after the add call.
I am trying to modify a Wordpress plugins' method without changing the plugin core code itself. I need to set some status flag in a different part of the website.
The method is defined in the plugin class like so:
add_action('plugins_action_name', [$this, 'local_method_name']);
The plugin method does not offer any actions or filters to hook into.
If this wasn't Wordpress but plain PHP I would write my own class, which extends the plugins' original class but has it's own method by the same name - but in Wordpress this gets me nowhere since I just move the problem from one plugin file to the next.
Is there a way to remove the plugins action altogether? And then redefine my own version of it?
Since the add_action has been called with $this - how would I remove it in some functions.php file?
Thanks
UPDATE
Indeed I want to learn how to handle different scenarios. Not expecting a one size fits all solution, but I do need to know how to avoid core changes, as each core-change complicates my deploy/update process exponentially.
Sure I will add some more details. My example plugin is WooCommerce Germanized Pro which comes with a WC_GZDP_Download_Handler::download() method which I needed to modify, in order to set some sort of "Warehouse downloaded the invoice" flag for each order. Which is later used to highlight new orders, filter orders that have been handed over to fulfilment etc.
There seems to be a Invoice Helper class which does in fact have a singleton pattern.
my modification in the download class is trivial:
public static function download( $pdf, $force = false ) {
... /* original code above, now my modifications */
if ($check_some_codition) {
$invoice = $pdf->get_invoice();
update_post_meta($invoice->get_id(), 'some-flag', 'some-value');
}
/* then resume original function (return the file to the browser) */
self::out( $filename, $file, $force );
}
I want to add some HTML code to a plugin but I want to do that in a child theme, the function that I wanna override it is in a file named as admin-functions.php
I want to add extra buttons to booked_render_custom_fields function
admin-functions.php:
function booked_render_custom_fields($calendar = false) { ?>
<button class="button">Text</button>;
<?php }
any suggestion? thanks
you can't really override a function like that. you can only use the filters and hooks that the plugin implements. but you got some options:
a) make a copy of the plugin, change it's name and make the changes you need. after that, it wont get updates anymore. you'll have to implement them manually.
b) you could add just one line to the original plugin and define a filter or hook to which you subscribe in your functions.php . so you only have to fix this one line after updating the plugin.
c) since the newer versions of wordpress, you have the possibilites to run your own code after any shortcode. so you could add or inject your own html into the output of the shortcode. https://developer.wordpress.org/reference/hooks/do_shortcode_tag/
I have a plugin that uses apply_filters like this:
$additional_fields = apply_filters('attachment_meta_add_fields', $additional_fields);
In my theme's functions.php, I do:
function addAttachmentMeta($additionalFields) {
return $addtionalFields;
}
add_filter( 'attachment_meta_add_fields', 'addAttachmentMeta', 1, 1 );
But the function addAttachmentMeta never runs.
How can I alter my apply or add filter statements to make it so that addAttachmentMeta gets called?
Edit:
This is a custom plugin that I wrote based off tutorials on how to add additional attachment meta fields. The whole source is here: http://pastebin.com/7NcjDsK5. As I mentioned in the comments, I know this is running and working because I can add additional fields in this plugin file, but not by using the filters because the filter doesn't get added.
I can see var_dumps before and after the apply_filters statement, but the function I've pointed to with add_filter never gets called.
According to the order WordPress' core loads, function.php gets called after all plugins are loaded and executed.
You need to make sure the apply_filters() in your plugin runs AFTER your add_filter() is called. Otherwise at the point where your filters are 'applied', add_filter() simply hasn't been called yet.
What you could do is use a hook to make that part of your plugin run after functions.php has loaded. You could use the add_action('after_setup_theme', 'function_name') hook.
Wrap the last three lines of your plugin file inside a function and execute it after functions.php runs.
function addAttachmentMeta() {
$additional_fields = array();
$additional_fields = apply_filters('attachment_meta_add_fields', $additional_fields);
$am = new Attachment_Meta( $additional_fields );
}
add_action('after_setup_theme', 'addAttachmentMeta');