Wordpress Meta Box plugin, "Fatal Error: Call to undefined method" - php

Huge issue with this plugin!!!!
I updated Wordpress and everything and now I have this error so I can't edit some Wordpress pages:
“Fatal error: Call to undefined method RW_Meta_Box::get_class_name() in /home/wwwrcf/public_html/wp-content/plugins/meta-box-group/class-rwmb-group-field.php on line 63”
public static function html( $meta, $field )
{
ob_start();
// Add filter to child field meta value, make sure it's added only once
if ( empty( self::$meta_queue ) )
{
add_filter( 'rwmb_field_meta', array( __CLASS__, 'child_field_meta' ), 10, 3 );
}
// Add group value to the queue
array_unshift( self::$meta_queue, $meta );
// Add clone index to make sure each child field has an unique ID.
$clone_index = '';
if ( $field['clone'] && preg_match( '|_\d+$|', $field['id'], $match ) )
{
$clone_index = $match[0];
}
foreach ( $field['fields'] as $child_field )
{
$child_field['field_name'] = self::child_field_name( $field['field_name'], $child_field['field_name'] );
$child_field['attributes']['id'] = ( isset( $child_field['attributes']['id'] ) ? $child_field['attributes']['id'] : $child_field['id'] ) . $clone_index;
****line 63 -> call_user_func( array( RW_Meta_Box::get_class_name( $child_field ), 'show' ), $child_field, RWMB_Group::$saved );
}
// Remove group value from the queue
array_shift( self::$meta_queue );
// Remove filter to child field meta value and reset class's parent field's meta
if ( empty( self::$meta_queue ) )
{
remove_filter( 'rwmb_field_meta', array( __CLASS__, 'child_field_meta' ) );
}
return ob_get_clean();
}
Need to fix this.
Thanks for your help!

Related

How do I create a woocommerce product title based on whether a variable exists or not using function.php?

I need some help with a woocommerce website with a function.php file that I edit within a plugin called WP All Import. It's linked to a plugin that imports csv & xml files.
In WP All Import I set the import title as [product_title({product_name[1]}, {size[1]}, {colour[1]})] and it picks up the items from an import.
What I'm trying to do is set the product name as a combination of variables. So in the example below, if both $size and $colour are empty I want the product name to just be $name. If $size is empty, then $name - $colour. If $ colour is empty then $name - $size. And then if they all have values $name - $colour - $size.
function product_title($name, $size, $colour)
{
$newName = $name;
if (strpos($size, "")) {
if (strpos($colour, ""))
{
$newName = "$name";
}
}
else if (strpos($size, ""))
{
$newName = "$name - $colour";
}
else if (strpos($colour, ""))
{
$newName = "$name - $size";
}
else
{
$newName = "$name - $colour - $size";
}
}
At the moment this is leaving the titles as blank. Where did I go wrong?
I've had to do this not so long ago. It's pretty tricky to understand. In short you can't use pre_get_post because the terms are not set yet. You must use save_post with wp_update_post, but there is a few thing to understand like the infinite loop case.
Don't hesitate to adapt it. I guessed that colors and sizes are custom taxonomies, just make sure the slugs matches. Modify it and have fun.
<?php
add_action( 'save_post', 'worker', 10, 3 );
function worker( $post_id, $post, $update ) {
// ... if not the admin side or if user can't edit post, then bail
if ( ! is_admin() || ! current_user_can( 'edit_post', $post_id ) )
return;
$worker = ( object ) [
'post_type' => 'product', // ... set our taxonomy in your case, "product"
'taxonomies' => [ 'colour', 'size', ], // ... set the taxonomies that we want to use in our title
];
// ... if not a post.php page or post-new.php page, then bail
$base = [
'post.php',
'post-new.php',
];
if( ! in_array( filter_input( INPUT_SERVER, 'REQUEST_URI' ), $base, true ) && $post->post_type != $worker->post_type )
return;
// ... do not update title if autosave
if( defined( 'DOING_AUTOSAVE' ) && DOING_AUTOSAVE )
return;
// ... fetch our terms and join them
$terms = join( ' - ', wp_list_pluck( wp_get_object_terms( $post_id, $worker->taxonomies ), 'name' ) );
// ... define our title structure
$self = $post->post_title . $terms . '#' . $post_id; // ... You should leave the post_id as a unique identifer, so you don't end up with 2 product with the same title
// ... https://developer.wordpress.org/reference/hooks/save_post/#avoiding-infinite-loops
remove_action( 'save_post', 'worker' );
wp_update_post( array(
'ID' => $post_id,
'post_title' => esc_attr( $self ),
'post_name' => sanitize_title( $self ),
) );
add_action( 'save_post', 'worker', 10, 3 );
}; ?>

Can't get custom fields of a woocommerce product

i am trying to get the custom fields with this function and multiply by the product price. I am getting the product price but when printing the custom fields, i am only getting zeros.. i dont understand why, i had tryed get_metadata() and get_post_custom() too.. but nothing works
function filter_woocommerce_cart_product_subtotal( $product_subtotal, $product, $quantity, $instance ) {
$fields = get_post_meta(get_the_id(), false);
$add_on = $product->get_price()*$fields[0] + $product->get_price()*$fields[1] + $product-
>get_price()*0.75*$fields[2];
return $product_subtotal + $add_on;
};
add_filter( 'woocommerce_cart_product_subtotal', 'filter_woocommerce_cart_product_subtotal', 10, 4 );
I have tryed to get single fields too but always getting zeros.
I can get the custom fields in function below and save it in a global variable but when i try to access the global variable in the function above, i get zero again.
function tour_product_add_on_cart_item_data( $cart_item, $product_id, $cart ){
/*
if( isset( $_POST['time_add_on'] ) ) {
$cart_item['time_add_on'] = sanitize_text_field( $_POST['time_add_on'] );
}
*/
if( isset( $_POST['date_add_on'] ) ) {
$cart_item['date_add_on'] = sanitize_text_field( $_POST['date_add_on'] );
}
if( isset( $_POST['place_add_on'] ) ) {
$cart_item['place_add_on'] = sanitize_text_field( $_POST['place_add_on'] );
}
if( isset( $_POST['adult_add_on'] ) ) {
$cart_item['adult_add_on'] = sanitize_text_field( $_POST['adult_add_on'] );
}
if( isset( $_POST['child_add_on'] ) ) {
$cart_item['child_add_on'] = sanitize_text_field( $_POST['child_add_on'] );
}
if( isset( $_POST['infant_add_on'] ) ) {
$cart_item['infant_add_on'] = sanitize_text_field( $_POST['infant_add_on'] );
}
$product = wc_get_product($product_id);
$GLOBALS["fee"] = $_POST['adult_add_on']*$product->get_price() +
$_POST['child_add_on']*$product->get_price() + $_POST['infant_add_on']*0.75*$product->get_price();
return $cart_item;
}
get_post_meta() second parameter is the meta key value. So you should use for example
$date_add_on = get_post_meta(get_the_id(), 'date_add_on')
So, i have resolved this issue. When you add a custom field to a woocommerce product or a wordpress post, you have to update it's meta data. Here is a good tutorial of every step you have to follow to add a custom field.
HOW TO ADD WOOCOMMERCE CUSTOM FIELDS TO A PRODUCT

How do I apply_filters to my custom function that is executed by add_action?

I have a custom function in my parent theme that hooks into the Wordpress admin_head, doing stuff with allowed domains which I define in the function. This part works perfectly.
But, I want to be able to add additional allowed domains to that function from the child theme (in other words, without modifying the original function in the parent theme). I thought that apply_filters may be a good solution but it doesn't seem to pass the additional domains in. What am I doing wrong? Or is there a better way to accomplish this?
This demonstrates the issue I'm trying to resolve:
function custom_function( $additional_domains ) {
$allowed_domains = array(
'domain1.com',
'domain2.com',
'domain3.com',
);
if ( $additional_domains ) {
array_push( $allowed_domains, $additional_domains );
}
print_r( $allowed_domains );
}
add_action('admin_head', 'custom_function');
function send_domains_to_custom_function( $domains ) {
return $domains;
}
add_filter( 'custom_function', 'send_domains_to_custom_function', 10, 1 );
$add_these_domains = array(
'domain4.com',
'domain5.com',
);
apply_filters( 'custom_function', $add_these_domains );
This is the result of the previous code:
Array
(
[0] => domain1.com
[1] => domain2.com
[2] => domain3.com
)
But this is the result I'm wanting:
Array
(
[0] => domain1.com
[1] => domain2.com
[2] => domain3.com
[3] => domain4.com
[3] => domain5.com
)
Update: Final full working solution
Thanks to #melvin, and to provide clarity for anyone else who may find this later, here's what I ended up with:
Parent theme function:
function custom_function( $additional_domains ) {
$allowed_domains = array(
'domain1.com',
'domain2.com',
'domain3.com',
);
$additional_domains = apply_filters( 'add_to_allowed_domains', $additional_domains );
if ( !empty($additional_domains) ) {
$allowed_domains = array_merge( $allowed_domains, $additional_domains );
}
print_r( $allowed_domains );
}
add_action('admin_head', 'custom_function');
Child theme function & filter:
add_filter('add_to_allowed_domains','add_to_domains_fn');
function add_to_domains_fn($domains){
$domains= array('domain4.com','domain5.com');
return $domains;
}
The parent theme function still works with the original allowed domains defined within it. If the child theme includes add_to_domains_fn() and the filter, it adds the additional domains in as expected.
See the following function from store-front theme of wordpress
function storefront_header_styles() {
$is_header_image = get_header_image();
$header_bg_image = '';
if ( $is_header_image ) {
$header_bg_image = 'url(' . esc_url( $is_header_image ) . ')';
}
$styles = array();
if ( '' !== $header_bg_image ) {
$styles['background-image'] = $header_bg_image;
}
$styles = apply_filters( 'storefront_header_styles', $styles );
foreach ( $styles as $style => $value ) {
echo esc_attr( $style . ': ' . $value . '; ' );
}
}
Have you seen how apply_filters is applied inorder to use the variable $styles?
$styles = apply_filters( 'storefront_header_styles', $styles );
Either the theme should put a filter in the position or you should manually add an apply_filter to the theme.
#UPDATE
I don't really get what code is from theme function and child theme. Assuming i have understood correctly, you need something as follows
function custom_function( $additional_domains ) {
$allowed_domains = array(
'domain1.com',
'domain2.com',
'domain3.com',
);
$allowed_domains = apply_filters( 'add_to_allowed_domains', $allowed_domains );
if ( $additional_domains ) {
array_push( $allowed_domains, $additional_domains );
}
print_r( $allowed_domains );
}
add_action('admin_head', 'custom_function');
After changing the function as the above, you can use
add_filter('add_to_allowed_domains','add_to_domains_fn');
function add_to_domains_fn($domains){
$domains= array('domain4.com','domain5.com');
return $domains;
}
N.B : Since the function in the parent theme doesn't have any filters there, adding apply_filters manually is not recommended. Because the changes get overridden on next theme update. So you can ask theme developer to add a filter there

If has_term, load other Wordpress theme

This is what I want to accomplish. In Wordpress I've created a taxonomy called categorie with the terms app, web and branding. When a project has the term app, I want to load another theme / blog. When a project has the term web or branding, I want to load single.php. The last one works just fine.
This is my code so far
function load_single_template($template) {
$new_template = '';
if( is_single() ) {
global $post;
if( has_term('app', 'categorie', $post) ) {
$new_template = get_theme_roots('themeApp');
} else {
$new_template = locate_template(array('single.php' ));
}
}
return ('' != $new_template) ? $new_template : $template;
}
add_action('template_include', 'load_single_template');
So when a project has the term app, I want to load the theme themeApp. Any suggestions? Thanks in advance.
We had to accomplish a similar task in our plugin, AppPresser. You can see our solution here: https://github.com/WebDevStudios/AppPresser/blob/master/inc/theme-switcher.php
Basically, you need to change the theme name in 3 filters: 'template', 'option_template', 'option_stylesheet'.
Getting the category is not so simple though, because the template check happens early enough in the WordPress process that the global $post and $wp_query objects are not available.
Here is one way that can be accomplished:
<?php
add_action( 'setup_theme', 'maybe_theme_switch', 10000 );
function maybe_theme_switch() {
// Not on admin
if ( is_admin() )
return;
$taxonomy = 'category';
$term_slug_to_check = 'uncategorized';
$post_type = 'post';
// This is one way to check if we're on a category archive page
if ( false !== stripos( $_SERVER['REQUEST_URI'], $taxonomy ) ) {
// Remove the taxonomy and directory slashes and it SHOULD leave us with just the term slug
$term_slug = str_ireplace( array( '/', $taxonomy ), '', $_SERVER['REQUEST_URI'] );
// If the term slug matches the one we're checking, do our switch
if ( $term_slug == $term_slug_to_check ) {
return yes_do_theme_switch();
}
}
// Try to get post slug from the URL since the global $post object isn't available this early
$post = get_page_by_path( $_SERVER['REQUEST_URI'], OBJECT, $post_type );
if ( ! $post )
return;
// Get the post's categories
$cats = get_the_terms( $post, $taxonomy );
if ( ! $cats )
return;
// filter out just the category slugs
$term_slugs = wp_list_pluck( $cats, 'slug' );
if ( ! $term_slugs )
return;
// Check if our category to check is there
$is_app_category = in_array( $term_slug_to_check, $term_slugs );
if ( ! $is_app_category )
return;
yes_do_theme_switch();
}
function yes_do_theme_switch( $template ) {
// Ok, switch the current theme.
add_filter( 'template', 'switch_to_my_app_theme' );
add_filter( 'option_template', 'switch_to_my_app_theme' );
add_filter( 'option_stylesheet', 'switch_to_my_app_theme' );
}
function switch_to_my_app_theme( $template ) {
// Your theme slug
$template = 'your-app-theme';
return $template;
}

Fatal error when changing slug in wordpress

I want to change the slug of a post with a custom field.
In example, if the custom field is "keyword" my post link will become: mysite.com/keyword.
I wrote this script in fonction.php:
function change_default_slug($id) {
// get part number
$partno = get_post_meta( $id, 'partno', true );
$post_to_update = get_post( $id );
// prevent empty slug, running at every post_type and infinite loop
if ( $partno == '' )
return;
$updated_post = array();
$updated_post['ID'] = $id;
$updated_post['post_name'] = $partno;
wp_update_post( $updated_post ); // update newly created post
}
add_action('save_post', 'change_default_slug');
add_action( 'add_meta_boxes', 'cd_meta_box_add' );
function cd_meta_box_add()
{
add_meta_box( 'my-meta-box-id', 'My First Meta Box', 'cd_meta_box_cb', 'post', 'normal', 'high' );
}
function cd_meta_box_cb( $post )
{
$values = get_post_custom( $post->ID );
$text = isset( $values['my_meta_box_text'] ) ? esc_attr( $values['my_meta_box_text'][0] ) : '';
wp_nonce_field( 'my_meta_box_nonce', 'meta_box_nonce' );
?>
<p>
<label for="my_meta_box_text">Text Label</label>
<input type="text" name="my_meta_box_text" id="my_meta_box_text" value="<?php echo $text; ?>" />
</p>
<?php
}
add_action( 'save_post', 'cd_meta_box_save' );
function cd_meta_box_save( $post_id )
{
// Bail if we're doing an auto save
if( defined( 'DOING_AUTOSAVE' ) && DOING_AUTOSAVE ) return;
// if our nonce isn't there, or we can't verify it, bail
if( !isset( $_POST['meta_box_nonce'] ) || !wp_verify_nonce( $_POST['meta_box_nonce'], 'my_meta_box_nonce' ) ) return;
// if our current user can't edit this post, bail
if( !current_user_can( 'edit_post' ) ) return;
// now we can actually save the data
$allowed = array(
'a' => array( // on allow a tags
'href' => array() // and those anchords can only have href attribute
)
);
// Probably a good idea to make sure your data is set
if( isset( $_POST['my_meta_box_text'] ) )
update_post_meta( $post_id, 'my_meta_box_text', wp_kses( $_POST['my_meta_box_text'], $allowed ) );
}
$partno = get_post_meta($post->ID,'my_meta_box_text',true);
echo $partno;
This script return me "Fatal error: Maximum execution time of 30 seconds exceeded". But it seems it work because my slug change. Any idea about this issue?
The 'save_post' action gets called by wp_update_post(), so your change_default_slug() function causes an infinite loop. You need to perform a check within change_default_slug() and bail out if the function has already been called:
function change_default_slug($id) {
static $beentheredonethat = false;
if ($beentheredonethat) return;
$beentheredonethat = true;
//do your stuff and save the post...
}

Categories