Support

Account

Home Forums ACF PRO Custom field filter updates URL but no filtering of posts? Reply To: Custom field filter updates URL but no filtering of posts?

  • Hi @amyk

    I’ve done something similar but used AJAX. I used taxonomies as checkboxes but you may be able to adjust to suit your needs.

    I had this in my template:

    
    <section class="collapse" id="filters">
    	<div class="container">
    		<div class="row">
    			<div class="col-12 col-md-3 pb-4">
    			<?php
                $brand = array(
                    'taxonomy'		=> 'brand',
                );
                $brands = get_categories( $brand );
                ?>
                <?php foreach($brands as $brand): ?>
                <div class="form-check">            
                    <label class=""><input type="checkbox" value="<?php echo $brand->term_id; ?>" class="form-check-input  brand" /><?php echo $brand->cat_name; ?></label>             
                    
                </div>
                <?php endforeach; ?>
                <a href="#" class="btn btn-outline-secondary d-block mx-auto" id="reset_brand">Reset Brands</a>  
    			</div><!-- /col-md-3 --> 
                
    			<div class="col-12 col-md-3 pb-4" id="checkboxes">
    			<?php
                $colour = array(
                    'taxonomy'		=> 'colour',
                );
                $colours = get_categories( $colour );
                ?>
                <?php foreach($colours as $colour): ?>
                <div class="form-check">              
                    <label class=""><input type="checkbox" value="<?php echo $colour->term_id; ?>" class="form-check-input  colour" /><?php echo $colour->cat_name; ?></label>                
                </div>
                <?php endforeach; ?>      
                <a href="#" class="btn btn-outline-secondary d-block mx-auto" id="reset_colour">Reset Colours</a>     
    			</div><!-- /col-md-3 -->  
                
    			<div class="col-12 col-md-3 pb-4">
    			<?php
                $finish = array(
                    'taxonomy'		=> 'finish',
                );
                $finishes = get_categories( $finish );
                ?>
                <?php foreach($finishes as $finish): ?>
                <div class="form-check">
                	<!--
                    <input type="checkbox" value="<?php echo $finish->term_id; ?>" class="form-check-input finish" />
                    <label class="form-check-label" for="<?php echo $finish->cat_name; ?>"><?php echo $finish->cat_name; ?></label>
                    -->                
                    <label class=""><input type="checkbox" value="<?php echo $finish->term_id; ?>" class="form-check-input  finish" /><?php echo $finish->cat_name; ?></label>                 
                </div>
                <?php endforeach; ?>
                <a href="#" class="btn btn-outline-secondary d-block mx-auto" id="reset_finish">Reset Finish</a>
    			</div><!-- /col-md-3 -->  
                
    			<div class="col-12 col-md-3 pb-4">
    			<?php
                $style = array(
                    'taxonomy'		=> 'style',
                );
                $styles = get_categories( $style );
                ?>
                <?php foreach($styles as $style): ?>
                <div class="form-check">              
                    <label class=""><input type="checkbox" value="<?php echo $style->term_id; ?>" class="form-check-input  style" /><?php echo $style->cat_name; ?></label>                  
                </div>
                <?php endforeach; ?>
                <a href="#" class="btn btn-outline-secondary d-block mx-auto" id="reset_style">Reset Style</a>
    			</div><!-- /col-md-3 -->                                                
    		</div><!-- /row -->
    	</div><!-- /container -->	   
    </section>   
    
    <section>
    	<div class="container-fluid pb-4">
    		<div class="row">
    			<div class="col-md-12">
    
    				<a class="float-right btn btn-outline-dark mb-3" data-toggle="collapse" href="#filters" role="button" aria-expanded="false" aria-controls="filters">Filter Kitchens <i class="far fa-caret-square-down"></i></a>
    
    			</div><!-- /col-md-12 -->														
    		</div><!-- /row -->    
    		<div class="row align-self-center" id="ajax_filter_kitchens">	
                
    			<?php      
                $args = array(
                    'post_type'			=> 'kitchens',
                    'posts_per_page'	=> -1,
                );
            
                $query = new WP_Query( $args );
                if( $query->have_posts() ) :
                    while( $query->have_posts() ): $query->the_post();
                        include __DIR__ . '/includes/loop-alt.php';
                    endwhile;
                    wp_reset_postdata();
                else :
                    echo 'No kitchens found matching your criteria.';
                endif;
                ?>
    		           
    		</div><!-- /row -->
    	</div><!-- /container -->	
    </section>    

    I didn’t want the default look of checkboxes, so added some CSS:

    /*** filter checkboxes ***/
    #filters label {
    	border:1px solid #ccc;
    	padding:10px;
    	margin:0 0 10px;
    	display:block; 
    }
    
    #filters label:hover {
    	background:#eee;
    	cursor:pointer;
    }
    #filters .form-check-input {
    	margin-left: 0;
    }
    #filters input[type=checkbox]{
    	opacity: 0;
    }
    #filters input[type="checkbox"]:checked label  {
    	background:#f00;
    }
    .selected {
    	background:#eee
    }
    .form-check {
        padding-left: 0;
    }

    In the footer or enqueue the script, I then had the following:

    
    <script type="text/javascript">
    //filter the kitchens
    jQuery(function($){
        filter_data();
    
        function filter_data()
        {
            $('.filter_data').html('<div id="loading" style="" ></div>');
            var action = 'filter_kitchens';		
    		
            var brand = get_filter('brand');
            var colour = get_filter('colour');
            var finish = get_filter('finish');
    		var style = get_filter('style');	
    		
    		$.ajax({
    			type        : "POST",
    			data		: { action:action, brand:brand, colour:colour, finish:finish, style:style},
    			dataType	: "html",
    			url			: '<?php echo admin_url('admin-ajax.php');?>', 
    
    			success     : function(data) {
    				//alert(this.data);
    				jQuery("#ajax_filter_kitchens").html(data);
    				console.log("action:" + action + " brand: " + brand + " colour: " + colour + " finish: " + finish + " style: " + style); //debug
    			},
    			error       : function(xhr, status, error) {
    				var err = eval("(" + xhr.responseText + ")");
    				alert(err.Message);
    			}
    		});
    		return false;
        }
    
        function get_filter(class_name)
        {
            var filter = [];
            $('.'+class_name+':checked').each(function(){
                filter.push($(this).val());
            });
            return filter;
        }
    
        $('.form-check-input').click(function(){
            filter_data();
        });
    	
    	$("#reset_brand").click(function(){
    		// get the current selected values
    		var brand = [];
    		$('.brand:checked').each(function(){
    			brand.push($(this).val());
    		});
    		
    		// loop through and remove the selected checkobox
    		var i;
    		for (i = 0; i < brand.length; i++) {
    			$(".brand:checkbox[value="+brand[i]+"]").parent().removeClass('selected'); //remove the highlighted lable
    			$(".brand:checkbox[value="+brand[i]+"]").prop("checked", false); //uncheck the hidden checkbox
    		}		
    		
    		// reset the array
    		brand = []; 
    		console.log(brand); //debug
    	
    		// update the filter
    	 	filter_data();			  
    	});	
    	
    	$("#reset_colour").click(function(){
    		// get the current selected values
    		var colour = [];
    		$('.colour:checked').each(function(){
    			colour.push($(this).val());
    		});
    		
    		// loop through and remove the selected checkobox
    		var i;
    		for (i = 0; i < colour.length; i++) {
    			$(".colour:checkbox[value="+colour[i]+"]").parent().removeClass('selected'); //remove the highlighted lable
    			$(".colour:checkbox[value="+colour[i]+"]").prop("checked", false); //uncheck the hidden checkbox
    		}		
    		
    		// reset the array
    		colour = []; 
    		console.log(colour); //debug
    	
    		// update the filter
    	 	filter_data();			  
    	});	
    	
    	$("#reset_finish").click(function(){
    		// get the current selected values
    		var finish = [];
    		$('.finish:checked').each(function(){
    			finish.push($(this).val());
    		});
    		
    		// loop through and remove the selected checkobox
    		var i;
    		for (i = 0; i < finish.length; i++) {
    			$(".finish:checkbox[value="+finish[i]+"]").parent().removeClass('selected'); //remove the highlighted lable
    			$(".finish:checkbox[value="+finish[i]+"]").prop("checked", false); //uncheck the hidden checkbox
    		}		
    		
    		// reset the array
    		finish = []; 
    		console.log(finish); //debug
    	
    		// update the filter
    	 	filter_data();			  
    	});		
    	
    	$("#reset_style").click(function(){
    		// get the current selected values
    		var style = [];
    		$('.style:checked').each(function(){
    			style.push($(this).val());
    		});
    		
    		// loop through and remove the selected checkobox
    		var i;
    		for (i = 0; i < style.length; i++) {
    			$(".style:checkbox[value="+style[i]+"]").parent().removeClass('selected'); //remove the highlighted lable
    			$(".style:checkbox[value="+style[i]+"]").prop("checked", false); //uncheck the hidden checkbox
    		}		
    		
    		// reset the array
    		style = []; 
    		console.log(style); //debug
    	
    		// update the filter
    	 	filter_data();			  
    	});		
    	
    	
    });
    </script>

    Finally, in my functions:

    
    ##########################
    # Ajax filter Kitchens
    ##########################
    function filter_kitchens() {
    	
    	$args = array(
    		'post_type'			=> 'kitchens',
    		'posts_per_page'	=> -1,
    	);
    
    	if( isset( $_POST['brand'] ) )
    		$args['tax_query'] = array(
    			array(
    				'taxonomy' => 'brand',
    				'field' => 'id',
    				'terms' => $_POST['brand']
    			)
    		);
    		
    	if( isset( $_POST['colour'] ) )
    		$args['tax_query'] = array(
    			array(
    				'taxonomy' => 'colour',
    				'field' => 'id',
    				'terms' => $_POST['colour']
    			)
    		);	
    		
    	if( isset( $_POST['finish'] ) )
    		$args['tax_query'] = array(
    			array(
    				'taxonomy' => 'finish',
    				'field' => 'id',
    				'terms' => $_POST['finish']
    			)
    		);
    		
    	if( isset( $_POST['style'] ) )
    		$args['tax_query'] = array(
    			array(
    				'taxonomy' => 'style',
    				'field' => 'id',
    				'terms' => $_POST['style']
    			)
    		);			
    
    	$query = new WP_Query( $args );
    	if( $query->have_posts() ) :
    		while( $query->have_posts() ): $query->the_post();
    			if(get_template_part('includes/loop-alt')): get_template_part('includes/loop-alt'); endif;
    		endwhile;
    		wp_reset_postdata();
    	else :
    		echo 'No kitchens found matching your criteria.';
    	endif;
    	
    	die();
    
    }
    // Fire AJAX action for both logged in and non-logged in users
    add_action('wp_ajax_filter_kitchens', 'filter_kitchens');
    add_action('wp_ajax_nopriv_filter_kitchens', 'filter_kitchens');

    May be way more than you need but you might be able to tailor to your needs.