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'
);
Related
I want to change different logo for each different pages in drupal and I also want to hide logo for some pages too.How can I do that?I've already search possible answers and I didn't find any.
As was stated by MilanG, logo is rendered in your page template (default page.tpl.php or theme suggestion) using $logo variable. This variable is set in template_preprocess_page(), and the best way to change it is to use the same preprocess function in your theme:
function mytheme_preprocess_page(&$variables) {
$logo_path = '/' . drupal_get_path('theme', 'mytheme') . '/logos/';
// Alter logo under some conditions
if ($first_condition) {
$variables['logo'] = $logo_path . 'logo1.png';
} elseif ($second_condition) {
$variables['logo'] = $logo_path . 'logo2.png';
} elseif ($third_condition) {
// Hide logo. Your page.tpl.php must contain
// something like <?php if ($logo): ?>
$variables['logo'] = null;
}
// etc.
}
The "standard" way for printing logo is printing $logo variable from page.tpl.php template. But you don't have to do it that way at all.
I.e. you can add your php code which will alter logo html code the way you like.
Or, you can place logo html inside static blocks and set for every block on what pages should it appear (in block settings). And of course create "logo" region for your theme.
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'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 have created a customized theme called "test", and I am trying to display the search results.
I added the function test_preprocess_search_results() to the template.php (copied the code from drupal page "function template_preprocess_search_results", then copy the search-result.tpl.php from search module to the "test"'s template folder.
function test_preprocess_search_results(&$variables) {
$variables['search_results'] = '';
if (!empty($variables['module'])) {
$variables['module'] = check_plain($variables['module']);
}
foreach ($variables['results'] as $result) {
$variables['search_results'] .= theme('search_result', array('result' => $result, 'module' => $variables['module']));
}
$variables['pager'] = theme('pager', array('tags' => NULL));
$variables['theme_hook_suggestions'][] = 'search_results__' . $variables['module'];
}
I am new in drupal, my concern is how can I make the search result display in some certain div which claimed in my page.tpl.php file? Do something like <?php print render($page['search_result']); ?> in page.tpl.php div ? I am not sure how does the default theme know where to display the search result? Can anyone help thanks
ps: after what I did, and refresh the cache, nothing show up
For search results you should use the search-results.tpl.php (all results list) and search-result.tpl.php (single list item) templates. Copy them from ROOT/modules/search folder into your theme folder and override them as you prefer.
On my Drupal powered website, I want to list available downloads at the top of a node page (within a narrow float:right <div>), not at the bottom where they normally appear.
Within my theme, I've overridden the theme_upload_attachments() function to generate a <div> of width 40%, but this is showing up at the bottom of the page.
Within the upload.module file is code that controls where the attachments are listed on the page:
// function upload_nodeapi(), line #284 of upload.module
$node->content['files'] = array(
'#value' => theme('upload_attachments', $node->files),
'#weight' => 50,
);
If I manually hack this #weight to -1, my custom list of attachments shows where I want, floating at the righthand side of the top of the content area.
However, I don't want to manually hack the core file upload.module, as my changes will be lost next time I apply an upgrade (say, for a security patch).
How/Where do I modify the #weight of content['files'] within my theme code?
Or, am I going about this the wrong way?
You'll need a module to do this, not just a theme. A module can implement hook_nodeapi(), which will give it a chance to change the contents of that $node->content array before it's rendered. If your module is named 'upload_tweaker' for example, you'd use the following function:
function upload_tweaker_nodeapi(&$node, $op) {
if ($op == 'view') {
$node->content['files']['#weight'] = -1;
}
}
Each module gets a crack at changing the node during this 'nodeapi' event; if you want to change the stuff that's added by one module, you need to make sure that your module loads after it. This can be done by naming it something like 'zzz', or by changing its "weight" field in the system table of your site's database. Modules can be weighted just like form elements.
api.drupal.org has more information.
For those who uses CCK and want to alter body weight:
CCK module uses pre_render function
/**
* Pre-render callback to adjust weights of non-CCK fields.
*/
function content_alter_extra_weights($elements) {
if (isset($elements['#content_extra_fields'])) {
foreach ($elements['#content_extra_fields'] as $key => $value) {
// Some core 'fields' use a different key in node forms and in 'view'
// render arrays. Check we're not on a form first.
if (!isset($elements['#build_id']) && isset($value['view']) && isset($elements[$value['view']])) {
$elements[$value['view']]['#weight'] = $value['weight'];
}
elseif (isset($elements[$key])) {
$elements[$key]['#weight'] = $value['weight'];
}
}
}
return $elements;
}
So due to this callback you are not able to alter weight using normal behavior.
You should do this:
function YOUR_MODULE_nodeapi(&$node, $op, $a3 = NULL, $a4 = NULL) {
// Only for node pages.
if ($op == 'view' && $a4) {
$body_weight = 15 // Any weight.
$node->content['#content_extra_fields']['body']['weight'] = $body_weight; // This value CCK module will use to alter body weight in the callback from above.
}
}