i'm new on drupal 8 and i want to try to custom the basic template of the webform module with my own template in TWIG , SASS.
I know i have to create a custom module but after read the drupal documentation , i don't know how i can do it correctly.
Any one can help me ?
i try to create a module with this code
function webform_example_form_alter(&$form, &$form_state, $id) {
if ($id == 'webform_submission_contact_form') {
$form['elements']['name']['#title'] = t('Name');
}
}
Your code example makes perfect sense to me.
You can also use hook_form_BASE_ID_alter(), which for the Contact form would be webform_example_form_webform_submission_contact_form_alter().
Related
[For Drupal 6] Let's say I've created a content type called "my_content_type". I can override the default template for that entire content-type by creating "page-node-my_content_type.tpl.php". But, what would be the best way to then further customize a single node of that content type (e.g., node 5555)?
I tried the following, but none worked:
page-node-5555.tpl.php
page-node-my_content_theme-5555.tpl.php
node-5555.tpl.php
None of these work. They all continue to use my original content-type template.
Drupal's page templates work on a suggestion system. Based on the current URL, an array of possible template files is created. It loops through the array (in reverse order) looking for template files that exists. The first one it finds, it will use.
drupal's theme system provides a hook for you to modify the template suggestions.. open up your template.php and find
function phptemplate_preprocess_page(&$vars) {
the $vars variable is what contains the suggestions, specifically $vars['template_files']
By default the only page suggestions that are available are
page.tpl.php
page-node.tpl.php
page-node-[node_id].tpl.php
As far as im aware, page-node-[node_type].tpl.php does not work by default, so its likely you have already modified the preprocess_page template to added in this functionality.
However if you want to add more specific templates you could do something like this...
function phptemplate_preprocess_page(&$variables) {
if ($variables['node']->type != "") {
$variables['template_files'][] = "page-node-" . $variables['node']->type;
$variables['template_files'][] = "page-node-" . $variables['node']->type . "-" . $variables['node']->nid;
}
}
this will allow the following hierarchy of template suggestions
page.tpl.php
page-node.tpl.php
page-node-[node_id].tpl.php
page-node-[node_type].tpl.php
page-node-[node_type]-[node_id].tpl.php
In Drupal 7 just copy the page.tpl.php template and rename it as
page--node--[node:id].tpl.php
Clear cache and start tweaking..
function phptemplate_preprocess_page(&$variables) {
if ($variables['node']->type != "") {
$variables['template_files'][] = "page-node-" . $variables['node']->type;
$variables['template_files'][] = "page-node-" . $variables['node']->type . "-" . $variables['node']->nid;
}
}
This code should not work because hook_preprocess_page() does not get passed any node information. hook_preprocess_node() does. So you can easily create a custom node.tpl, but you cannot easily create a custom page.tpl for a specific node. Not that I've been able to figure out anyway :)
Later...
In default Drupal, page-node-NID.tpl.php will work with no special coding. On a site of mine, it wasn't working, however, and I used the following code to make it work:
/**
* Implementation of hook_preprocess_page().
*/
function MYMODULE_preprocess_page(&$variables) {
// Allow per-node theming of page.tpl
if (arg(0) == 'node' && is_numeric(arg(1))) {
$variables['template_files'][] = "page-node-" . arg(1);
}
}
i'm on Drupal 7 and i have aspecific tpl.php file for a content field_image: "field--field_image.tpl.php". I need to create a preprocess function for this field and for my theme.
Supposing my theme name is "My Theme"
It should look like
function my_theme_preprocess_field(&$variables, $hook) {
$variables['classes_array'][] = 'aClassName';
}
but it doesn't work. I am wrong. But where?
Thanks
You can use template_preprocess_field() (like you do in your code above) but just test the particular field is the right one for you:
function my_theme_preprocess_field(&$variables, $hook) {
$element = $variables['element'];
if (isset($element['#field_name'])) {
if ($element['#field_name'] == 'field_image') {
$variables['classes_array'][] = 'aClassName';
}
}
}
Once you've implemented the hook don't forget to clear your caches, hook implementations are cached in Drupal 7 so won't be picked up until the cache is cleared.
You could declare a mytheme_preprocess_field(&$variables, $hook) in your theme's template.php where you can check your field and do operations on its label or markup, add classes, anything. So you wouldn't need field specific tpls. - eg.
function mytheme_preprocess_field(&$variables, $hook) {
if ($variables['element']['#field_name'] == 'field_machine_name') {
$variables['items'][0]['#markup'] = 'add custom markup';
}
}
Hope this helps someone.
In drupal 7 you can rewrite output of the field in template_preprocess_node() by altering "#markup" value of the field.
Also you can use regexp to change whatever you want in page content :)
How can I create a custom page.tpl.php for a specific view?
I'm not talking about styling the view itself, just the page where that view gets rendered.
Thank you.
#Keith Morgan - It's page.
Per Allartk's solution
In Drupal 7 template.php:
function <theme>_preprocess_page(&$variables) {
if (($views_page = views_get_page_view()) && $views_page->name === "galleries") {
$variables['theme_hook_suggestions'][] = 'page__views__galleries';
}
}
Then in your theme directory, create the page--views--galleries.tpl.php file.
Clear drupal cache and template should work.
I used 'galleries' as and example views name.
You can create a template file to theme almost any aspect of views output. In your case you want to create a custom template for your page display.
On the view designer, click the Theme link in Basic Settings. You'll see some template file naming options depending on if you want to theme the whole view (e.g., views-view--example--page.tpl.php), each row (e.g., views-view-fields--example--page.tpl.php) and so on.
Copy the appropriate template you want to customize from /sites/all/modules/views/theme to your theme and customize as you wish.
Once you create your custom template file, you can go back to the view designer Theme link to make sure it is being used. Your template should be bolded.
Hope this helps.
There's some documentation on template suggestions, and you might be interested in page.tpl.php suggestions. If it's a page view, you could use a path suggestion. So if your view is at http://www.example.com/photos, the page.tpl.php file would be named page-photos.tpl.php.
Had a similar problem, which was remedied by putting a .tpl.php in my theme's template folder. The naming convention for a page display of views in drupal 7 is page--path-to-view.tpl.php
In a drupal 7 theme I added a template suggestion in template.php:
function sovon_preprocess_page(&$variables) {
if(views_get_page_view()) {
$variables['theme_hook_suggestions'][] = 'page__view';
}
}
See http://api.drupalize.me/api/drupal/function/views_get_page_view/7 and http://drupal.org/node/223440#custom-suggestions for more information.
Assuming a view as a page, you can use the results of page_manager_get_current_page() in your preprocess to determine if your view is active, then take the appropriate steps (tack on body classes, add a template suggestion, etc).
using sillygwailo's suggestion I got this to work for me very nicely:
function YOUR-THEME-NAME_preprocess_page(&$vars) {
//allow template suggestions based on url paths.
$alias = drupal_get_path_alias(str_replace('/edit','',$_GET['q']));
if ($alias != $_GET['q']) { $suggestions = array();
$template_filename = 'page';
foreach (explode('/', $alias) as $path_part) {
$template_filename = $template_filename . '-' . $path_part;
$suggestions[] = $template_filename;
}
$alias_array = explode('/', $alias);
$variables['template_files'] = $suggestions;
Then if your view is at www.example.com/photos , create a page-photos.tpl.php in your theme directory and drupal will use that as your template.
If that checked answer doesnt work(because it didnt for me) you can create a page--(urlname).tpl.php and then style your theme however you want it. Then you can import your view in one of several ways ...
print render($page['content']);
or
$view = views_get_view('viewname');
print $view->execute_display('default', $args);
$args is just an array and can be blank..you can just leave it off entirely
The person managing a site I'm working on wants to be able to decide what blocks go where. There is already a nice interface for this in Drupal (selecting the region from a drop down) but I'd like to hide certain blocks from this user. These are blocks he should not be able to move around.
Afaik this is not possible via the Permissions. Is there a module that allows fine grained control of what blocks can be managed by whom? I'd rather not write a custom interface ...
Thanks,
Stef
Well, you can create a simple custom module like this (replace my_module with your custom module's name, obviously):
function my_module_perm()
{
return array('view special blocks');
}
function my_module_form_alter(&$form, &$form_state, $form_id) {
if ($form_id == 'block_admin_display_form') {
if(!user_access('view special blocks')) {
$special_blocks = array( ); // Specially hidden blocks go here
foreach($special_blocks as $block) {
unset($form[$block]);
}
}
}
}
And then:
Add the blocks you want to hide into the $special_blocks array (it's basically the id of the block's div minus block_ )
Create a new account, and possibly a new role for this guy
Permission-wise, the new user's role should have access administration pages and administer blocks on, but shouldn't have view special blocks
Tested on Drupal 6.6, should work on other 6.x versions (and maybe 5.x with a few modifications)
Take those blocks out of regions and embed them into your template manually using module_invoke().
$block = module_invoke('module_name', 'block', 'view', 'block name or ID');
print '<h2>' . $block['subject'] . '</h2>';
print $block['content'];
Maybe give Blockqueue a try? I've never used it, but it appears to cover your use case.
What is the best method for including a CSS or Javascript file for a specific node in Drupal 6.
I want to create a page on my site that has a little javascript application running, so the CSS and javascript is specific to that page and would not want to be included in other page loads at all.
I'd advise against using hook_nodeapi for that. Adding CSS and Javascript is related to layout so hook_nodeapi is not the place for it: use themeing. This way, you can override those files when you're going to develop a new theme. Doing that with the nodeapi approach would be a bit harder (you'd have to search the js/css list for the files, remove them and replace them with your own).
Anyway: what you need to do is add a node preprocess function that adds those files for you. You can do this either in a module or in a custom theme. For a module this would be:
function mymodule_preprocess_node(&$variables) {
$node = $variables['node'];
if (!empty($node) && $node->nid == $the_specific_node_id) {
drupal_add_js(drupal_get_path('module', 'mymodule') . "/file.js", "module");
drupal_add_css(drupal_get_path('module', 'mymodule') . "/file.css", "module");
}
}
or for a theme:
function mytheme_preprocess_node(&$variables) {
$node = $variables['node'];
if (!empty($node) && $node->nid == $the_specific_node_id) {
drupal_add_js(path_to_theme() . "/file.js", "theme");
drupal_add_css(path_to_theme(). "/file.css", "theme");
}
}
Don't forget to clear the cache, first.
These functions are called before the node is themed. Specifing the js/css there allows for a cascaded approach: you can have the generic/basic stuff in the module and provide enhanced or specific functionality in the theme.
I use the preprocess functions but this has some issues. $variables['styles'] is usually set before the node preprocess function is called. In other words drupal_get_css is already called which makes you calling drupal_add_css useless. The same goes for drupal_add_js. I work around this by resetting the $variables['styles'] value.
function mytheme_preprocess_node(&$variables) {
$node = $variables['node'];
if (!empty($node) && $node->nid == $the_specific_node_id) {
drupal_add_js(path_to_theme() . "/file.js", "theme");
drupal_add_css(path_to_theme(). "/file.css", "theme");
$variables['styles'] = drupal_get_css();
$variables['script'] = drupal_get_js();
}
}
This seems to work for most cases.
P.S. There's hardly any ever need to create a module to solve a theming problem.
Cheers.
This seems like a good solution:
http://drupal.org/project/js_injector
and
http://drupal.org/project/css_injector
It works when you want to insert inline code into something other than technically a node so there's no node id and no PHP input option available. Like I used it to inject small jQuery tweaks into a couple of admin pages. It works by path rather than node id.
The best solution I've come up with so far is to enable the PHP input mode, and then call drupal_add_css and drupal_add_js as appropriate in a PHP block in the start of the body of your node.
This should do the trick - a quickie module that uses the hook_nodeapi to insert the JS/CSS when the node is viewed.
function mymodule_nodeapi(&$node, $op, $a3 = NULL, $a4 = NULL) {
// the node ID of the node you want to modify
$node_to_modify = 6;
// do it!
if($op == 'view' && $node->nid == $node_to_modify) {
drupal_add_js(drupal_get_path('module', 'mymodule') . '/mymodule.js');
drupal_add_css(drupal_get_path('module', 'mymodule') . '/mymodule.css');
}
}
This avoids security issues with enabling the PHP input filter, and doesn't require a separate node template file which could become outdated if you updated the main node template and forgot about your custom one.
You can have a custom template for that node (node-needsjs.tpl.php) which calls the javascript. That's a little cleaner than using PHP right in the node body, and makes changes to content easier in the future.
EDIT: I don't think I was very clear above. You want to name the template file node-(nodeid).tpl.php. So if it was Node 1, call the file node-1.tpl.php