Embed Drupal Views Using PHP

When theming Drupal and wanting to output a view there are occasions where using a view display (e.g. a page, or a block - perhaps placed within a custom region ;-) ), or using Views Attach will not suffice.

Instead, you can embed a view using the following PHP snippet:
(NOTE: you'll need to have the core PHP input filter enabled if embedding in a node body)

<?php
$view
= views_get_view('VIEWNAME');
print
$view->preview('default');
?>

or, if you need to use an argument with the view:

<?php
$args
= array(ARGUMENTS);
$view = views_get_view('VIEWNAME');
print
$view->preview('default', $args);
?>

NOTE:

  • replace VIEWNAME with your actual view name - e.g. 'my_drupal_posts'
  • replace ARGUMENTS with the argument(s) your view is expecting - e.g. this may be a node id

The PHP snippets above will output your view's 'default' display. However, you can output other displays from your view (if your view has multiple displays) - e.g. to output a view's first block display you'd modify the snippet by replacing the Views display id 'default' with 'block_1' and use:

<?php
$args
= array(ARGUMENTS);
$view = views_get_view('VIEWNAME');
print
$view->preview('block_1', $args);
?>

Access checking:

NOTE: Some views require access checking (e.g. views which should only be accessed by certain roles). The implementations above do not include access checking. If your view requires access checking please see the comment discussion (particularly comments #1, #3, and #4) for examples of modified/alternative code.

8 comments

dixon_ August 10th, 2010 @ 3:18pm

Or you could use this approach which more or less does what you are doing, but with less code ;)

<?php
print views_embed_view('my_view', 'block_1', $arg1, $arg2);
?>
Laurence August 10th, 2010 @ 3:55pm

@ dixon_
whilst there is slightly less initial written code in your example, the views_embed_view() function (from Views 'views.module' file) basically contains the code I have outlined:

<?php
function views_embed_view($name, $display_id = 'default') {
 
$args = func_get_args();
 
array_shift($args); // remove $name
 
if (count($args)) {
   
array_shift($args); // remove $display_id
 
}
 
$view = views_get_view($name);
  if (!
$view || !$view->access($display_id)) {
    return;
  }
  return
$view->preview($display_id, $args);
}
?>

which, overall, results in views_embed_view() utilising more code not less.

Guest August 10th, 2010 @ 4:50pm

views_embed_view() is the right way to do it. It's the primary public API function that includes things like access checking.

Laurence August 10th, 2010 @ 5:38pm

@ Guest
'right' is subjective - I'd think access checking for views is rarely necessary, and if it were the original code could be extended:

<?php
$view
= views_get_view('VIEWNAME');
if (
$view->access('default')) {
  print
$view->preview('default');
}
?>
dereine August 10th, 2010 @ 9:56pm

using an api function is always the case you want.

a) you have less code in your custom code.
b) what happens if something of the api of views changes but this function keeps his functionality
c) it makes easier to read the code, with views_embed_view it's sure that you want to embed a view.

Laurence August 11th, 2010 @ 12:10am

@ dereine
a) slightly, yes, although you utilise more overall
b) futureproofing should be a consideration, but 'what if' arguments are always two-sided
c) views_get_view('VIEWNAME') is pretty straightforward to read - would you not agree?

Brock Boland August 11th, 2010 @ 3:12am

I have to agree with Guest in #3: I've definitely built sites with views that were only accessible to privileged users.

Drupal Theme Garden August 11th, 2010 @ 12:48pm

Thanks for this useful article.

One question: could you give some example of using $args (for $view->preview('default', $args);)?

Comments are closed

If you want to ask a question or have something to add please contact me.