Adding Bootstrap Badges to Drupal Views Lists
There is a neat little trick in Views to create lists with counts. For example, if I created a list of categories for blog posts, I can have Views add the number of posts in each category with a little extra configuration.
The trick for adding the counts is in the views display configuration to setup a contextual filter with the option Display a summary. This option provides the additional setting, Display record count with link, that turns on the counts.
The challenge is I want to output the counts as Bootstrap badges in an HTML list to take full advantage of Bootstrap's standard components. So I need to wrap the count markup in with
<span class="badge">12</span>
At first glance the answer would seem to be to override views-view-list.tpl.php in your theme. That doesn't work. When you select the Display a summary setting in views, it redirects the theming to a different template, views-view-summary.tpl.php. (This one stumped me for a while, so I hope this saves you the time I spent figuring out why my views-view-list.tpl.php wasn't firing.)
To override the list view, you need to create a hook-views-view-summary.tpl.php template using the code:
If you are doing the override in your theme, name the template file, mytheme-views-view-summary.tpl.php. If in a module, mymodule-views-view-summary.tpl.phpviews-view-summary.tpl.php.
This template will work using Views' built preprocessing function, template_preprocess_views_view_summary. However, you will likely want to implement your own preprocessing function. Notice that in addition to the <span class="badge"> the above template allows for additional classes. You might want to add a pull-right for example to take advantage of Bootstrap's built in float classes.
An example custom preprocess function would look like this: (replace "hook" with your theme or module name)
function hook_preprocess_views_view_summary(&$vars) { // leverage views built in logic for vars preprocessing template_preprocess_views_view_summary($vars); // add support for badge classes $vars['row_badge_classes'] = array(); // set default badge classes $row_classes_default = 'pull-right'; foreach ($vars['rows'] as $id => $row) { $vars['row_badge_classes'][$id] = $row_badge_classes_default; } }
If you are implementing your override in a theme, your done. If in a module, you need one extra piece. You need to add your override to the theme registry. Normally I would do this using hook_theme:
function mymodule_theme() { $themes = array(); $themes['views_view_summary'] = array( 'arguments' => array( 'view' => NULL, 'options' => NULL, 'rows' => NULL, 'title' => NULL, 'context' => NULL, ), 'template' => 'mymodule-views-view-summary', 'original hook' => 'views_view_summary', 'path' => drupal_get_path('module', 'mymodule') . '/theme/list', 'preprocess functions' => array( 'template_preprocess', 'template_preprocess_views_view_summary', 'mymodule_preprocess_views_view_summary', ), ); return $themes; }
I actually could not get this to work. It would call my preprocess function, but not override the template with my template. So I took an alternative approach of using hook_theme_registry_alter:
function mymodule_theme_registry_alter(&$theme_registry) { $theme = &$theme_registry['views_view_summary']; $theme['path'] = drupal_get_path('module', 'mymodule') . '/theme/list'; $theme['template'] = 'mymodule-views-view-summary'; }
That worked and it is less code. Now all the list views should be outputting badgeified lists.