| 1 |
<?php
|
| 2 |
// $Id: template.php,v 1.44 2009/11/05 12:09:53 johnalbin Exp $
|
| 3 |
|
| 4 |
/**
|
| 5 |
* @file
|
| 6 |
* Contains theme override functions and preprocess functions for the Zen theme.
|
| 7 |
*
|
| 8 |
* IMPORTANT WARNING: DO NOT MODIFY THIS FILE.
|
| 9 |
*
|
| 10 |
* The base Zen theme is designed to be easily extended by its sub-themes. You
|
| 11 |
* shouldn't modify this or any of the CSS or PHP files in the root zen/ folder.
|
| 12 |
* See the online documentation for more information:
|
| 13 |
* http://drupal.org/node/193318
|
| 14 |
*/
|
| 15 |
|
| 16 |
// Auto-rebuild the theme registry during theme development.
|
| 17 |
if (theme_get_setting('zen_rebuild_registry')) {
|
| 18 |
drupal_rebuild_theme_registry();
|
| 19 |
}
|
| 20 |
|
| 21 |
|
| 22 |
/**
|
| 23 |
* Implements HOOK_theme().
|
| 24 |
*/
|
| 25 |
function zen_theme(&$existing, $type, $theme, $path) {
|
| 26 |
// When #341140 is fixed, replace _zen_path() with drupal_get_path().
|
| 27 |
include_once './' . _zen_path() . '/zen-internals/template.theme-registry.inc';
|
| 28 |
return _zen_theme($existing, $type, $theme, $path);
|
| 29 |
}
|
| 30 |
|
| 31 |
/**
|
| 32 |
* Return a themed breadcrumb trail.
|
| 33 |
*
|
| 34 |
* @param $breadcrumb
|
| 35 |
* An array containing the breadcrumb links.
|
| 36 |
* @return
|
| 37 |
* A string containing the breadcrumb output.
|
| 38 |
*/
|
| 39 |
function zen_breadcrumb($breadcrumb) {
|
| 40 |
// Determine if we are to display the breadcrumb.
|
| 41 |
$show_breadcrumb = theme_get_setting('zen_breadcrumb');
|
| 42 |
if ($show_breadcrumb == 'yes' || $show_breadcrumb == 'admin' && arg(0) == 'admin') {
|
| 43 |
|
| 44 |
// Optionally get rid of the homepage link.
|
| 45 |
$show_breadcrumb_home = theme_get_setting('zen_breadcrumb_home');
|
| 46 |
if (!$show_breadcrumb_home) {
|
| 47 |
array_shift($breadcrumb);
|
| 48 |
}
|
| 49 |
|
| 50 |
// Return the breadcrumb with separators.
|
| 51 |
if (!empty($breadcrumb)) {
|
| 52 |
$breadcrumb_separator = theme_get_setting('zen_breadcrumb_separator');
|
| 53 |
$trailing_separator = $title = '';
|
| 54 |
if (theme_get_setting('zen_breadcrumb_title')) {
|
| 55 |
if ($title = drupal_get_title()) {
|
| 56 |
$trailing_separator = $breadcrumb_separator;
|
| 57 |
}
|
| 58 |
}
|
| 59 |
elseif (theme_get_setting('zen_breadcrumb_trailing')) {
|
| 60 |
$trailing_separator = $breadcrumb_separator;
|
| 61 |
}
|
| 62 |
return '<div class="breadcrumb">' . implode($breadcrumb_separator, $breadcrumb) . "$trailing_separator$title</div>";
|
| 63 |
}
|
| 64 |
}
|
| 65 |
// Otherwise, return an empty string.
|
| 66 |
return '';
|
| 67 |
}
|
| 68 |
|
| 69 |
/**
|
| 70 |
* Implements theme_menu_item_link()
|
| 71 |
*/
|
| 72 |
function zen_menu_item_link($link) {
|
| 73 |
if (empty($link['localized_options'])) {
|
| 74 |
$link['localized_options'] = array();
|
| 75 |
}
|
| 76 |
|
| 77 |
// If an item is a LOCAL TASK, render it as a tab
|
| 78 |
if ($link['type'] & MENU_IS_LOCAL_TASK) {
|
| 79 |
$link['title'] = '<span class="tab">' . check_plain($link['title']) . '</span>';
|
| 80 |
$link['localized_options']['html'] = TRUE;
|
| 81 |
}
|
| 82 |
|
| 83 |
return l($link['title'], $link['href'], $link['localized_options']);
|
| 84 |
}
|
| 85 |
|
| 86 |
/**
|
| 87 |
* Duplicate of theme_menu_local_tasks() but adds clearfix to tabs.
|
| 88 |
*/
|
| 89 |
function zen_menu_local_tasks() {
|
| 90 |
$output = '';
|
| 91 |
|
| 92 |
if ($primary = menu_primary_local_tasks()) {
|
| 93 |
$output .= '<ul class="tabs primary clearfix">' . $primary . '</ul>';
|
| 94 |
}
|
| 95 |
if ($secondary = menu_secondary_local_tasks()) {
|
| 96 |
$output .= '<ul class="tabs secondary clearfix">' . $secondary . '</ul>';
|
| 97 |
}
|
| 98 |
|
| 99 |
return $output;
|
| 100 |
}
|
| 101 |
|
| 102 |
/**
|
| 103 |
* Return a set of blocks available for the current user.
|
| 104 |
*
|
| 105 |
* @param $region
|
| 106 |
* Which set of blocks to retrieve.
|
| 107 |
* @param $show_blocks
|
| 108 |
* A boolean to determine whether to render sidebar regions or not. Should be
|
| 109 |
* the same value as passed to theme_page.
|
| 110 |
* @return
|
| 111 |
* A string containing the themed blocks for this region.
|
| 112 |
*
|
| 113 |
* @see zen_show_blocks_discovery()
|
| 114 |
*/
|
| 115 |
function zen_blocks($region, $show_blocks = NULL) {
|
| 116 |
// Since Drupal 6 doesn't pass $show_blocks to theme_blocks, we manually call
|
| 117 |
// theme('blocks', NULL, $show_blocks) so that this function can remember the
|
| 118 |
// value on later calls.
|
| 119 |
static $render_sidebars = TRUE;
|
| 120 |
if (!is_null($show_blocks)) {
|
| 121 |
$render_sidebars = $show_blocks;
|
| 122 |
}
|
| 123 |
|
| 124 |
// If zen_blocks was called with a NULL region, its likely we were just
|
| 125 |
// setting the $render_sidebars static variable.
|
| 126 |
if ($region) {
|
| 127 |
$output = '';
|
| 128 |
|
| 129 |
// If $renders_sidebars is FALSE, don't render any region whose name begins
|
| 130 |
// with "sidebar_".
|
| 131 |
if (($render_sidebars || (strpos($region, 'sidebar_') !== 0)) && ($list = block_list($region))) {
|
| 132 |
foreach ($list as $key => $block) {
|
| 133 |
// $key == module_delta
|
| 134 |
$output .= theme('block', $block);
|
| 135 |
}
|
| 136 |
}
|
| 137 |
|
| 138 |
// Add any content assigned to this region through drupal_set_content() calls.
|
| 139 |
$output .= drupal_get_content($region);
|
| 140 |
|
| 141 |
$elements['#children'] = $output;
|
| 142 |
$elements['#region'] = $region;
|
| 143 |
|
| 144 |
return $output ? theme('region', $elements) : '';
|
| 145 |
}
|
| 146 |
}
|
| 147 |
|
| 148 |
/**
|
| 149 |
* Examine the $show_blocks variable before template_preprocess_page() is called.
|
| 150 |
*
|
| 151 |
* @param $vars
|
| 152 |
* An array of variables to pass to the page template.
|
| 153 |
*
|
| 154 |
* @see zen_blocks()
|
| 155 |
*/
|
| 156 |
function zen_show_blocks_discovery(&$vars) {
|
| 157 |
if ($vars['show_blocks'] == FALSE) {
|
| 158 |
// Allow zen_blocks() to statically cache the $show_blocks variable. A TRUE
|
| 159 |
// value is assumed, so we only need to override when $show_blocks is FALSE.
|
| 160 |
theme('blocks', NULL, FALSE);
|
| 161 |
}
|
| 162 |
}
|
| 163 |
|
| 164 |
/**
|
| 165 |
* Override or insert variables into templates before other preprocess functions have run.
|
| 166 |
*
|
| 167 |
* @param $vars
|
| 168 |
* An array of variables to pass to the theme template.
|
| 169 |
* @param $hook
|
| 170 |
* The name of the template being rendered.
|
| 171 |
*/
|
| 172 |
function zen_preprocess(&$vars, $hook) {
|
| 173 |
// In D6, the page.tpl uses a different variable name to hold the classes.
|
| 174 |
$key = ($hook == 'page' || $hook == 'maintenance_page') ? 'body_classes' : 'classes';
|
| 175 |
|
| 176 |
// Create a D7-standard classes_array variable.
|
| 177 |
if (array_key_exists($key, $vars)) {
|
| 178 |
// Views (and possibly other modules) have templates with a $classes
|
| 179 |
// variable that isn't a string, so we leave those variables alone.
|
| 180 |
if (is_string($vars[$key])) {
|
| 181 |
$vars['classes_array'] = explode(' ', $vars[$key]);
|
| 182 |
unset($vars[$key]);
|
| 183 |
}
|
| 184 |
}
|
| 185 |
else {
|
| 186 |
$vars['classes_array'] = array($hook);
|
| 187 |
}
|
| 188 |
}
|
| 189 |
|
| 190 |
/**
|
| 191 |
* Override or insert variables into the page templates.
|
| 192 |
*
|
| 193 |
* @param $vars
|
| 194 |
* An array of variables to pass to the theme template.
|
| 195 |
* @param $hook
|
| 196 |
* The name of the template being rendered ("page" in this case.)
|
| 197 |
*/
|
| 198 |
function zen_preprocess_page(&$vars, $hook) {
|
| 199 |
// If the user is silly and enables Zen as the theme, add some styles.
|
| 200 |
if ($GLOBALS['theme'] == 'zen') {
|
| 201 |
include_once './' . _zen_path() . '/zen-internals/template.zen.inc';
|
| 202 |
_zen_preprocess_page($vars, $hook);
|
| 203 |
}
|
| 204 |
// Add conditional stylesheets.
|
| 205 |
elseif (!module_exists('conditional_styles')) {
|
| 206 |
$vars['styles'] .= $vars['conditional_styles'] = variable_get('conditional_styles_' . $GLOBALS['theme'], '');
|
| 207 |
}
|
| 208 |
|
| 209 |
// Classes for body element. Allows advanced theming based on context
|
| 210 |
// (home page, node of certain type, etc.)
|
| 211 |
// Remove the mostly useless page-ARG0 class.
|
| 212 |
if ($index = array_search(preg_replace('![^abcdefghijklmnopqrstuvwxyz0-9-_]+!s', '', 'page-'. drupal_strtolower(arg(0))), $vars['classes_array'])) {
|
| 213 |
unset($vars['classes_array'][$index]);
|
| 214 |
}
|
| 215 |
if (!$vars['is_front']) {
|
| 216 |
// Add unique class for each page.
|
| 217 |
$path = drupal_get_path_alias($_GET['q']);
|
| 218 |
$vars['classes_array'][] = drupal_html_class('page-' . $path);
|
| 219 |
// Add unique class for each website section.
|
| 220 |
list($section, ) = explode('/', $path, 2);
|
| 221 |
if (arg(0) == 'node') {
|
| 222 |
if (arg(1) == 'add') {
|
| 223 |
$section = 'node-add';
|
| 224 |
}
|
| 225 |
elseif (is_numeric(arg(1)) && (arg(2) == 'edit' || arg(2) == 'delete')) {
|
| 226 |
$section = 'node-' . arg(2);
|
| 227 |
}
|
| 228 |
}
|
| 229 |
$vars['classes_array'][] = drupal_html_class('section-' . $section);
|
| 230 |
}
|
| 231 |
if (theme_get_setting('zen_wireframes')) {
|
| 232 |
$vars['classes_array'][] = 'with-wireframes'; // Optionally add the wireframes style.
|
| 233 |
}
|
| 234 |
// We need to re-do the $layout and body classes because
|
| 235 |
// template_preprocess_page() assumes sidebars are named 'left' and 'right'.
|
| 236 |
$vars['layout'] = 'none';
|
| 237 |
if (!empty($vars['sidebar_first'])) {
|
| 238 |
$vars['layout'] = 'first';
|
| 239 |
}
|
| 240 |
if (!empty($vars['sidebar_second'])) {
|
| 241 |
$vars['layout'] = ($vars['layout'] == 'first') ? 'both' : 'second';
|
| 242 |
}
|
| 243 |
// If the layout is 'none', then template_preprocess_page() will already have
|
| 244 |
// set a 'no-sidebars' class since it won't find a 'left' or 'right' sidebar.
|
| 245 |
if ($vars['layout'] != 'none') {
|
| 246 |
// Remove the incorrect 'no-sidebars' class.
|
| 247 |
if ($index = array_search('no-sidebars', $vars['classes_array'])) {
|
| 248 |
unset($vars['classes_array'][$index]);
|
| 249 |
}
|
| 250 |
// Set the proper layout body classes.
|
| 251 |
if ($vars['layout'] == 'both') {
|
| 252 |
$vars['classes_array'][] = 'two-sidebars';
|
| 253 |
}
|
| 254 |
else {
|
| 255 |
$vars['classes_array'][] = 'one-sidebar';
|
| 256 |
$vars['classes_array'][] = 'sidebar-' . $vars['layout'];
|
| 257 |
}
|
| 258 |
}
|
| 259 |
}
|
| 260 |
|
| 261 |
/**
|
| 262 |
* Override or insert variables into the maintenance page template.
|
| 263 |
*
|
| 264 |
* @param $vars
|
| 265 |
* An array of variables to pass to the theme template.
|
| 266 |
* @param $hook
|
| 267 |
* The name of the template being rendered ("maintenance_page" in this case.)
|
| 268 |
*/
|
| 269 |
function zen_preprocess_maintenance_page(&$vars, $hook) {
|
| 270 |
// If Zen is the maintenance theme, add some styles.
|
| 271 |
if ($GLOBALS['theme'] == 'zen') {
|
| 272 |
include_once './' . _zen_path() . '/zen-internals/template.zen.inc';
|
| 273 |
_zen_preprocess_page($vars, $hook);
|
| 274 |
}
|
| 275 |
// Add conditional stylesheets.
|
| 276 |
elseif (!module_exists('conditional_styles')) {
|
| 277 |
$vars['styles'] .= $vars['conditional_styles'] = variable_get('conditional_styles_' . $GLOBALS['theme'], '');
|
| 278 |
}
|
| 279 |
|
| 280 |
// Classes for body element. Allows advanced theming based on context
|
| 281 |
// (home page, node of certain type, etc.)
|
| 282 |
$vars['body_classes_array'] = explode(' ', $vars['body_classes']);
|
| 283 |
}
|
| 284 |
|
| 285 |
/**
|
| 286 |
* Override or insert variables into the node templates.
|
| 287 |
*
|
| 288 |
* @param $vars
|
| 289 |
* An array of variables to pass to the theme template.
|
| 290 |
* @param $hook
|
| 291 |
* The name of the template being rendered ("node" in this case.)
|
| 292 |
*/
|
| 293 |
function zen_preprocess_node(&$vars, $hook) {
|
| 294 |
// Create the build_mode variable.
|
| 295 |
switch ($vars['node']->build_mode) {
|
| 296 |
case NODE_BUILD_NORMAL:
|
| 297 |
$vars['build_mode'] = $vars['teaser'] ? 'teaser' : 'full';
|
| 298 |
break;
|
| 299 |
case NODE_BUILD_PREVIEW:
|
| 300 |
$vars['build_mode'] = 'preview';
|
| 301 |
break;
|
| 302 |
case NODE_BUILD_SEARCH_INDEX:
|
| 303 |
$vars['build_mode'] = 'search_index';
|
| 304 |
break;
|
| 305 |
case NODE_BUILD_SEARCH_RESULT:
|
| 306 |
$vars['build_mode'] = 'search_result';
|
| 307 |
break;
|
| 308 |
case NODE_BUILD_RSS:
|
| 309 |
$vars['build_mode'] = 'rss';
|
| 310 |
break;
|
| 311 |
case NODE_BUILD_PRINT:
|
| 312 |
$vars['build_mode'] = 'print';
|
| 313 |
break;
|
| 314 |
}
|
| 315 |
|
| 316 |
// Create the user_picture variable.
|
| 317 |
$vars['user_picture'] = $vars['picture'];
|
| 318 |
|
| 319 |
// Create the Drupal 7 $display_submitted variable.
|
| 320 |
$vars['display_submitted'] = theme_get_setting('toggle_node_info_' . $vars['node']->type);
|
| 321 |
|
| 322 |
// Special classes for nodes.
|
| 323 |
// Class for node type: "node-type-page", "node-type-story", "node-type-my-custom-type", etc.
|
| 324 |
$vars['classes_array'][] = drupal_html_class('node-type-' . $vars['type']);
|
| 325 |
if ($vars['promote']) {
|
| 326 |
$vars['classes_array'][] = 'node-promoted';
|
| 327 |
}
|
| 328 |
if ($vars['sticky']) {
|
| 329 |
$vars['classes_array'][] = 'node-sticky';
|
| 330 |
}
|
| 331 |
if (!$vars['status']) {
|
| 332 |
$vars['classes_array'][] = 'node-unpublished';
|
| 333 |
$vars['unpublished'] = TRUE;
|
| 334 |
}
|
| 335 |
else {
|
| 336 |
$vars['unpublished'] = FALSE;
|
| 337 |
}
|
| 338 |
if ($vars['uid'] && $vars['uid'] == $GLOBALS['user']->uid) {
|
| 339 |
$vars['classes_array'][] = 'node-by-viewer'; // Node is authored by current user.
|
| 340 |
}
|
| 341 |
if ($vars['teaser']) {
|
| 342 |
$vars['classes_array'][] = 'node-teaser'; // Node is displayed as teaser.
|
| 343 |
}
|
| 344 |
if (isset($vars['preview'])) {
|
| 345 |
$vars['classes_array'][] = 'node-preview';
|
| 346 |
}
|
| 347 |
}
|
| 348 |
|
| 349 |
/**
|
| 350 |
* Override or insert variables into the comment templates.
|
| 351 |
*
|
| 352 |
* @param $vars
|
| 353 |
* An array of variables to pass to the theme template.
|
| 354 |
* @param $hook
|
| 355 |
* The name of the template being rendered ("comment" in this case.)
|
| 356 |
*/
|
| 357 |
function zen_preprocess_comment(&$vars, $hook) {
|
| 358 |
include_once './' . _zen_path() . '/zen-internals/template.comment.inc';
|
| 359 |
_zen_preprocess_comment($vars, $hook);
|
| 360 |
}
|
| 361 |
|
| 362 |
/**
|
| 363 |
* Preprocess variables for region.tpl.php
|
| 364 |
*
|
| 365 |
* Prepare the values passed to the theme_region function to be passed into a
|
| 366 |
* pluggable template engine. Uses the region name to generate a template file
|
| 367 |
* suggestions. If none are found, the default region.tpl.php is used.
|
| 368 |
*
|
| 369 |
* @see region.tpl.php
|
| 370 |
*/
|
| 371 |
function zen_preprocess_region(&$vars, $hook) {
|
| 372 |
// Create the $content variable that templates expect.
|
| 373 |
$vars['content'] = $vars['elements']['#children'];
|
| 374 |
$vars['region'] = $vars['elements']['#region'];
|
| 375 |
|
| 376 |
// Setup the default classes.
|
| 377 |
$region = 'region-' . str_replace('_', '-', $vars['region']);
|
| 378 |
$vars['classes_array'] = array('region', $region);
|
| 379 |
|
| 380 |
// Sidebar regions get a common template suggestion a couple extra classes.
|
| 381 |
if (strpos($vars['region'], 'sidebar_') === 0) {
|
| 382 |
$vars['template_files'][] = 'region-sidebar';
|
| 383 |
$vars['classes_array'][] = 'column';
|
| 384 |
$vars['classes_array'][] = 'sidebar';
|
| 385 |
}
|
| 386 |
|
| 387 |
// Setup the default template suggestion.
|
| 388 |
$vars['template_files'][] = $region;
|
| 389 |
}
|
| 390 |
|
| 391 |
/**
|
| 392 |
* Override or insert variables into the block templates.
|
| 393 |
*
|
| 394 |
* @param $vars
|
| 395 |
* An array of variables to pass to the theme template.
|
| 396 |
* @param $hook
|
| 397 |
* The name of the template being rendered ("block" in this case.)
|
| 398 |
*/
|
| 399 |
function zen_preprocess_block(&$vars, $hook) {
|
| 400 |
$block = $vars['block'];
|
| 401 |
|
| 402 |
// Drupal 7 uses a $content variable instead of $block->content.
|
| 403 |
$vars['content'] = $block->content;
|
| 404 |
// Drupal 7 should use a $title variable instead of $block->subject.
|
| 405 |
$vars['title'] = $block->subject;
|
| 406 |
|
| 407 |
// Special classes for blocks.
|
| 408 |
$vars['classes_array'][] = 'block-' . $block->module;
|
| 409 |
$vars['classes_array'][] = 'region-' . $vars['block_zebra'];
|
| 410 |
$vars['classes_array'][] = $vars['zebra'];
|
| 411 |
$vars['classes_array'][] = 'region-count-' . $vars['block_id'];
|
| 412 |
$vars['classes_array'][] = 'count-' . $vars['id'];
|
| 413 |
|
| 414 |
$vars['edit_links_array'] = array();
|
| 415 |
if (theme_get_setting('zen_block_editing') && user_access('administer blocks')) {
|
| 416 |
include_once './' . _zen_path() . '/zen-internals/template.block-editing.inc';
|
| 417 |
zen_preprocess_block_editing($vars, $hook);
|
| 418 |
$vars['classes_array'][] = 'with-block-editing';
|
| 419 |
}
|
| 420 |
}
|
| 421 |
|
| 422 |
/**
|
| 423 |
* Override or insert variables into templates after preprocess functions have run.
|
| 424 |
*
|
| 425 |
* @param $vars
|
| 426 |
* An array of variables to pass to the theme template.
|
| 427 |
* @param $hook
|
| 428 |
* The name of the template being rendered.
|
| 429 |
*/
|
| 430 |
function zen_process(&$vars, $hook) {
|
| 431 |
if (array_key_exists('classes_array', $vars)) {
|
| 432 |
$vars['classes'] = implode(' ', $vars['classes_array']);
|
| 433 |
}
|
| 434 |
}
|
| 435 |
|
| 436 |
/**
|
| 437 |
* Override or insert variables into the block templates after preprocess functions have run.
|
| 438 |
*
|
| 439 |
* @param $vars
|
| 440 |
* An array of variables to pass to the theme template.
|
| 441 |
* @param $hook
|
| 442 |
* The name of the template being rendered ("block" in this case.)
|
| 443 |
*/
|
| 444 |
function zen_process_block(&$vars, $hook) {
|
| 445 |
$vars['edit_links'] = !empty($vars['edit_links_array']) ? '<div class="edit">' . implode(' ', $vars['edit_links_array']) . '</div>' : '';
|
| 446 |
}
|
| 447 |
|
| 448 |
if (!function_exists('drupal_html_class')) {
|
| 449 |
/**
|
| 450 |
* Prepare a string for use as a valid class name.
|
| 451 |
*
|
| 452 |
* Do not pass one string containing multiple classes as they will be
|
| 453 |
* incorrectly concatenated with dashes, i.e. "one two" will become "one-two".
|
| 454 |
*
|
| 455 |
* @param $class
|
| 456 |
* The class name to clean.
|
| 457 |
* @return
|
| 458 |
* The cleaned class name.
|
| 459 |
*/
|
| 460 |
function drupal_html_class($class) {
|
| 461 |
// By default, we filter using Drupal's coding standards.
|
| 462 |
$class = strtr(drupal_strtolower($class), array(' ' => '-', '_' => '-', '/' => '-', '[' => '-', ']' => ''));
|
| 463 |
|
| 464 |
// http://www.w3.org/TR/CSS21/syndata.html#characters shows the syntax for valid
|
| 465 |
// CSS identifiers (including element names, classes, and IDs in selectors.)
|
| 466 |
//
|
| 467 |
// Valid characters in a CSS identifier are:
|
| 468 |
// - the hyphen (U+002D)
|
| 469 |
// - a-z (U+0030 - U+0039)
|
| 470 |
// - A-Z (U+0041 - U+005A)
|
| 471 |
// - the underscore (U+005F)
|
| 472 |
// - 0-9 (U+0061 - U+007A)
|
| 473 |
// - ISO 10646 characters U+00A1 and higher
|
| 474 |
// We strip out any character not in the above list.
|
| 475 |
$class = preg_replace('/[^\x{002D}\x{0030}-\x{0039}\x{0041}-\x{005A}\x{005F}\x{0061}-\x{007A}\x{00A1}-\x{FFFF}]/u', '', $class);
|
| 476 |
|
| 477 |
return $class;
|
| 478 |
}
|
| 479 |
} /* End of drupal_html_class conditional definition. */
|
| 480 |
|
| 481 |
if (!function_exists('drupal_html_id')) {
|
| 482 |
/**
|
| 483 |
* Prepare a string for use as a valid HTML ID and guarantee uniqueness.
|
| 484 |
*
|
| 485 |
* @param $id
|
| 486 |
* The ID to clean.
|
| 487 |
* @return
|
| 488 |
* The cleaned ID.
|
| 489 |
*/
|
| 490 |
function drupal_html_id($id) {
|
| 491 |
$id = strtr(drupal_strtolower($id), array(' ' => '-', '_' => '-', '[' => '-', ']' => ''));
|
| 492 |
|
| 493 |
// As defined in http://www.w3.org/TR/html4/types.html#type-name, HTML IDs can
|
| 494 |
// only contain letters, digits ([0-9]), hyphens ("-"), underscores ("_"),
|
| 495 |
// colons (":"), and periods ("."). We strip out any character not in that
|
| 496 |
// list. Note that the CSS spec doesn't allow colons or periods in identifiers
|
| 497 |
// (http://www.w3.org/TR/CSS21/syndata.html#characters), so we strip those two
|
| 498 |
// characters as well.
|
| 499 |
$id = preg_replace('/[^A-Za-z0-9\-_]/', '', $id);
|
| 500 |
|
| 501 |
return $id;
|
| 502 |
}
|
| 503 |
} /* End of drupal_html_id conditional definition. */
|
| 504 |
|
| 505 |
/**
|
| 506 |
* Returns the path to the Zen theme.
|
| 507 |
*
|
| 508 |
* drupal_get_filename() is broken; see #341140. When that is fixed in Drupal 6,
|
| 509 |
* replace _zen_path() with drupal_get_path('theme', 'zen').
|
| 510 |
*/
|
| 511 |
function _zen_path() {
|
| 512 |
static $path = FALSE;
|
| 513 |
if (!$path) {
|
| 514 |
$matches = drupal_system_listing('zen\.info$', 'themes', 'name', 0);
|
| 515 |
if (!empty($matches['zen']->filename)) {
|
| 516 |
$path = dirname($matches['zen']->filename);
|
| 517 |
}
|
| 518 |
}
|
| 519 |
return $path;
|
| 520 |
}
|