J'ai un type de message personnalisé (orateur) et j'aimerais charger la liste des orateurs triés par nom de famille. Je n'arrive pas à comprendre. J'ai essayé le code de ce post: https://stackoverflow.com/questions/16416217/wordpress-orderby-last-Word-in-title
mais cela n'a pas semblé fonctionner.
add_action( 'init', 'create_post_type' );
function create_post_type() {
register_post_type( 'event',
array(
'labels' => array(
'name' => __( 'Conferences' ),
'singular_name' => __( 'Conference' )
),
'public' => true,
'has_archive' => true,
'supports' => array('title','editor','thumbnail'),
)
);
register_post_type( 'speaker',
array(
'labels' => array(
'name' => __( 'Speakers' ),
'singular_name' => __( 'Speaker' )
),
'public' => true,
'has_archive' => true,
'supports' => array('title','editor','thumbnail'),
)
);
register_post_type( 'sponsor',
array(
'labels' => array(
'name' => __( 'Sponsors' ),
'singular_name' => __( 'Sponsor' )
),
'public' => true,
'has_archive' => true,
'supports' => array('title','editor','thumbnail'),
)
);
register_post_type( 'venue',
array(
'labels' => array(
'name' => __( 'Venues' ),
'singular_name' => __( 'Venue' )
),
'public' => true,
'has_archive' => true,
'supports' => array('title','editor','thumbnail'),
)
);
register_post_type( 'session',
array(
'labels' => array(
'name' => __( 'Sessions' ),
'singular_name' => __( 'Session' )
),
'public' => true,
'has_archive' => true,
'supports' => array('title','editor','thumbnail'),
)
);
}
Le code que j'appelle le type de message personnalisé est le suivant:
<?php
// args
$args = array(
'numberposts' => -1,
'post_type' => 'speaker',
'meta_key' => 'speaker-front-page',
'meta_value' => '1',
'orderby' => 'speaker_last_name',
'order' => 'ASC'
);
// query
add_filter( 'posts_orderby' , 'posts_orderby_lastname' );
$the_query = new WP_Query( $args );
?>
<?php if( $the_query->have_posts() ): ?> <div id="speakerrow"><h1>SPEAKERS<h1><hr>
<?php while( $the_query->have_posts() ) : $the_query->the_post();
echo '<div class="flex_column av_one_third flex_column_div">';
echo do_shortcode("[av_image src='". get_field('speaker-photo')."' attachment='' attachment_size='full' align='center' animation='pop-up' styling='' hover='av-hover-grow' link='".get_the_permalink()."' target='' caption='' font_size='' appearance='' overlay_opacity='0.4' overlay_color='#000000' overlay_text_color='#ffffff'][/av_image]" );
echo do_shortcode("[av_heading tag='h2' padding='10' heading='". get_the_title()."' color='' style='blockquote modern-quote modern-centered' subheading_active='subheading_below' subheading_size='15']". get_field('speaker-company')."[/av_heading]");
echo '</div>';
?>
le mieux que je pouvais penser était d'ajouter un métafield personnalisé appelé nom de famille et de trier par là. J'aime ne pas avoir à taper le nom de famille du locuteur deux fois si possible.
comment puis-je ajouter l'ordre par champ pour trier par le deuxième (et dernier) mot dans le titre de l'article?
Pour commander par le nom de famille du locuteur, vous pouvez utiliser la configuration suivante (PHP 5.4+):
// args
$args = [
'posts_per_page' => 10,
'post_type' => 'speaker',
'meta_key' => 'speaker-front-page',
'meta_value' => '1',
'orderby' => 'wpse_last_Word', //<-- Our custom ordering!
'order' => 'ASC'
];
// query
$the_query = new WP_Query( $args );
où l'entrée 'wpse_last_Word'
est prise en charge par les éléments suivants:
/**
* Order posts by the last Word in the post_title.
* Activated when orderby is 'wpse_last_Word'
* @link https://wordpress.stackexchange.com/a/198624/26350
*/
add_filter( 'posts_orderby', function( $orderby, \WP_Query $q )
{
if( 'wpse_last_Word' === $q->get( 'orderby' ) && $get_order = $q->get( 'order' ) )
{
if( in_array( strtoupper( $get_order ), ['ASC', 'DESC'] ) )
{
global $wpdb;
$orderby = " SUBSTRING_INDEX( {$wpdb->posts}.post_title, ' ', -1 ) " . $get_order;
}
}
return $orderby;
}, PHP_INT_MAX, 2 );
Ceci est basé sur ma réponse ici sur les conditions de commande par le dernier mot.
La réponse acceptée est assez fragile et ne pourra pas gérer les nombreuses variations de l’ordre par paramètres .
Voici un filtre qui devrait être un peu plus robuste:
/**
* Order posts by the last Word in the post_title.
* Activated when orderby is 'wpse_last_Word'
* @link http://wordpress.stackexchange.com/a/198624/26350
*/
add_filter('posts_orderby', function($orderby_sql, \WP_Query $q) {
$orderbys = $q->get('orderby');
if (!$orderbys) {
return;
}
if ($orderby_sql) {
$orderby_sql_array = [$orderby_sql];
}
else {
$orderby_sql_array = [];
}
if (!is_array($orderbys)) {
$words = explode(' ', $orderbys);
$orderbys = [];
foreach ($words as $Word) {
$orderbys[$Word] = $q->get('order');
}
}
global $wpdb;
foreach ($orderbys as $orderby => $direction) {
if ($orderby == 'wpse_last_Word') {
if (!$direction || !in_array(strtoupper($direction), ['ASC', 'DESC'])) {
$direction = 'DESC';
}
$orderby_sql_array[] = "SUBSTRING_INDEX({$wpdb->posts}.post_title, ' ', -1) $direction";
}
}
return implode(', ', $orderby_sql_array);
}, 100, 2);
L’utilisation de base est (mais elle acceptera des variations plus complexes de l’ordre par paramètres ):
$args = [
'posts_per_page' => 10,
'post_type' => 'speaker',
'meta_key' => 'speaker-front-page',
'meta_value' => '1',
'orderby' => 'wpse_last_Word',
'order' => 'ASC'
];
$the_query = new WP_Query( $args );