Is there a way to build a drupal template for a content type which not import the tag and the begin of the tag ?
in exemple, i would create a "newsletter" content type which is based on a "page--newsletter.tpl.php" as it tell here : http://drupal.org/node/1089656
But all the xxx.tpl.php i ever seen not include the top of the HTML code
Is there a way for it ?
*EDIT : * I'm trying to change the html.tpl.php to another when the $node->type is equal to "newsletter"
(look easier like that)
function themename_preprocess_html(&$vars, $hook) {
if ($node = menu_get_object()) {
array_splice($vars['theme_hook_suggestions'], -1, 0, 'html__' . str_replace('-', '_', $node->type));
}
#print_r($vars['theme_hook_suggestions']); // print out suggestions
}
Related
Building a site in Drupal 8, using classy subtheme. Run into a puzzling theming issue - adding body class to html.html.twig based on a taxonomy term on that node.
Themers use this to customize page display, in my case using it to define a few sections of my site so I can change color and format.
I have tried some preprocess functions I saw on google but to no result.
Has anyone else run into and solved this issue?
Use this to get all fields of the node and check for whatever you need:
\Drupal::service('current_route_match')->getParameter('node')->toArray();
In your .theme file you can use the html preprocess hook:
function your_theme_preprocess_html(&$variables) {
$body_classes = [];
$nodeFields = \Drupal::service('current_route_match')->getParameter('node')->toArray();
// if something, then set $body_classes to something.
$variables['attributes']['class'] += $body_classes;
}
And then in your html twig template add the attributes to the body element:
<body{{ attributes }}>
Hope this helps.
With the answer of Frank Drebin I get a PHP fatal error (Unsupported operand types) with the "+=" operand. If you want to add the node ID and node type to your body class, you can use this code for example:
// Add the node ID and node type to the body class
$body_classes = [];
$nodeFields = \Drupal::service('current_route_match')->getParameter('node')->toArray();
if (is_array($nodeFields) && count($nodeFields) > 0) {
if (isset($nodeFields['nid'])) {
$body_classes[] = 'node-' . $nodeFields['nid'][0]['value'];
}
if (isset($nodeFields['type'])) {
$body_classes[] = $nodeFields['type'][0]['target_id'];
}
}
$variables['attributes']['class'] = $body_classes;
I have the site based on drupal 7.
I need to create widget for iframe. I created new content type and removed all sidebars, headers, footers from there. I left only content. It works good.
But this page loads all my scripts and css (less) from mytheme.info. And I want just to use scripts and css from my custom module. Is it possible to do?
You can make use of template_process_html to do so.
Add the following code to your theme's template.php file.
function [YOUR_THEME]_process_html(&$vars) {
// first check for the path of the page you need to unset the js & css for.
// assuming the path is 'node/12'
if(arg(0) === 'node' && arg(1) === '12') {
$vars['scripts'] = array();
$vars['styles'] = array();
}
}
To check if current page is a specific content type; You can use $vars['classes'] or $vars['classes_array'], which holds the css classes to add to <body> tag. In case of a node page, it adds a class name node-type-NODE_TYPE_MACHINE_NAME to the classes string.
if(strpos($vars['classes'], 'node-type-[YOUR_TYPE]') === TRUE) {
OR
if(in_array('node-type-[YOUR_TYPE]', $vars['classes_array']) === TRUE) {
Update
You can add any js / css files to the array
$vars['scripts'] = array(
'path/to/js/file1.js',
'path/to/js/file2.js'
);
$vars['styles'] = array(
'path/to/css/file1.css',
'path/to/css/file2.css'
);
I'm trying to modify the page.vars in my bootstrap subtheme to change a class based on content type.
Code as standard in page.vars
elseif (!empty($variables['page']['sidebar_first']) || !empty($variables['page']['sidebar_second'])) {
$variables['content_column_class'] = ' class="col-sm-9"';
}
My modified code:
elseif (!empty($variables['page']['sidebar_first']) || !empty($variables['page']['sidebar_second'])) {
$node = $variables['node'];
if ($node->type == 'standard') {
$variables['content_column_class'] = ' class="col-sm-6"';
}
}
What I'm trying to achieve is putting the class col-sm-6 onto every standard content type page.
It looks like the code you're sharing is correct, but you need to tell your sub-theme to read the page.vars.php file. I just dealt with a similar problem and came up with this solution based on information found here.
What you need to do is add a theme function in your sub-theme's template.php something like:
function SUB_THEME_theme(&$existing, $type, $theme, $path) {
bootstrap_include($theme, 'theme/system/page.vars.php');
$hooks = array();
return $hooks;
}
Then you can add theme/system/page.vars.php in your sub-theme and any functions in the page.vars.php file will be included in the registry and applied after the bootstrap base theme. Once you've done that your above code should work as it is.
I created a module to highlight the code samples in the articles based on the highlight.js library. This library require code samples to be embed in <pre><code> ... </code></pre> tags. I don't want to add the <pre> tag when I write an article, because other highlighter libraries don't need it and I want to be able to switch library without modifying the articles. So I need to dynamically wrap <code> tags with <pre>. I tried to implement _node_view( and _node_view_alter( hooks without success.
My code look like
function highlight_node_view($node, $view_mode, $langcode) {
$node->content['body']['und'][0]['safe_value'] = "test";
$node->body['und'][0]['safe_value'] = "test";
$node->content['body']['und'][0]['value'] = "test";
$node->body['und'][0]['value'] = "test";
}
function highlight_node_view_alter($build, $node) {
$build["body"]["#items"]["0"]["value"] = "TEST";
$build["body"]["#items"]["0"]["safe_value"] = "TEST";
$build["body"]["#formater"]["0"]["#markup"] = "TEST";
}
If I print the content in my template with
<pre>
<?php
ob_start("minimal_htmlspecialchars_callback");
print_r($content);
ob_end_flush();
?>
</pre>
I can confirm that all the values are correctly replaced by "test" but a call to
<?php print render($content['body']); ?>
still render the original content instead of "test"
What is the proper way to alter the content of an article from a module ?
I have successfully altered body field data, you have to place code in your module file like bellow. BTW I'm using drupal 8.2
use Drupal\Core\Entity\EntityInterface;
use Drupal\Core\Entity\Display\EntityViewDisplayInterface;
/**
* Implements hook_ENTITY_TYPE_view() for node entities.
*/
function module_name_node_view(array &$build, EntityInterface $node, EntityViewDisplayInterface $display, $view_mode) {
$build['body'][0]['#text'] = 'test by ajay';
}
I finally found a solution in a previous stackoverflow question ( Modify how a node in drupal will look when viewed ) and the following code work fine.
function highlight_node_view($node, $view_mode, $langcode) {
$alteredBody = $node->body['und'][0]['safe_value'];
$alteredBody = str_replace("<code>", "<pre><code>", $alteredBody);
$alteredBody = str_replace("</code>", "</code></pre>", $alteredBody);
$node->content['body'] = array(
'#markup' => $node->body['und'][0]['safe_value'] = $alteredBody
);
}
But I'm still not sure to fully understand the rendering system. So if somebody have a better solution or a more detailed explanation, I'll appreciate it.
[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);
}
}