2

I have a content type that includes a field to store how that node should be displayed (display_option). display_option has two values (1|2).

I have created a view with two displays. Both are pages. Both use the path /node/% and use the node id as a contextual filter.

Display 1 has an additional filter criteria for requiring that display_option = 1.

Display 2 has the same filter but with the criteria that display_option = 2.

I can supply a node id to each display preview and they both individually produce the content I am looking for.

I was hoping Drupal would simply select the correct display based on the filter criteria but it doesn't. It always uses the display that is first in the view.

So I was looking at adding a pre-process function of some kind to template.php to manually change the view display id based on the node data.

I see quite a few views pre-processing functions and I am not sure which to use or at what point in the page build and view build process.

Any help would be appreciated including another method for accomplishing this.

3 Answers 3

2

The simple way to do this is

print $view views_get_view('yourviews_name','yourdisplayname');

for more information you can read documentation here

2

These options are not in order of relevance, just as they come to me.

Option 1 - hook_menu

As zhilevan suggests, you could simply use hook_menu to define your own callback for node/% and return

views_get_view('yourviews_name','yourdisplayname');

from a conditional (if/switch) that checks 'display_option' via node_load(arg(1));

If you do this you may have to fiddle with your module's weight in system table to make sure your path takes precedence over node.

I am a little wary of this approach because the existing node/* is such a useful callback and triggers all the node view hooks etc related to your content

Option 2 - Page Manager

You should be able to accomplish this with page manager (part of ctools)

If you took this option I expect that you might want to also use page manager existing pages module to override the node view page. There are some great tutorials for page manager if you need them.

Option 3 - Context

Rather than display your view as pages, you could make render it as blocks and then use context to pick which block to put in your content region based on display_option field. The node id argument could then be passed to views as a default argument 'Node from URL'.

To do this you would also need context_entity_field so that you can use node fields as conditions in contexts.

This option means that you don't have to actually override the core node path (node/*), which seems a lighter touch

Option 4 - Display Suite

Display suite allows you to create custom view modes for your nodes. You can also allow node authors to pick a display for individual nodes (I really like display suite, and I tend to use it a lot).

You could then set up the different view modes to contain the view of your choice, either by adding views_get_view() call in you theme (see option 1), or by using a display suite 'dynamic field' to add the two different views as fields to your node, and show only one in each view mode.

This way you do not need your field 'display_options', as the selection is already handled by ds. If you did not want to give node authors a full choice of view modes, you could try contextual view modes, and make the selection of view mode from your existing field (via context_entity_field)

Option 5 - View field

You could present a restricted choice of views in the node edit form to add to the node as a additional field. The options could be the two page views you have created. This would require View field.

2

For similar use-case I used

hook_views_pre_view(&$view, &$display_id, &$args)

then do the logic and simply

$view->set_display('name_of_your_display');

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.