Drupal, Ubercart, products templates (prices templates) - drupal

I want to change the template of my Ubercart products. More in detail, I want to add the label "From..." in front of each price. But I cannot find the template to do it.
I'm also using theme developer module and this is what I get:
zen_uc_product_price <
phptemplate_uc_product_price <
theme_uc_product_price
But I cannot find such files.
thanks

You can also make a node-product.tpl.php file, if so this is the way to get prices:
<?php
$context = array(
'type' => 'product',
'revision' => 'altered', // using altered to get the bare price with no themeing
'field' => 'sell_price',
'subject' => array('node' => $node)
);
$dp = uc_price($node->sell_price, $context);
$context['field'] = 'list_price';
$lp = uc_price($node->list_price, $context);
?>
<div class="price clear-block <?php if($dp != $lp) print 'discounted'; ?>">
<?php print 'From: ' . $node->content['display_price']['#value']; ?>
<?php //print $node->content['list_price']['#value']; ?>
</div>
This became a bit more than it should be:
Use:
content['display_price']['#value']; ?>
Unless you want to theme discounted pricing :-)
Just copied out from one of my projects.
Last: you can probably use theme_uc_product_price:
you add a function in template.php (Pasting in default implementation from uc_product.module
function zen_uc_product_price($price, $context, $options = array()) {
$output = '<div class="product-info '. implode(' ', (array)$context['class']) .'">';
$output .= uc_price($price, $context, $options);
$output .= '</div>';
return $output;
}
Inspect the $context variable for when to add the "From" part.

To add a prefix or suffix to the price, you can go to
/admin/store/settings/store/edit/format

Related

How to get_field() in posts loop in WordPress?

I am trying to create a function for a shortcode to loop through an 'articles' custom post type. This is essentially a downloadable file uploaded by users and is a custom post type without the content field/editor box in the post editor. This custom post type also has a 'download_link' ACF field attached to it which is the location of the file for downloads. This is the href attribute for each post in the feed. However, the field is not generating any output in the function below. However the title is being populated. I know that all the article posts have a value provided for this particular field. Am I missing something? Thanks.
// CREATE A FEED OF ARTICLES WITH LINKS
function articles_download_feed(){
$articles_query = new WP_Query(array('post_type' => 'article',
'post_status' => 'any'));
if( $articles_query->have_posts() ){
$output = '<ul>';
while( $articles_query->have_posts() ){
$articles_query->the_post();
$articleID = get_the_ID();
$title = get_the_title($articleID);
if(get_field('download_link', $articleID)){
$download = get_field('download_link', $articleID, true);
} else {
$download = 'ABC';
}
$output .= '<li><a target="_blank" href="'.$download.'">'.$title.'</a></li>';
}
$output .= '</ul>';
wp_reset_postdata();
return $output;
}
} add_shortcode('articles_feed', 'articles_download_feed');
I managed to fix this issue myself.
I set up the 'dile_dl_link' custom field for 'article' type posts via the add_post_meta() WP function, instead of via Advanced Custom Fields (below is the segment of code to create a new article):
// CREATE NEW ARTICLE LINK FROM GRAVITY FORM SUBMISSION
function article_upload_createlink($entry, $form){
// Fields
$post_title = ucwords($entry[8]);
$post_status = 'publish';
$post_excerpt = $entry[9];
$post_type = 'article';
$dl_link = $entry[3];
// Post being created
$new_article = array(
'post_title' => $post_title,
'post_status' => $post_status,
'post_excerpt' => $post_excerpt,
'post_type' => $post_type,
);
// ID for post
$theId = wp_insert_post($new_article);
// Update download_link
add_post_meta($theId, 'file_dl_link', $dl_link);
} add_action( 'gform_after_submission_7', 'article_upload_createlink', 10, 2 );
The function in question as presented in the question has been changed as seen below:
// CREATE A FEED OF ARTICLES WITH LINKS
function articles_download_feed(){
$articles_query = new WP_Query(array('post_type' => 'article', 'post_status' => 'any'));
if( $articles_query->have_posts() ){
$output = '';
while( $articles_query->have_posts() ){
$articles_query->the_post();
$articleID = get_the_ID();
$title = get_the_title();
$excerpt = get_the_excerpt();
$get_dllink = get_post_meta($articleID, 'file_dl_link', true);
$output .= '<div class="wpb_wrapper">
<div class="vc_empty_space" style="height: 24px">
<span class="vc_empty_space_inner"></span>
</div>
<div class="wpb_text_column ">
<div class="wpb_wrapper">
<h4>'.$title.'</h4>
<p>'.$excerpt.'</p></div>
</div>
<div class="w-btn-wrapper align_left">
<a target="_blank" class="w-btn style_raised color_primary icon_none" href="'.$get_dllink.'"><span class="w-btn-label">DOWNLOAD</span><span class="ripple-container"></span></a>
</div>
</div>
<div class="w-separator type_default size_medium thick_1 style_solid color_border cont_none">
<span class="w-separator-h"></span>
</div>';
}
wp_reset_postdata();
return $output;
}
}
add_shortcode('articles_feed', 'articles_download_feed');

Wordpress - Custom plugin to return related posts by category

I'm learning how to create custom plugins for Wordpress, I am trying to get related posts by category.
The problem is, I am returning all posts regardless of it's category whether it's the same category or not.
I've done a var_dump on the $categoriesIds[] and it is pulling the right category for each post.
I'm guessing something is not right with the WP_Query?
Can someone point out what is missing with the code?
function Add_related_posts($content) {
// If it's not a singular post, return the content
if (!is_singular('post')) {
return $content;
}
// Get post categories
$categories = get_the_terms(get_the_ID(), 'category');
$categoriesIds = [];
foreach ($categories as $category) {
$categoriesIds[] = $category->term_id;
}
$loop = new WP_Query(array(
'category_in' => $categoriesIds,
'posts_per_page' => 4,
'post_not_in' => array(get_the_ID()),
'orderby' => 'rand'
));
// If there are posts
if ($loop->have_posts()) {
$content .= 'RELATED POSTS:<br><ul>';
while ($loop->have_posts()) {
$loop->the_post();
$content .= '<li>' . get_the_title() . '</li>';
}
}
$content .= '</ul>';
// Restore data
wp_reset_query();
return $content;
}
Categories are pulled as expected. But in argument in WP_Query, you got one problem.
It should be category__in, NOT category_in.
Try this:
'category__in' => $categoriesIds,
See documentation: http://codex.wordpress.org/Class_Reference/WP_Query#Category_Parameters

How to add placeholder in buddypress registration ? How to make field description as input placeholder?

How to add placeholder in buddypress registration?
Can we use field description as placeholder for input field?
In register.php under bp-template.These two lines of code make xprofile
$field_type = bp_xprofile_create_field_type( bp_get_the_profile_field_type() );
$field_type->edit_field_html();
How to edit them.Where these lines are connected.How to edit x-profile field.
Or even better yet, combining these two answers. Simply add this to your functions.php:
function wp_add_placeholder($elements){
$elements['placeholder'] = bp_get_the_profile_field_name();
return $elements;
}
add_action('bp_xprofile_field_edit_html_elements','wp_add_placeholder');
There is always a better way to do it then editing the core:
function wp_add_placeholder($elements){
$elements['placeholder'] = 'Placeholder';
return $elements;
}
add_action('bp_xprofile_field_edit_html_elements','wp_add_placeholder');
just struggled with this issue and fastest thing i came up were override classes that handles different fields:
First you need to find class named BP_XProfile_Field_Type_Textbox (for textbox). In bp v2.0.2 it can be found on bp-xprofile/bp-xprofile-class.php:2358. Copy whole class in your functions and rename class name as you desire. let's say i renamed it as CUSTOM_BP_XProfile_Field_Type_Textbox. Inside this class there are function called public function edit_field_html( array $raw_properties = array() ).
Replace:
$html = $this->get_edit_field_html_elements( array_merge(
array(
'type' => 'text',
'value' => bp_get_the_profile_field_edit_value(),
),
$raw_properties
) );
?>
<label for="<?php bp_the_profile_field_input_name(); ?>"><?php bp_the_profile_field_name(); ?> <?php if ( bp_get_the_profile_field_is_required() ) : ?><?php esc_html_e( '(required)', 'buddypress' ); ?><?php endif; ?></label>
<?php do_action( bp_get_the_profile_field_errors_action() ); ?>
<input <?php echo $html; ?>>
<?php
}
With that:
$required = bp_get_the_profile_field_is_required() ? ' ' . esc_html__( '(required)', 'buddypress' ) : '';
$html = $this->get_edit_field_html_elements( array_merge(
array(
'type' => 'text',
'value' => bp_get_the_profile_field_edit_value(),
'placeholder' => bp_get_the_profile_field_name() . $required
),
$raw_properties
) );
?>
<?php do_action( bp_get_the_profile_field_errors_action() ); ?>
<input <?php echo $html; ?>>
<?php
}
Next thing you need to do is override function that hendles field classes. Copy function called bp_xprofile_get_field_types into your theme and rename it. let's say i renamed it as custom_bp_xprofile_get_field_types.
In fields array rename 'textbox' value from BP_XProfile_Field_Type_Textbox to CUSTOM_BP_XProfile_Field_Type_Textbox (the class you created and modified).
Finl thing you need to do is override function that print final result. Copy function called bp_xprofile_create_field_type into your theme and rename it. let's say i renamed it as custom_bp_xprofile_create_field_type.
In this function replace:
$field = bp_xprofile_get_field_types();
with:
$field = custom_bp_xprofile_get_field_types();
to use your modified field output
In register.php use just created new function instead of original buddypresses one so the final result will be:
$field_type = custom_bp_xprofile_create_field_type( bp_get_the_profile_field_type() );
$field_type->edit_field_html();
It is good to copy register.php to YOUR_THEME/buddypress/members/register.php to not lose your changes after updating the bp plugin.
If you like to modify other fields just rename field's class in classes array in custom_bp_xprofile_get_field_types and copy bp's class of that field and rename it as in fields array.
Hope that helps. There might be better way, but i didn't find any.

How to add custom post type archive to menu

I have been searching for weeks and I still haven't found a proper solution to this problem.
I am writing a Wordpress Theme. I have a custom post type called Works. I would like to add my Works archive to my menu and have it as well as it's posts highlighted when I access them.
I can access my archive and posts on the following links
Works archive: /works/
Works single post: /works/postname/
My solution so fare have been to name my archive-works.php template file with a template name (Work archive). Then create an empty page using that template and adding the page to the menu. This highlights the archive in the menu but not the single posts.
I can easily solve this with a custom link and some javascript but there must be a better and cleaner way.
You can do a simple trick in your functions.php:
add_filter('nav_menu_css_class', 'current_type_nav_class', 10, 2);
function current_type_nav_class($classes, $item) {
// Get post_type for this post
$post_type = get_query_var('post_type');
// Go to Menus and add a menu class named: {custom-post-type}-menu-item
// This adds a 'current_page_parent' class to the parent menu item
if( in_array( $post_type.'-menu-item', $classes ) )
array_push($classes, 'current_page_parent');
return $classes;
}
In your case, you just have to add a class 'works-menu-item' with that archive menu item by the admin panel;
To add "custom posttype archive link" to menu, please look at the following guide
Open file functions.php , and enter code below
add_action('admin_head-nav-menus.php', 'wpclean_add_metabox_menu_posttype_archive');
function wpclean_add_metabox_menu_posttype_archive() {
add_meta_box('wpclean-metabox-nav-menu-posttype', __('Custom Post Type Archives'), 'wpclean_metabox_menu_posttype_archive', 'nav-menus', 'side', 'default');
}
function wpclean_metabox_menu_posttype_archive() {
$post_types = get_post_types(array('show_in_nav_menus' => true, 'has_archive' => true), 'object');
if ($post_types) :
$items = array();
$loop_index = 999999;
foreach ($post_types as $post_type) {
$item = new stdClass();
$loop_index++;
$item->object_id = $loop_index;
$item->db_id = 0;
$item->object = 'post_type_' . $post_type->query_var;
$item->menu_item_parent = 0;
$item->type = 'custom';
$item->title = $post_type->labels->name;
$item->url = get_post_type_archive_link($post_type->query_var);
$item->target = '';
$item->attr_title = '';
$item->classes = array();
$item->xfn = '';
$items[] = $item;
}
$walker = new Walker_Nav_Menu_Checklist(array());
echo '<div id="posttype-archive" class="posttypediv">';
echo '<div id="tabs-panel-posttype-archive" class="tabs-panel tabs-panel-active">';
echo '<ul id="posttype-archive-checklist" class="categorychecklist form-no-clear">';
echo walk_nav_menu_tree(array_map('wp_setup_nav_menu_item', $items), 0, (object) array('walker' => $walker));
echo '</ul>';
echo '</div>';
echo '</div>';
echo '<p class="button-controls">';
echo '<span class="add-to-menu">';
echo '<input type="submit"' . disabled(1, 0) . ' class="button-secondary submit-add-to-menu right" value="' . __('Add to Menu') . '" name="add-posttype-archive-menu-item" id="submit-posttype-archive" />';
echo '<span class="spinner"></span>';
echo '</span>';
echo '</p>';
endif;
}
Thanks
Thanks to rasmussvanejensen for her/his nice question and thethangtran for the answer, I am still confused why Wordpress has not yet added such a good feature to its code base by default.
By the way I think there is even a better solution than the one provided by thethangtran, as it may break on some situations.
Note 1
According to the Codex, using register_post_type, one can add extra post_types to the installation. There is chance, some one need to change the 'query_var' and thus the provided code will break.
Note 2
In addition, it may not handle the current-menu-item class, which will be used for css customization to show the menu item as active.
Note 3
As another note on the code, there is no need to define the loop_index, item and items variables. they are absolutely useless.
A better solution
So I suggest using this alternative, for those who want a more robust solution to on this:
function prefix_add_metabox_menu_posttype_archive(){
add_meta_box( 'prefix_metabox_menu_posttype_archive', __( 'Archives' ), 'prefix_metabox_menu_posttype_archive', 'nav-menus', 'side', 'default' );
}
add_action( 'admin_head-nav-menus.php', 'prefix_add_metabox_menu_posttype_archive' );
function prefix_metabox_menu_posttype_archive(){
$post_types = get_post_types( array( 'show_in_nav_menus' => true, 'has_archive' => true ), 'object' );
if( $post_types ){
foreach( $post_types as $post_type ){
$post_type->classes = array( $post_type->name );
$post_type->type = $post_type->name;
$post_type->object_id = $post_type->name;
$post_type->title = $post_type->labels->name;
$post_type->object = 'cpt_archive';
}
$walker = new Walker_Nav_Menu_Checklist( array() );?>
<div id="cpt-archive" class="posttypediv">
<div id="tabs-panel-cpt-archive" class="tabs-panel tabs-panel-active">
<ul id="ctp-archive-checklist" class="categorychecklist form-no-clear"><?php
echo walk_nav_menu_tree( array_map( 'wp_setup_nav_menu_item', $post_types ), 0, (object) array( 'walker' => $walker ) );?>
</ul>
</div>
</div>
<p class="button-controls">
<span class="add-to-menu">
<input type="submit"<?php disabled( $nav_menu_selected_id, 0 ); ?> class="button-secondary submit-add-to-menu" value="<?php esc_attr_e( 'Add to Menu' ); ?>" name="add-ctp-archive-menu-item" id="submit-cpt-archive" />
</span>
</p><?php
}
}
function prefix_cpt_archive_menu_filter( $items, $menu, $args ){
foreach( $items as &$item ){
if( $item->object != 'cpt_archive' ) continue;
$item->url = get_post_type_archive_link( $item->type );
if( get_query_var( 'post_type' ) == $item->type ){
$item->classes []= 'current-menu-item';
$item->current = true;
}
}
return $items;
}
add_filter( 'wp_get_nav_menu_items', 'prefix_cpt_archive_menu_filter', 10, 3 );
Navigate to Appearance > Menus;
Make sure you have the Works' custom post type selected at Screen Options;
Click on the name of your custom post type to expand it and then click on the ‘View all’ tab;
You will see an option for All Works. Check the box next to it and then click on the Add to Menu button;
Your custom post type archive will now appear as a menu item in the right column;
By default, the label will be "All Works". You can change this by writing something different at the Navigation Label;
Click on the Save Menu button to save your changes.
I found a solution on GitHub and it works out of the box by simply adding it to the functions.php without any walkers or extra classes.
This code solves it by comparing the slug of the current post type
with the navigation items, and adds a class accordingly.
Code on GitHub

Is there an alternative to wp_list_categories

I would like to display a list of all categories, using their hierarchy. I want to use jquery to manipulate other objects when the categories are clicked, so I need to remove the links that are added by default.
wp_list_categories does this wonderfully, automatically adding hierarchy of the sub-categories and adding the nested lists. I just do not want the links that are added by default.
Is there an alternative to wp_list_categories which does not give each category a link to its respective page?
When I tried get_categories(), it did not respect the hierarchy of the categories.
Using latest WP version.
The output of teh wp_list_categories() function is passed through a filter, which you could use to modify the resulting HTML:
$output = apply_filters( 'wp_list_categories', $output, $args );
If you want to actually modify the HTML that is generated by the function, you can extend the Walker_Category class, a good explanation can be found here http://scribu.net/wordpress/extending-the-category-walker.html
The Walker_Category class is what ultimately worked for me. It had all the of the leverage I needed to make a custom list.
However, I just wanted to post my first attempt, that worked pretty well for a simple list. It uses nested loops.
<div class="tab-row">
<?php $args = array(
'taxonomy' => 'taxonomyName',
'parent' => 0
);
$categories = get_categories($args);
$catid = array();
foreach($categories as $category) {
echo '<ul class="parent-tab"><div class="parent-item">' . $category->name . '</div>';
array_push($catid, $category->term_id);
echo '</ul>';
} ?>
</div>
<div class="child-row">
<?php
$countStop = count($categories);
$i = 0;
while ($i < $countStop) {
echo "<ul class='child-list'>";
$args = array(
'taxonomy' => 'taxonomyName',
'parent' => $catid[$i]
);
$categories = get_categories($args);
foreach($categories as $category) {
echo '<li class="child-item">' . $category->name .'</li>';
}
echo "</ul>";
$i++;
}
?>
</div>
I used get_categories() which eliminated the links, and created my taxonomy hierarchy by only displaying the parents in the first loop, and in the nested loop, pulling out the children of that parent by retrieving the parent ID.

Resources