I'm trying to find a way to let users select nodes from views results, and then get information from the selected nodes (such as node ID) for use in my module. This would probably be done in a form.
More broadly, what I'm trying to accomplish is to present users with a list of nodes tagged with a certain term x, have them to select any number of nodes from that list, and then have my module apply another term y to the selected nodes. I can handle that last part, but I'm struggling with creating a list of nodes that users can select from, and then somehow getting the information about the nodes selected that way.
I assumed views are the way to go but after a lot of searching I haven't found a way to achieve this functionality. Can anyone can show me a solution or point me in the right direction?
Thanks!
I'm using Drupal 7, and Views 7.x-3.7
EDIT: If I had the ability to select nodes with checkboxes via a module like VBO, I would like to do something like the following (terrible) pseudo-code:
foreach (vbo_selected_node) {
$node = vbo_selected_node -> node;
$nid = $node -> nid;
$node = node_load($nid);
$node->field_vocabulary_field['und'][0]['tid'] = $termID;
}
I hope that makes sense. Basically I want to take each selected node and apply another term to it.
I've been through a similar scenario and came up with a solution through custom module. I'm not sure if it is the best option but still you can use node_load_multiple() method. A quick reference can be found in
http://eureka.ykyuen.info/2012/08/08/drupal-7-get-mulitple-nodes-using-entityfieldquery-and-node_load_multiple/
Related
I hope this is not a stupid question I have been searching for most of the day!
I have a Content Type (Documents) which simply contains a title, file and a category. The category value is required and is 'powered' by Taxonomy.
I now wish to create a view which will display these documents grouped and titled by the taxonomy term.
Using my limited Drupal knowledge I intent to iterate through the relevant terms IDs (using taxonomy_get_tree($vid)) and then render each view accordingly.
To do this I have been hoping to use this snippet.
view = views_get_view('documents');
$view->set_display($display_id);
$filter = $view->get_item($display_id, 'filter', 'field_dl_category');
$filter['value']['value'] = $filter_value;
$view->set_item($display_id, 'filter', 'field_dl_category', $filter);
$viewsoutput = $view->render();
But this is not working; when I query the value of the $filter ($view->get_item($display_id, 'filter', 'field_dl_category')) I get null returned.
Might this be that my filter name is not the same as the CCK field name?
I am using Drupal 7.
Any help much appreciated, I am running out of ideas (and time).
I finally managed to get this working but I took a slightly different approach.
I changed my view and added the relevant contextual filter and then used this function views_embed_view to get at my required results.
If this helps! this is my solution:
$display_id = 'default';
$vid = 7;
$terms = taxonomy_get_tree($vid);
foreach($terms As $term){
$content = views_embed_view('documents', $display_id, $term->tid);
//now we see if any content has been provided
if(trim($content) != ''){
print "<h3>" . $term->name . "</h3>";
print $content;
}
}
In my case the trim($content) returns '' with no data as the view template has been edited, this might not be the case for all.
I am a very new Drupal developer so I'm sure there are much better ways of doing this, if so please do post.
I am going to go ahead and assume that you want to show, using Views, a list of document nodes grouped by the category that they have been tagged with.
There are two (of maybe more) ways by which you can do this in Views 3:
(a) Choose a display style that allows you to select a Grouping field. (You could try the table style that ships with Views by default). Suppose you have properly related the node table to the taxonomy_term_data table through a Views relationship, you could choose taxonomy_term_data.name as the grouping field.
Note that this grouping is done before the view is just rendered. So, your query would just have to select a flat list of (content, tag) pairs.
(b) You could also make use of the Attachment display type to achieve something similar. Show the used categories first in a list view clicking on which will show a page (attachment) with all documents tagged in that chosen category.
To understand how to do (a) or (b), turn on the advanced_help module (which is not a Views requisite but is recommended) first.
For (a), read the section on Grouping in styles i.e. views/help/style-grouping.html and
For (b), read the section on Attachment display i.e. views/help/display-attachment.html
A couple of things about your approach:
(a) It will show all terms from that vocabulary irrespective of whether or not they were used to tag at least one document.
(b) views_embed_view() will return NULL even if the currently viewing user does not have access to the view. So, ensure that you catch that case.
Here's an alternative:
$view = views_get_view('view_machine_name');
$view->init_display('default');
$view->display_handler->display->display_options['filters']['your_filter_name']['default_value'] = 'your_value';
$view->is_cacheable = FALSE;
$view->execute();
print $view->render();
I know you can probably set this using some convoluted method and obviously that would be better. But if you just want a quick and dirty straight access without messing around this will get you there.
I consistently find myself up against the following use case, and have yet to grok the proper workflow / solution:
I would like to display two views.
In the first view, each row displays one node of type-x.
The second view shows nodes of type-y, which are associated with node type-x via a nodereference, as follows:
View-1 View-2
------ ------
row1 X-a <---> Y-a
row2 X-b <---> Y-b
row3 X-c <---> Y-c
row4 etc <---> etc
For example, X is an event, and Y is a venue. Or, X is a porfolio page, and Y is a paged gallery.
I understand that there are other ways of approaching this - for example using node views rather than fields, but I am trying to leverage views to create 2 distinct custom queries related by an argument passed from one view to the other.
This is a variation of a question I asked earlier (Programmatic Views in Drupal 7), and hopefully a clarification.
Any help, even (or especially) just on the semantic level, is greatly appreciated.
You should use the EVA module. It does what you need in an elegant way.
https://drupal.stackexchange.com/questions/5732/is-there-a-good-tutorial-for-entity-views-attach-module
Hm I am not sure if I understand it correctly, but I think what you want to do is pass an argument to the view and then filter the results by it.
The option to configure the parameters in the UI is called 'Contextual Filters'.
Then you can call the view from your code like this(suppose your parameter is a node id):
<?php
print views_embed_view('example_view', 'page', $node->nid);
?>
If I understand, I think the best way would be to use only one view, and set a relationship on the node reference. Then create a field for the field you are displaying from the first node, and a field for the second node.
How can i display content nodes in blocks depending on the selected language by the user?
I already know how to do it for 'normal' nodes, just not in blocks.
Edit: I tried to do this with views. Filtering on a node and content translation: language. The problem is, i don't know how to filter two id's (of the nodes), just one.
If you have created the nodes after each other, you can do it pretty easily, since you can query for a range of node ids.
The views UI doesn't support making OR in where clauses, so it's not easy to make a query that looks like this.
SELECT nid FROM {nodes} WHERE nid = 5 OR nid = 10 OR nid = 17;
Making OR is views have been asked a few times here, I've answer it here.
I have a page which should list nodes. The views is called from a locality page (a taxonomy term page). What I need is almost the same as using the Taxonomy: tid in arguments and passing the tid.
I can't use the term_node table, as (for other reasons) we have a custom table term_node_hierarchy (with nid and tid only). The table term_node_hierarchy is like term_node but also saves the tid of the parents (from an "external" code)
I've been looking for options but still no joy.
Currently I'm building an array of the nid's that should be displayed on the current page, and passing them like print views_build_view('embed', $view, $matching_nids); but the Argument Node: ID states This argument is a single Node ID. As said, only the first node is displayed when printing the views. It would be great if it could filter on more than one nid.
I'm open to any kind of suggestions on how to do this.
Thanks
You could create your own module for this. You could populate the $page_content variable with the results of your own custom query where you allow the user to sort against multiple nids. You could do this a number of different ways. You could display a list of the existing nids with corresponding checkboxes, so that, when the user clicks submit, all the nids that match the selected checkboxes get used in the query. Then you just display the result of that query. That's the easiest way I can think of to offer that degree of flexibility.
I have two views that I would like to combine into one.
The first view shows all items of X where company ID = Y. This is to give preferential sort to the client first, and then everyone else.
So I created a second view, all items of X, where company ID != Y.
I created it as an Attachment to attach to the first view, but I don't think I got the intended result.
How can I combine these views so the first view results are listed first, and then the second view is too, using the same pager, filters, and arguments?
Is there any way of achieving this without programming it?
From a MySQL point of view, the order-by-field syntax would be the appropriate way to handle this. Example:
SELECT * FROM tickets ORDER BY FIELD(priority, 'High', 'Normal', 'Low');
It would be great if there is a module that add this kind of functionality to Views, but AFAIK, it does not exist.
If you want to solve this without programming, I think you can use the rules module to automatically set the 'sticky' checkbox on nodes where company ID = Y. With that in place, you can order the View on the sticky value.
Along the lines of the 'sticky' idea, if you didn't want to override that, maybe you could add a checkbox field to the company type -- isClient. Make it false for everyone except the client, and sort by that.
I haven't done this, but maybe you need to create both versions as attachments, and attach them both to another display...?
for drupal 5 there was views union. Someone started something for D6, but I don't know how far they got.
http://drupal.org/node/275162
Create the second view as an attachment and attach it to first.
Set all Inherit arguments, Inherit exposed filters and Inherit pager to Yes.
how is the client parameter passed to the view? as an url argument? if so, you can create your second view like i outline here and then select the exclude the argument option on the appropriate location.
usually the easiest way to achieve this is with a small hook_query_alter, but that requires a small amount of programming.
A little bit later... but I've found a better solution using only the Views module:
Create a Block View with that shows the first list that you need ("all items of X where company ID = Y")
Create another View that must be a "Page view" with the second list (all items of X, where company ID != Y)
In the "HEADER" settings of this second view, click "Add" and select "Global: View area".
In the "View to insert" list, select the first you have created (and check "Inherid contextual filters" if you are using it)
And that's it!