Cómo mostrar posts regulares y tipos de post personalizados que pertenecen a una categoría usando solo la plantilla genérica category.php
1) Mi sitio tiene posts normales y 2 custom post types (noticias y ensayos) 2) Todos comparten categorías normales como deportes y salud (sin taxonomías personalizadas) 3) Usando la plantilla genérica category.php, ¿cómo hago para que esta plantilla maneje todas las categorías mostrando todo el contenido que pertenezca a ellas, sin importar el tipo de contenido?
En otras palabras, me gustaría que la plantilla category.php genérica maneje la visualización de todas las categorías pero que incluya también los custom post types.
Puede ser una pregunta tonta pero he vuelto a WordPress después de un largo tiempo y me está costando entender los temas predeterminados para hacer esto. Estoy confundido y frustrado en este momento.
Por favor ayuda
Echa un vistazo a la función query_posts() - tu amiga para alterar la consulta principal/predeterminada. Debes llamar a la variable global $wp_query
previamente para modificar la consulta original en lugar de reemplazarla.
Algo como esto debería funcionar. Coloca las primeras cuatro líneas en tu archivo category.php
justo antes de que comience el loop principal:
// Modifica el loop por defecto, incluye tipos de entrada personalizados
global $wp_query;
$args = array_merge( $wp_query->query, array( 'post_type' => 'any' ) );
query_posts( $args );
// El inicio del loop luce así:
while ( have_posts() ) : the_post();
Si deseas ser más selectivo al mostrar tus tipos de entrada, puedes proporcionar un array con los tipos de entrada deseados en lugar del genérico 'post_type'=>'any'
:
$args = array_merge( $wp_query->query, array( 'post_type' => array('post','news','essays') ) );
Y bienvenido de vuelta al universo WordPress y a la comunidad de WPSE.
Estoy seguro de que la frustración desaparecerá pronto ;)

Al principio usé la solución de Maugly pero luego encontré esta en el codex de WordPress:
add_action( 'pre_get_posts', 'add_my_custom_post_type' );
/**
* @param WP_Query $query
* @return WP_Query
*/
function add_my_custom_post_type( $query ) {
if ($query->is_main_query())
$query->set( 'post_type', array( 'post', 'page', 'any_custom_type' ) );
return $query;
}
Espero que ayude a alguien... quizás no es la solución más limpia pero es un poco más limpia que la de Maugly...

► Aquí está mi versión de la sugerencia de @Kower. Resuelve un par de problemas en el administrador.
add_action('pre_get_posts', 'agregar_mi_tipo_de_entrada_personalizada');
/**
* @param WP_Query $query
* @return WP_Query
*/
function agregar_mi_tipo_de_entrada_personalizada($query) {
if(
empty($query->query['post_type'])
or $query->query['post_type'] === 'post'
){
$query->set('post_type', array('post', 'my_custom_type'));
}
}

Quería añadir a esto, en referencia a la respuesta de @tivnet. (Me hubiera gustado dejar un comentario pero mi reputación no es lo suficientemente alta)
Descubrí que las soluciones funcionaban, sin embargo presumiblemente tenían la consecuencia no deseada de afectar también al área de administración, lo que significa que al visitar las entradas en wp-admin (wp-admin/edit.php) también mostraba todas las páginas y todos los tipos de entradas personalizadas en la lista genérica de entradas. ¿Quizás confuso para otros usuarios? Sin embargo, añadiendo:
and !is_admin()
dentro de la declaración if() parece resolver este problema manteniendo la modificación de pre_get_posts en el front-end.
add_action('pre_get_posts', 'add_my_custom_post_type');
/**
* @param WP_Query $query
* @return WP_Query
*/
function add_my_custom_post_type($query) {
if(
empty($query->query['post_type'])
or $query->query['post_type'] === 'post'
and !is_admin()
){
$query->set('post_type', 'any');
}
}

Para incluir un tipo de publicación personalizada en el bucle regular (es decir, la página de entradas) solo agrega el siguiente código a index.php antes de if ( have_posts() ) :
$args = array(
'post_type' => array('post', 'custom_post_type'),
'post_status' => 'publish',
);
$new_post_loop = new WP_Query( $args );
luego modifica las siguientes dos líneas:
if ( have_posts() ) :
cámbialo por if ( $new_post_loop -> have_posts() ) :
y
while ( have_posts() ) : the_post();
por while ( $new_post_loop -> have_posts() ) : $new_post_loop -> the_post();
Esta solución evita el problema de tener el tipo de publicación personalizada listado en la pantalla de todas las entradas en el backend, lo cual ocurre al usar add_action('pre_get_posts') ;)

function namespace_add_custom_types( $query )
{
// Verifica si es una categoría o etiqueta y si no se suprimen los filtros
if( is_category() || is_tag() && empty( $query->query_vars['suppress_filters'] ) )
{
// Establece los tipos de post a incluir en la consulta
$query->set( 'post_type', array(
'post', 'nav_menu_item', 'your-custom-post-type-here' // 'post', 'elemento_de_menu', 'tu-tipo-de-post-personalizado-aqui'
));
return $query;
}
}
// Añade el filtro para modificar las consultas antes de obtener los posts
add_filter( 'pre_get_posts', 'namespace_add_custom_types' );
