I have a table which include names, the last name of each entry needs to be truncated ex. Miles Davis becomes Miles D.
I achieve this with the following JS:
$('.trunc-name').each(function (d, td) {
$(td).text($(td).text().replace(/^(\S+)\s+(\S).*/, '$1 $2.'));
});
and the td class is set to trunc-name:
<td class="trunc-name"><?php foreach ($resident_name_terms as $object) { echo $object->name; } ?></td>
Those table contents (which are actually WP taxonomy terms) are filterable via a select form - the options of which are getting truncated too.
Select:
if( $terms = get_terms( array(
'taxonomy' => 'resident_name',
'orderby' => 'name'
) ) ) :
echo '<select name="resident_name_filter"><option value="" selected="selected">' . __( 'All Residents', 'mv' ) . '</option>';
foreach ( $terms as $term ) :
echo '<option class="trunc-name" value="' . $term->term_id . '">' . $term->name . '</option>';
endforeach;
echo '</select>';
endif;
So far everything works fine. The problem is that when I change criteria via a select option for that column (built with AJAX), the newly outputted values are not truncated.
Query Params:
$relation = 'AND';
$params = array();
$args['tax_query']['relation'] = $relation;
foreach ( $taxonomies as $tax ) {
if( isset( $_POST[ $tax . '_filter' ] ) && !empty( $_POST[ $tax . '_filter' ] ) ) {
$args['tax_query'][] = array(
'taxonomy' => $tax,
'field' => 'id',
'terms' => $_POST[ $tax . '_filter' ],
);
}
};
Loop:
$query = new WP_Query( $args );
if( $query->have_posts() ) : ?>
<table style="width:100%" id="incident-reports">
<tr>
<th>Resident</th>
</tr>
<?php
while( $query->have_posts() ): $query->the_post();
$resident_name_terms = get_the_terms( $post->ID, 'resident_name' );
?>
<tr>
<td class="trunc-name"><?php foreach ($resident_name_terms as $object) { echo $object->name; } ?></td>
</tr>
<?php endwhile; ?>
</table>
endif;
Any help is, as always, greatly appreciated!
You need to run the truncate code in the success: function after it creates the new elements.
$.ajax({
...
success: function(response) {
... // code that adds the new HTML
$('.trunc-name').each(function (d, td) {
$(td).text($(td).text().replace(/^(\S+)\s+(\S).*/, '$1 $2.'));
});
}
});
Related
I want to add a custom dropdown list of an attribute (in this case it's the brand), with the options lead to the attribute page as a link.
I got this working
add_filter('woocommerce_before_shop_loop','wc_reg_for_menus', 1, 2);
function wc_reg_for_menus() {
$terms = get_terms( 'pa_marke' );
if ( ! empty( $terms ) && ! is_wp_error( $terms ) ){
echo '<select>';
foreach ( $terms as $term ) {
echo '<option value="'.$term->name.'">'.$term->name.'</option>';
}
echo '</select>';
}
}
And I think I somehow need to add this part
get_term_link( WP_Term|int|string $term, string $taxonomy = '' )
Thank you!
Felix
Your code works well for getting values for a specific taxonomy (attribute).I only changed the get_terms function.
I also added some data attributes to get the taxonomy and slug of each term (option).
add_filter( 'woocommerce_before_shop_loop','wc_reg_for_menus' );
function wc_reg_for_menus() {
$terms = get_terms( array(
'taxonomy' => 'pa_marke',
'hide_empty' => false,
));
if ( ! empty( $terms ) && ! is_wp_error( $terms ) ){
echo '<select id="shop_pa_marke">';
foreach ( $terms as $term ) {
echo '<option value="' . $term->name . '" data-taxonomy="' . $term->taxonomy . '" data-slug="' . $term->slug . '">' . $term->name . '</option>';
}
echo '</select>';
}
}
Then you will need to use a jQuery script to redirect the user based on the chosen attribute option.
add_action( 'wp_footer', 'redirect_after_select_option' );
function redirect_after_select_option() {
?>
<script type="text/javascript">
jQuery( function($){
$('#shop_pa_marke').change(function(){
const url = window.location.href;
const taxonomy = $(this).children("option:selected").data('taxonomy').replace('pa_','filter_');
const slug = $(this).children("option:selected").data('slug');
let urlParams = new URLSearchParams(window.location.search);
urlParams.set(taxonomy, slug);
window.location.replace( '?'+urlParams.toString() );
});
});
</script>
<?php
}
The code has been tested and works. Add it to your active theme's functions.php.
Thank you!
Just now I found a solution without jQuery, that works quite fine as well:
add_filter('woocommerce_before_shop_loop','wc_reg_for_menus', 1, 2);
function wc_reg_for_menus() {
$terms = get_terms( 'pa_marke' );
if ( ! empty( $terms ) && ! is_wp_error( $terms ) ){
echo '<select onchange="location = this.value;">';
foreach ( $terms as $term ) {
echo '<option value="'.get_term_link( $term ).'">'.$term->name.'</option>';
}
echo '</select>';
}
}
Only after the new page loaded, the first option of the menu is selected again, but that´s ok for me, because it won't be displayed there later on.
My code:
<?php
function filter_profiles_by_country()
{
$url = get_site_url();
if ( $terms = get_terms( array('taxonomy' => 'country','orderby' => 'name') ) )
{
// if categories exist, display the dropdown
echo '<select name="categoryfilter" onchange="if (this.value) window.location.href=this.value">';
echo ' <option value="'.$url.'/profiles">All Profiles...</option>';
foreach ( $terms as $term )
{
// ID of the category as an option value
echo ' <option value="'.$url ."/country/". $term->name . '">' . $term->name . '</option>';
}
echo '</select>';
}
}
?>
When I click on All Profiles, it should take me to /profiles/ page. But it is not working.
<?php
function filter_profiles_by_country(){
$url = get_site_url();
global $wp;
$current_url = home_url(add_query_arg(array(), $wp->request));
if( $terms = get_terms( array(
'taxonomy' => 'country',
'orderby' => 'name'
) ) ) :
// if categories exist, display the dropdown
echo '<select name="categoryfilter" onchange="if (this.value) window.location.href=this.value"><option value="'.$url.'/profiles/">All Profiles...</option>';
foreach ( $terms as $term ) :
$loadedItem = $url."/country/".$term->name;
$selectedItem = ($current_url == $loadedItem)? "selected": "";
echo '<option '.$selectedItem.' value="'.$url ."/country/". $term->name . '">' . $term->name . '</option>'; // ID of the category as an option value
endforeach;
echo '</select>';
endif;
}
?>
Try this.
It's my first post here as well as I'm a beginner so please bear with me.
What I'd like to accomplish is to create an AJAX function that will list all available categories in form of checkboxes that a user can select from. After selecting and hitting 'Apply' I'd like to show a list of all tags (also in form of checkboxes) from posts that are assigned to the selected category/categories. Then user can select from available tags and then after hitting final 'Apply' button the corresponding posts will be shown.
Similarly to TED.com 'What interests you?' but in AJAX. So first step would be Categories, second step would be Tags. Then posts that belong to selected category and that have selected tags assigned will be displayed.
So far, I figured how to list all available categories but when filtering by Tags it gives me a list of all tags not the tags for selected category only. Then the actual results (posts) are duplicated as well. How to filter by tags and remove duplication is beyond me unfortunately. I've put my function into shortcode as I'm using block builder so I can paste the shortcode into a Code module and place it anywhere on the page.
My function:
Edit: (now updated with Vitauts' answer + added code to remove duplicated results)
function filter_articles_shortcode() {
$siteurl = site_url();
$form = '<form id="filter2" action=" '. $siteurl .'/wp-admin/admin-ajax.php" method="POST">';
if( $cats = get_terms(
array(
'taxonomy' => 'category',
'orderby' => 'name'
)
)
) :
$form .= '<div>';
foreach ( $cats as $cat ) :
$form .= '<input name="cFilter[]" type="checkbox" id="'. $cat->slug .'" value="'. $cat->term_id .'">';
$form .= '<label for="'. $cat->slug .'">'. $cat->name .'</label>';
$form .= '<span>(' . $cat->count . ')</span>';
$form .= '<br />';
endforeach;
$form .= '</div>';
endif;
$form .= '<button id="cat-btn">Apply</button>';
$form .= '<input type="hidden" name="action" value="catFilter">';
$form .= '</form>';
$form .= '<div id="results"></div>';
return $form;
}
add_shortcode('filter-articles', 'filter_articles_shortcode');
add_action('wp_ajax_catFilter', 'show_filter_results');
add_action('wp_ajax_nopriv_catFilter', 'show_filter_results');
//
////
//
function show_filter_results() {
if( isset( $_POST['cFilter'] ) ) {
$args['tax_query'] = array(
array(
'taxonomy' => 'category',
'field' => 'id',
'terms' => $_POST['cFilter']
)
);
}
$query = new WP_Query( $args );
if( $query->have_posts() ) :
while( $query->have_posts() ): $query->the_post();
$w = the_title('<h3>', '</h3>', true);
$w .= the_category(', ');
$w .= the_tags('<div>',', ','</div>');
$w .= '<hr />';
echo $w;
endwhile;
wp_reset_postdata();
else :
echo 'nothing';
endif;
$siteurl = site_url();
$o .= '<form id="filter-tags" action=" '. $siteurl .'/wp-admin/admin-ajax.php" method="POST">';
$utags = array();
if( $query->have_posts() ) :
while( $query->have_posts() ): $query->the_post();
$tags = get_the_tags();
if ( !empty($tags) ) {
foreach( $tags as $tag ) {
$utag = $tag;
if(! in_array($utag, $utags)) {
$utags[] = $utag;
$o .= '<input name="tFilter[]" type="checkbox" id="tag−'. $utag->slug .'" value="'. $utag->term_id .'" />';
$o .= '<label for="tag−'. $utag->slug .'">'. $utag->name .'</label>';
$o .= '<span>(' . $utag->count . ')</span>';
$o .= '<br />';
}
}
}
endwhile;
$o .= '<button id="tags-btn">Tags</button>';
$o .= '<input type="hidden" name="action" value="tagFilter">';
foreach ($_POST['cFilter'] as $cfilter) {
$o .= '<input type="hidden" name="cFilter[]" value="' . esc_attr($cfilter) . '">';
}
wp_reset_postdata();
else :
echo 'nothing';
endif;
$o .= '</form>';
$o .= '<div id="tag-results"></div>';
echo $o;
echo "<script>
jQuery(function($){
$('#filter-tags').submit(function() {
var tags = $('#filter-tags');
$.ajax({
url:tags.attr('action'),
data:tags.serialize(),
type:tags.attr('method'),
beforeSend:function(xhr){
tags.find('#tags-btn').text('Searching...');
},
success:function(data){
tags.find('#tags-btn').text('Tag');
$('#tag-results').html(data);
}
});
return false;
});
});
</script>";
die();
}
add_action('wp_ajax_tagFilter', 'show_tags_results');
add_action('wp_ajax_nopriv_tagFilter', 'show_tags_results');
//
////
//
function show_tags_results() {
if( isset( $_POST['tFilter'] ) ) {
$args2['tax_query'] = array(
'relation' => 'AND',
array(
'taxonomy' => 'category',
'field' => 'id',
'terms' => $_POST['cFilter'],
'include_children' => false
),
array(
'taxonomy' => 'post_tag',
'field' => 'id',
'terms' => $_POST['tFilter'],
)
);
}
$query = new WP_Query( $args2 );
if( $query->have_posts() ) :
while( $query->have_posts() ): $query->the_post();
$e = the_title('<h3>', '</h3>', true);
$e .= the_category(', ');
$e .= the_tags('<div>',', ','</div>');
$e .= '<hr />';
echo $e;
endwhile;
wp_reset_postdata();
else :
echo 'nothing';
endif;
die();
}
AJAX:
jQuery(document).ready(function($){
$('#filter2').submit(function(){
var filter2 = $('#filter2');
$.ajax({
url:filter2.attr('action'),
data:filter2.serialize(), // form data
type:filter2.attr('method'), // POST
beforeSend:function(xhr){
filter2.find('#cat-btn').text('Searching...');
},
success:function(data){
filter2.find('#cat-btn').text('Apply'); // changing the button label back
$('#results').html(data); // insert data
}
});
return false;
});
});
On a side note - ideally I'd like to remove the 'Apply' buttons and instead have data show automatically via AJAX. In other words: select a category(ries) and immediately show all tags then select a tag(s) and immediately show all posts.
Any help will be appreciated and thank you for your time.
You need some changes to your code. First, tags list form needs to resubmit cFilter value, so in show_filter_results() add this code before/after hidden action field.
foreach ($_POST['cFilter'] as $cfilter) {
$o .= '<input type="hidden" name="cFilter[]" value="' . esc_attr($cfilter) . '">';
}
Then in show_tags_results() change tax_query to this
$args2['tax_query'] = array(
'relation' => 'AND',
array(
'taxonomy' => 'category',
'field' => 'id',
'terms' => $_POST['cFilter'],
'include_children' => false
),
array(
'taxonomy' => 'post_tag',
'field' => 'id',
'terms' => $_POST['tFilter'],
)
);
Here is My code, it should be filtering by category, it displays all posts on any checkbox I click, I don't know how to fix this, I have tried everything.
<form id="filter">
<?php
if( $terms = get_terms( 'category', 'orderby=name' ) ) : // to make it simple I use default categories
foreach ( $terms as $term ) :
echo '<input type="checkbox" name="category[]" value="' . $term->term_id . '" class="br">' . $term->name;
echo '';
endforeach;
endif;
?>
<div class="filter-output"></div>
</form>
Here is the js (coded inside a template page)
jQuery('#filter .br').click(function(){
// Declaratie van array
var choices = {};
jQuery('.contents').remove();
jQuery('.filter-output').empty();
jQuery('input[type=checkbox]:checked').each(function() {
if (!choices.hasOwnProperty(this.name))
choices[this.name] = [this.value];
else
choices[this.name].push(this.value);
});
console.log(choices);
jQuery.ajax({
url: '<?php echo admin_url('admin-ajax.php'); ?>',
type :'POST',
data : {
'action' : 'call_post', // Naam van de PHP functie
'choices' : choices,
},
success: function (result) {
jQuery('.filter-output').append(result);
// Voor testen - Resultaat (Kan later verwijderd worden)
//console.log(Resultaat);
//console.log(Keuzes);
},
error: function(err){
// Voor testen - Error (Kan later verwijderd worden)
console.log(err);
console.log(choices);
}
});
})
funstions.php
add_action('wp_ajax_call_post', 'call_post');
add_action('wp_ajax_nopriv_call_post', 'call_post');
function call_post(){
// Verkijgen van AJAX data:
$choices = $_POST['choices'];
$meta_query = array('relation' => 'OR');
foreach($choices as $Key=>$Value){
if(count($Value)){
foreach ($Value as $Inkey => $Invalue) {
$meta_query[] = array( 'key' => $Key, 'value' => $Invalue, 'compare' => '=' );
}
}
}
$args = array(
'post_type' => 'post',
'meta_query' =>$meta_query
);
$query = new WP_Query($args);
//if( ! empty ($params['template'])) {
////$template = $params['template'];
if( $query->have_posts() ) :
while( $query->have_posts() ): $query->the_post();
the_title();
endwhile;
wp_reset_query();
else :
wp_send_json($query->posts);
endif;
//}
die(); }
Anyone please help, I have been trying to make this work since yesterday and with no luck at all
I've refactored your code and made it work:
Template:
<?php
/**
*
* Template Name: Filter Posts
*
*/
get_header();
$args = array(
'post_type' => 'post',
'posts_per_page' => -1,
);
$tax_query = array();
$categories = get_terms( 'category', 'orderby=name' );
if ( ! empty( $choices = get_request_param( 'choices' ) ) ) {
$term_ids = explode(',', $choices);
$tax_query[] = array(
'taxonomy' => 'category',
'field' => 'term_id',
'terms' => $term_ids
);
$args['tax_query'] = $tax_query;
}
$query = new WP_Query( $args );
if ( ! empty( $categories ) ) : ?>
<form action="?" method="post" class="form-filter">
<?php foreach ( $categories as $category ) : ?>
<div class="checkbox">
<input type="checkbox" name="category[]" data-category="<?php echo esc_attr( $category->term_id ); ?>" id="<?php echo esc_attr( $category->slug ); ?>">
<label for="<?php echo esc_attr( $category->slug ); ?>">
<?php echo esc_html( $category->name ); ?>
</label>
</div><!-- /.checkbox -->
<?php endforeach; ?>
</form><!-- /.form-filter -->
<?php endif; ?>
<div class="filter-output">
<ul>
<?php while ( $query->have_posts() ) : $query->the_post(); ?>
<li>
<?php the_title(); ?>
</li>
<?php endwhile; ?>
</ul>
</div><!-- /.filter-output -->
<?php
wp_reset_postdata();
get_footer();
Javascript:
;(function(window, document, $) {
var $win = $(window);
var $doc = $(document);
$doc.on('change', '.form-filter', function() {
var choices = '';
$('.form-filter input:checked').each(function() {
if ( choices === '' ) {
choices += $(this).data('category');
} else {
choices += ',' + $(this).data('category');
}
});
$.ajax({
url: window.location.href,
type: 'GET',
data: {
'choices' : choices,
},
success: function(response) {
var newPosts = $(response).filter('.filter-output').html();
$('.filter-output').html(newPosts);
}
});
});
})(window, document, window.jQuery);
functions.php
function get_request_param( $key = '' ) {
$value = false;
if ( ! $key ) {
return $value;
}
if ( isset( $_POST[$key] ) ) {
$value = $_POST[$key];
} elseif ( isset( $_GET[$key] ) ) {
$value = $_GET[$key];
}
return $value;
}
Few notes:
1) Use jquery change event, instead of click for the filter form.
2) WP AJAX is not needed in this case. You can simply make a GET request to the same page and change the HTML where needed.
3) Use GET method instead of POST
Ask to everyone, i have problem. Here i try to use multiple chechbox to my custom post metabox.
<?php
function prodetail() {
add_meta_box('pro_metabox', 'Detail Property', 'pro_metabox', 'property', 'normal', 'default');
}
function pro_metabox() {
global $post;
echo '<input type="hidden" name="eventmeta_noncename" id="eventmeta_noncename" value="' .
wp_create_nonce( plugin_basename(__FILE__) ) . '" />';
$postmeta = maybe_unserialize( get_post_meta( $post->ID, 'elements', true ) );
$elements = array(
'pool' => 'Pool',
'garage' => 'Garage',
'balcon' => 'Balcon',
'yard' => 'Yard',
'internet' => 'Internet'
);
foreach ( $elements as $id => $element) {
if ( is_array( $postmeta ) && in_array( $id, $postmeta ) ) {
$checked = 'checked="checked"';
} else {
$checked = null;
}
?>
<div class="pro-inn">
<div class="procols">
<div class="pro-inn">
<input type="checkbox" name="multval[]" value="<?php echo $id; ?>" <?php echo $checked; ?> />
<?php echo $element;?>
</div>
</div>
</div>
<?php
}
}
function pro_meta($post_id, $post) {
if ( !wp_verify_nonce( $_POST['eventmeta_noncename'], plugin_basename(__FILE__) )) {
return $post->ID;
}
if ( !current_user_can( 'edit_post', $post->ID ))
return $post->ID;
if ( ! empty( $_POST['multval'] ) ) {
update_post_meta( $post_id, 'elements', $_POST['multval'] );
} else {
delete_post_meta( $post_id, 'elements' );
}
}
add_action('save_post', 'pro_meta', 1, 2);
?>
help me to add code to show this checked result to single.php because my code use foreach just show Array text not show text like Pool Garage Balcon ect.
Thanks
Use this code in your single.php file for your custom post
$meta_value = get_post_meta( $post->ID, 'elements', true );
foreach($meta_value as $key=>$value){
echo $value . ' ';
}
It will show results same as you mentioned in the question ie:
(Pool Garage Balcon ect.)