WordPress: Breadcrumb-Navigation ohne Plugin

wordpress-breadcrumb

Breadcrumb-Navigationen sind in komplexen Websites ein wichtiges Navigations- und Orientierungselement. Sobald Ihr WordPress als "echtes" CMS einsetzt, werdet ihr allerdings merken, dass viele Plugins und Snippets zu sehr auf den Einsatz in Blogs ausgerichtet sind. Sobald diverse statische und hierarchisch verschachtelte Seiten und Custom Post Types im Spiel sind, stößt so manche Breadcrumb an ihre Grenzen.
Das folgende Snippet berücksichtigt alle Anforderungen die ich bisher an eine Breadcrumb gestellt habe. Da ich meinen Blog auch selbst als Archiv nutze, lege ich den entsprechenden Code hier ab. Sicher wird das Snippet euch auch mal weiterhelfen.

Modernes Webdesign

Neue Workflows, Techniken und Designideen – inkl. Rapid Prototyping, Responsive Design und Sass.

In unserem Shop kaufen
Signierte DVD, keine Versandkosten

Bei Amazon bestellen
Standard-Version

Code für die functions.php

Den folgenden Code fügt Ihr in die functions.php eures WordPress-Themes ein.


// breadcrumb
function nav_breadcrumb() {
 
  $delimiter = '»';
  $home = 'Home'; 
  $before = '<span class="current">'; 
  $after = '</span>'; 
 
  if ( !is_home() && !is_front_page() || is_paged() ) {
 
    echo '<div id="breadcrumb">';
 
    global $post;
    $homeLink = get_bloginfo('url');
    echo '<a href="' . $homeLink . '">' . $home . '</a> ' . $delimiter . ' ';
 
    if ( is_category() ) {
      global $wp_query;
      $cat_obj = $wp_query->get_queried_object();
      $thisCat = $cat_obj->term_id;
      $thisCat = get_category($thisCat);
      $parentCat = get_category($thisCat->parent);
      if ($thisCat->parent != 0) echo(get_category_parents($parentCat, TRUE, ' ' . $delimiter . ' '));
      echo $before . single_cat_title('', false) . $after;
 
    } elseif ( is_day() ) {
      echo '<a href="' . get_year_link(get_the_time('Y')) . '">' . get_the_time('Y') . '</a> ' . $delimiter . ' ';
      echo '<a href="' . get_month_link(get_the_time('Y'),get_the_time('m')) . '">' . get_the_time('F') . '</a> ' . $delimiter . ' ';
      echo $before . get_the_time('d') . $after;
 
    } elseif ( is_month() ) {
      echo '<a href="' . get_year_link(get_the_time('Y')) . '">' . get_the_time('Y') . '</a> ' . $delimiter . ' ';
      echo $before . get_the_time('F') . $after;
 
    } elseif ( is_year() ) {
      echo $before . get_the_time('Y') . $after;
 
    } elseif ( is_single() && !is_attachment() ) {
      if ( get_post_type() != 'post' ) {
        $post_type = get_post_type_object(get_post_type());
        $slug = $post_type->rewrite;
        echo '<a href="' . $homeLink . '/' . $slug['slug'] . '/">' . $post_type->labels->singular_name . '</a> ' . $delimiter . ' ';
        echo $before . get_the_title() . $after;
      } else {
        $cat = get_the_category(); $cat = $cat[0];
        echo get_category_parents($cat, TRUE, ' ' . $delimiter . ' ');
        echo $before . get_the_title() . $after;
      }
 
    } elseif ( !is_single() && !is_page() && get_post_type() != 'post' && !is_404() ) {
      $post_type = get_post_type_object(get_post_type());
      echo $before . $post_type->labels->singular_name . $after;
 
    } elseif ( is_attachment() ) {
      $parent = get_post($post->post_parent);
      $cat = get_the_category($parent->ID); $cat = $cat[0];
      echo get_category_parents($cat, TRUE, ' ' . $delimiter . ' ');
      echo '<a href="' . get_permalink($parent) . '">' . $parent->post_title . '</a> ' . $delimiter . ' ';
      echo $before . get_the_title() . $after;
 
    } elseif ( is_page() && !$post->post_parent ) {
      echo $before . get_the_title() . $after;
 
    } elseif ( is_page() && $post->post_parent ) {
      $parent_id  = $post->post_parent;
      $breadcrumbs = array();
      while ($parent_id) {
        $page = get_page($parent_id);
        $breadcrumbs[] = '<a href="' . get_permalink($page->ID) . '">' . get_the_title($page->ID) . '</a>';
        $parent_id  = $page->post_parent;
      }
      $breadcrumbs = array_reverse($breadcrumbs);
      foreach ($breadcrumbs as $crumb) echo $crumb . ' ' . $delimiter . ' ';
      echo $before . get_the_title() . $after;
 
    } elseif ( is_search() ) {
      echo $before . 'Ergebnisse für Ihre Suche nach "' . get_search_query() . '"' . $after;
 
    } elseif ( is_tag() ) {
      echo $before . 'Beiträge mit dem Schlagwort "' . single_tag_title('', false) . '"' . $after;
 
    } elseif ( is_author() ) {
       global $author;
      $userdata = get_userdata($author);
      echo $before . 'Beiträge veröffentlicht von ' . $userdata->display_name . $after;
 
    } elseif ( is_404() ) {
      echo $before . 'Fehler 404' . $after;
    }
 
    if ( get_query_var('paged') ) {
      if ( is_category() || is_day() || is_month() || is_year() || is_search() || is_tag() || is_author() ) echo ' (';
      echo ': ' . __('Page') . ' ' . get_query_var('paged');
      if ( is_category() || is_day() || is_month() || is_year() || is_search() || is_tag() || is_author() ) echo ')';
    }
 
    echo '</div>';
 
  }
}

Breadcrumb im Theme aufrufen

Mit diesem Snippet bindet Ihr die Breadcrumb im Theme ein. Dabei ist es irrelevant ob sich die Navi innerhalb oder außerhalb des WordPress-Loops befindet.

<?php if (function_exists('nav_breadcrumb')) nav_breadcrumb(); ?>

Je nachdem, auf welcher Unterseite des Projektes Ihr euch befindet, wird nun die Breadcrumb dargestellt. Im Gegensatz zu vielen anderen Lösungen die ich kenne, arbeitet diese Breadcrumb einwandfrei mit Archiven, Seiten und Kategorien. Auch Custom Post Types werden berücksichtigt.

WordPress-Breadcrumb ohne Plugin

Der Code wurde ursprünglich unter dimox.net/wordpress-breadcrumbs-without-a-plugin veröffentlicht. Ich habe ihn nur meinen Anforderungen entsprechend leicht abgewandelt und die Begriffe übersetzt.

Update vom 13. Februar 2012

Ich habe eine Anpassung am Code vorgenommen, die die Breadcrumb-Darstellung beim Einsatz einer Pagination verbessert.